Revision history for KeyPgCondCreate


Revision [21489]

Last edited on 2016-05-19 07:58:41 by fxm [Updated the comment of example]
Additions:
' Thread#A XOR + <==> Thread#B
' While bool#1 <> true <------------------------ bool#1 = true
' Wend <-----------------------------------. Do_something_with_exclusion
' bool#1 = false .---------- | --> While bool#2 <> true
' Do_something_with_exclusion | .------ | ----> CondWait(cond#2, mut)
' bool#2 = true ---------------' | .-- | --> Wend
' CondSignal(cond#2) --------------' | | bool#2 = false
' Do_something_with_exclusion | | Do_something_with_exclusion
'MutexUnlock(mut) ----------------------' '-- MutexUnlock(mut)
Deletions:
' Thread#A XOR + <==> Thread#B
' While bool#1 <> true bool#1 = true
' Wend <---------------------------------. Do_something_with_exclusion
' bool#1 = false | While bool#2 <> true
' Do_something_with_exclusion .------ | ------> CondWait(cond#2, mut)
' bool#2 = true | .-- | ----> Wend
' CondSignal(cond#2) ------------' | | bool#2 = false
' Do_something_with_exclusion | | Do_something_with_exclusion
'MutexUnlock(mut) --------------------' '---- MutexUnlock(mut)
'..... .....'


Revision [21487]

Edited on 2016-05-19 07:30:38 by fxm [Updated the comment of example]
Additions:
' Do_something_with_exclusion Do_something_with_exclusion
' Wend <---------------------------------. Do_something_with_exclusion
' bool#1 = false | While bool#2 <> true
' Do_something_with_exclusion .------ | ------> CondWait(cond#2, mut)
' bool#2 = true | .-- | ----> Wend
' CondSignal(cond#2) ------------' | | bool#2 = false
' Do_something_with_exclusion | | Do_something_with_exclusion
'..... .....'
Deletions:
'Do_something_with_exclusion Do_something_with_exclusion
' Wend <---------------------------------. While bool#2 <> true
' bool#1 = false .------ | -----> CondWait(cond#2, mut)
' Do_something_with_exclusion | .-- | ----> Wend
' bool#2 = true | | | bool#2 = false
' CondSignal(cond#2) ------------' | | Do_something_with_exclusion


Revision [21485]

