On Sun, Sep 19, 2010 at 10:32 AM, Philip Levis <[email protected]> wrote:
> On Sep 19, 2010, at 1:27 AM, Eric Decker wrote:
>
> >
> > Under heavy loads and just the right circumstances this can cause an in
> use receive slot to become
> > unlocked causing a packet loss. The unlocked slot will get used for a
> new incoming packet. The packet
> > contained in the slot's msg buffer will be lost and the msg buffer reused
> for the new incoming packet.
> >
>
> Can you walk me through the code execution that causes this to happen?
> endPacket(SUCCESS) causes a buffer swap in SerialDispatcherP. Is the issue
> when both buffers are locked in SerialDispatcherP? I.e.,
>
> buffer A is locked
> buffer A completes, remains locked
> buffer B is locked
> buffer B completes, nosync unlocks A before it is ready?
>
That is what happens. But the issue really is endPacket(FAIL) should not be
getting called immediately after endPacket(SUCCESS) because
there is no intervening startPacket. It violates the interlayer signalling
protocol. Which also results in inconsistent buffer state. (the slot
becomes
unlocked and another packet can come in and over write packet information
that will get used by a higher layer).
> I guess this suggests that there are really three states: unlocked,
> in-progress, and complete. nosync should unlock an in-progress buffer but
> not a complete one. But it would be really helpful if you could write down
> the exact code execution that makes this happen.
That sounds right and also ties in with receiveTask not really dealing with
the 2 slot queue properly. But that is a different issue. Let's not go
there until this
one is resolved. I have code by the way that fixes the endPacket(SUCCESS),
endPacket(FAIL) problem. And I share :-)
> For a task to be delayed for so long is, well, pretty long...
>
yes it is long. For this to be a problem the system is under heavy load.
If there are heavy interrupts, this prevents the task layer from making
progress. The window opens when the 1st packet is received and handed off
to task level. The window closes when receiveTask level has processed the
1st packet and unlocked it. The time the window is open can be extended if
there are tasks in front of the SerialDispatcherP__receiveTask().
The problem is immediately following the call to endPacket(SUCCESS) another
call to endPacket(FAIL) is done in nosync which the packet finish code jumps
to.
More succinctly:
Packet 1 is being received into Buffer A in slot 0. Slot 0 locked.
Packet 1 completes and receiveTask posted. (window opens).
endPacket(SUCCESS) (slot 0), switch to BufB(slot 1)
system busy, receiveTask hasn't run yet, start receiving new packet (P2
-> BufB(slot1))
tasks in front of receiveTask (are taking a while), new packet
interarrival rate is high etc.
Packet 2 completes (prior to receiveTask signalling BufA(slot0)).
endPacket(SUCCESS) (slot 1), causes a switch so new current slot is
slot 0 (which has BufA and is locked)
but then we jump to nosync and do another endPacket(FAIL) which unlocks
slot 0.
new Packet 3 starts to come in. It starts to write into slot0, BufA because
it is unlocked.
Also note eventually receiveTask will execute and it will hand off a packet
that is either okay (new incoming data didn't show up, we got lucky (most of
the time)),
partially corrupted (front of packet overwritten with Packet 3 data), or a
different packet (all of Packet3 came in).
Pretty hozed but we only run into this under heavily loaded scenerios.
But when it hits it hits strangely, corrupted packets, missed packets, etc.
And it really depends on what else is going on in the system. What kind of
interrupt packet interarrival rate is present and what tasks and how
long do they run in front of a receiveTask invokation.
endPacket(FAIL) should only get called after a startPacket has been issued
and we are aborting the current packet. This will cause
the upper layer to reuse the current slot for the next packet.
It should not be getting called after an endPacket(SUCCESS) under any
circumstances. It violates the interlayer signalling protocol. There must
be a startPacket issued prior to any endPacket(FAIL) being issued.
> Phil
--
Eric B. Decker
Senior (over 50 :-) Researcher
_______________________________________________
Tinyos-help mailing list
[email protected]
https://www.millennium.berkeley.edu/cgi-bin/mailman/listinfo/tinyos-help