[Vm-dev] VM Maker: VMMaker.oscog-eem.3128.mcz

commits at source.squeak.org commits at source.squeak.org
Sun Jan 2 21:06:34 UTC 2022


Eliot Miranda uploaded a new version of VMMaker to project VM Maker:
http://source.squeak.org/VMMaker/VMMaker.oscog-eem.3128.mcz

==================== Summary ====================

Name: VMMaker.oscog-eem.3128
Author: eem
Time: 2 January 2022, 1:06:23.161391 pm
UUID: 8522e1f3-7b76-400f-91d1-2c491364717b
Ancestors: VMMaker.oscog-eem.3127

Oops! Forgot to commit the CoInterpreterPrimitives versions of primitiveResume (comment change only) and primitiveSuspend (the new semantics)

=============== Diff against VMMaker.oscog-eem.3127 ===============

Item was changed:
  ----- Method: CoInterpreterPrimitives>>primitiveResume (in category 'process primitives') -----
  primitiveResume
  	"Put this process on the scheduler's lists thus allowing it to proceed next time there is
  	 a chance for processes of it's priority level.  It must go to the back of its run queue so
  	 as not to preempt any already running processes at this level.  If the process's priority
  	 is higher than the current process, preempt the current process."
  	| proc ctxt inInterpreter |
  	proc := self stackTop.  "rcvr"
+ 	"Alas in Spur we need a read barrier"
  	ctxt := objectMemory followField: SuspendedContextIndex ofObject: proc. "written this way to get better Slang inlining"
  	(objectMemory isContext: ctxt) ifFalse:
  		[^self primitiveFailFor: PrimErrBadReceiver].
  	"We're about to switch process, either to an interpreted frame or a
  	 machine code frame. To know whether to return or enter machine code
  	 we have to know from whence we came.  We could have come from the
  	 interpreter, either directly or via a machine code primitive.  We could have
  	 come from machine code.  The instructionPointer tells us where from:"
  	inInterpreter := instructionPointer >= objectMemory startOfMemory.
  	(self resume: proc preemptedYieldingIf: preemptionYields from: CSResume) ifTrue:
+ 		[self forProcessPrimitiveReturnToExecutivePostContextSwitch: inInterpreter]!
- 		[self forProcessPrimitiveReturnToExecutivePostContextSwitch: inInterpreter]
- 
- 	"Personally I would like to check MyList, which should not be one of the elements of the scheduler lists.
- 	 But there are awful race conditions in things like should:notTakeMoreThan: that mean we can't.
- 	 eem 9/27/2010 23:08, updated eem 5/20/2021 15:36. e.g.
- 
- 	| proc field |
- 	proc := self stackTop.  ''rcvr''
- 	''We only have to check for myList being nil.  If it is nil then this is either the active process or
- 	 a process suspended with primitiveSuspend (and if it is the activeProcess suspendedContext will
- 	 be nil and the isContext: test will fail).  If it is not nil then either the process is waiting on some
- 	 semaphore-like list or on one of the scheduler's lists. If it is on some semaphore-like list it should
- 	 not resume.  If it is on one of the scheduler's lists it is runnable (already resumed).''
- 	field := objectMemory followField: MyListIndex ofObject: proc.
- 	objectMemory nilObject = field ifFalse:
- 		[^self primitiveFailFor: PrimErrInappropriate].
- 	field := objectMemory followField: SuspendedContextIndex ofObject: proc.
- 	(objectMemory isContext: field) ifFalse:
- 		[^self primitiveFailFor: PrimErrBadReceiver].
- 	''We're about to switch process, either to an interpreted frame or a
- 	 machine code frame. To know whether to return or enter machine code
- 	 we have to know from whence we came.  We could have come from the
- 	 interpreter, either directly or via a machine code primitive.  We could have
- 	 come from machine code.  The instructionPointer tells us where from:''
- 	inInterpreter := instructionPointer >= objectMemory startOfMemory.
- 	(self resume: proc preemptedYieldingIf: preemptionYields from: CSResume) ifTrue:
- 		[self forProcessPrimitiveReturnToExecutivePostContextSwitch: inInterpreter]"!

Item was changed:
  ----- Method: CoInterpreterPrimitives>>primitiveSuspend (in category 'process primitives') -----
  primitiveSuspend
+ 	"Primitive. Suspend the receiver, aProcess, such that it can be executed again
+ 	 by sending #resume. If the given process is not the active process, take it off
+ 	 its corresponding list. If the list was not its run queue assume it was on some
+ 	 condition variable (Semaphore, Mutex) and back up its pc to the send that
+ 	 invoked the wait state the process entered.  Hence when the process resumes
+ 	 it will reenter the wait state. Answer the list the receiver was previously on iff
+ 	 it was not active and not blocked, otherwise answer nil."
+ 	| process myList ok |
- 	"Primitive. Suspend the receiver, aProcess such that it can be executed again
- 	by sending #resume. If the given process is not currently running, take it off
- 	its corresponding list. The primitive returns the list the receiver was previously on."
- 	| process myList |
  	process := self stackTop.
  	process = self activeProcess ifTrue:
  		[| inInterpreter |
  		"We're going to switch process, either to an interpreted frame or a machine
  		 code frame. To know whether to return or enter machine code we have to
  		 know from whence we came.  We could have come from the interpreter,
  		 either directly or via a machine code primitive.  We could have come from
  		 machine code.  The instructionPointer tells us where from:"
  		self pop: 1 thenPush: objectMemory nilObject.
  		inInterpreter := instructionPointer >= objectMemory startOfMemory.
  		self transferTo: self wakeHighestPriority from: CSSuspend.
  		^self forProcessPrimitiveReturnToExecutivePostContextSwitch: inInterpreter].
+ 	"Alas in Spur we need a read barrier"
+ 	myList := objectMemory followField: MyListIndex ofObject: process.
- 	myList := objectMemory fetchPointer: MyListIndex ofObject: process.
- 	"XXXX Fixme. We should really check whether myList is a kind of LinkedList or not
- 	but we can't easily so just do a quick check for nil which is the most common case."
  	myList = objectMemory nilObject ifTrue:
  		[^self primitiveFailFor: PrimErrBadReceiver].
+ 	ok := self removeProcess: process fromList: myList.
+ 	ok ifFalse:
+ 		[^self primitiveFailFor: PrimErrOperationFailed].
+ 	objectMemory storePointerUnchecked: MyListIndex ofObject: process withValue: objectMemory nilObject.
+ 	self assert: RevisedSuspend.
+ 	(RevisedSuspend
+ 	 and: [(objectMemory fetchClassTagOfNonImm: myList) ~= classLinkedListClassTag])
+ 		ifTrue:
+ 			[self backupProcess: process toBlockingSendTo: myList.
+ 			 self pop: 1 thenPush: objectMemory nilObject]
+ 		ifFalse:
+ 			[self pop: 1 thenPush: myList]!
- 	"Alas in Spur we need a read barrier"
- 	(objectMemory isForwarded: myList) ifTrue:
- 		[myList := objectMemory followForwarded: myList.
- 		 objectMemory storePointer: MyListIndex ofObject: process withValue: myList].
- 	self removeProcess: process fromList: myList.
- 	self successful ifTrue:
- 		[objectMemory storePointerUnchecked: MyListIndex ofObject: process withValue: objectMemory nilObject.
- 		 self pop: 1 thenPush: myList]!



More information about the Vm-dev mailing list