martinling / libserialport

Unofficial personal repository for libserialport - see git://sigrok.org/libserialport for official repo
http://sigrok.org/wiki/Libserialport
GNU Lesser General Public License v3.0
65 stars 34 forks source link

send_receive.c Timed out, 0/7 bytes receive #37

Closed patoskhy closed 4 years ago

patoskhy commented 4 years ago

Hello

Executing send_receive brings me a (Timed out, 0/7 bytes receive) response, as seen in the photo.

Sin título

I have windows 10, USB Serial Chipset CH340.

Under the knowledge database that they possess, that could be what generates this condition.

jamesljlster commented 4 years ago

Hello @patoskhy,

What port configuration did you use? I faced similar problem a few years ago. After setting data bits to 8 by sp_set_config_bits(), the problem solved. I don't know if this solution would work for you or not. But it always worth a try.

patoskhy commented 4 years ago

Hello

Thanks for answering, I am attaching a photo with the configuration. Sin título2

I was reading and some people work on win xp. So install this OS on an old PC.

the setting is 115200 so that's fine

jamesljlster commented 4 years ago

Hello @patoskhy,

Are you using Arduino as development board? Arduino board will be reset while a serial connection is connected. At this time it need some time to process serial initialization. If you send data immediately after opening the port, Arduino would probably response nothing.

patoskhy commented 4 years ago

hi @jamesljlster

not really. I am using a POS terminal of a particular company and the project to occupy is this. https://github.com/TransbankDevelopers/transbank-pos-sdk-c

The issue is that it occupies libserialport for serial port communication and I see that in this git they know a lot about it. that is why I execute send_receive.c from the libserialport project with the necessary parameters for the correct execution of this.

resulting in the first comment. that's why I was asking why this could happen and what would be a possible solution.

what this code should do is a polling to the POS terminal

code of send_receive.c

include

include

include

include

int check(enum sp_return result);

int main(int argc, char **argv) {

if (argc < 2 || argc > 3) {
    printf("Usage: %s <port 1> [<port 2>]\n", argv[0]);
    return -1;
}
int num_ports = argc - 1;
char **port_names = argv + 1;

struct sp_port *ports[2];

for (int i = 0; i < num_ports; i++) {
    printf("Looking for port %s.\n", port_names[i]);
    check(sp_get_port_by_name(port_names[i], &ports[i]));

    printf("Opening port.\n");
    check(sp_open(ports[i], SP_MODE_READ_WRITE));

    printf("Setting port to 115200 8N1, no flow control.\n");
    check(sp_set_baudrate(ports[i], 115200));
    check(sp_set_bits(ports[i], 8));
    check(sp_set_parity(ports[i], SP_PARITY_NONE));
    check(sp_set_stopbits(ports[i], 1));
    check(sp_set_flowcontrol(ports[i], SP_FLOWCONTROL_NONE));
}

for (int tx = 0; tx < num_ports; tx++) {

    int rx = num_ports == 1 ? 0 : ((tx == 0) ? 1 : 0);
    struct sp_port *tx_port = ports[tx];
    struct sp_port *rx_port = ports[rx];

    char POLL_MESSAGE[] = {0x02, 0x30, 0x31, 0x30, 0x30, 0x03, 0x02};

    int size = 7;

    unsigned int timeout = 1500;

    int result;

    printf("Sending '%s' (%d bytes) on port %s.\n",
            POLL_MESSAGE, size, sp_get_port_name(tx_port));
    result = check(sp_blocking_write(tx_port, POLL_MESSAGE, size, timeout));

    if (result == size)
        printf("Sent %d bytes successfully.\n", size);
    else
        printf("Timed out, %d/%d bytes sent.\n", result, size);

    char *buf = malloc(size + 1);

    printf("Receiving %d bytes on port %s.\n",
            size, sp_get_port_name(rx_port));
    result = check(sp_blocking_read(rx_port, buf, size, timeout));

    if (result == size)
        printf("Received %d bytes successfully.\n", size);
    else
        printf("Timed out, %d/%d bytes received.\n", result, size);

    buf[result] = '\0';
    printf("Received '%s'.\n", buf);

    free(buf);
}

for (int i = 0; i < num_ports; i++) {
    check(sp_close(ports[i]));
    sp_free_port(ports[i]);
}

return 0;

}

int check(enum sp_return result) {

char *error_message;

switch (result) {
case SP_ERR_ARG:
    printf("Error: Invalid argument.\n");
    abort();
case SP_ERR_FAIL:
    error_message = sp_last_error_message();
    printf("Error: Failed: %s\n", error_message);
    sp_free_error_message(error_message);
    abort();
case SP_ERR_SUPP:
    printf("Error: Not supported.\n");
    abort();
case SP_ERR_MEM:
    printf("Error: Couldn't allocate memory.\n");
    abort();
case SP_OK:
default:
    return result;
}

}

jamesljlster commented 4 years ago

Hello @patoskhy,

I have not seen POS terminal before, so doing some information searching on Google... It seems that the communication to the POS terminal is using RS-232. Is there a way to check the POS terminal does receive serial data correctly? If serial data couldn't be received by the POS terminal, maybe you need to connect a null modem. https://en.wikipedia.org/wiki/Null_modem

martinling commented 4 years ago

This isn't the sort of question the libserialport developers can help with. The code is fine, having been adapted directly from the example program. It's sending the poll message that you've asked it to, and not receiving a response. We don't know anything about the device you're talking to and why it's not responding.