Edited on 2016-05-19 06:25:37 by fxm [Updated second example: Strengthening immunity against all simultaneous conditional waitings]
Additions:
'MutexLock(mut) MutexLock(mut)
'Do_something_with_exclusion Do_something_with_exclusion
' CondWait(cond#1, mut) <--------------------- CondSignal(cond#1)
' Wend <---------------------------------. While bool#2 <> true
' bool#1 = false .------ | -----> CondWait(cond#2, mut)
' Do_something_with_exclusion | .-- | ----> Wend
' bool#2 = true | | | bool#2 = false
' CondSignal(cond#2) ------------' | | Do_something_with_exclusion
'MutexUnlock(mut) --------------------' '---- MutexUnlock(mut)
Dim sync As Any Ptr 'Any Ptr handle to mutex
MutexLock(tp->sync) 'Mutex (Lock) for user thread
CondWait(tp->cond2, tp->sync) 'CondWait to receive signal2 from main-thread
MutexUnlock(tp->sync) 'Mutex (Unlock) for user thread
MutexUnlock(tp->sync) 'Mutex (Unlock) for user thread
Tptr->sync = MutexCreate
MutexLock(Tptr->sync) 'Mutex (Lock) for main thread
While Tptr->ready1 <> Tptr->true 'Process loop against spurious wakeups
CondWait(Tptr->cond1, Tptr->sync) 'CondWait to receive signal1 from user-thread
PSet (Pptr->x, Pptr->y) 'Plotting one point
Tptr->ready2 = Tptr->true 'Set ready2
CondSignal(Tptr->cond2) 'CondSignal to send signal2 to user thread
Tptr->quit = Tptr->true 'Set quit
MutexUnlock(Tptr->sync) 'Mutex (Unlock) for main thread
MutexUnlock(Tptr->sync) 'Mutex (Unlock) for main thread
MutexDestroy(Tptr->sync)
Deletions:
'..... MutexLock(mut#1)
'MutexLock(mut#1) Do_something#B_with_exclusion#1
' CondWait(cond#1, mut#1) <------------------- CondSignal(cond#1)
' Wend <-------------------------------------- MutexUnlock(mut#1)
' bool#1 = false .....
' Do_something#A_with_exclusion#1 .....
'MutexUnlock(mut#1) .....
'MutexLock(mut#2) .....
' Do_something#A_with_exclusion#2 MutexLock(mut#2)
' bool#2 = true While bool#2 <> true
' CondSignal(cond#2) ----------------------------> CondWait(cond#2, mut#2)
'MutexUnlock(mut#2) ----------------------------> Wend
'..... bool#2 = false
'..... Do_something#B_with_exclusion#2
'..... MutexUnlock(mut#2)
Dim sync1 As Any Ptr 'Any Ptr handle to mutex1
Dim sync2 As Any Ptr 'Any Ptr handle to mutex2
MutexLock(tp->sync1) 'Mutex1 (Lock) for user thread
MutexUnlock(tp->sync1) 'Mutex1 (Unlock) for user thread
MutexLock(tp->sync2) 'Mutex2 (Lock) for user thread
CondWait(tp->cond2, tp->sync2) 'CondWait to receive signal2 from main-thread
MutexUnlock(tp->sync2) 'Mutex2 (Unlock) for user thread
MutexUnlock(tp->sync2) 'Mutex2 (Unlock) for user thread
Tptr->sync1 = MutexCreate
Tptr->sync2 = MutexCreate
MutexLock(Tptr->sync1) 'Mutex1 (Lock) for main thread
While Tptr->ready1 <> Tptr->true 'Process loop against spurious wakeups
CondWait(Tptr->cond1, Tptr->sync1) 'CondWait to receive signal1 from user-thread
PSet (Pptr->x, Pptr->y) 'Plotting one point
MutexUnlock(Tptr->sync1) 'Mutex1 (Unlock) for main thread
MutexLock(Tptr->sync2) 'Mutex2 (Lock) for main thread
Tptr->ready2 = Tptr->true 'Set ready2
CondSignal(Tptr->cond2) 'CondSignal to send signal2 to user thread
Tptr->quit = Tptr->true 'Set quit
MutexUnlock(Tptr->sync2) 'Mutex2 (Unlock) for main thread
MutexUnlock(Tptr->sync2) 'Mutex2 (Unlock) for main thread
MutexDestroy(Tptr->sync1)
MutexDestroy(Tptr->sync2)


Revision [21483]

Edited on 2016-05-19 04:10:40 by fxm [Updated second example: Strengthening immunity against all simultaneous conditional waitings]
Additions:
'..... MutexLock(mut#1)
'MutexLock(mut#1) Do_something#B_with_exclusion#1
' While bool#1 <> true bool#1 = true
' CondWait(cond#1, mut#1) <------------------- CondSignal(cond#1)
' Wend <-------------------------------------- MutexUnlock(mut#1)
' bool#1 = false .....
' Do_something#A_with_exclusion#1 .....
'MutexUnlock(mut#1) .....
'MutexLock(mut#2) .....
' Do_something#A_with_exclusion#2 MutexLock(mut#2)
' bool#2 = true While bool#2 <> true
' CondSignal(cond#2) ----------------------------> CondWait(cond#2, mut#2)
'MutexUnlock(mut#2) ----------------------------> Wend
'..... bool#2 = false
'..... Do_something#B_with_exclusion#2
'..... MutexUnlock(mut#2)
Deletions:
'MutexLock(mut#1) MutexLock(mut#1)
' While bool#1 <> true Do_something#B_with_exclusion#1
' CondWait(cond#1, mut#1) bool#1 = true
' Wend CondSignal(cond#1)
' bool#1 = false MutexUnlock(mut#1)
' Do_something#A_with_exclusion#1 MutexLock(mut#2)
'MutexUnlock(mut#1) While bool#2 <> true
'MutexLock(mut#2) CondWait(cond#2, mut#2)
' Do_something#A_with_exclusion#2 Wend
' bool#2 = true bool#2 = false
' CondSignal(cond#2) Do_something#B_with_exclusion#2
'MutexUnlock(mut#2) MutexUnlock(mut#2)


