Skip to content

Latest commit

 

History

History
283 lines (201 loc) · 10.5 KB

serial.md

File metadata and controls

283 lines (201 loc) · 10.5 KB

NAME

Serial wrapper functions for Linux userspace termios tty devices.

SYNOPSIS

#include <periphery/serial.h>

/* Primary Functions */
int serial_open(serial_t *serial, const char *path, uint32_t baudrate);
int serial_open_advanced(serial_t *serial, const char *path,
                            uint32_t baudrate, unsigned int databits,
                            serial_parity_t parity, unsigned int stopbits,
                            bool xonxoff, bool rtscts);
int serial_read(serial_t *serial, uint8_t *buf, size_t len, int timeout_ms);
int serial_write(serial_t *serial, const uint8_t *buf, size_t len);
int serial_flush(serial_t *serial);
int serial_input_waiting(serial_t *serial, unsigned int *count);
int serial_output_waiting(serial_t *serial, unsigned int *count);
int serial_poll(serial_t *serial, int timeout_ms);
int serial_close(serial_t *serial);

/* Getters */
int serial_get_baudrate(serial_t *serial, uint32_t *baudrate);
int serial_get_databits(serial_t *serial, unsigned int *databits);
int serial_get_parity(serial_t *serial, serial_parity_t *parity);
int serial_get_stopbits(serial_t *serial, unsigned int *stopbits);
int serial_get_xonxoff(serial_t *serial, bool *xonxoff);
int serial_get_rtscts(serial_t *serial, bool *rtscts);

/* Setters */
int serial_set_baudrate(serial_t *serial, uint32_t baudrate);
int serial_set_databits(serial_t *serial, unsigned int databits);
int serial_set_parity(serial_t *serial, enum serial_parity parity);
int serial_set_stopbits(serial_t *serial, unsigned int stopbits);
int serial_set_xonxoff(serial_t *serial, bool enabled);
int serial_set_rtscts(serial_t *serial, bool enabled);

/* Miscellaneous */
int serial_fd(serial_t *serial);
int serial_tostring(serial_t *serial, char *str, size_t len);

/* Error Handling */
int serial_errno(serial_t *serial);
const char *serial_errmsg(serial_t *serial);

ENUMERATIONS

  • serial_parity_t
    • PARITY_NONE: No parity
    • PARITY_ODD: Odd parity
    • PARITY_EVEN: Even parity

DESCRIPTION

int serial_open(serial_t *serial, const char *path, uint32_t baudrate);

Open the tty device at the specified path (e.g. "/dev/ttyUSB0"), with the specified baudrate, and the defaults of 8 data bits, no parity, 1 stop bit, software flow control (xonxoff) off, hardware flow control (rtscts) off.

serial should be a valid pointer to an allocated Serial handle structure.

Returns 0 on success, or a negative Serial error code on failure.


int serial_open_advanced(serial_t *serial, const char *path,
                            uint32_t baudrate, unsigned int databits,
                            serial_parity_t parity, unsigned int stopbits,
                            bool xonxoff, bool rtscts);

Open the tty device at the specified path (e.g. "/dev/ttyUSB0"), with the specified baudrate, data bits, parity, stop bits, software flow control (xonxoff), and hardware flow control (rtscts) settings.

serial should be a valid pointer to an allocated Serial handle structure. databits can be 5, 6, 7, or 8. parity can be PARITY_NONE, PARITY_ODD, or PARITY_EVEN as defined above. stopbits can be 1 or 2.

Returns 0 on success, or a negative Serial error code on failure.


int serial_read(serial_t *serial, uint8_t *buf, size_t len, int timeout_ms);

Read up to len number of bytes from the serial port into the buf buffer with the specified millisecond timeout. A 0 timeout can be specified for a non-blocking read. A negative timeout can be specified for a blocking read that will read until all of the requested number of bytes are read. A positive timeout in milliseconds can be specified for a blocking read with timeout.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced(). timeout_ms can be positive for a timeout in milliseconds, 0 for a non-blocking read, or a negative number for a blocking read.

Returns the number of bytes read on success, 0 on timeout, or a negative Serial error code on failure.


int serial_write(serial_t *serial, const uint8_t *buf, size_t len);

Write len number of bytes from the buf buffer to the serial port.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns the number of bytes written on success, or a negative Serial error code on failure.


int serial_flush(serial_t *serial);

Flush the write buffer of the serial port (i.e. force its write immediately).

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns 0 on success, or a negative Serial error code on failure.


