Table of Contents
UART Wildcard User Guide
UART Direction Control in a Multitasking System
RS485 multidrop communications are often used to establish communications with a remote instrument. Typically, a command and response protocol is used. The Mosaic Controller issues a command, usually terminated with a specified terminating character such as a carriage return, and the remote instrument then transmits a response back to the Mosaic Controller. It is the Mosaic Controller's responsibility to revert to the RS485 receive mode immediately after transmitting the terminating command character to the remote.
In multitasking RS485 applications, the time to go from transmit mode to receive mode on the RS485 link may be too long, causing characters to be dropped when the remote instrument responds to a command from the Mosaic Controller. This situation can arise because the task that controls RS485 communications is not running when the transmission of the terminating command character completes, and receive mode is not entered until the RS485 task regains control.
Of course, if a full duplex RS422 interface to the remote were available, this would solve the problem. Many instruments only support RS485, so we need a way to turn off the RS485 transmitter immediately after the last character in a command finishes transmitting.
Single Task Applications
To start the discussion, let's consider the simplest case of a one-task (non-multitasking) application. In this case, the simplest approach to RS485 communications yields good results.
With the RS485 channel in transmit mode (see the function RS485_Xmit_UART), we use CH1_Emit or CH2_Emit to send the entire command, including the terminating character. Each CH1_Emit or CH2_Emit places a character in the proper outgoing 16-byte FIFO (First-In/First-Out) buffer in the UART, and the UART automatically transmits them until the buffer is empty. All the serial driver routines are FIFO-aware, so the programmer doesn't have to worry about buffering; it's handled transparently. After emitting all the command characters, we revert to the receive mode using the command:
RS485_Rcv_When_Xmit_Donewhich accepts the channel_num and Wildcard_num as input parameters. This command polls the XMIT_HAS_COMPLETED_MASK bit in the UARTís line status register, PAUSEs if there are characters remaining to be sent, and changes to receive mode when the transmission is complete. This works well for a single-task system, as the PAUSE will simply loop back to the single task, and the receive mode will be entered as soon as the last character is transmitted.
In a multitasking application we have to be more careful about time delays. For example, if there are 4 tasks running with the default 5 msec timeslice period, then each PAUSE invoked by RS485_Rcv_When_Xmit_Done will typically involve a 15 msec delay as the other 3 tasks use their timeslices. If the terminating command character is transmitted during one of these 15 msec delays, incoming characters from the remote instrument may be missed if the remote starts transmitting as soon as the terminating command character is received.
The solution is to ensure that the RS485 task maintains control while the very last character in the command string is being sent, so that the RS485 task can revert to receive mode with no time delay. To maintain multitasking efficiency, we should break the command string into two parts:
1. the command (not including terminator), and
To facilitate this approach, an additional function has been added to the UART Wildcard kernel extension Version 1.1. It is:
Loop_Until_Xmit_Donewhich accepts the channel_num and module_num as input parameters. This function is very similar to Wait_Until_Xmit_Done, but it does not PAUSE while waiting. Using this function as described below, we are able to avoid task switches as the terminating character is transmitted and the RS485 receive mode is entered.
Assume we're using channel 1 of the UART Wildcard. We transmit the command string by repeatedly calling CH1_Emit (but we don't emit the terminating character yet). We call
Wait_Until_Xmit_Doneto wait and PAUSE until the transmission completes. Time delays due to task switches during this process should not matter, because the remote instrument is waiting for the terminating character to come in from the Mosaic Controller.
Next, call the following commands (of course, supply the proper parameters for each function):
DISABLE.INTERRUPTS \ prevent task switching while sending last character
This sequence of function calls retains control while the last (terminating) character of the command is transmitted, then immediately enters the RS485 receive mode. Disabling interrupts should always be done sparingly, but is warranted in this case to ensure that no incoming characters are lost. We disable interrupts for only the time it takes to transmit one character, which at 19200 baud is about half a millisecond. As soon as Loop_Until_Xmit_Done is finished (meaning the character has been transmitted), RS485_Rcv_UART is called to immediately enter receive mode, and interrupts are re-enabled. At this point, the UART input FIFO buffer is able to accept up to 16 incoming characters before being serviced, so in some applications it may be efficient to PAUSE at this point to give other tasks a chance to run.
In summary, this approach should lead to high reliability acquisition of response data from remote RS485 instruments.
Home|Site Map|Products|Manuals|Resources|Order|About Us
Copyright (c) 2006 Mosaic Industries, Inc.
Your source for single board computers, embedded controllers, and operator interfaces for instruments and automation