Revision [21477]

Edited on 2016-05-17 12:50:24 by fxm [Updated second example: Strengthening immunity against all simultaneous conditional waitings]
Additions:
'MutexUnlock(mut#1) While bool#2 <> true
'MutexLock(mut#2) CondWait(cond#2, mut#2)
' Do_something#A_with_exclusion#2 Wend
' bool#2 = true bool#2 = false
' CondSignal(cond#2) Do_something#B_with_exclusion#2
Deletions:
'MutexUnlock(mut#1) While bool#2 <> true
'MutexLock(mut#2) CondWait(cond#2, mut#2)
' Do_something#A_with_exclusion#2 Wend
' bool#2 = true bool#2 = false
' CondSignal(cond#2) Do_something#B_with_exclusion#2


Revision [21476]

Edited on 2016-05-17 06:09:11 by fxm [Updated second example: Strengthening immunity against all simultaneous conditional waitings]
Additions:
' Thread#A XOR + <==> Thread#B
'..... .....
'MutexLock(mut#1) MutexLock(mut#1)
' While bool#1 <> true Do_something#B_with_exclusion#1
' CondWait(cond#1, mut#1) bool#1 = true
' Wend CondSignal(cond#1)
' bool#1 = false MutexUnlock(mut#1)
' Do_something#A_with_exclusion#1 MutexLock(mut#2)
'MutexUnlock(mut#1) While bool#2 <> true
'MutexLock(mut#2) CondWait(cond#2, mut#2)
' Do_something#A_with_exclusion#2 Wend
' bool#2 = true bool#2 = false
' CondSignal(cond#2) Do_something#B_with_exclusion#2
'MutexUnlock(mut#2) MutexUnlock(mut#2)
'..... .....
Dim sync1 As Any Ptr 'Any Ptr handle to mutex1
Dim cond1 As Any Ptr 'Any Ptr handle to conditional1
Dim sync2 As Any Ptr 'Any Ptr handle to mutex2
Dim cond2 As Any Ptr 'Any Ptr handle to conditional2
Dim ready1 As Byte 'Boolean to coordinates ready1
Dim ready2 As Byte 'Boolean to coordinates ready2
MutexLock(tp->sync1) 'Mutex1 (Lock) for user thread
tp->ready1 = true 'Set ready1
CondSignal(tp->cond1) 'CondSignal to send signal1 to main thread
MutexUnlock(tp->sync1) 'Mutex1 (Unlock) for user thread
MutexLock(tp->sync2) 'Mutex2 (Lock) for user thread
While tp->ready2 <> true 'Process loop against spurious wakeups
CondWait(tp->cond2, tp->sync2) 'CondWait to receive signal2 from main-thread
tp->ready2 = false
If tp->quit = tp->true Then 'Test for ending user thread
MutexUnlock(tp->sync2) 'Mutex2 (Unlock) for user thread
Exit Do
End If
MutexUnlock(tp->sync2) 'Mutex2 (Unlock) for user thread
Tptr->sync1 = MutexCreate
Tptr->cond1 = CondCreate
Tptr->sync2 = MutexCreate
Tptr->cond2 = CondCreate
MutexLock(Tptr->sync1) 'Mutex1 (Lock) for main thread
While Tptr->ready1 <> Tptr->true 'Process loop against spurious wakeups
CondWait(Tptr->cond1, Tptr->sync1) 'CondWait to receive signal1 from user-thread
Tptr->ready1 = Tptr->false
PSet (Pptr->x, Pptr->y) 'Plotting one point
MutexUnlock(Tptr->sync1) 'Mutex1 (Unlock) for main thread
MutexLock(Tptr->sync2) 'Mutex2 (Lock) for main thread
Tptr->ready2 = Tptr->true 'Set ready2
CondSignal(Tptr->cond2) 'CondSignal to send signal2 to user thread
If Inkey <> "" Then
Tptr->quit = Tptr->true 'Set quit
MutexUnlock(Tptr->sync2) 'Mutex2 (Unlock) for main thread
Exit Do
MutexUnlock(Tptr->sync2) 'Mutex2 (Unlock) for main thread
MutexDestroy(Tptr->sync1)
CondDestroy(Tptr->cond1)
MutexDestroy(Tptr->sync2)
CondDestroy(Tptr->cond2)
Deletions:
' Thread#A XOR + <==> Thread#B
'..... .....
'MutexLock(mut) MutexLock(mut)
' While Thread#A_signal <> false While Thread#A_signal <> true
' CondWait(cond, mut) CondWait(cond, mut)
' Wend Wend
' Do_something#A_with_exclusion Do_something#B_with_exclusion
' Thread#A_signal = true Thread#A_signal = false
' CondSignal(cond) CondSignal(cond)
'MutexUnlock(mut) MutexUnlock(mut)
'..... .....
Dim sync As Any Ptr 'Any Ptr handle to mutex
Dim cond As Any Ptr 'Any Ptr handle to conditional
Dim ready As Byte 'Boolean to coordinates ready
MutexLock(tp->sync) 'Mutex (Lock) for user thread
While tp->ready <> false 'Process loop against spurious wakeups
CondWait(tp->cond, tp->sync) 'CondWait to receive signal from main-thread
tp->ready = true 'Set ready
CondSignal(tp->cond) 'CondSignal to send signal to main thread
MutexUnlock(tp->sync) 'Mutex (Unlock) for user thread
Loop Until tp->quit = tp->true 'Test for ending user thread
Tptr->sync = MutexCreate
Tptr->cond = CondCreate
MutexLock(Tptr->sync) 'Mutex (Lock) for main thread
While Tptr->ready <> Tptr->true 'Process loop against spurious wakeups
CondWait(Tptr->cond, Tptr->sync) 'CondWait to receive signal from user-thread
PSet (Pptr->x, Pptr->y) 'Plotting one point
Tptr->ready = Tptr->false 'Reset ready
CondSignal(Tptr->cond) 'CondSignal to send signal to user thread
MutexUnlock(Tptr->sync) 'Mutex (Unlock) for main thread
Loop Until Inkey <> ""
MutexLock(Tptr->sync) 'Mutex (Lock) for main thread
Tptr->ready = Tptr->false 'Reset ready
Tptr->quit = Tptr->true 'Set quit
CondSignal(Tptr->cond) 'CondSignal to send signal to user thread
MutexUnlock(Tptr->sync) 'Mutex (Unlock) for main thread
MutexDestroy(Tptr->sync)
CondDestroy(Tptr->cond)


