Nios® V Processor Software Developer Handbook

ID 743810
Date 10/02/2023
Public

A newer version of this document is available. Customers should click here to go to the newest version.

Document Table of Contents

3.4.3.2.2. Blocking versus Non-Blocking I/O

Character mode devices can be configured to operate in blocking mode or nonblocking mode. The mode is specified in the device’s file descriptor.

  • In blocking mode, a function call to read from the device waits until the device receives new data.
  • In non-blocking mode, the function calls to read new data returns immediately and reports whether new data was received.

Depending on the function you use to read the file handle, an error code is returned, specifying whether new data arrived.

The UART and JTAG UART components are initialized in blocking mode. However, each component can be made non-blocking with the fnctl() or the ioctl() function, as seen in the following open system call, which specifies that the device being opened is to function in non-blocking mode:

fd = open ("/dev/<your uart name>", O_NONBLOCK | O_RDWR);

The fnctl() system call shown in the example below specifies that a device that is already open is to function in non-blocking mode.

The behavior of the UART and JTAG UART peripherals can also be modified with an ioctl() function call. The ioctl() function supports the following parameters:

  • For UART peripherals:
    • TIOCMGET (reports baud rate of UART)
    • TIOCMSET (sets baud rate of UART)
  • For JTAG UART peripherals:
    • TIOCSTIMEOUT (timeout value for connecting to workstation)
    • TIOCGCONNECTED (find out whether host is connected)

The altera_avalon_uart_driver.enable_ioctl BSP setting enables and disables the ioctl() function for the UART peripherals. The ioctl() function is automatically enabled for the JTAG UART peripherals.

The ioctl() function is not compatible with the altera_avalon_uart_driver.enable_small_driver and hal.enable_reduced_driver BSP settings. If either of these settings is enabled, ioctl() is not implemented.

fnctl() System Call

/* You can specify <file_descriptor> to be
* STDIN_FILENO, STDOUT_FILENO, or STDERR_FILENO
* if you are using STDIO
*/
fnctl(<file_descriptor>, F_SETFL, O_NONBLOCK

Non-Blocking Device Code Fragment

input_chars[128];
return_chars = scanf("%128s", &input_chars);
if(return_chars == 0)
{
if(errno != EWOULDBLOCK)
{
/* check other errnos */
}
}
else
{
/* process received characters */
}