440 "remove all waiting processes from the list of waiting processes |
440 "remove all waiting processes from the list of waiting processes |
441 and resume them. |
441 and resume them. |
442 NOTE: Must be called when known that waitingProcesses is nonNil and |
442 NOTE: Must be called when known that waitingProcesses is nonNil and |
443 also with blocked interrupts" |
443 also with blocked interrupts" |
444 |
444 |
445 |processes anyDead currentPriority needsReschedule| |
445 |processes anyDead needsReschedule| |
446 |
446 |
447 processes := waitingProcesses. |
447 processes := waitingProcesses. |
448 "/ do not set to nil - a waiting process may be suspended and will not be resumed... |
448 "/ do not set to nil - a waiting process may be suspended and will not be resumed by #makeRunnable: ... |
449 "/ waitingProcesses := nil. |
449 "/ waitingProcesses := nil. |
450 |
450 |
451 currentPriority := Processor currentPriority. |
|
452 needsReschedule := false. |
451 needsReschedule := false. |
453 anyDead := false. |
452 anyDead := false. |
454 processes do:[:eachProcess | |
453 processes do:[:eachProcess | |
455 (eachProcess isNil or:[eachProcess isDead]) ifTrue:[ |
454 (Processor makeRunnable:eachProcess) ifTrue:[ |
456 Transcript show:'oops: a dead process: '; showCR:eachProcess. |
455 needsReschedule := true. |
457 anyDead := true. |
|
458 ] ifFalse:[ |
456 ] ifFalse:[ |
459 (Processor makeRunnable:eachProcess) ifTrue:[ |
457 "if process is nil or dead (or for other reasons) makeRunnable returns false. |
460 needsReschedule := true. |
458 So check here." |
|
459 (eachProcess isNil or:[eachProcess isDead]) ifTrue:[ |
|
460 "printing to Transcript might not be a good idea while interrupts are blocked" |
|
461 'Semaphore>>wakeupWaiters: removing a dead process: ' infoPrint. eachProcess infoPrintCR. |
|
462 anyDead := true. |
461 ]. |
463 ]. |
462 ] |
464 ]. |
463 ]. |
465 ]. |
464 anyDead ifTrue:[ |
466 anyDead ifTrue:[ |
465 "interrupts are already blocked by sender" |
467 "interrupts are already blocked by sender" |
466 waitingProcesses := processes reject:[:p | p isNil or:[p isDead]] |
468 waitingProcesses := processes reject:[:p | p isNil or:[p isDead]] |
467 ]. |
469 ]. |
582 |
584 |
583 needsReschedule := false. |
585 needsReschedule := false. |
584 wasBlocked := OperatingSystem blockInterrupts. |
586 wasBlocked := OperatingSystem blockInterrupts. |
585 [ |
587 [ |
586 count := count + 1. |
588 count := count + 1. |
587 waitingProcesses notNil ifTrue:[ |
589 waitingProcesses size ~~ 0 ifTrue:[ |
588 needsReschedule := self wakeupWaiters. |
590 needsReschedule := self wakeupWaiters. |
589 ]. |
591 ]. |
590 ] ensure:[ |
592 ] ensure:[ |
591 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
593 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
592 ]. |
594 ]. |
603 This can be used for process synchronization, if multiple processes are |
605 This can be used for process synchronization, if multiple processes are |
604 waiting for a common event." |
606 waiting for a common event." |
605 |
607 |
606 |wasBlocked needsReschedule| |
608 |wasBlocked needsReschedule| |
607 |
609 |
608 waitingProcesses notNil ifTrue:[ |
610 waitingProcesses size ~~ 0 ifTrue:[ |
609 needsReschedule := false. |
611 needsReschedule := false. |
610 wasBlocked := OperatingSystem blockInterrupts. |
612 wasBlocked := OperatingSystem blockInterrupts. |
611 [ |
613 [ |
612 "first, make them all runnable, but do not schedule |
614 "first, make them all runnable, but do not schedule |
613 (in case one has higher prio and goes into a wait immediately again.)" |
615 (in case one has higher prio and goes into a wait immediately again.)" |
743 |
745 |
744 OperatingSystem blockInterrupts. |
746 OperatingSystem blockInterrupts. |
745 needsReschedule := false. |
747 needsReschedule := false. |
746 [ |
748 [ |
747 count := count + 1. |
749 count := count + 1. |
748 waitingProcesses notNil ifTrue:[ |
750 waitingProcesses size ~~ 0 ifTrue:[ |
749 needsReschedule := self wakeupWaiters. |
751 needsReschedule := self wakeupWaiters. |
750 ]. |
752 ]. |
751 ] ensure:[ |
753 ] ensure:[ |
752 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
754 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
753 ]. |
755 ]. |
811 |
813 |
812 wasBlocked := OperatingSystem blockInterrupts. |
814 wasBlocked := OperatingSystem blockInterrupts. |
813 |
815 |
814 count <= 0 ifTrue:[ |
816 count <= 0 ifTrue:[ |
815 activeProcess := Processor activeProcess. |
817 activeProcess := Processor activeProcess. |
816 |
|
817 " |
818 " |
818 need a while-loop here, since more than one process may |
819 need a while-loop here, since more than one process may |
819 wait for it and another one may also wake up. |
820 wait for it and another one may also wake up. |
820 Thus, the count is not always non-zero after returning from |
821 Thus, the count is not always non-zero after returning from |
821 suspend. |
822 suspend. |
838 ] doUntil:[count > 0]. |
839 ] doUntil:[count > 0]. |
839 ]. |
840 ]. |
840 |
841 |
841 count := count - 1. |
842 count := count - 1. |
842 count == 0 ifTrue:[ |
843 count == 0 ifTrue:[ |
843 lastOwner := Processor activeProcess. |
844 activeProcess isNil ifTrue:[activeProcess := Processor activeProcess]. |
|
845 lastOwner := activeProcess. |
844 ]. |
846 ]. |
845 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
847 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
846 |
848 |
847 "Modified: / 13-12-1995 / 13:26:33 / stefan" |
849 "Modified: / 13-12-1995 / 13:26:33 / stefan" |
848 "Modified: / 11-08-2011 / 14:36:43 / cg" |
850 "Modified: / 11-08-2011 / 14:36:43 / cg" |
981 Processor removeTimedBlock:timeoutBlock. |
982 Processor removeTimedBlock:timeoutBlock. |
982 timeoutBlock := nil. |
983 timeoutBlock := nil. |
983 ]. |
984 ]. |
984 ]. |
985 ]. |
985 |
986 |
986 "if we come here, we have accquired the semaphore" |
987 "if we come here, we have acquired the semaphore" |
987 count := count - 1. |
988 count := count - 1. |
988 count == 0 ifTrue:[ |
989 count == 0 ifTrue:[ |
989 lastOwner := Processor activeProcess. |
990 activeProcess isNil ifTrue:[activeProcess := Processor activeProcess]. |
|
991 lastOwner := activeProcess. |
990 ]. |
992 ]. |
991 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
993 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
992 ^ self |
994 ^ self |
993 |
995 |
994 "Modified: / 13-12-1995 / 13:27:24 / stefan" |
996 "Modified: / 13-12-1995 / 13:27:24 / stefan" |