Revision [20096]

Edited on 2016-02-10 15:55:50 by DkLwikki [Update link format]
Additions:
[[KeyPgDeclare|declare]] [[KeyPgFunction|function]] **Condcreate** ( ) [[KeyPgAs|as]] [[KeyPgAny|any]] [[KeyPgPtr|ptr]]
Once the conditional is **Condcreate**d and the threads are started, one or more of them (including the main thread executing main program) can be set to ##[[KeyPgCondWait|Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal|Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast|Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy|Conddestroy]]## must be used to avoid leaking resources in the OS.
See also ##[[KeyPgCondWait|Condwait]]## and ##[[KeyPgCondSignal|Condsignal]]##
CondWait hcondstart, hmutexstart
Print id;
Print "unable to create thread"
ThreadWait threads(i)
Static As Integer I
MutexLock(tp->sync) 'Mutex (Lock) for user thread
While tp->ready <> false 'Process loop against spurious wakeups
CondWait(tp->cond, tp->sync) 'CondWait to receive signal from main-thread
Wend
tp->procedure(tp->p) 'Procedure(Any Ptr) to be executed by user thread
I += 1
Locate 30, 38
Print I;
tp->ready = true 'Set ready
CondSignal(tp->cond) 'CondSignal to send signal to main thread
MutexUnlock(tp->sync) 'Mutex (Unlock) for user thread
Sleep 5
See also the similar ##[[KeyPgMutexCreate|Mutexcreate]]## example
- Threading is not allowed in //[[CompilerOptlang|-lang qb]]//
- ##[[KeyPgCondBroadcast|Condbroadcast]]##
- ##[[KeyPgCondDestroy|Conddestroy]]##
- ##[[KeyPgCondSignal|Condsignal]]##
- ##[[KeyPgCondWait|Condwait]]##
- ##[[KeyPgMutexCreate|Mutexcreate]]##
- ##[[KeyPgMutexLock|Mutexlock]]##
- ##[[KeyPgMutexUnlock|Mutexunlock]]##
- ##[[KeyPgThreadCreate|Threadcreate]]##
Deletions:
[[KeyPgDeclare declare]] [[KeyPgFunction function]] **Condcreate** ( ) [[KeyPgAs as]] [[KeyPgAny any]] [[KeyPgPtr ptr]]
Once the conditional is **Condcreate**d and the threads are started, one or more of them (including the main thread executing main program) can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.
See also ##[[KeyPgCondWait Condwait]]## and ##[[KeyPgCondSignal Condsignal]]##
CondWait hcondstart, hmutexstart
Print id;
Print "unable to create thread"
ThreadWait threads(i)
Static As Integer I
MutexLock(tp->sync) 'Mutex (Lock) for user thread
While tp->ready <> false 'Process loop against spurious wakeups
CondWait(tp->cond, tp->sync) 'CondWait to receive signal from main-thread
Wend
tp->procedure(tp->p) 'Procedure(Any Ptr) to be executed by user thread
I += 1
Locate 30, 38
Print I;
tp->ready = true 'Set ready
CondSignal(tp->cond) 'CondSignal to send signal to main thread
MutexUnlock(tp->sync) 'Mutex (Unlock) for user thread
Sleep 5
See also the similar ##[[KeyPgMutexCreate Mutexcreate]]## example
- Threading is not allowed in //[[CompilerOptlang -lang qb]]//
- ##[[KeyPgCondBroadcast Condbroadcast]]##
- ##[[KeyPgCondDestroy Conddestroy]]##
- ##[[KeyPgCondSignal Condsignal]]##
- ##[[KeyPgCondWait Condwait]]##
- ##[[KeyPgMutexCreate Mutexcreate]]##
- ##[[KeyPgMutexLock Mutexlock]]##
- ##[[KeyPgMutexUnlock Mutexunlock]]##
- ##[[KeyPgThreadCreate Threadcreate]]##


