[Tinyos Core WG] FW: UartByte -- fixed, I think

David Moss dmm at rincon.com
Wed May 14 09:45:14 PDT 2008


Will the owner(s) of this module please shepherd this code into the
baseline?  My co-worker Mark has tested this, I haven't.  When UartByte is
fixed, we should see this unit test pass:
http://www.lavalampmotemasters.com/reports/html/index.html

-David


-----Original Message-----
From: Mark Hays [mailto:mhh at rincon.com] 
Sent: Wednesday, April 16, 2008 12:31 PM
To: dangator at gmail.com
Cc: dmm; jrwy; ram; mhh
Subject: UartByte -- fixed, I think

I'm pretty sure this works -- just drop it
someplace in your include path. It replaces
tos/chips/atm128/HplAtm128UartP.nc.

--Mark

THE FIX:
========
The old code got the TXEN and TXCIE bits
confused (function enable vs interrupt
enable). Same with RXEN and RXCIE. Basically,
it's a long stream of typos...

Old code: on init, enable TX and RX
interrupts, as well as TX/RX functions.

New code: enable TX/RX functions but
disable interrupts. The interface has
separate interrupt control functions.
Atm128UartP.nc enables RX interrupts
on init.

Old code for interrupts: jangled the
xyzEN bits instead of the xyzCIE bits.
In other words, it toggled the *function
enables* instead of the *interrupt
enables*!

New code: bangs on the right bits. The
TX/RX functions are left on, and interrupt
generation is toggled.

Lockup explanation: the old code always
sent a byte, then waited for the TXC
or transmit-complete bit to be set. Since
the disableTxIntr() actually disabled the
transmit *function*, the transmit never
actually occurred, and therefore never
completed -> lockup!

The previous fix worked for exactly one
byte... because the old init code happened
to enable everything at system boot.
UartByte.send was still subject to the
race condition of seeing TXC be set *before*
the TX interrupt handler cleared this bit.
It's a tight loop though, so it probably
worked most of the time. The first call to
UartStream.send would cause the next
UartByte.send call to freeze the MCU.

Look at Atm128UartP to fully appreciate
this (it enables/disables interrupts in
all the right spots). UartByte.send was
always executed *after* disableTxIntr().
Note that UartByte.send cannot possibly
work reliably if TX interrupts are
enabled -- because entering the TX
interrupt handler automagically clears
the TXC bit :-)

UartStream worked because it ran after
enableTxIntr() which turned the TX
function on (which is Real Helpful if
you're trying to send stuff).

-------------- next part --------------
An embedded and charset-unspecified text was scrubbed...
Name: HplAtm128UartP.nc
Url: https://www.millennium.berkeley.edu/pipermail/tinyos-2.0wg/attachments/20080514/41ddb071/attachment.txt 


More information about the Tinyos-2.0wg mailing list