http://groups.google.com/group/comp.programming.threads?hl=en
comp.programming.threads@googlegroups.com
Today's topics:
* Using a thread to complete object initialization - 1 messages, 1 author
http://groups.google.com/group/comp.programming.threads/t/64cb03b37b5d9fea?hl=en
* AMD Advanced Synchronization Facility: HTM - 1 messages, 1 author
http://groups.google.com/group/comp.programming.threads/t/c1c6c6327aed79b6?hl=en
==============================================================================
TOPIC: Using a thread to complete object initialization
http://groups.google.com/group/comp.programming.threads/t/64cb03b37b5d9fea?hl=en
==============================================================================
== 1 of 1 ==
Date: Fri, May 29 2009 2:52 pm
From: "Chris M. Thomasson"
"Chris M. Thomasson" <no@spam.invalid> wrote in message
news:eyVTl.121693$3k7.15720@newsfe17.iad...
> "vl106" <vl106@hotmail.com> wrote in message
> news:785dtvF1k4nfnU1@mid.uni-berlin.de...
>>I have the following problem: a function shall return a complex object.
>>The caller
>> shall receive the object immediately (e.g. without blocking). The real
>> initialization
>> is done by a worker thread (as being time-consuming). I came up with the
>> following
>> solution. Any better ideas?
>> [...]
>
> Something like the following quick pseudo-code:
> ______________________________________________________________________
> void worker_threads();
>
>
> class future {
> HANDLE m_event; // manual-reset event set to false
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Should probably just use an automatic reset event here. Unless you want to
allow multiple threads to wait on a single future. However, then some "reset
event logic" would need to be implemented. I would advise you to just use
the automatic event, and only allow a single thread to wait on a future
object...
> [...]
> ______________________________________________________________________
==============================================================================
TOPIC: AMD Advanced Synchronization Facility: HTM
http://groups.google.com/group/comp.programming.threads/t/c1c6c6327aed79b6?hl=en
==============================================================================
== 1 of 1 ==
Date: Sat, May 30 2009 8:12 am
From: EricP
EricP wrote:
>
> It depends on what one thinks of blocking events vs wait loops.
> One must remember that with ASF, the act of reading a memory
> location during an update causes an Abort.
> So contenders must go away and do something else for a while.
>
> If going with a wait loop approach, I decided in the end that
> using an atomic up-down counter to allocate delay time slots was
> the best approach.
In a nut shell, this is just a global counter to reserve time
delay slots and prevent contention. What we want to avoid is
an Abort loop where A locks some lines, B aborts A,
C aborts B, A aborts C, etc.
A locker is susceptible to contention during its Update Time (UT)
which is from the point where it does its first locked write
and begins to acquire exclusive ownership over the cache lines
until it COMMITs its changes. UT is primarily the time it
takes to move the cache lines from remote L2 to our local L2.
As I mentioned previously, the maximum UT window seems to be
quite variable across systems, from 50ns to 400ns so the code
would need to be able to learn how big a delay was required
for each contender.
The example below serializes contention, gives approximate
FIFO order, a linear delay for each contender,
and automatic timer adjustment.
Eric
// Up-down counter for allocating delay slots.
volatile LONG g_DelaySlotNum;
// Delay duration for each delay slot, automatically adjusted
volatile LONG g_DelayTicks = 100;
void DlinkSafePushAfter (DlinkPT priorP, DlinkPT newP)
{
LONG slotNum, count, curTicks, newTicks, slotTicks = 0;
DlinkPT nextP;
for (;;)
{
SPECULATE
{ nextP = LOCK MOV priorP->FlinkP;
LOCK PREFETCHW nextP;
LOCK PREFETCHW newP;
LOCK MOV newP->FlinkP = priorP->FlinkP;
LOCK MOV priorP->FlinkP = newP;
LOCK MOV newP->BlinkP = priorP;
LOCK MOV newP->FlinkP = nextP;
LOCK MOV nextP->BlinkP = newP;
COMMIT;
break;
}
catch (int reason)
{
// The abort could be spurious, like an interrupt,
// or due to collision, or uncorrectable.
if (reason & ASF_ABORTCODE_CONTENTION)
{
// Serialize access by waiting a little.
// Assign a unique delay slot to each wait.
// We don't know how big a delay slot should be so
// adjust the size up by 50% until we stop colliding.
if (slotTicks == 0)
{ // First collision, use current slot size
slotTicks = g_DelayTicks;
}
else
{ // Subsequent collision. Increase slot size by 50%
// but only if no one else has just done so.
// Otherwise use their updated value.
newTicks = slotTicks + (slotTicks >> 1);
curTicks = InterlockedCompareExchange
(&g_DelayTicks, newTicks, slotTicks);
if (curTicks == slotTicks)
slotTicks = newTicks; // Use our new slot size
else
slotTicks = curTicks; // Use others slot size
}
// Reserve a delay slot and wait a while
slotNum = InterlockedIncrement (&g_DelaySlotNum);
for(count = slotNum*slotTicks; count > 0; count--)
{ Pause;
}
InterlockedDecrement (&g_DelaySlotNum);
}
else
{
FatalExit (0);
}
}
}
}
==============================================================================
You received this message because you are subscribed to the Google Groups "comp.programming.threads"
group.
To post to this group, visit http://groups.google.com/group/comp.programming.threads?hl=en
To unsubscribe from this group, send email to comp.programming.threads+unsubscribe@googlegroups.com
To change the way you get mail from this group, visit:
http://groups.google.com/group/comp.programming.threads/subscribe?hl=en
To report abuse, send email explaining the problem to abuse@googlegroups.com
==============================================================================
Google Groups: http://groups.google.com/?hl=en
No comments:
Post a Comment