Revision [17850]

Edited on 2015-12-07 07:59:46 by FxMwikki [Added code in the main thread to avoid any thread blocking when its stopping is requested]
Additions:
While tp->ready <> false 'Process loop against spurious wakeups
tp->ready = true 'Set ready
Tptr->ready = Tptr->false 'Reset ready
MutexLock(Tptr->sync) 'Mutex (Lock) for main thread
Tptr->ready = Tptr->false 'Reset ready
Tptr->quit = Tptr->true 'Set quit
CondSignal(Tptr->cond) 'CondSignal to send signal to user thread
MutexUnlock(Tptr->sync) 'Mutex (Unlock) for main thread
Deletions:
While tp->Ready <> false 'Process loop against spurious wakeups
tp->Ready = true 'Set Ready
Tptr->Ready = Tptr->false 'Reset Ready
Tptr->quit = Tptr->true


Revision [17651]

Edited on 2015-05-09 03:14:04 by FxMwikki [Changed a little the first example for executing more logically]
Additions:
Dim Shared hcondstart As Any Ptr
Dim Shared hmutexstart As Any Ptr
Dim Shared start As Integer = 0
Dim Shared threadcount As Integer
Dim Shared hmutexready As Any Ptr
Dim Shared hcondready As Any Ptr
Sub mythread(ByVal id_ptr As Any Ptr)
Dim id As Integer = Cast(Integer, id_ptr)