int serial_input_waiting(serial_t *serial, unsigned int *count);

Query the number of bytes waiting to be read from the serial port.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns 0 on success, or a negative Serial error code on failure.


int serial_output_waiting(serial_t *serial, unsigned int *count);

Query the number of bytes waiting to be written to the serial port.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns 0 on success, or a negative Serial error code on failure.


bool serial_poll(serial_t *serial, int timeout_ms);

Poll for data available for reading from the serial port.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced(). timeout_ms can be positive for a timeout in milliseconds, 0 for a non-blocking poll, or a negative number for a blocking poll.

Returns 1 on success (data available for reading), 0 on timeout, or a negative Serial error code on failure.


int serial_close(serial_t *serial);

Close the tty device.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns 0 on success, or a negative Serial error code on failure.


int serial_get_baudrate(serial_t *serial, uint32_t *baudrate);
int serial_get_databits(serial_t *serial, unsigned int *databits);
int serial_get_parity(serial_t *serial, serial_parity_t *parity);
int serial_get_stopbits(serial_t *serial, unsigned int *stopbits);
int serial_get_xonxoff(serial_t *serial, bool *xonxoff);
int serial_get_rtscts(serial_t *serial, bool *rtscts);

Query the baudrate, data bits, parity, stop bits, software flow control (xonxoff), or hardware flow control (rtscts), respectively, of the underlying tty device.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns 0 on success, or a negative Serial error code on failure.


int serial_set_baudrate(serial_t *serial, uint32_t baudrate);
int serial_set_databits(serial_t *serial, unsigned int databits);
int serial_set_parity(serial_t *serial, enum serial_parity parity);
int serial_set_stopbits(serial_t *serial, unsigned int stopbits);
int serial_set_xonxoff(serial_t *serial, bool enabled);
int serial_set_rtscts(serial_t *serial, bool enabled);

Set the baudrate, data bits, parity, stop bits, software flow control (xonxoff), or hardware flow control (rtscts), respectively, on the underlying tty device.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

Returns 0 on success, or a negative Serial error code on failure.


int serial_fd(serial_t *serial);

Return the file descriptor (for the underlying tty device) of the Serial handle.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

This function is a simple accessor to the Serial handle structure and always succeeds.


int serial_tostring(serial_t *serial, char *str, size_t len);

Return a string representation of the Serial handle.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

This function behaves and returns like snprintf().


int serial_errno(serial_t *serial);

Return the libc errno of the last failure that occurred.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().


const char *serial_errmsg(serial_t *serial);

Return a human readable error message of the last failure that occurred.

serial should be a valid pointer to a Serial handle opened with serial_open() or serial_open_advanced().

RETURN VALUE

The periphery Serial functions return 0 on success or one of the negative error codes below on failure.

The libc errno of the failure in an underlying libc library call can be obtained with the serial_errno() helper function. A human readable error message can be obtained with the serial_errmsg() helper function.

Error Code Description
SERIAL_ERROR_ARG Invalid arguments
SERIAL_ERROR_OPEN Opening serial port
SERIAL_ERROR_QUERY Getting serial port attributes
SERIAL_ERROR_IO Reading/writing serial port
SERIAL_ERROR_CONFIGURE Setting serial port attributes
SERIAL_ERROR_CLOSE Closing serial port

EXAMPLE

#include <stdio.h>
#include <stdlib.h>

#include "serial.h"

int main(void) {
    serial_t serial;
    const char *s = "Hello World!";
    char buf[128];
    int ret;

    /* Open /dev/ttyUSB0 with baudrate 115200, and defaults of 8N1, no flow control */
    if (serial_open(&serial, "/dev/ttyUSB0", 115200) < 0) {
        fprintf(stderr, "serial_open(): %s\n", serial_errmsg(&serial));
        exit(1);
    }

    /* Write to the serial port */
    if (serial_write(&serial, s, strlen(s)) < 0) {
        fprintf(stderr, "serial_write(): %s\n", serial_errmsg(&serial));
        exit(1);
    }

    /* Read up to buf size or 2000ms timeout */
    if ((ret = serial_read(&serial, buf, sizeof(buf), 2000)) < 0) {
        fprintf(stderr, "serial_read(): %s\n", serial_errmsg(&serial));
        exit(1);
    }

    printf("read %d bytes: _%s_\n", ret, buf);

    serial_close(&serial);
    return 0;
}