• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 3119
  • Last Modified:

Serial port program help

Heres the deal.
Ive got two boxes, one running Windows and the other running Linux.
Ive got the two boxes connected with a serial cable on COM1.
Ive got a Teraterm Pro session open on the Windows box and my program running on my Linux box.
When i type a key e.g. A on the Teraterm window, i wnt it to be displayed on the Linux box screen.

Im baffled why it wont work, but then again a complete newbie!

Heres my code, so if anyone can point me in the right direction id really appreciate it.

#include <stdio.h>      /*Standard input/output definitions*/
#include <string.h>     /*String function definitions*/
#include <unistd.h>     /*Unix standard function definitions*/
#include <fcntl.h>      /*File control definitions*/
#include <errno.h>      /*Error number definitions*/
#include <termios.h>    /*POSIX terminal control definitions*/


main()
{
int n, fd; /* File descriptor for the port */
struct termios options;
char inBuffer[100];

      fd = open("/dev/ttyS0", O_RDWR | O_NOCTTY | O_NDELAY);
      if(fd == 0)
      {
          perror("open_port: Unable to open    /dev/ttyS0 -");
                 return;
      }
      else
             {
         fcntl(fd, F_SETFL, 0);
      }

      /*Configire port*/
      /*Get the current options for the port*/

      tcgetattr(fd, &options);

      /*Set the Baud rates to 19200*/

      cfsetispeed(&options, B19200);
      cfsetospeed(&options, B19200);

      /*Enable received and set local mode*/

      options.c_cflag |= (CLOCAL | CREAD);

      /*Set new options for port*/

      tcsetattr(fd, TCSANOW, &options);

      /*Set data bits*/

      options.c_cflag &= ~CSIZE;    /*Mask the character size bits*/
      options.c_cflag |= CS8;       /*Select 8 data bits*/

      /*Set RAW input*/

      options.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);

      /*Set Raw output*/

      options.c_oflag &= ~OPOST;

      /*Set timeout to 1 sec*/

      options.c_cc[VMIN] = 0;
      options.c_cc{VTIME] = 10;

            /* read characters from port */

             n = read(fd, inBuffer, 1);                      /* read 1 byte*/

             /* check if we got anything */
             if (n)
             {
         /* examine the bytes and do something with them */

         /* then reply to sender if needed */
                write(fd, "OK", 2);
             }


      close(fd);
}

Thanks
0
aaronmcl
Asked:
aaronmcl
  • 3
  • 2
  • 2
2 Solutions
 
bookiCommented:
aaronmcl,

Is your serial cable nulled (null modem)? The transmit and recieve pins have to be switched.. you can't use a regular serial cable (with or without gender changer).

b.
0
 
Kent OlsenData Warehouse Architect / DBACommented:
Hi aaronmcl,

You might actually be reading the data, but the return is getting buffered so that you don't see it.

Write a message to stderr to show that the character was received.


             n = read(fd, inBuffer, 1);                      /* read 1 byte*/

             /* check if we got anything */
             if (n)
             {
        /* examine the bytes and do something with them */

                fprintf (stderr, "Got %c\n", n > 0x20 ? n : ' ');

        /* then reply to sender if needed */
                write(fd, "OK", 2);
             }

 


Good Luck,
Kent
0
 
aaronmclAuthor Commented:
Kent

Tried what you suggested but no difference.

0
Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
Kent OlsenData Warehouse Architect / DBACommented:

I also misspoke/mistyped.  sigh....

You want to test what was read, not the count.

               fprintf (stderr, "Got %c\n", *inBuffer > 0x20 ? *inBuffer : ' ');


Does the program exit immediately or wait until a key is pressed on the other system?

When the key is pressed does the linux program exit immediately?

Following booki's lead, how are the two systems cabled together?  If you're using "standard" ethernet cables you'll need a hub/switch/router in between the systems to manage the send/receive signals.  Without the additional electronics you'll need a cross-over cable.


Kent
0
 
bookiCommented:
aaronmcl,

Aside from a mistyped curly brace your code works fine.

>>    options.c_cc{VTIME] = 10;

         options.c_cc[VTIME] = 10;

I tested by sending from winxp (first from a little prog I wrote then also with hyperterminal) and recieving on a linux box.  Baud rate 9600 and 19200 worked fine.

You're probably not using a null modem/crossover cable.

A null cable is laid out as follows, if you want to make your own:
1&6     4
4           1&6
2           3
3           2
5           5
7           8
8           7

*source: idt,  Q_20935708

b.
0
 
bookiCommented:
aaronmcl,

One more thing... All changes you make to your termios struct "options" AFTER calling tcsetattr() have no effect.  Therefore, as you may have noticed, your call to read() blocks despite having set VMIN of 0.  It looks like a default of 1 is used.

b.
0
 
aaronmclAuthor Commented:
Sorry for the delay in replying.
Ill give your ammended code a try Kent.
booki im using a crossover cable so the cable is fine and i had previously corrected the curly brace, just a typo.
Ill try recompiling when i get home but if youve tried it already booki then im confident it'll work.

Thanks for the help guys appreciated!

0

Featured Post

Upgrade your Question Security!

Add Premium security features to your question to ensure its privacy or anonymity. Learn more about your ability to control Question Security today.

  • 3
  • 2
  • 2
Tackle projects and never again get stuck behind a technical roadblock.
Join Now