2017-05-26 07:25 AM
Hello,
I am having problems communicating with my NUCLEO-F767ZI board over the virtual COM port on Linux. The board uses USART3 to communicate via the ST-Link USB port with the PC.
The ST-Link connects fine to the PC on device /dev/ttyACM0 and I can program it fine. I can even mount its disk partition as a mass storage device.
I am using the re-routing of printf() to the USART interface to output debug text, as proposed in the ST examples, and this works fine on a Windows PC. On a Linux machine however, I don't get the output.
I have tried 'screen' to open a serial console, as well as an Arduino IDE serial console, no luck. I have added udev rules for the ST-Link device in /etc/udev to be able to access the device without being root. I can work with other, Arduino-compatible boards over the same /dev/ttyACM0 device just fine.
Does anyone have experience with these boards under Linux and can help me out? What am I missing here?
#serial-interface #nucleo-f767zi #linux Note: this post was migrated and contained many threaded conversations, some content may be missing.2017-05-26 07:41 AM
Serial ports under Linux are opened in a terminal emulation mode, i.e. character are filtered and lines are buffered.
You need to switch it to 'raw' mode, to get every character directly, and unmodified.
I need to look up some older example code I have.
Perhaps you find some example elswhere in the meantime...
2017-05-27 06:49 AM
Thanks for the hint. I tried playing around with setting the serial port to 'raw' but still can't get anything out of the board.
I looked a little closer at what the Arduino boards do in terms of serial communication, and apparently it's much more complex than the simple code I use on the F767 that just retargets the printf function to the USART. I guess that simple solution just does not work on Linux.
So if anyone has any working code that allows printing strings over the USB serial port, that would be really helpful.
2017-05-27 01:00 PM
Something like this, incomplete example, error checking and other stuff skipped:
(Seems the 'Formatting as Souce Code' option is pretty useless)
♯ include <unistd.h>
♯ include <stdio.h> // Standard input/output definitions
♯ include <stdlib.h> // standard library functions
♯ include <fcntl.h> // File control definitions
♯ include <termios.h> // POSIX terminal control definitions
♯ include <string.h> // String function definitions
♯ include <errno.h> // Error number definitions
your_function_here ()
{
...
struct termios options, oldoptions;
...
iFD = openLine (iSerLine, devtype);
...
// Configure port reading; block read(), until data arrive
fcntl (iFD, F_SETFL, 0);
// Get the current options for the port, and copy for restoration
tcgetattr (iFD, &oldoptions);
memcpy (&options, &oldoptions, sizeof (struct termios));
// Set the baud rates to the defined value
cfsetispeed (&options, iBaudRate);
cfsetospeed (&options, iBaudRate);
// Enable the receiver and set local mode
options.c_cflag |= (CLOCAL | CREAD);
options.c_cflag &= ~PARENB; // Mask the character size to 8 bits, no parity
options.c_cflag &= ~CSTOPB;
options.c_cflag &= ~CSIZE;
options.c_cflag |= CS8; // Select 8 data bits
if (hwFCntl)
options.c_cflag |= CRTSCTS; // enable hardware flow control
else
options.c_cflag &= ~CRTSCTS; // Disable hardware flow control
// Enable data to be processed as raw input
options.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);
options.c_iflag &= ~(ICRNL | INLCR | IXON | IXOFF);
options.c_oflag &= ~OPOST;
options.c_cc[VTIME] = 0; // no inter-character timer
options.c_cc[VMIN] = 1; // number of characters expected
// options.c_cc[VEOF] = 4;
// enable the new options for the port
tcsetattr (iFD, TCSANOW, &options);
}
static int openLine (int iSerLine, int devtype)
{
if (devtype == DEVTYPE_SERIAL)
sprintf (devName, '/dev/ttyS%d', iSerLine);
else
sprintf (devName, '/dev/ttyUSB%d', iSerLine);
// (fd == -1) -> Could not open the port
return (iFD = open (devName, O_RDONLY | O_NOCTTY | O_NDELAY));
}
Works for me, at least (Linux Mint 17 Distro).
2017-05-27 01:23 PM
Seems like every ******* code example goes into moderation now ...
2017-05-27 03:35 PM
But you can cuss
Using source code formatting has put stuff into moderation for months now, forum coding is complicated stuff...
2017-05-28 05:59 AM
But you can cuss
I better use '*' for that - at least for now...
My code example is moderated for almost one day now...
2017-05-29 03:43 AM
stty is your friend.
2017-05-29 04:01 AM
To add some comments on the example code:
Pay special attention to the
tcgetattr()/tcsetattr()
calls, and the port settings modifications in between.Keep you old settings (
oldoptions
struct here), write a function where you restore these settings back before closing the file (serial line), and register this function with atexit().This way, you can safely terminate you application with Ctrl-C/Ctrl-D without changing serial device settings.
2017-05-29 04:26 AM
Thank you, I will try that. Basically I am writing my own serial terminal client, right? I was hoping to find some code for the microcontroller that makes it behave like any Arduino-compatible board, which would make many things easier. Anyway, I will try your example, if it works that is at least another option.