MutexLock hmutexready
Print "Thread #" & id & " is waiting..."
CondSignal hcondready
MutexUnlock hmutexready

MutexLock hmutexstart
Do While start = 0
CondWait hcondstart, hmutexstart
Loop

MutexUnlock hmutexstart
For i As Integer = 1 To 40
Print id;
Next i
Dim threads(1 To 9) As Any Ptr
hcondstart = CondCreate()
hmutexstart = MutexCreate()
hcondready = CondCreate()
hmutexready = MutexCreate()
MutexLock(hmutexready)
For i As Integer = 1 To 9
threads(i) = ThreadCreate(@mythread, Cast(Any Ptr, i))
If threads(i) = 0 Then
Print "unable to create thread"
End If
Next i
Print "Waiting until all threads are ready..."
Do Until threadcount = 9
CondWait(hcondready, hmutexready)
Loop
MutexUnlock(hmutexready)
Print
Print "Go!"
MutexLock hmutexstart
CondBroadcast hcondstart
MutexUnlock hmutexstart
For i As Integer = 1 To 9
If threads(i) <> 0 Then
ThreadWait threads(i)
End If
Next i
MutexDestroy hmutexready
CondDestroy hcondready
MutexDestroy hmutexstart
CondDestroy hcondstart
Deletions:
dim shared hcondstart as any ptr
dim shared hmutexstart as any ptr
dim shared start as integer = 0
dim shared threadcount as integer
dim shared hmutexready as any ptr
dim shared hcondready as any ptr
sub mythread(byval id_ptr as any ptr)
dim id as integer = cast(integer, id_ptr)
print "Thread #" & id & " is waiting..."
mutexlock hmutexready
condsignal hcondready
mutexunlock hmutexready

Mutexlock hmutexstart
do while start = 0
Condwait hcondstart, hmutexstart
loop

Mutexunlock hmutexstart
for i as integer = 1 to 40
print id;
next i
end sub
dim threads(1 to 9) as any ptr
hcondstart = condcreate()
hmutexstart = mutexcreate()
hcondready = condcreate()
hmutexready = mutexcreate()
for i as integer = 1 to 9
threads(i) = ThreadCreate(@mythread, cast(any ptr, i))
if threads(i) = 0 then
print "unable to create thread"
end if
next i
print "Waiting until all threads are ready..."
mutexlock(hmutexready)
do until threadcount = 9
condwait(hcondready, hmutexready)
loop
mutexunlock(hmutexready)
print "Go!"
mutexlock hmutexstart
condbroadcast hcondstart
mutexunlock hmutexstart
for i as integer = 1 to 9
if threads(i) <> 0 then
threadwait threads(i)
end if
next i
mutexdestroy hmutexready
conddestroy hcondready
mutexdestroy hmutexstart
conddestroy hcondstart


Revision [17649]

Edited on 2015-05-02 01:33:30 by FxMwikki [Update example]
Additions:
Locate 30, 62
Deletions:
Locate 30, 63


Revision [17647]

Edited on 2015-05-01 16:13:55 by FxMwikki [Update example]
Additions:
Static As Integer I
CondWait(tp->cond, tp->sync) 'CondWait to receive signal from main-thread
I += 1
Locate 30, 38
Print I;
CondSignal(tp->cond) 'CondSignal to send signal to main thread
Locate 30, 27
Print "calculated:";
Locate 30, 54
Print "plotted:";
Tptr->cond = CondCreate
Static As Integer I
CondWait(Tptr->cond, Tptr->sync) 'CondWait to receive signal from user-thread
I += 1
Locate 30, 63
Print I;
CondSignal(Tptr->cond) 'CondSignal to send signal to user thread
Sleep
Deletions:
Condwait(tp->cond, tp->sync) 'CondWait to receive signal from main-thread
Condsignal(tp->cond) 'CondSignal to send signal to main thread
Tptr->cond = Condcreate
Condwait(Tptr->cond, Tptr->sync) 'CondWait to receive signal from user-thread
Condsignal(Tptr->cond) 'CondSignal to send signal to user thread


