comparison MasterLoop.c @ 120:d4c881c7f03a

Added fn to send inter-master requests, and cleaned up code
author Me@portablequad
date Sat, 03 Sep 2011 20:41:51 -0700
parents ac11b50220bd
children 24466227d8bb
comparison
equal deleted inserted replaced
32:5197c66f356b 33:e829b6b0438c
47 * from then on, will be doing continuation, but do suspension self 47 * from then on, will be doing continuation, but do suspension self
48 * directly at end of master loop 48 * directly at end of master loop
49 *So VMS__init just births the master virtual processor same way it births 49 *So VMS__init just births the master virtual processor same way it births
50 * all the others -- then does any extra setup needed and puts it into the 50 * all the others -- then does any extra setup needed and puts it into the
51 * work queue. 51 * work queue.
52 *However means have to make masterEnv a global static volatile the same way 52 *However means have to make masterEnv a global static volatile.
53 * did with readyToAnimateQ in core loop. -- for performance, put the
54 * jump to the core loop directly in here, and have it directly jump back.
55 * 53 *
56 * 54 *
57 *Aug 18, 2010 -- Going to a separate MasterVP for each core, to see if this 55 *Aug 18, 2010 -- Going to a separate MasterVP for each core, to see if this
58 * avoids the suspected bug in the system stack that causes bizarre faults 56 * avoids the suspected bug in the system stack that causes bizarre faults
59 * at random places in the system code. 57 * at random places in the system code.
60 * 58 *
61 *So, this function is coupled to each of the MasterVPs, -- meaning this 59 *So, this function is coupled to each of the MasterVPs, -- meaning this
62 * function can't rely on a particular stack and frame -- each MasterVP that 60 * function can't rely on a particular stack and frame -- each MasterVP that
63 * animates this function has a different one. 61 * animates this function has a different stack.
64 * 62 *
65 *At this point, the masterLoop does not write itself into the queue anymore, 63 *At this point, the masterLoop does not write itself into the queue anymore,
66 * instead, the coreLoop acquires the masterLock when it has nothing to 64 * instead, the coreLoop acquires the masterLock when it has nothing to
67 * animate, and then animates its own masterLoop. However, still try to put 65 * animate, and then animates its own masterLoop. However, still try to put
68 * several AppVPs into the queue to amortize the startup cost of switching 66 * several AppVPs into the queue to amortize the startup cost of switching
94 // of setup code.. (VP creator sets up the stack as if this function 92 // of setup code.. (VP creator sets up the stack as if this function
95 // was called normally, but actually get here by jmp) 93 // was called normally, but actually get here by jmp)
96 //So, setup values about stack ptr, jmp pt and all that 94 //So, setup values about stack ptr, jmp pt and all that
97 //masterPr->nextInstrPt = &&masterLoopStartPt; 95 //masterPr->nextInstrPt = &&masterLoopStartPt;
98 96
99 97 //Sept 2011
100 //Note, got rid of writing the stack and frame ptr up here, because 98 //Old code jumped directly to this point, but doesn't work on x64
101 // only one 99 // So, just make this an endless loop, and do assembly function at end
102 // core can ever animate a given MasterVP, so don't need to communicate 100 // that saves its own return addr, then jumps to core_loop.
103 // new frame and stack ptr to the MasterVP storage before a second 101 while(1)
104 // version of that MasterVP can get animated on a different core. 102 {
105 //Also got rid of the busy-wait.
106
107
108 //masterLoopStartPt:
109 //The animating materVP suspends at end of this loop, then later resumes and
110 // comes back here
111 while(1){
112 103
113 //============================= MEASUREMENT STUFF ======================== 104 //============================= MEASUREMENT STUFF ========================
114 #ifdef MEAS__TIME_MASTER 105 #ifdef MEAS__TIME_MASTER
115 //Total Master time includes one coreloop time -- just assume the core 106 //Total Master time includes one coreloop time -- just assume the core
116 // loop time is same for Master as for AppVPs, even though it may be 107 // loop time is same for Master as is for AppVPs, even though it may be
117 // smaller due to higher predictability of the fixed jmp. 108 // smaller due to higher predictability of the fixed jmp.
118 saveLowTimeStampCountInto( masterPr->startMasterTSCLow ); 109 saveLowTimeStampCountInto( masterPr->startMasterTSCLow );
119 #endif 110 #endif
120 //======================================================================== 111 //========================================================================
121 112
122 masterEnv = (MasterEnv*)_VMSMasterEnv; 113 masterEnv = (MasterEnv*)_VMSMasterEnv;
123 114
124 //GCC may optimize so doesn't always re-define from frame-storage 115 //GCC may optimize so doesn't always re-define from frame-storage
125 masterPr = (VirtProcr*)volatileMasterPr; //on stack, to be sure after jmp 116 masterPr = (VirtProcr*)volatileMasterPr; //on stack, reload after jmp
126 thisCoresIdx = masterPr->coreAnimatedBy; 117 thisCoresIdx = masterPr->coreAnimatedBy;
127 readyToAnimateQ = masterEnv->readyToAnimateQs[thisCoresIdx]; 118 readyToAnimateQ = masterEnv->readyToAnimateQs[thisCoresIdx];
128 schedSlots = masterEnv->allSchedSlots[thisCoresIdx]; 119 schedSlots = masterEnv->allSchedSlots[thisCoresIdx];
129 120
130 requestHandler = masterEnv->requestHandler; 121 requestHandler = masterEnv->requestHandler;
131 slaveScheduler = masterEnv->slaveScheduler; 122 slaveScheduler = masterEnv->slaveScheduler;
132 semanticEnv = masterEnv->semanticEnv; 123 semanticEnv = masterEnv->semanticEnv;
133 124
134 //First, check for requests from other MasterVPs, and handle them 125 //First, check for requests from other MasterVPs, and handle them
135 if( masterEnv->requestsWaitingFor[thisCoresIdx] ) 126 if( currReq = masterEnv->interMasterRequestsFor[thisCoresIdx] )
136 { masterReqQ = masterEnv->masterReqQs[thisCoresIdx]; 127 { do
137 while( currReq = readVMSQ(masterReqQ) ) 128 { handleInterMasterReq( currReq, semanticEnv, masterPr );
138 { handleMasterReq( currReq, semanticEnv, masterPr ); 129 }
139 } 130 while( currReq = currReq->nextReqst );
140 } 131 }
141 //Now, take care of the SlaveVPs 132 //Now, take care of the SlaveVPs
142 //Go through the slots -- if Slave there newly suspended, handle its request 133 //Go through the slots -- if Slave there newly suspended, handle its request
143 // then, either way, ask assigner to fill each slot 134 // then, either way, ask assigner to fill each slot
144 numSlotsFilled = 0; 135 numSlotsFilled = 0;
145 for( slotIdx = 0; slotIdx < NUM_SCHED_SLOTS; slotIdx++) 136 for( slotIdx = 0; slotIdx < NUM_SCHED_SLOTS; slotIdx++)
146 { 137 {
147 currSlot = schedSlots[ slotIdx ]; 138 currSlot = schedSlots[ slotIdx ];
148 139
206 /*This is for inter-master communication. Either the master itself or 197 /*This is for inter-master communication. Either the master itself or
207 * the plugin sends one of these requests. Some are handled here, by the 198 * the plugin sends one of these requests. Some are handled here, by the
208 * master_loop, others are handed off to the plugin. 199 * master_loop, others are handed off to the plugin.
209 */ 200 */
210 void inline 201 void inline
211 handleMasterReq( MasterReq *currReq, void *_semEnv, VirtProcr *masterPr ) 202 handleInterMasterReq( InterMasterReqst *currReq, void *_semEnv,
212 { 203 VirtProcr *masterPr )
213 switch( currReq->reqType ) 204 { switch( currReq->reqType )
214 { case interVMSReq: 205 { case destVMSCore:
215 handleInterVMSReq( (InterVMSCoreReq *)currReq, masterPr); 206 handleInterVMSCoreReq( (InterVMSCoreReqst *)currReq, masterPr);
216 break; 207 break;
217 case interPluginReq: 208 case destPlugin:
218 (*interPluginReqHdlr)( (InterPluginReq *)currReq, _semEnv ); 209 (*interPluginReqHdlr)( ((InterPluginReqst *)currReq)->pluginReq,
210 _semEnv );
219 break; 211 break;
220 default: 212 default:
221 break; 213 break;
222 } 214 }
223 } 215 }
224 216
225 void inline 217 void inline
226 handleInterVMSReq( InterVMSCoreReq *currReq, VirtProcr *masterPr ) 218 handleInterVMSReq( InterVMSCoreReqst *currReq, VirtProcr *masterPr )
227 { 219 {
228 switch( currReq->reqType ) 220 switch( currReq->reqType )
229 { 221 {
230 case transfer_free: handleTransferFree( currReq, masterPr ); 222 case transfer_free_ptr: handleTransferFree( currReq, masterPr );
231 break; 223 break;
232 } 224 }
233 } 225 }
226
234 227
235 228
236 /*Work Stealing Alg -- racy one 229 /*Work Stealing Alg -- racy one
237 *This algorithm has a race condition -- the coreloops are accessing their 230 *This algorithm has a race condition -- the coreloops are accessing their
238 * own queues at the same time that this work-stealer on a different core 231 * own queues at the same time that this work-stealer on a different core