Accessing the serial port with RTEMS

hwulf at et-inf.fho-emden.de hwulf at et-inf.fho-emden.de
Fri Apr 20 12:30:13 UTC 2007


Hi,

I wanted to access the serial port with RTEMS.
As RTEMS is compliant to the POSIX standard,
I thought of using the POSIX functions for it.

But I can't open the serial port with the open()
function. Does anyone have an advice of what's
wrong with the code?

Or is there another way to access the serial port?

Thank you very much in advance and kind regards,
  Hank



/******************************************************************************
  *
  * INCLUDES
  *
  *  
****************************************************************************/
#include <rtems.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <errno.h>
#include <termios.h>

/******************************************************************************
  *
  * FUNCTION PROTOTYPES
  *
  *  
****************************************************************************/

rtems_task Init(rtems_task_argument argument);

/******************************************************************************
  *
  * GLOBAL VARIABLES
  *
  *  
****************************************************************************/

/*
  *  Keep the names and IDs in global variables so another task can use them.
  */

/******************************************************************************
  *
  * CONFIGURATION INFORMATION
  *
  *  
****************************************************************************/
#include <bsp.h> /* for device driver prototypes */

#define CONFIGURE_INIT
#define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
#define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER

#define CONFIGURE_MAXIMUM_TASKS             3
#define CONFIGURE_MAXIMUM_MESSAGE_QUEUES	2
#define CONFIGURE_MAXIMUM_SEMAPHORES		5

#define CONFIGURE_RTEMS_INIT_TASKS_TABLE

#define CONFIGURE_EXTRA_TASK_STACKS         (2 * RTEMS_MINIMUM_STACK_SIZE)
#define CONFIGURE_MICROSECONDS_PER_TICK	10000
//#define CONFIGURE_TICKS_PER_TIMESLICE   5
//#define CONFIGURE_MEMORY_OVERHEAD			1000
//#define CONFIGURE_EXECUTIVE_RAM_WORK_AREA	1000
#define CONFIGURE_INIT_TASK_INITIAL_MODES (RTEMS_PREEMPT | \
                                            RTEMS_NO_TIMESLICE | \
                                            RTEMS_NO_ASR | \
                                            RTEMS_INTERRUPT_LEVEL(0))
#define MAX_ITERATIONS						20

#define _DEBUG_

#include <confdefs.h>

/******************************************************************************
  *
  * MACROS
  *
  *  
****************************************************************************/
/*
  *  Macro to print an task name that is composed of ASCII characters.
  *
  */

#define put_name( _name, _crlf ) \
	do { \
		rtems_unsigned32 c0, c1, c2, c3; \
		\
		c0 = ((_name) >> 24) & 0xff; \
		c1 = ((_name) >> 16) & 0xff; \
		c2 = ((_name) >> 8) & 0xff; \
		c3 = (_name) & 0xff; \
		putchar( (char)c0 ); \
		if ( c1 ) putchar( (char)c1 ); \
		if ( c2 ) putchar( (char)c2 ); \
		if ( c3 ) putchar( (char)c3 ); \
		if ( (_crlf) ) \
			putchar( '\n' ); \
	} while (0)

/*
  *  This allows us to view the "Test_task" instantiations as a set
  *  of numbered tasks by eliminating the number of application
  *  tasks created.
  *
  *  In reality, this is too complex for the purposes of this
  *  example.  It would have been easier to pass a task argument. :)
  *  But it shows how rtems_id's can sometimes be used.
  */

#define task_number( tid ) \
	( rtems_get_index( tid ) - \
		rtems_configuration_get_rtems_api_configuration()->number_of_initialization_tasks  
)


#include <stdio.h>

/*
  *  Keep the names and IDs in global variables so another task can use them.
  */

/******************************************************************************
  * Shared data. Use them with semaphores only!
  * Task1_postbox is protected by semaphore with ID 0,
  * Task2_postbox is protected by semaphore with ID 1.
  *  
****************************************************************************/



/******************************************************************************
  *
  * INIT
  *
  *  
****************************************************************************/
rtems_task Init(rtems_task_argument argument)
{
	rtems_status_code status;
	int fd = 0;
	struct termios options;

	/* open the serial port */
	fd = open("\\\\.\\CNCA0", O_RDWR | O_NOCTTY | O_NONBLOCK);
	if(fd == -1)
		printf("Could not open serial port \\.\CNCA0.\n");
	else
		fcntl(fd, F_SETFL, 0);

	/* get the current options */
	tcgetattr(fd, &options);

	/* setting the baud rate */
	cfsetispeed(&options, B19200);
	cfsetospeed(&options, B19200);

	/* set raw input, 1 second timeout */
	options.c_cflag |= (CLOCAL | CREAD);

	/* 8N1, no parity */
	options.c_cflag &= ~PARENB;
	options.c_cflag &= ~CSTOPB;
	options.c_cflag &= ~CSIZE;
	options.c_cflag |= CS8;

	options.c_cflag &= ~(CRTSCTS);			/* no hardware flow control */
	options.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);
	options.c_oflag &= ~(OPOST);
	options.c_cc[VMIN] = 0;
	options.c_cc[VTIME] = 10;

	/* set the options */
	tcsetattr(fd, TCSANOW, &options);

	if(write(fd, "ATZ\r", 4) < 0)
		printf("write() of 4 bytes failed!\n");

	exit(0);
}




More information about the users mailing list