Revision [17643]

Edited on 2015-05-01 04:23:16 by FxMwikki [Added example]
Additions:
{{fbdoc item="filename" value="examples/manual/threads/condcreate2.bas"}}%%(freebasic)
'Visual example of mutual exclusion + mutual synchronization between 2 threads
'by using Mutex and CondVar:
'the "user-defined thread" computes the points coordinates on a circle,
'and the "main thread" plots the points.
'
'Principle of mutual exclusion + mutual synchronisation
' Thread#A XOR + <==> Thread#B
'..... .....
'MutexLock(mut) MutexLock(mut)
' While Thread#A_signal <> false While Thread#A_signal <> true
' CondWait(cond, mut) CondWait(cond, mut)
' Wend Wend
' Do_something#A_with_exclusion Do_something#B_with_exclusion
' Thread#A_signal = true Thread#A_signal = false
' CondSignal(cond) CondSignal(cond)
'MutexUnlock(mut) MutexUnlock(mut)
'..... .....
'
'Behavior:
'- Unnecessary to pre-calculate the first point.
'- Each calculated point is plotted one time only.
'
'If you comment out the lines containing "MutexLock" and "MutexUnlock",
'"CondWait" and "CondSignal", ".ready"
'(inside "user-defined thread" or/and "main thread"),
'there will be no longer mutual exclusion nor mutual synchronization
'between computation of coordinates and plotting of points,
'and many points will not be plotted on circle (due to non coherent coordinates).
'-----------------------------------------------------------------------------------------------------
Type ThreadUDT 'Generic user thread UDT
Dim handle As Any Ptr 'Any Ptr handle to user thread
Dim sync As Any Ptr 'Any Ptr handle to mutex
Dim cond As Any Ptr 'Any Ptr handle to conditional
Dim ready As Byte 'Boolean to coordinates ready
Dim quit As Byte 'Boolean to end user thread
Declare Static Sub Thread (ByVal As Any Ptr) 'Generic user thread procedure
Dim procedure As Sub (ByVal As Any Ptr) 'Procedure(Any Ptr) to be executed by user thread
Dim p As Any Ptr 'Any Ptr to pass to procedure executed by user thread
Const false As Byte = 0 'Constante "false"
Const true As Byte = Not false 'Constante "true"
End Type
Static Sub ThreadUDT.Thread (ByVal param As Any Ptr) 'Generic user thread procedure
Dim tp As ThreadUDT Ptr = param 'Casting to generic user thread UDT
Do
MutexLock(tp->sync) 'Mutex (Lock) for user thread
While tp->Ready <> false 'Process loop against spurious wakeups
Condwait(tp->cond, tp->sync) 'CondWait to receive signal from main-thread
Wend
tp->procedure(tp->p) 'Procedure(Any Ptr) to be executed by user thread
tp->Ready = true 'Set Ready
Condsignal(tp->cond) 'CondSignal to send signal to main thread
MutexUnlock(tp->sync) 'Mutex (Unlock) for user thread
Sleep 5
Loop Until tp->quit = tp->true 'Test for ending user thread
End Sub
'-----------------------------------------------------------------------------------------------------
Type Point2D
Dim x As Integer
Dim y As Integer
End Type
Const x0 As Integer = 640 / 2
Const y0 As Integer = 480 / 2
Const r0 As Integer = 200
Const pi As Single = 4 * Atn(1)
Sub PointOnCircle (ByVal p As Any Ptr)
Dim pp As Point2D Ptr = p
Dim teta As Single = 2 * pi * Rnd
pp->x = x0 + r0 * Cos(teta)
Sleep 5 'To increase possibility of uncorrelated data occurrence
pp->y = y0 + r0 * Sin(teta)
End Sub
Screen 12
Locate 30, 2
Print "<any_key> : exit";
Dim Pptr As Point2D Ptr = New Point2D
Dim Tptr As ThreadUDT Ptr = New ThreadUDT
Tptr->sync = MutexCreate
Tptr->cond = Condcreate
Tptr->procedure = @PointOnCircle
Tptr->p = Pptr
Tptr->handle = ThreadCreate(@ThreadUDT.Thread, Tptr)
Do
MutexLock(Tptr->sync) 'Mutex (Lock) for main thread
While Tptr->ready <> Tptr->true 'Process loop against spurious wakeups
Condwait(Tptr->cond, Tptr->sync) 'CondWait to receive signal from user-thread
Wend
PSet (Pptr->x, Pptr->y) 'Plotting one point
Tptr->Ready = Tptr->false 'Reset Ready
Condsignal(Tptr->cond) 'CondSignal to send signal to user thread
MutexUnlock(Tptr->sync) 'Mutex (Unlock) for main thread
Sleep 5
Loop Until Inkey <> ""

