00001
00002 #include "pose.h"
00003
00005 void opt::Step()
00006 {
00007 Event *ev;
00008 POSE_TimeType lastGVT = localPVT->getGVT();
00009
00010 if (!parent->cancels.IsEmpty()) CancelUnexecutedEvents();
00011 if (eq->RBevent) Rollback();
00012 if (!parent->cancels.IsEmpty()) CancelEvents();
00013 parent->Status();
00014
00015
00016 ev = eq->currentPtr;
00017 if (ev->timestamp > POSE_UnsetTS) {
00018 idle = 0;
00019 currentEvent = ev;
00020 ev->done = 2;
00021 specEventCount++;
00022 eventCount++;
00023 stepCount++;
00024 parent->ResolveFn(ev->fnIdx, ev->msg);
00025 ev->done = 1;
00026 eq->mem_usage++;
00027 eq->ShiftEvent();
00028 if (eq->currentPtr->timestamp > POSE_UnsetTS) {
00029 prioMsg *pm = new prioMsg;
00030 pm->setPriority(eq->currentPtr->timestamp-POSE_TimeMax);
00031 POSE_Objects[parent->thisIndex].Step(pm);
00032 }
00033 #if !CMK_TRACE_DISABLED
00034 if(pose_config.stats)
00035 localStats->Loop();
00036 #endif
00037 }
00038 }
00039
00041 void opt::Rollback()
00042 {
00043 #if !CMK_TRACE_DISABLED
00044 double critStart;
00045 if(pose_config.trace)
00046 critStart = CmiWallTimer();
00047 #endif
00048 #if !CMK_TRACE_DISABLED
00049 if(pose_config.stats)
00050 localStats->SwitchTimer(RB_TIMER);
00051 #endif
00052 Event *ev = eq->currentPtr->prev, *recoveryPoint;
00053
00054 recoveryPoint = eq->RBevent;
00055
00056 while ((recoveryPoint != eq->back()) && (recoveryPoint->done == 0)
00057 && (recoveryPoint != eq->currentPtr))
00058 recoveryPoint = recoveryPoint->next;
00059 if (recoveryPoint == eq->currentPtr) {
00060 eq->SetCurrentPtr(eq->RBevent);
00061 eq->RBevent = NULL;
00062 #if !CMK_TRACE_DISABLED
00063 if(pose_config.stats)
00064 localStats->SwitchTimer(SIM_TIMER);
00065 #endif
00066 #if !CMK_TRACE_DISABLED
00067 if(pose_config.trace)
00068 traceUserBracketEvent(40, critStart, CmiWallTimer());
00069 #endif
00070 return;
00071 }
00072 CmiAssert(recoveryPoint != eq->back());
00073 CmiAssert(eq->RBevent->prev->next == eq->RBevent);
00074 CmiAssert(eq->RBevent->next->prev == eq->RBevent);
00075
00076 rbCount++;
00077 rbFlag = 1;
00078
00079 #if !CMK_TRACE_DISABLED
00080 if(pose_config.stats)
00081 localStats->Rollback();
00082 #endif
00083 while (ev != recoveryPoint) {
00084 UndoEvent(ev);
00085 ev = ev->prev;
00086 }
00087
00088
00089 if (userObj->usesAntimethods()) {
00090 targetEvent = recoveryPoint;
00091 UndoEvent(recoveryPoint);
00092 }
00093 else {
00094 #ifdef MEM_TEMPORAL
00095 if (!recoveryPoint->serialCPdata) {
00096 #else
00097 if (!recoveryPoint->cpData) {
00098 #endif
00099 UndoEvent(recoveryPoint);
00100 RecoverState(recoveryPoint);
00101 }
00102 else {
00103 targetEvent = recoveryPoint;
00104 UndoEvent(recoveryPoint);
00105 }
00106 }
00107
00108 eq->SetCurrentPtr(eq->RBevent);
00109 avgRBoffset =
00110 (avgRBoffset*(rbCount-1)+(eq->currentPtr->timestamp-localPVT->getGVT()))/rbCount;
00111 eq->FindLargest();
00112 eq->RBevent = targetEvent = NULL;
00113 #if !CMK_TRACE_DISABLED
00114 if(pose_config.stats)
00115 localStats->SwitchTimer(SIM_TIMER);
00116 #endif
00117 #if !CMK_TRACE_DISABLED
00118 if(pose_config.trace)
00119 traceUserBracketEvent(40, critStart, CmiWallTimer());
00120 #endif
00121 }
00122
00124 void opt::UndoEvent(Event *e)
00125 {
00126 if (e->done == 1) {
00127
00128 eq->eventCount++;
00129 currentEvent = e;
00130 CancelSpawn(e);
00131 #if !CMK_TRACE_DISABLED
00132 if(pose_config.stats)
00133 localStats->Undo();
00134 #endif
00135 parent->UNDOs++;
00136 localPVT->decEventCount();
00137 eventCount--;
00138
00139 parent->ResolveFn(((e->fnIdx) * -1), e->msg);
00140 parent->basicStats[1]++;
00141 if (e->commitBfrLen > 0) free(e->commitBfr);
00142 e->commitBfr = NULL;
00143 e->commitErr = 0;
00144 e->done = e->commitBfrLen = 0;
00145 #ifdef MEM_TEMPORAL
00146 if (e->serialCPdata) {
00147 userObj->localTimePool->tmp_free(e->timestamp, e->serialCPdata);
00148 e->serialCPdata = NULL;
00149 e->serialCPdataSz = 0;
00150 }
00151 #else
00152 delete e->cpData;
00153 e->cpData = NULL;
00154 #endif
00155 eq->mem_usage--;
00156 }
00157 }
00158
00160 void opt::CancelEvents()
00161 {
00162 #if !CMK_TRACE_DISABLED
00163 double critStart;
00164 if(pose_config.trace)
00165 critStart = CmiWallTimer();
00166 #endif
00167 #if !CMK_TRACE_DISABLED
00168 if(pose_config.stats)
00169 localStats->SwitchTimer(CAN_TIMER);
00170 #endif
00171 Event *ev, *tmp, *recoveryPoint;
00172 int found;
00173 CancelNode *it=NULL, *last=NULL;
00174
00175 last = parent->cancels.GetItem();
00176 while (!parent->cancels.IsEmpty()) {
00177 it = parent->cancels.GetItem();
00178 found = 0;
00179
00180
00181 while (!found) {
00182
00183 ev = eq->currentPtr;
00184 if (ev == eq->back()) ev = ev->prev;
00185 if (ev->timestamp <= it->timestamp) {
00186
00187 while (!found && (ev->timestamp > POSE_UnsetTS) &&
00188 (ev->timestamp <= it->timestamp)) {
00189 if (ev->evID == it->evID) found = 1;
00190 else ev = ev->next;
00191 }
00192 if (!found) {
00193 found = eq->eqh->DeleteEvent(it->evID, it->timestamp);
00194 if (found) ev = NULL;
00195 }
00196 }
00197 if (!found) {
00198 ev = eq->currentPtr;
00199 if (ev == eq->back()) ev = ev->prev;
00200 if (ev->timestamp >= it->timestamp) {
00201 while (!found && (ev->timestamp > POSE_UnsetTS) &&
00202 (ev->timestamp >= it->timestamp)) {
00203 if (ev->evID == it->evID) found = 1;
00204 else ev = ev->prev;
00205 }
00206 }
00207 }
00208 if (!found) {
00209 if (it == last) {
00210 #if !CMK_TRACE_DISABLED
00211 if(pose_config.stats)
00212 localStats->SwitchTimer(SIM_TIMER);
00213 #endif
00214 #if !CMK_TRACE_DISABLED
00215 if(pose_config.trace)
00216 traceUserBracketEvent(20, critStart, CmiWallTimer());
00217 #endif
00218 return;
00219 }
00220 it = parent->cancels.GetItem();
00221 }
00222 }
00223
00224
00225 if (ev && (ev->done == 0)) {
00226 if (ev == eq->currentPtr) eq->ShiftEvent();
00227
00228
00229 eq->DeleteEvent(ev);
00230 }
00231 else if (ev) {
00232 #if !CMK_TRACE_DISABLED
00233 if(pose_config.stats)
00234 localStats->SwitchTimer(RB_TIMER);
00235 #endif
00236 recoveryPoint = ev;
00237 tmp = eq->currentPtr->prev;
00238 #if !CMK_TRACE_DISABLED
00239 if(pose_config.stats)
00240 localStats->Rollback();
00241 #endif
00242 while (tmp != recoveryPoint) {
00243 UndoEvent(tmp);
00244 tmp = tmp->prev;
00245 }
00246 rbFlag = 1;
00247 if (userObj->usesAntimethods()) {
00248 targetEvent = recoveryPoint;
00249 UndoEvent(recoveryPoint);
00250 }
00251 else {
00252 #ifdef MEM_TEMPORAL
00253 if (!recoveryPoint->serialCPdata) {
00254 #else
00255 if (!recoveryPoint->cpData) {
00256 #endif
00257 UndoEvent(recoveryPoint);
00258 RecoverState(recoveryPoint);
00259 }
00260 else {
00261 targetEvent = recoveryPoint;
00262 UndoEvent(recoveryPoint);
00263 }
00264 }
00265 eq->SetCurrentPtr(recoveryPoint->next);
00266
00267
00268 eq->DeleteEvent(recoveryPoint);
00269 targetEvent = NULL;
00270
00271 while ((eq->currentPtr->prev->timestamp > POSE_UnsetTS)
00272 && (eq->currentPtr->prev->done == 0))
00273 eq->currentPtr = eq->currentPtr->prev;
00274 #if !CMK_TRACE_DISABLED
00275 if(pose_config.stats)
00276 localStats->SwitchTimer(CAN_TIMER);
00277 #endif
00278 }
00279 if (it == last) {
00280 parent->cancels.RemoveItem(it);
00281 #if !CMK_TRACE_DISABLED
00282 if(pose_config.stats)
00283 localStats->SwitchTimer(SIM_TIMER);
00284 #endif
00285 #if !CMK_TRACE_DISABLED
00286 if(pose_config.trace)
00287 traceUserBracketEvent(20, critStart, CmiWallTimer());
00288 #endif
00289 return;
00290 }
00291 else parent->cancels.RemoveItem(it);
00292 }
00293 #if !CMK_TRACE_DISABLED
00294 if(pose_config.stats)
00295 localStats->SwitchTimer(SIM_TIMER);
00296 #endif
00297 #if !CMK_TRACE_DISABLED
00298 if(pose_config.trace)
00299 traceUserBracketEvent(20, critStart, CmiWallTimer());
00300 #endif
00301 }
00302
00304 void opt::CancelUnexecutedEvents()
00305 {
00306 #if !CMK_TRACE_DISABLED
00307 double critStart;
00308 if(pose_config.trace)
00309 critStart = CmiWallTimer();
00310 #endif
00311 #if !CMK_TRACE_DISABLED
00312 if(pose_config.stats)
00313 localStats->SwitchTimer(CAN_TIMER);
00314 #endif
00315 Event *ev, *tmp, *recoveryPoint;
00316 int found;
00317 CancelNode *it=NULL, *last=NULL;
00318
00319 last = parent->cancels.GetItem();
00320 while (!parent->cancels.IsEmpty()) {
00321 it = parent->cancels.GetItem();
00322 found = 0;
00323
00324
00325 while (!found) {
00326 ev = eq->currentPtr;
00327 if (ev == eq->back()) ev = ev->prev;
00328 if (ev->timestamp <= it->timestamp) {
00329
00330 while (!found && (ev->timestamp > POSE_UnsetTS) &&
00331 (ev->timestamp <= it->timestamp)) {
00332 if (ev->evID == it->evID) found = 1;
00333 else ev = ev->next;
00334 }
00335 if (!found) {
00336 found = eq->eqh->DeleteEvent(it->evID, it->timestamp);
00337 if (found) ev = NULL;
00338 }
00339 }
00340 if (!found) {
00341 ev = eq->currentPtr;
00342 if (ev == eq->back()) ev = ev->prev;
00343 if (ev->timestamp >= it->timestamp) {
00344 while (!found && (ev->timestamp > POSE_UnsetTS) &&
00345 (ev->timestamp >= it->timestamp)) {
00346 if (ev->evID == it->evID) found = 1;
00347 else ev = ev->prev;
00348 }
00349 }
00350 }
00351 if (!found) {
00352 if (it == last) {
00353 #if !CMK_TRACE_DISABLED
00354 if(pose_config.stats)
00355 localStats->SwitchTimer(SIM_TIMER);
00356 #endif
00357 #if !CMK_TRACE_DISABLED
00358 if(pose_config.trace)
00359 traceUserBracketEvent(20, critStart, CmiWallTimer());
00360 #endif
00361 return;
00362 }
00363 it = parent->cancels.GetItem();
00364 }
00365 }
00366
00367 if (ev && (ev->done == 0)) {
00368 if (ev == eq->currentPtr) eq->ShiftEvent();
00369 eq->DeleteEvent(ev);
00370 if (it == last) {
00371 parent->cancels.RemoveItem(it);
00372 #if !CMK_TRACE_DISABLED
00373 if(pose_config.stats)
00374 localStats->SwitchTimer(SIM_TIMER);
00375 #endif
00376 #if !CMK_TRACE_DISABLED
00377 if(pose_config.trace)
00378 traceUserBracketEvent(20, critStart, CmiWallTimer());
00379 #endif
00380 return;
00381 }
00382 else parent->cancels.RemoveItem(it);
00383 }
00384 else if (ev && (ev->done == 1)) {
00385 if (it == last) {
00386 #if !CMK_TRACE_DISABLED
00387 if(pose_config.stats)
00388 localStats->SwitchTimer(SIM_TIMER);
00389 #endif
00390 #if !CMK_TRACE_DISABLED
00391 if(pose_config.trace)
00392 traceUserBracketEvent(20, critStart, CmiWallTimer());
00393 #endif
00394 return;
00395 }
00396 }
00397 else if (!ev) {
00398 if (it == last) {
00399 parent->cancels.RemoveItem(it);
00400 #if !CMK_TRACE_DISABLED
00401 if(pose_config.stats)
00402 localStats->SwitchTimer(SIM_TIMER);
00403 #endif
00404 #if !CMK_TRACE_DISABLED
00405 if(pose_config.trace)
00406 traceUserBracketEvent(20, critStart, CmiWallTimer());
00407 #endif
00408 return;
00409 }
00410 else parent->cancels.RemoveItem(it);
00411 }
00412 }
00413 #if !CMK_TRACE_DISABLED
00414 if(pose_config.stats)
00415 localStats->SwitchTimer(SIM_TIMER);
00416 #endif
00417 #if !CMK_TRACE_DISABLED
00418 if(pose_config.trace)
00419 traceUserBracketEvent(20, critStart, CmiWallTimer());
00420 #endif
00421 }
00422
00424 void opt::RecoverState(Event *recoveryPoint)
00425 {
00426 Event *ev;
00427 #ifdef MEM_TEMPORAL
00428 CmiAssert(!recoveryPoint->serialCPdata);
00429 #else
00430 CmiAssert(!recoveryPoint->cpData);
00431 #endif
00432 CpvAccess(stateRecovery) = 1;
00433 ev = recoveryPoint->prev;
00434 #ifdef MEM_TEMPORAL
00435 while ((ev != eq->front()) && (!ev->serialCPdata)) {
00436 #else
00437 while ((ev != eq->front()) && (!ev->cpData)) {
00438 #endif
00439 if (ev->commitBfrLen > 0)
00440 free(ev->commitBfr);
00441 ev->commitBfr = NULL;
00442 ev->commitBfrLen = 0;
00443 ev = ev->prev;
00444 }
00445 CmiAssert(ev != eq->front());
00446
00447
00448 currentEvent = targetEvent = ev;
00449 parent->ResolveFn(((ev->fnIdx) * -1), ev->msg);
00450 parent->basicStats[1]++;
00451 if (ev->commitBfrLen > 0)
00452 free(ev->commitBfr);
00453 ev->commitBfr = NULL;
00454 ev->commitBfrLen = 0;
00455 #ifdef MEM_TEMPORAL
00456 if (ev->serialCPdata) {
00457 userObj->localTimePool->tmp_free(ev->timestamp, ev->serialCPdata);
00458 ev->serialCPdata = NULL;
00459 ev->serialCPdataSz = 0;
00460 }
00461 #else
00462 delete ev->cpData;
00463 ev->cpData = NULL;
00464 #endif
00465 targetEvent = NULL;
00466
00467
00468 while (ev != recoveryPoint) {
00469 if (ev->done == 1) {
00470 currentEvent = ev;
00471 parent->ResolveFn(ev->fnIdx, ev->msg);
00472 }
00473 ev = ev->next;
00474 }
00475 CpvAccess(stateRecovery) = 0;
00476 }