From: "DuckE" <nospam_steved94@home.com>
Subject: How can I avoid Using a Semaphore? (long)
Date: Sat, 13 Jan 2001 16:18:16 GMT
Date: 2001-01-13T16:18:16+00:00 [thread overview]
Message-ID: <cd%76.260429$U46.8278617@news1.sttls1.wa.home.com> (raw)
I have an application that receives a streams of data from TCP/IP sockets.
The stream of data is separated into "packets" each beginning with a 32 bit
length value.
For each of these sockets I have a task that receives the length, then gets
a pre-allocated data buffer that is large enough to hold the data, receives
the data into the data buffer, and then puts a reference to the buffer into
a queue for processing by other tasks.
Pseudo code for the main loop for the receive task is something like:
Loop
Receive 4 bytes of data from the socket
Convert the 4 bytes to an integer value
Get a buffer from available buffers that is large enough to hold
remaining data in message
Receive remaining part of message into buffer
Queue the message for processing by other tasks
End Loop
To avoid memory leaks I am using a controlled type with reference counting
to implement my data buffer. Since multiple threads may simultaneously have
access to the buffer, I use a protected type for reference counting.
Since I am using a protected type for reference counting, I cannot assign
packets within a protected type (to implement queue's of packets for
instance) since these assignments would be attempting to do a protected
operation within a protected type.
I have worked around this using a semaphore (the semaphore is created using
a protected type) around the assignment of packets:
lock semaphore
assign packet
unlock semaphore
This technique has proven reliable in production code, but I don't find it
to be very "clean".
Suggestions?
Here is a subset of my packet implementation:
package NPUnetworkPacketUtil is
type aPacketNPU is private;
private
protected type aRefCounterNPU is
procedure PlaseHoldNPU;
procedure ReleaseHoldNPU( lastHoldNPU : out boolean );
private
referenceCountNPU : Natural := 0;
end aRefCounterNPU;
type aPacketBufNPU( bufSizeNPU : Positive );
type aPacketBUfPtrNPU is accesss all aPacketBufNPU;
type aPacketNPU is new Ada.Finalization.Controlled with
record
packetBufPtrNPU : aPacketBufPtrNPU;
end record;
procedure Initialize( object : in out aPacketNPU );
procedure Adjust( object : in out aPacketNPU );
procedure Finalize( object : in out aPacketNPU );
type aPacketBufNPU( bufSizeNPU : Positive ) is limited
record
dataBufferNPU : aliased aDataArrayNPU( 1 .. bufSizeNPU );
holdLockNPU : aRefCounterNPU;
end record;
end NPUnetworkPacketUtil ;
package body NPUnetworkPacketUtil is
protected body aRefCounterNPU is
procedure PlaceHoldNPU is
begin
referenceCountNPU := referenceCountNPU + 1;
end PlaceHoldNPU;
procedure ReleaseHoldNPU( lastHoldNPU : out boolean ) is
begin
referenceCountNPU := referenceCountNPU - 1;
lastHoldNPU := referenceCountNPU = 0;
end ReleaseHoldNPU;
end aRefCounterNPU;
procedure Initialize( object : in out aPacketNPU ) is
begin
object.packetBufPtrNPU := null;
end Initialize;
procedure Adjust( object : in out aPacketNPU ) is
begin
if object.packetBufPtrNPU /= null then
packetBufPtrNPU.holdLockNPU.PlaceHoldNPU;
end if;
end Adjust;
procedure Finalize( object : in out aPacketNPU ) is
lastHold : boolean;
begin
if object.packetBufPtrNPU /= null then
packetBufNPU.holdLockNPU.ReleaseHoldNPU( lastHold );
if lastHold then
-- Take action to put buffer in the free pool
end if;
end if;
end Finalize;
end NPUnetworkPacketUtil;
Thank's in advance,
SteveD
next reply other threads:[~2001-01-13 16:18 UTC|newest]
Thread overview: 36+ messages / expand[flat|nested] mbox.gz Atom feed top
2001-01-13 16:18 DuckE [this message]
2001-01-15 1:06 ` How can I avoid Using a Semaphore? Nick Roberts
2001-01-15 3:17 ` Robert Dewar
2001-01-16 3:53 ` DuckE
2001-01-17 15:42 ` Nick Roberts
2001-01-20 18:16 ` DuckE
2001-01-20 19:16 ` Robert Dewar
2001-01-21 1:28 ` DuckE
2001-01-21 16:04 ` Robert Dewar
2001-01-21 23:23 ` DuckE
2001-01-22 0:28 ` mark_lundquist
2001-01-22 1:51 ` Robert Dewar
2001-01-23 2:36 ` DuckE
2001-01-22 0:35 ` Built-in types (was " mark_lundquist
2001-01-22 1:54 ` Robert Dewar
2001-01-22 16:18 ` mark_lundquist
2001-01-22 17:20 ` Robert Dewar
2001-01-22 23:17 ` Mark Lundquist
[not found] ` <m33deaaeks.fsf@ns40.infomatch.bc.ca>
2001-02-02 22:01 ` Mark Lundquist
[not found] ` <94km00$bv8$1@nnrp1.deja.com>
2001-02-02 22:03 ` Mark Lundquist
2001-01-21 16:53 ` Nick Roberts
2001-01-21 18:24 ` Robert Dewar
2001-01-23 0:21 ` Nick Roberts
2001-01-22 0:16 ` mark_lundquist
2001-01-22 16:51 ` How can I avoid Using a Semaphore? (long) mark_lundquist
2001-01-23 6:02 ` DuckE
2001-02-02 22:00 ` Sucking (was Re: How can I avoid Using a Semaphore? (long)) Mark Lundquist
2001-02-03 1:44 ` Jeffrey Carter
2001-02-03 3:21 ` DuckE
2001-02-05 20:07 ` Mark Lundquist
2001-02-06 7:16 ` Sven Nilsson
2001-02-02 22:18 ` How can I avoid Using a Semaphore? (long) Mark Lundquist
2001-02-03 3:01 ` DuckE
2001-02-02 21:38 ` Niklas Holsti
-- strict thread matches above, loose matches on Subject: below --
2001-02-07 21:55 Beard, Frank
2001-02-08 23:42 Beard, Frank
replies disabled
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox