154 Processor := self basicNew initialize. |
154 Processor := self basicNew initialize. |
155 ]. |
155 ]. |
156 |
156 |
157 " |
157 " |
158 allow configurations without processes |
158 allow configurations without processes |
|
159 (but such configurations are no longer distributed) |
159 " |
160 " |
160 PureEventDriven := self threadsAvailable not. |
161 PureEventDriven := self threadsAvailable not. |
161 PureEventDriven ifTrue:[ |
162 PureEventDriven ifTrue:[ |
162 'PROCESSOR: no process support - running event driven' errorPrintNL |
163 'Processor [error]: no process support - running event driven' errorPrintCR |
163 ]. |
164 ]. |
164 |
165 |
165 "Modified: 7.3.1996 / 19:22:49 / cg" |
|
166 "Modified: 23.9.1996 / 14:24:50 / stefan" |
166 "Modified: 23.9.1996 / 14:24:50 / stefan" |
|
167 "Modified: 10.1.1997 / 18:03:03 / cg" |
167 ! ! |
168 ! ! |
168 |
169 |
169 !ProcessorScheduler class methodsFor:'instance creation'! |
170 !ProcessorScheduler class methodsFor:'instance creation'! |
170 |
171 |
171 new |
172 new |
197 1 to:sz do:[:index | |
198 1 to:sz do:[:index | |
198 "/ (KnownProcesses at:index) isNil ifTrue:[ |
199 "/ (KnownProcesses at:index) isNil ifTrue:[ |
199 (KnownProcesses at:index) == 0 ifTrue:[ |
200 (KnownProcesses at:index) == 0 ifTrue:[ |
200 id := KnownProcessIds at:index. |
201 id := KnownProcessIds at:index. |
201 id notNil ifTrue:[ |
202 id notNil ifTrue:[ |
202 'PROCESSOR: terminating thread ' errorPrint. |
203 'Processor [warning]: terminating thread ' errorPrint. |
203 id errorPrint. |
204 id errorPrint. |
204 ' (no longer refd)' errorPrintNL. |
205 ' (no longer refd)' errorPrintNL. |
205 |
206 |
206 self threadDestroy:id. |
207 self threadDestroy:id. |
207 KnownProcessIds at:index put:nil. |
208 KnownProcessIds at:index put:nil. |
619 "/ this safes a bit of memory allocation in the scheduler) |
621 "/ this safes a bit of memory allocation in the scheduler) |
620 |
622 |
621 dispatchAction := [self dispatch]. |
623 dispatchAction := [self dispatch]. |
622 |
624 |
623 handlerAction := [:ex | |
625 handlerAction := [:ex | |
624 ('ProcessorScheduler [info]: ignored signal (', ex signal printString, ')') infoPrintNL. |
626 ('Processor [info]: ignored signal (', ex signal printString, ')') infoPrintCR. |
625 ex return |
627 ex return |
626 ]. |
628 ]. |
627 |
629 |
628 ignoredSignals := SignalSet |
630 ignoredSignals := SignalSet |
629 with:(Process terminateSignal) |
631 with:(Process terminateSignal) |
639 |
641 |
640 "/ we arrive here in standalone Apps, |
642 "/ we arrive here in standalone Apps, |
641 "/ when the last process at or above UserSchedulingPriority process died. |
643 "/ when the last process at or above UserSchedulingPriority process died. |
642 "/ regular ST/X stays in above loop forever |
644 "/ regular ST/X stays in above loop forever |
643 |
645 |
644 'PROCESSOR: finish dispatch (no more processes)' infoPrintNL. |
646 'Processor [info]: finish dispatch (no more processes)' infoPrintNL. |
645 |
647 |
646 "Modified: 23.9.1996 / 14:19:56 / stefan" |
648 "Modified: 23.9.1996 / 14:19:56 / stefan" |
647 "Modified: 10.1.1997 / 15:09:25 / cg" |
649 "Modified: 10.1.1997 / 18:03:17 / cg" |
648 ! |
650 ! |
649 |
651 |
650 exitWhenNoMoreUserProcesses:aBoolean |
652 exitWhenNoMoreUserProcesses:aBoolean |
651 exitWhenNoMoreUserProcesses := aBoolean |
653 exitWhenNoMoreUserProcesses := aBoolean |
652 ! ! |
654 ! ! |
832 " |
834 " |
833 switch failed for some reason - |
835 switch failed for some reason - |
834 destroy the bad process |
836 destroy the bad process |
835 " |
837 " |
836 p id ~~ 0 ifTrue:[ |
838 p id ~~ 0 ifTrue:[ |
837 'PROCESSOR: problem with process ' errorPrint. |
839 'Processor [warning]: problem with process ' errorPrint. |
838 p id errorPrint. |
840 p id errorPrint. |
839 p name notNil ifTrue:[ |
841 p name notNil ifTrue:[ |
840 ' (' errorPrint. p name errorPrint. ')' errorPrint. |
842 ' (' errorPrint. p name errorPrint. ')' errorPrint. |
841 ]. |
843 ]. |
842 '; hard-terminate it.' errorPrintNL. |
844 '; hard-terminate it.' errorPrintCR. |
843 p state:#suspended. |
845 p state:#suspended. |
844 self terminateNoSignal:p. |
846 self terminateNoSignal:p. |
845 ] |
847 ] |
846 ]. |
848 ]. |
847 zombie notNil ifTrue:[ |
849 zombie notNil ifTrue:[ |
1191 |listArray l p prio "{ Class: SmallInteger }" | |
1193 |listArray l p prio "{ Class: SmallInteger }" | |
1192 |
1194 |
1193 prio := HighestPriority. |
1195 prio := HighestPriority. |
1194 listArray := quiescentProcessLists. |
1196 listArray := quiescentProcessLists. |
1195 [prio >= 1] whileTrue:[ |
1197 [prio >= 1] whileTrue:[ |
1196 l := listArray at:prio. |
1198 l := listArray at:prio. |
1197 l notNil ifTrue:[ |
1199 l notNil ifTrue:[ |
1198 l notEmpty ifTrue:[ |
1200 l notEmpty ifTrue:[ |
1199 p := l first. |
1201 p := l first. |
1200 " |
1202 " |
1201 if it got corrupted somehow ... |
1203 if it got corrupted somehow ... |
1202 " |
1204 " |
1203 p id isNil ifTrue:[ |
1205 p id isNil ifTrue:[ |
1204 'PROCESSOR: process with nil id removed' errorPrintNL. |
1206 'Processor [warning]: process with nil id removed' errorPrintCR. |
1205 l removeFirst. |
1207 l removeFirst. |
1206 ^ nil. |
1208 ^ nil. |
1207 ]. |
1209 ]. |
1208 ^ p |
1210 ^ p |
1209 ] |
1211 ] |
1210 ]. |
1212 ]. |
1211 prio := prio - 1 |
1213 prio := prio - 1 |
1212 ]. |
1214 ]. |
1213 ^ nil |
1215 ^ nil |
1214 |
1216 |
1215 "Modified: 29.7.1996 / 11:49:47 / cg" |
1217 "Modified: 10.1.1997 / 18:03:28 / cg" |
1216 ! |
1218 ! |
1217 |
1219 |
1218 isPureEventDriven |
1220 isPureEventDriven |
1219 "this is temporary - (maybe not :-). |
1221 "this is temporary - (maybe not :-). |
1220 you can run ST/X either with or without processes. |
1222 you can run ST/X either with or without processes. |
1458 "notice: this is slightly faster than putting the if-code into |
1460 "notice: this is slightly faster than putting the if-code into |
1459 the ifAbsent block, because [] is a shared cheap block, created at compile time |
1461 the ifAbsent block, because [] is a shared cheap block, created at compile time |
1460 " |
1462 " |
1461 (l isNil or:[(l remove:aProcess ifAbsent:[]) isNil]) ifTrue:[ |
1463 (l isNil or:[(l remove:aProcess ifAbsent:[]) isNil]) ifTrue:[ |
1462 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
1464 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
1463 'PROCESSOR: bad suspend: not on run list' errorPrintNL. |
1465 'Processor [warning]: bad suspend: not on run list' errorPrintCR. |
1464 "/ MiniDebugger enterWithMessage:'bad suspend: not on run list'. |
1466 "/ MiniDebugger enterWithMessage:'bad suspend: not on run list'. |
1465 self threadSwitch:scheduler. |
1467 self threadSwitch:scheduler. |
1466 ^ self |
1468 ^ self |
1467 ]. |
1469 ]. |
1468 |
1470 |
1574 |
1576 |
1575 " |
1577 " |
1576 debugging consistency check - will be removed later |
1578 debugging consistency check - will be removed later |
1577 " |
1579 " |
1578 activeProcess priority ~~ currentPriority ifTrue:[ |
1580 activeProcess priority ~~ currentPriority ifTrue:[ |
1579 'PROCESSOR: oops - process changed priority' errorPrintNL. |
1581 'Processor [warning]: process changed its priority' errorPrintCR. |
1580 currentPriority := activeProcess priority. |
1582 currentPriority := activeProcess priority. |
1581 ]. |
1583 ]. |
1582 |
1584 |
1583 l := quiescentProcessLists at:currentPriority. |
1585 l := quiescentProcessLists at:currentPriority. |
1584 sz := l size. |
1586 sz := l size. |
1585 |
1587 |
1586 " |
1588 " |
1587 debugging consistency checks - will be removed later |
1589 debugging consistency checks - will be removed later |
1588 " |
1590 " |
1589 sz == 0 ifTrue:[ |
1591 sz == 0 ifTrue:[ |
1590 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
1592 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
1591 'PROCESSOR: oops - empty runnable list' errorPrintNL. |
1593 'Processor [warning]: empty runnable list' errorPrintCR. |
1592 ^ self |
1594 ^ self |
1593 ]. |
1595 ]. |
1594 |
1596 |
1595 " |
1597 " |
1596 check if the running process is not the only one |
1598 check if the running process is not the only one |
1597 " |
1599 " |
1598 sz ~~ 1 ifTrue:[ |
1600 sz ~~ 1 ifTrue:[ |
1599 " |
1601 " |
1600 bring running process to the end |
1602 bring running process to the end |
1601 " |
1603 " |
1602 l removeFirst. |
1604 l removeFirst. |
1603 l addLast:activeProcess. |
1605 l addLast:activeProcess. |
1604 |
1606 |
1605 " |
1607 " |
1606 and switch to first in the list |
1608 and switch to first in the list |
1607 " |
1609 " |
1608 self threadSwitch:(l first). |
1610 self threadSwitch:(l first). |
1609 ]. |
1611 ]. |
1610 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
1612 wasBlocked ifFalse:[OperatingSystem unblockInterrupts]. |
1611 |
1613 |
1612 "Modified: 29.7.1996 / 11:55:53 / cg" |
1614 "Modified: 10.1.1997 / 18:04:35 / cg" |
1613 ! ! |
1615 ! ! |
1614 |
1616 |
1615 !ProcessorScheduler methodsFor:'semaphore signalling'! |
1617 !ProcessorScheduler methodsFor:'semaphore signalling'! |
1616 |
1618 |
1617 disableSemaphore:aSemaphore |
1619 disableSemaphore:aSemaphore |
2138 an #EBADF error, leading to high-frequency polling and a locked up system. |
2140 an #EBADF error, leading to high-frequency polling and a locked up system. |
2139 (you could still fix things by interrupting on the console and fixing the |
2141 (you could still fix things by interrupting on the console and fixing the |
2140 readFdArray/writeFdArray in the debugger)" |
2142 readFdArray/writeFdArray in the debugger)" |
2141 |
2143 |
2142 readFdArray keysAndValuesDo:[:idx :fd | |
2144 readFdArray keysAndValuesDo:[:idx :fd | |
2143 |rslt sema| |
2145 |rslt sema| |
2144 |
2146 |
2145 rslt := OperatingSystem |
2147 rslt := OperatingSystem |
2146 selectOnAnyReadable:(Array with:fd) |
2148 selectOnAnyReadable:(Array with:fd) |
2147 writable:nil |
2149 writable:nil |
2148 exception:nil |
2150 exception:nil |
2149 withTimeOut:0. |
2151 withTimeOut:0. |
2150 |
2152 |
2151 (rslt isNil and:[OperatingSystem lastErrorSymbol == #EBADF]) ifTrue:[ |
2153 (rslt isNil and:[OperatingSystem lastErrorSymbol == #EBADF]) ifTrue:[ |
2152 ('PROCESSOR: removing invalid read fileDescriptor: ' , fd printString) errorPrintNL. |
2154 ('Processor [warning]: removing invalid read fileDescriptor: ' , fd printString) errorPrintCR. |
2153 readFdArray at:idx put:nil. |
2155 readFdArray at:idx put:nil. |
2154 OperatingSystem clearLastErrorNumber. |
2156 OperatingSystem clearLastErrorNumber. |
2155 (sema := readSemaphoreArray at:idx) notNil ifTrue:[ |
2157 (sema := readSemaphoreArray at:idx) notNil ifTrue:[ |
2156 readSemaphoreArray at:idx put:nil. |
2158 readSemaphoreArray at:idx put:nil. |
2157 sema signal. |
2159 sema signal. |
2158 ]. |
2160 ]. |
2159 ] |
2161 ] |
2160 ]. |
2162 ]. |
2161 |
2163 |
2162 writeFdArray keysAndValuesDo:[:idx :fd | |
2164 writeFdArray keysAndValuesDo:[:idx :fd | |
2163 |rslt sema| |
2165 |rslt sema| |
2164 |
2166 |
2165 rslt := OperatingSystem |
2167 rslt := OperatingSystem |
2166 selectOnAnyReadable:nil |
2168 selectOnAnyReadable:nil |
2167 writable:(Array with:fd) |
2169 writable:(Array with:fd) |
2168 exception:nil |
2170 exception:nil |
2169 withTimeOut:0. |
2171 withTimeOut:0. |
2170 |
2172 |
2171 (rslt isNil and:[OperatingSystem lastErrorSymbol == #EBADF]) ifTrue:[ |
2173 (rslt isNil and:[OperatingSystem lastErrorSymbol == #EBADF]) ifTrue:[ |
2172 ('PROCESSOR: removing invalid write fileDescriptor: ' , fd printString) errorPrintNL. |
2174 ('Processor [warning]: removing invalid write fileDescriptor: ' , fd printString) errorPrintCR. |
2173 writeFdArray at:idx put:nil. |
2175 writeFdArray at:idx put:nil. |
2174 OperatingSystem clearLastErrorNumber. |
2176 OperatingSystem clearLastErrorNumber. |
2175 (sema := writeSemaphoreArray at:idx) notNil ifTrue:[ |
2177 (sema := writeSemaphoreArray at:idx) notNil ifTrue:[ |
2176 writeSemaphoreArray at:idx put:nil. |
2178 writeSemaphoreArray at:idx put:nil. |
2177 sema signal. |
2179 sema signal. |
2178 ]. |
2180 ]. |
2179 ] |
2181 ] |
2180 ]. |
2182 ]. |
2181 |
2183 |
2182 "Modified: 12.4.1996 / 09:32:58 / stefan" |
2184 "Modified: 12.4.1996 / 09:32:58 / stefan" |
2183 "Modified: 29.8.1996 / 22:42:28 / cg" |
2185 "Modified: 10.1.1997 / 18:03:51 / cg" |
2184 ! |
2186 ! |
2185 |
2187 |
2186 schedulerInterrupt |
2188 schedulerInterrupt |
2187 "forced reschedule - switch to scheduler process which will decide |
2189 "forced reschedule - switch to scheduler process which will decide |
2188 what to do now." |
2190 what to do now." |