Tptr->quit = Tptr->true
ThreadWait(Tptr->handle)
MutexDestroy(Tptr->sync)
CondDestroy(Tptr->cond)
Delete Tptr
Delete Pptr
See also the similar ##[[KeyPgMutexCreate Mutexcreate]]## example


Revision [17625]

Edited on 2015-04-26 16:15:02 by FxMwikki [Added link to other example]
Additions:
See also ##[[KeyPgCondWait Condwait]]## and ##[[KeyPgCondSignal Condsignal]]##
Deletions:
See also ##[[KeyPgCondWait Condwait]]##


Revision [17621]

Edited on 2015-04-26 06:59:41 by FxMwikki [Added link to other example]
Additions:
See also ##[[KeyPgCondWait Condwait]]##


Revision [17610]

Edited on 2015-04-25 15:50:58 by FxMwikki [Rewording]
Additions:
Once the conditional is **Condcreate**d and the threads are started, one or more of them (including the main thread executing main program) can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.
Deletions:
Once the conditional is **Condcreate**d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional (including the main thread executing main program). At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.


Revision [16961]

Edited on 2013-09-27 14:04:03 by FxMwikki [Conditional variable can be used with all threads including the main thread executing main program]
Additions:
Once the conditional is **Condcreate**d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional (including the main thread executing main program). At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.
Deletions:
Once the conditional is **Condcreate**d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.


Revision [15461]

Edited on 2011-10-22 15:10:33 by FxMwikki [Suppression of the link to KeyPgCondCreate itself]
Additions:
Once the conditional is **Condcreate**d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.
Deletions:
Once the conditional is ##**[[KeyPgCondCreate Condcreate]]**##d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.


Revision [15211]

Edited on 2011-09-03 05:47:03 by SirMud [Suppression of the link to KeyPgCondCreate itself]
Additions:
Once the conditional is ##**[[KeyPgCondCreate Condcreate]]**##d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.
Deletions:
Once the conditional is ##**[[KeyPgCondCreate Condcreate**##d]] and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.


Revision [15210]

Edited on 2011-09-03 05:46:47 by SirMud [Suppression of the link to KeyPgCondCreate itself]
Additions:
Once the conditional is ##**[[KeyPgCondCreate Condcreate**##d]] and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.
Deletions:
Once the conditional is ##**KeyPgCondCreate Condcreate**##d and the threads are started, one or more of them can be set to ##[[KeyPgCondWait Condwait]]## for the conditional, they will be stopped until some other thread ##[[KeyPgCondSignal Condsignal]]##s that the waiting thread can restart. ##[[KeyPgCondBroadcast Condbroadcast]]## can be used to restart all threads waiting for the conditional. At the end of the program ##[[KeyPgCondDestroy Conddestroy]]## must be used to avoid leaking resources in the OS.


Revision [14275]

Edited on 2009-08-29 21:51:47 by CountingPine [Remove CamelCase links in "New to FreeBASIC"]
Additions:
- New to ""FreeBASIC""
Deletions:
- New to FreeBASIC


Revision [12242]

The oldest known version of this page was created on 2008-01-18 14:08:47 by JeffMarshall [Remove CamelCase links in "New to FreeBASIC"]
Valid XHTML :: Valid CSS: :: Powered by WikkaWiki



sf.net phatcode