|
libFAUDES
Sections
Index
|
cfl_generator.cppGo to the documentation of this file.00001 /** @file cfl_generator.cpp Class vGenerator */ 00002 00003 /* FAU Discrete Event Systems Library (libfaudes) 00004 00005 Copyright (C) 2006 Bernd Opitz 00006 Copyright (C) 2007 Thomas Moor 00007 Exclusive copyright is granted to Klaus Schmidt 00008 00009 This library is free software; you can redistribute it and/or 00010 modify it under the terms of the GNU Lesser General Public 00011 License as published by the Free Software Foundation; either 00012 version 2.1 of the License, or (at your option) any later version. 00013 00014 This library is distributed in the hope that it will be useful, 00015 but WITHOUT ANY WARRANTY; without even the implied warranty of 00016 MERCHANTABILITY or FITNES FOR A PARTICULAR PURPOSE. See the GNU 00017 Lesser General Public License for more details. 00018 00019 You should have received a copy of the GNU Lesser General Public 00020 License along with this library; if not, write to the Free Software 00021 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ 00022 00023 00024 #include "cfl_generator.h" 00025 00026 00027 namespace faudes { 00028 00029 // msObjectCount (static) 00030 Idx vGenerator::msObjectCount = 0; 00031 00032 // msObjectCount (static) 00033 bool vGenerator::msStateNamesEnabledDefault = true; 00034 00035 // default prototypes (static) 00036 const EventSet vGenerator::msAlphabetVoid; 00037 const StateSet vGenerator::msStatesVoid; 00038 const TransSet vGenerator::msTransRelVoid; 00039 const AttributeVoid vGenerator::msGlobalVoid; 00040 00041 00042 // constructor 00043 vGenerator::vGenerator(void) : 00044 // my name 00045 mMyName("Generator"), 00046 // have std symboltables 00047 mpStateSymbolTable(&mStateSymbolTable), 00048 mpEventSymbolTable(GlobalEventSymbolTablep()), 00049 // other members 00050 mStateNamesEnabled(msStateNamesEnabledDefault), 00051 // initialise heap members 00052 mpAlphabet(0), 00053 mpStates(0), 00054 mpTransRel(0), 00055 mpGlobalAttribute(0), 00056 // initialise prototypes 00057 pAlphabetPrototype(&msAlphabetVoid), 00058 pStatesPrototype(&msStatesVoid), 00059 pTransRelPrototype(&msTransRelVoid), 00060 pGlobalPrototype(&msGlobalVoid) 00061 { 00062 FAUDES_OBJCOUNT_INC("Generator"); 00063 FD_DG("vGenerator(" << this << ")::vGenerator()"); 00064 // track generator objects 00065 msObjectCount++; 00066 mId = msObjectCount; 00067 // allocate core members 00068 NewCore(); 00069 // fix std names 00070 mInitStates.Name("InitStates"); 00071 mMarkedStates.Name("MarkedStates"); 00072 } 00073 00074 // copy constructor 00075 vGenerator::vGenerator(const vGenerator& rOtherGen) : 00076 // my name 00077 mMyName("Generator"), 00078 // have std symboltables 00079 mpStateSymbolTable(&mStateSymbolTable), 00080 mpEventSymbolTable(GlobalEventSymbolTablep()), 00081 // other members 00082 mStateNamesEnabled(msStateNamesEnabledDefault), 00083 // initialise heap members 00084 mpAlphabet(0), 00085 mpStates(0), 00086 mpTransRel(0), 00087 mpGlobalAttribute(0), 00088 // initialise prototypes 00089 pAlphabetPrototype(&msAlphabetVoid), 00090 pStatesPrototype(&msStatesVoid), 00091 pTransRelPrototype(&msTransRelVoid), 00092 pGlobalPrototype(&msGlobalVoid) 00093 { 00094 FAUDES_OBJCOUNT_INC("Generator"); 00095 FD_DG("vGenerator(" << this << ")::vGenerator(" << &rOtherGen << ")"); 00096 // track generator objects 00097 msObjectCount++; 00098 mId = msObjectCount; 00099 // allocate core members 00100 NewCore(); 00101 // perform copy 00102 Assign(rOtherGen); 00103 } 00104 00105 // construct from file 00106 vGenerator::vGenerator(const std::string& rFileName) : 00107 // my name 00108 mMyName("Generator"), 00109 // have std symboltables 00110 mpStateSymbolTable(&mStateSymbolTable), 00111 mpEventSymbolTable(GlobalEventSymbolTablep()), 00112 // other members 00113 mStateNamesEnabled(msStateNamesEnabledDefault), 00114 // initialise heap members 00115 mpAlphabet(0), 00116 mpStates(0), 00117 mpTransRel(0), 00118 mpGlobalAttribute(0), 00119 // initialise prototypes 00120 pAlphabetPrototype(&msAlphabetVoid), 00121 pStatesPrototype(&msStatesVoid), 00122 pTransRelPrototype(&msTransRelVoid), 00123 pGlobalPrototype(&msGlobalVoid) 00124 { 00125 FAUDES_OBJCOUNT_INC("Generator"); 00126 FD_DG("vGenerator(" << this << ")::vGenerator(" << rFileName << ")"); 00127 // track generator objects 00128 msObjectCount++; 00129 mId = msObjectCount; 00130 // allocate core members 00131 NewCore(); 00132 // fix std names 00133 mInitStates.Name("InitStates"); 00134 mMarkedStates.Name("MarkedStates"); 00135 // set defaults for file io 00136 mStateNamesEnabled=true; 00137 // do read 00138 Read(rFileName); 00139 // restore defaults 00140 mStateNamesEnabled=msStateNamesEnabledDefault; 00141 } 00142 00143 // construct on heap 00144 vGenerator* vGenerator::New(void) const { 00145 FD_DG("vGenerator(" << this << ")::New()"); 00146 // allocate 00147 vGenerator* res = new vGenerator(); 00148 // fix configuration 00149 res->EventSymbolTablep(mpEventSymbolTable); 00150 res->mStateNamesEnabled=mStateNamesEnabled; 00151 return res; 00152 } 00153 00154 // construct on heap 00155 vGenerator* vGenerator::Copy(void) const { 00156 FD_DG("vGenerator(" << this << ")::Copy()"); 00157 // copy construct 00158 vGenerator* res = new vGenerator(*this); 00159 return res; 00160 } 00161 00162 // destruct 00163 vGenerator::~vGenerator(void) { 00164 FAUDES_OBJCOUNT_DEC("Generator"); 00165 // free my members 00166 DeleteCore(); 00167 } 00168 00169 // configure attribute types 00170 void vGenerator::ConfigureAttributeTypes(const AttributeVoid* pNewGlobalPrototype, 00171 const StateSet* pNewStatesPrototype, const EventSet* pNewAlphabetPrototype, 00172 const TransSet* pNewTransRelPrototype) { 00173 FD_DG("vGenerator(" << this << ")::ConfigureAtributes(..)"); 00174 pGlobalPrototype= pNewGlobalPrototype; 00175 pStatesPrototype= pNewStatesPrototype; 00176 pAlphabetPrototype= pNewAlphabetPrototype; 00177 pTransRelPrototype= pNewTransRelPrototype; 00178 FD_DG("vGenerator(" << this << ")::ConfigureAtributes(): done"); 00179 } 00180 00181 // indicate new core 00182 void vGenerator::UpdateCore(void) { 00183 // fix std names 00184 if(mpAlphabet) mpAlphabet->Name("Alphabet"); 00185 if(mpStates) mpStates->Name("States"); 00186 if(mpTransRel) mpTransRel->Name("TransRel"); 00187 // fix symbol table 00188 if(mpAlphabet) EventSymbolTablep(mpEventSymbolTable); 00189 } 00190 00191 // protected helper: allocate core on heap 00192 void vGenerator::NewCore(void) { 00193 FD_DG("vGenerator(" << this << ")::NewCore()"); 00194 DeleteCore(); 00195 // allocate (use prototypes, fallback to void attributes) 00196 if(pAlphabetPrototype) mpAlphabet= pAlphabetPrototype->New(); 00197 else mpAlphabet = new EventSet(); 00198 if(pStatesPrototype) mpStates=pStatesPrototype->New(); 00199 else mpStates = new StateSet(); 00200 if(pTransRelPrototype) mpTransRel= pTransRelPrototype->New(); 00201 else mpTransRel = new TransSet(); 00202 if(pGlobalPrototype) mpGlobalAttribute=pGlobalPrototype->New(); 00203 else mpGlobalAttribute = new AttributeVoid(); 00204 // update callback 00205 UpdateCore(); 00206 } 00207 00208 // protected helper: free core from heap 00209 void vGenerator::DeleteCore(void) { 00210 if(mpAlphabet) delete mpAlphabet; 00211 if(mpStates) delete mpStates; 00212 if(mpTransRel) delete mpTransRel; 00213 if(mpGlobalAttribute) delete mpGlobalAttribute; 00214 mpAlphabet=0; 00215 mpStates=0; 00216 mpTransRel=0; 00217 mpGlobalAttribute=0; 00218 // update callback 00219 UpdateCore(); 00220 } 00221 00222 00223 00224 // copy from other vGenerator (try to convert attributes) 00225 vGenerator& vGenerator::Assign(const vGenerator& rGen) { 00226 FD_DG("vGenerator(" << this << ")::Assign(" << &rGen << ")"); 00227 // prepare result (call clear for virtual stuff) 00228 Clear(); 00229 // have same event symboltable 00230 EventSymbolTablep(rGen.mpEventSymbolTable); 00231 // copy state symboltable 00232 StateSymbolTable(rGen.mStateSymbolTable); 00233 // set other members 00234 Name(rGen.Name()); 00235 StateNamesEnabled(rGen.StateNamesEnabled()); 00236 InjectInitStates(rGen.mInitStates); 00237 InjectMarkedStates(rGen.mMarkedStates); 00238 // core members, try attributes 00239 InjectStates(*rGen.mpStates); 00240 InjectAlphabet(*rGen.mpAlphabet); 00241 InjectTransRel(*rGen.mpTransRel); 00242 GlobalAttributeTry(*rGen.mpGlobalAttribute); 00243 #ifdef FAUDES_DEBUG_CODE 00244 if(!Valid()) { 00245 FD_DG("vGenerator()::Copy(): invalid generator"); 00246 DWrite(); 00247 abort(); 00248 } 00249 #endif 00250 return *this; 00251 } 00252 00253 // copy from other vGenerator (try to convert attributes) 00254 vGenerator& vGenerator::Assign(const Type& rSrc) { 00255 FD_DG("vGenerator(" << this << ")::Assign([type] " << &rSrc << ")"); 00256 Clear(); 00257 const vGenerator* vgen=dynamic_cast<const vGenerator*>(&rSrc); 00258 if(vgen) Assign(*vgen); 00259 return *this; 00260 } 00261 00262 // copy from other vGenerator (clear attributes) 00263 vGenerator& vGenerator::AssignWithoutAttributes(const vGenerator& rGen) { 00264 FD_DG("vGenerator(" << this << ")::Assign(" << &rGen << ")"); 00265 // prepare result (call clear for virtual stuff) 00266 Clear(); 00267 // have same event symboltable 00268 EventSymbolTablep(rGen.mpEventSymbolTable); 00269 // copy state symboltable 00270 StateSymbolTable(rGen.mStateSymbolTable); 00271 // set other members 00272 Name(rGen.Name()); 00273 StateNamesEnabled(rGen.StateNamesEnabled()); 00274 InjectInitStates(rGen.mInitStates); 00275 InjectMarkedStates(rGen.mMarkedStates); 00276 // core members, ignore attributes 00277 mpStates->AssignWithoutAttributes(rGen.States()); 00278 mpAlphabet->AssignWithoutAttributes(rGen.Alphabet()); 00279 mpTransRel->AssignWithoutAttributes(rGen.TransRel()); 00280 #ifdef FAUDES_DEBUG_CODE 00281 if(!Valid()) { 00282 FD_DG("vGenerator()::Copy(): invalid generator"); 00283 DWrite(); 00284 abort(); 00285 } 00286 #endif 00287 return *this; 00288 } 00289 00290 00291 // Move(gen) destructive copy 00292 void vGenerator::Move(vGenerator& rGen) { 00293 FD_DG("vGenerator(" << this << ")::Move(" << &rGen << ")"); 00294 // test types 00295 bool tmm=false; 00296 if(typeid(rGen.Alphabet())!=typeid(Alphabet())) tmm=true; 00297 if(typeid(rGen.States())!=typeid(States())) tmm=true; 00298 if(typeid(rGen.TransRel())!=typeid(TransRel())) tmm=true; 00299 if(typeid(rGen.GlobalAttribute())!=typeid(GlobalAttribute())) tmm=true; 00300 if(tmm) { 00301 FD_DG("vGenerator(" << this << ")::Move(" << &rGen << "): using std copy"); 00302 rGen.Assign(*this); 00303 Clear(); 00304 return; 00305 } 00306 // prepare result (call clear for virtual stuff) 00307 rGen.Clear(); 00308 // have same event symboltable 00309 rGen.EventSymbolTablep(mpEventSymbolTable); 00310 // copy state symboltable (todo: make this pointer based?) 00311 rGen.StateSymbolTable(mStateSymbolTable); 00312 // copy members 00313 rGen.Name(Name()); 00314 rGen.StateNamesEnabled(StateNamesEnabled()); 00315 rGen.InjectInitStates(InitStates()); 00316 rGen.InjectMarkedStates(MarkedStates()); 00317 // delete destination core 00318 if(rGen.mpStates) delete rGen.mpStates; 00319 if(rGen.mpAlphabet) delete rGen.mpAlphabet; 00320 if(rGen.mpTransRel) delete rGen.mpTransRel; 00321 if(rGen.mpGlobalAttribute) delete rGen.mpGlobalAttribute; 00322 // move and invalidate core members 00323 rGen.mpStates=mpStates; 00324 rGen.mpAlphabet=mpAlphabet; 00325 rGen.mpTransRel=mpTransRel; 00326 rGen.mpGlobalAttribute=mpGlobalAttribute; 00327 mpStates=0; 00328 mpAlphabet=0; 00329 mpTransRel=0; 00330 mpGlobalAttribute=0; 00331 // register core update 00332 rGen.UpdateCore(); 00333 // install new empty core members 00334 NewCore(); 00335 // clear myself (incl derived classes members) 00336 Clear(); 00337 } 00338 00339 // operator = 00340 vGenerator& vGenerator::operator = (const vGenerator& rOtherGen) { 00341 FD_DG("vGenerator(" << this << ")::operator = " << &rOtherGen); 00342 return Assign(rOtherGen); 00343 } 00344 00345 // Version(idx) 00346 void vGenerator::Version(Idx version, vGenerator& rResGen) const { 00347 FD_DG("vGenerator(" << this << ")::Version(" << version << ")"); 00348 std::ostringstream o; 00349 o << version; 00350 Version(o.str(),rResGen); 00351 } 00352 00353 // Version(string) 00354 void vGenerator::Version(const std::string& rVersion, vGenerator& rResGen) const { 00355 FD_DG("vGenerator(" << this << ")::Version(" << rVersion << ")"); 00356 // second arg must not be us 00357 if(this==&rResGen) { 00358 std::stringstream errstr; 00359 errstr << "Destination must not match source."; 00360 throw Exception("vGenerator::Version(string)", errstr.str(), 96); 00361 } 00362 // prepare Empty generator 00363 rResGen.Clear(); 00364 rResGen.GlobalAttribute(GlobalAttribute()); 00365 EventSet::Iterator eit; 00366 StateSet::Iterator lit; 00367 TransSet::Iterator tit; 00368 std::map<Idx,Idx> eventoldnewmap; 00369 rResGen.Name(Name()+"_"+rVersion); 00370 // create versioned mAlphabet 00371 for (eit = AlphabetBegin(); eit != AlphabetEnd(); ++eit) { 00372 Idx newevent= rResGen.InsEvent(EventName(*eit)+"_"+rVersion); 00373 eventoldnewmap[*eit] = newevent; 00374 rResGen.EventAttribute(newevent,EventAttribute(*eit)); 00375 } 00376 // create new stateset 00377 for (lit = StatesBegin(); lit != StatesEnd(); ++lit) { 00378 rResGen.InsState(*lit); 00379 rResGen.StateAttribute(*lit,StateAttribute(*lit)); //would be faster if directly copied ? 00380 if (StateName(*lit) != "") rResGen.StateName(*lit,StateName(*lit)); 00381 } 00382 // created versioned transrel 00383 for (tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 00384 Transition trans=Transition(tit->X1, eventoldnewmap[tit->Ev], tit->X2); 00385 rResGen.SetTransition(trans); 00386 rResGen.TransAttribute(trans, TransAttribute(*tit)); 00387 } 00388 // set i/m states 00389 rResGen.mInitStates=mInitStates; 00390 rResGen.mMarkedStates=mMarkedStates; 00391 // behavioural flags 00392 rResGen.mStateNamesEnabled = mStateNamesEnabled; 00393 } 00394 00395 00396 // Version(string,string) 00397 void vGenerator::Version(const std::string& rPattern, const std::string& rReplacement, vGenerator& rResGen) const { 00398 FD_DG("vGenerator(" << this << ")::Version(" << rPattern << ", " << rReplacement << ", ...)"); 00399 // second arg must not be us 00400 if(this==&rResGen) { 00401 std::stringstream errstr; 00402 errstr << "Destination must not match source."; 00403 throw Exception("vGenerator::Version(string,string)", errstr.str(), 96); 00404 } 00405 // ignore invalid pattern 00406 if(rPattern.empty()) { 00407 rResGen.Assign(*this); 00408 return; 00409 } 00410 // trivial case 00411 if (rPattern==rReplacement) { 00412 rResGen.Assign(*this); 00413 return; 00414 } 00415 // prepare Empty generator 00416 rResGen.Clear(); 00417 rResGen.GlobalAttribute(GlobalAttribute()); 00418 rResGen.Name(Name()+"_"+rReplacement); 00419 EventSet::Iterator eit; 00420 StateSet::Iterator lit; 00421 TransSet::Iterator tit; 00422 std::map<Idx,Idx> eventoldnewmap; 00423 // create versioned mAlphabet 00424 std::string newstring; 00425 std::string::size_type pos = 0; 00426 int patternlength=rPattern.size(); 00427 int replacementlength=rReplacement.size(); 00428 for (eit = AlphabetBegin(); eit != AlphabetEnd(); ++eit) { 00429 // search for all pattern occurences in event name and replace 00430 newstring=EventName(*eit); 00431 while ( (pos = newstring.find(rPattern, pos)) != std::string::npos ) { 00432 newstring.replace(pos, patternlength, rReplacement); 00433 //pos++; 00434 pos=pos+replacementlength; 00435 } 00436 Idx newevent= rResGen.InsEvent(newstring); 00437 eventoldnewmap[*eit] = newevent; 00438 rResGen.EventAttribute(newevent,EventAttribute(*eit)); 00439 } 00440 // create new stateset 00441 for (lit = StatesBegin(); lit != StatesEnd(); ++lit) { 00442 rResGen.InsState(*lit); 00443 rResGen.StateAttribute(*lit,StateAttribute(*lit)); //would be faster if directly copied ? 00444 if (StateName(*lit) != "") rResGen.StateName(*lit,StateName(*lit)); 00445 } 00446 // created versioned transrel 00447 for (tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 00448 Transition trans=Transition(tit->X1, eventoldnewmap[tit->Ev], tit->X2); 00449 rResGen.SetTransition(trans); 00450 rResGen.TransAttribute(trans, TransAttribute(*tit)); 00451 } 00452 // set i/m states 00453 rResGen.mInitStates=mInitStates; 00454 rResGen.mMarkedStates=mMarkedStates; 00455 // behavioural flags 00456 rResGen.mStateNamesEnabled = mStateNamesEnabled; 00457 } 00458 00459 00460 // Name(rName) 00461 void vGenerator::Name(const std::string& rName) { 00462 FD_DV("vGenerator(" << this << ")::Name(\"" << rName << "\")"); 00463 mMyName = rName; 00464 } 00465 00466 // Name() 00467 const std::string& vGenerator::Name(void) const { 00468 return mMyName; 00469 } 00470 00471 // Valid() 00472 bool vGenerator::Valid(void) { 00473 FD_DG("vGenerator(" << this << ")::Valid()"); 00474 // core members on heap 00475 if(mpAlphabet==0) return false; 00476 if(mpStates==0) return false; 00477 if(mpTransRel==0) return false; 00478 if(mpGlobalAttribute==0) return false; 00479 // transitions to be known 00480 TransSet::Iterator tit; 00481 StateSet::Iterator lit; 00482 for(tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 00483 if(! ExistsState(tit->X1)) return false; 00484 if(! ExistsEvent(tit->Ev)) return false; 00485 if(! ExistsState(tit->X2)) return false; 00486 } 00487 // init states to be known 00488 for(lit = InitStatesBegin(); lit != InitStatesEnd(); ++lit) 00489 if(! ExistsState(static_cast<Idx>(*lit))) return false; 00490 for(lit = MarkedStatesBegin(); lit != MarkedStatesEnd(); ++lit) 00491 if(! ExistsState(static_cast<Idx>(*lit))) return false; 00492 // sets to have proper names 00493 if(mpAlphabet->Name() != "Alphabet") return false; 00494 if(mpStates->Name() != "States") return false; 00495 if(mInitStates.Name() != "InitStates") return false; 00496 if(mMarkedStates.Name() != "MarkedStates") return false; 00497 // event symbol table 00498 NameSet::Iterator eit; 00499 for(eit = AlphabetBegin(); eit != AlphabetEnd(); eit ++) { 00500 if(EventName(*eit)=="") return false; 00501 } 00502 // done 00503 return true; 00504 } 00505 00506 // AlphabetSize() 00507 Idx vGenerator::AlphabetSize(void) const { 00508 return mpAlphabet->Size(); 00509 } 00510 00511 // Size() 00512 Idx vGenerator::Size(void) const { 00513 return mpStates->Size(); 00514 } 00515 00516 // Clear() 00517 void vGenerator::Clear(void) { 00518 FD_DG("vGenerator(" << this << ")::Clear()"); 00519 mpAlphabet->Clear(); 00520 mpStates->Clear(); 00521 mpStateSymbolTable->Clear(); 00522 mpTransRel->Clear(); 00523 mInitStates.Clear(); 00524 mMarkedStates.Clear(); 00525 ClearGlobalAttribute(); 00526 } 00527 00528 // ClearGlobalAttribute() 00529 void vGenerator::ClearGlobalAttribute(void) { 00530 mpGlobalAttribute->Clear(); 00531 } 00532 00533 // ClearStateAttributes() 00534 void vGenerator::ClearStateAttributes(void) { 00535 mpStates->ClearAttributes(); 00536 } 00537 00538 // ClearEventAttributes() 00539 void vGenerator::ClearEventAttributes(void) { 00540 mpAlphabet->ClearAttributes(); 00541 } 00542 00543 // ClearTransAttributes() 00544 void vGenerator::ClearTransAttributes(void) { 00545 mpTransRel->ClearAttributes(); 00546 } 00547 00548 // ClearAttributes() 00549 void vGenerator::ClearAttributes(void) { 00550 ClearGlobalAttribute(); 00551 ClearStateAttributes(); 00552 ClearEventAttributes(); 00553 ClearTransAttributes(); 00554 } 00555 00556 00557 // ClearStates() 00558 void vGenerator::ClearStates(void) { 00559 mpStates->Clear(); 00560 mpTransRel->Clear(); 00561 mInitStates.Clear(); 00562 mMarkedStates.Clear(); 00563 mpStateSymbolTable->Clear(); 00564 } 00565 00566 // TransRelSize() 00567 Idx vGenerator::TransRelSize(void) const { 00568 return mpTransRel->Size(); 00569 } 00570 00571 // InitStatesSize() 00572 Idx vGenerator::InitStatesSize(void) const { 00573 return mInitStates.Size(); 00574 } 00575 00576 // MarkedStatesSize() 00577 Idx vGenerator::MarkedStatesSize(void) const { 00578 return mMarkedStates.Size(); 00579 } 00580 00581 // AlphabetEmpty() 00582 bool vGenerator::AlphabetEmpty(void) const { 00583 return mpAlphabet->Empty(); 00584 } 00585 00586 // Empty() 00587 bool vGenerator::Empty(void) const { 00588 return mpStates->Empty(); 00589 } 00590 00591 // TransRelEmpty() 00592 bool vGenerator::TransRelEmpty(void) const { 00593 return mpTransRel->Empty(); 00594 } 00595 00596 // InitStatesEmpty() 00597 bool vGenerator::InitStatesEmpty(void) const { 00598 return mInitStates.Empty(); 00599 } 00600 00601 // MarkedStatesEmpty() 00602 bool vGenerator::MarkedStatesEmpty(void) const { 00603 return mMarkedStates.Empty(); 00604 } 00605 00606 00607 // ClearMinStateIndexMap() 00608 void vGenerator::ClearMinStateIndexMap(void) const { 00609 FD_DG("vGenerator::ClearMinStateIndexMap()"); 00610 // fake const 00611 vGenerator* fakeconst = const_cast<vGenerator*>(this); 00612 fakeconst->mMinStateIndexMap.clear(); 00613 } 00614 00615 // MinStateIndex(index) 00616 Idx vGenerator::MinStateIndex(Idx index) const { 00617 std::map<Idx,Idx>::const_iterator minit; 00618 minit = mMinStateIndexMap.find(index); 00619 Idx fidx; 00620 if(minit != mMinStateIndexMap.end()) { 00621 fidx= minit->second; 00622 } else { 00623 fidx=index; 00624 } 00625 return fidx; 00626 } 00627 00628 // MinStateIndex() 00629 const std::map<Idx,Idx>& vGenerator::MinStateIndexMap(void) const { 00630 return mMinStateIndexMap; 00631 } 00632 00633 00634 // SetMinStateIndexMap() 00635 void vGenerator::SetMinStateIndexMap(void) const { 00636 FD_DG("vGenerator::SetMinStateIndexMap()"); 00637 // fake const 00638 vGenerator* fakeconst = const_cast<vGenerator*>(this); 00639 // clear map 00640 fakeconst->ClearMinStateIndexMap(); 00641 StateSet::Iterator it; 00642 Idx minindex = 0; 00643 // if generator states get names 00644 if(StateNamesEnabled()) { 00645 // named initial states first 00646 for(it = InitStatesBegin(); it != InitStatesEnd(); ++it) { 00647 if(StateName(static_cast<Idx>(*it)) != "") { 00648 fakeconst->mMinStateIndexMap[*it] = ++minindex; 00649 } 00650 } 00651 // then all other named states 00652 for(it = StatesBegin(); it != StatesEnd(); ++it) { 00653 if(mMinStateIndexMap.count(*it) == 0) { 00654 if(StateName(static_cast<Idx>(*it)) != "") { 00655 fakeconst->mMinStateIndexMap[*it] = ++minindex; 00656 } 00657 } 00658 } 00659 // at last all anonymous states 00660 for(it = StatesBegin(); it != StatesEnd(); ++it) { 00661 if(mMinStateIndexMap.count(*it) == 0) { 00662 fakeconst->mMinStateIndexMap[*it] = ++minindex; 00663 } 00664 } 00665 } 00666 // if generator states are all anonymous 00667 else { 00668 // all initial states first 00669 for(it = InitStatesBegin(); it != InitStatesEnd(); ++it) { 00670 fakeconst->mMinStateIndexMap[*it] = ++minindex; 00671 } 00672 // then the rest 00673 for(it = StatesBegin(); it != StatesEnd(); ++it) { 00674 if(mMinStateIndexMap.count(*it) == 0) { 00675 fakeconst->mMinStateIndexMap[*it] = ++minindex; 00676 } 00677 } 00678 } 00679 #ifdef FAUDES_DEBUG_CONTAINER 00680 std::map<Idx,Idx>::const_iterator _it; 00681 for(_it = mMinStateIndexMap.begin(); _it != mMinStateIndexMap.end(); ++_it) { 00682 FD_DC("vGenerator::MinStateIndexMap: " << _it->first 00683 << " <-- " << SStr(_it->second)); 00684 } 00685 #endif 00686 } 00687 00688 // EventSymbolTablep() const 00689 SymbolTable* vGenerator::EventSymbolTablep(void) const { 00690 return mpEventSymbolTable; 00691 } 00692 00693 // GlobalEventSymbolTablep() const 00694 SymbolTable* vGenerator::GlobalEventSymbolTablep(void) { 00695 return SymbolTable::GlobalEventSymbolTablep(); 00696 } 00697 00698 // EventSymbolTablep(pSymTab) 00699 void vGenerator::EventSymbolTablep(SymbolTable* pSymTab) { 00700 mpEventSymbolTable=pSymTab; 00701 // todo: set symboltable in mpAlphabet 00702 } 00703 00704 // EventSymbolTablep(rOtherGen) 00705 void vGenerator::EventSymbolTablep(const vGenerator& rOtherGen) { 00706 EventSymbolTablep(rOtherGen.EventSymbolTablep()); 00707 } 00708 00709 // EventIndex(rName) 00710 Idx vGenerator::EventIndex(const std::string& rName) const { 00711 return mpEventSymbolTable->Index(rName); 00712 } 00713 00714 // EventName(index) 00715 std::string vGenerator::EventName(Idx index) const { 00716 return mpEventSymbolTable->Symbol(index); 00717 } 00718 00719 // EventName(index, name) 00720 void vGenerator::EventName(Idx index, const std::string& rName) { 00721 FD_DG("vGenerator(" << this << ")::EventName(" 00722 << index << ",\"" << rName << "\")"); 00723 #ifdef FAUDES_CHECKED 00724 if (! ExistsEvent(index)) { 00725 std::stringstream errstr; 00726 errstr << "event \"" << index << "\" not found in generator \"" 00727 << Name() << "\""; 00728 throw Exception("vGenerator::EventName(name)", errstr.str(), 89); 00729 } 00730 #endif 00731 mpEventSymbolTable->SetEntry(index, rName); 00732 } 00733 00734 // UniqueEventName(rName) 00735 std::string vGenerator::UniqueEventName(const std::string& rName) const { 00736 std::string name=rName; 00737 if(name=="") name="ev"; 00738 return mpEventSymbolTable->UniqueSymbol(name) ; 00739 } 00740 00741 00742 // EventRename 00743 bool vGenerator::EventRename(Idx event, const std::string& rNewName) { 00744 // consistency 00745 FD_DG("vGenerator(" << this << ")::EventRename(" << EStr(event) << ", " << rNewName << ")"); 00746 #ifdef FAUDES_CHECKED 00747 if (! ExistsEvent(event)) { 00748 std::stringstream errstr; 00749 errstr << "event \"" << event << "\" not found in generator \"" 00750 << Name() << "\""; 00751 throw Exception("vGenerator::EventReame(name)", errstr.str(), 89); 00752 } 00753 #endif 00754 // prepare formal result 00755 bool res=ExistsEvent(rNewName); 00756 // insert new event 00757 Idx newidx=InsEvent(rNewName); 00758 // bail out if events are the same 00759 if(newidx==event) return true; 00760 // copy event attribute 00761 if(!res) EventAttribute(newidx,EventAttribute(event)); 00762 // store new transitions (with their attributes) 00763 TransSet* newtrans= TransRel().New(); 00764 // iterate over transitions 00765 TransSet::Iterator tit; 00766 for (tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 00767 if(tit->Ev!=event) continue; 00768 Transition trans= Transition(tit->X1, newidx, tit->X2); 00769 newtrans->Insert(trans); 00770 newtrans->Attribute(trans,TransAttribute(*tit)); 00771 tit=ClrTransition(tit); 00772 } 00773 // merge transitions 00774 for(tit=newtrans->Begin(); tit!=newtrans->End(); tit++) { 00775 SetTransition(*tit); 00776 TransAttribute(*tit,newtrans->Attribute(*tit)); 00777 } 00778 // free temp 00779 delete newtrans; 00780 // remore original event 00781 DelEvent(event); 00782 // done 00783 return res; 00784 } 00785 00786 00787 00788 // NewEventSet() 00789 EventSet vGenerator::NewEventSet(void) const { 00790 EventSet res; 00791 res.SymbolTablep(mpEventSymbolTable); 00792 return res; 00793 } 00794 00795 // NewEventSetp() 00796 EventSet* vGenerator::NewEventSetp(void) const { 00797 EventSet* res = new EventSet(); 00798 res->SymbolTablep(mpEventSymbolTable); 00799 return res; 00800 } 00801 00802 00803 // StateSymbolTable() const 00804 const SymbolTable& vGenerator::StateSymbolTable(void) const { 00805 return mStateSymbolTable; 00806 } 00807 00808 // StateSymbolTable(rSymTab) 00809 void vGenerator::StateSymbolTable(const SymbolTable& rSymTab) { 00810 mStateSymbolTable=rSymTab; 00811 mpStateSymbolTable=&mStateSymbolTable; 00812 } 00813 00814 // StateIndex(rName) 00815 Idx vGenerator::StateIndex(const std::string& rName) const { 00816 return mpStateSymbolTable->Index(rName); 00817 } 00818 00819 // StateName(index) 00820 std::string vGenerator::StateName(Idx index) const { 00821 return mpStateSymbolTable->Symbol(index); 00822 } 00823 00824 // StateName(index, name) 00825 void vGenerator::StateName(Idx index, const std::string& rName) { 00826 FD_DG("vGenerator(" << this << ")::StateName(" 00827 << index << ",\"" << rName << "\")"); 00828 #ifdef FAUDES_CHECKED 00829 if (! ExistsState(index)) { 00830 std::stringstream errstr; 00831 errstr << "state name \"" << rName << "\" not found in generator \"" 00832 << Name() << "\""; 00833 throw Exception("vGenerator::StateName(name)", errstr.str(), 90); 00834 } 00835 #endif 00836 mpStateSymbolTable->SetEntry(index, rName); 00837 } 00838 00839 00840 // ClearStateNames() 00841 void vGenerator::ClearStateNames(void) { 00842 FD_DG("vGenerator(" << this << ")::ClearStateNames()"); 00843 mpStateSymbolTable->Clear(); 00844 mStateNamesEnabled = false; 00845 } 00846 00847 00848 // ClrStateName(index) 00849 void vGenerator::ClrStateName(Idx index) { 00850 FD_DG("Generator(" << this << ")::ClrStateName(\"" << index << "\")"); 00851 #ifdef FAUDES_CHECKED 00852 if (! ExistsState(index)) { 00853 std::stringstream errstr; 00854 errstr << "state \"" << index << "\" not found in generator \"" 00855 << Name() << "\""; 00856 throw Exception("vGenerator::ClrStateName(name)", errstr.str(), 90); 00857 } 00858 #endif 00859 mpStateSymbolTable->ClrEntry(index); 00860 } 00861 00862 // ClrStateName(rName) 00863 void vGenerator::ClrStateName(const std::string& rName) { 00864 FD_DG("vGenerator(" << this << ")::ClrStateName(\"" << rName << "\")"); 00865 Idx index = StateIndex(rName); 00866 ClrStateName(index); 00867 } 00868 00869 00870 // StateNamesEnabled() 00871 bool vGenerator::StateNamesEnabled(void) const { 00872 return mStateNamesEnabled; 00873 } 00874 00875 // StateNamesEnabled(flag) 00876 void vGenerator::StateNamesEnabled(bool flag) { 00877 mStateNamesEnabled = flag; 00878 } 00879 00880 // StateNamesEnabled(flag) 00881 void vGenerator::StateNamesEnabledDefault(bool flag) { 00882 msStateNamesEnabledDefault = flag; 00883 } 00884 00885 // SetDefaultStateNames() 00886 void vGenerator::SetDefaultStateNames(void) { 00887 FD_DG("vGenerator(" << this << ")::SetDefaultStateNames()"); 00888 StateSet::Iterator it; 00889 for (it = StatesBegin(); it != StatesEnd(); ++it) { 00890 mpStateSymbolTable->SetDefaultSymbol(*it); 00891 } 00892 } 00893 00894 // EnforceStateNames(rTemplate) 00895 void vGenerator::EnforceStateNames(const std::string& rTemplate) { 00896 FD_DG("vGenerator(" << this << ")::EnforceStateNames(temp)"); 00897 StateSet::Iterator it; 00898 for (it = StatesBegin(); it != StatesEnd(); ++it) { 00899 if(StateName(*it)=="") { 00900 std::string name=UniqueStateName(rTemplate + "_1"); 00901 StateName(*it,name); 00902 } 00903 } 00904 } 00905 00906 // UniqueStateName(rName) 00907 std::string vGenerator::UniqueStateName(const std::string& rName) const { 00908 std::string name=rName; 00909 if(name=="") name="st"; 00910 return mpStateSymbolTable->UniqueSymbol(name) ; 00911 } 00912 00913 00914 // iterator AlphabetBegin() const 00915 EventSet::Iterator vGenerator::AlphabetBegin(void) const { 00916 return mpAlphabet->Begin(); 00917 } 00918 00919 // iterator AlphabetEnd() const 00920 EventSet::Iterator vGenerator::AlphabetEnd(void) const { 00921 return mpAlphabet->End(); 00922 } 00923 00924 // iterator StatesBegin() const 00925 StateSet::Iterator vGenerator::StatesBegin(void) const { 00926 return mpStates->Begin(); 00927 } 00928 00929 // iterator StatesEnd() const 00930 StateSet::Iterator vGenerator::StatesEnd(void) const { 00931 return mpStates->End(); 00932 } 00933 00934 // iterator TransRelBegin() const 00935 TransSet::Iterator vGenerator::TransRelBegin(void) const { 00936 return mpTransRel->Begin(); 00937 } 00938 00939 // iterator TransRelEnd() const 00940 TransSet::Iterator vGenerator::TransRelEnd(void) const { 00941 return mpTransRel->End(); 00942 } 00943 00944 // iterator TransRelBegin(x1) const 00945 TransSet::Iterator vGenerator::TransRelBegin(Idx x1) const { 00946 return mpTransRel->Begin(x1); 00947 } 00948 00949 // iterator TransRelEnd(x1) const 00950 TransSet::Iterator vGenerator::TransRelEnd(Idx x1) const { 00951 return mpTransRel->End(x1); 00952 } 00953 00954 // iterator TransRelBegin(x1, ev) const 00955 TransSet::Iterator vGenerator::TransRelBegin(Idx x1, Idx ev) const { 00956 return mpTransRel->Begin(x1, ev); 00957 } 00958 00959 // iterator TransRelEnd(x1, ev) const 00960 TransSet::Iterator vGenerator::TransRelEnd(Idx x1, Idx ev) const { 00961 return mpTransRel->End(x1, ev); 00962 } 00963 00964 // iterator FindTransition(trans) 00965 TransSet::Iterator vGenerator::FindTransition(const Transition& rTrans) const { 00966 return mpTransRel->Find(rTrans); 00967 } 00968 00969 // iterator FindTransition(x1, ex x2) 00970 TransSet::Iterator vGenerator::FindTransition(Idx x1, Idx ev, Idx x2) const { 00971 return mpTransRel->Find(Transition(x1, ev, x2)); 00972 } 00973 00974 // iterator FindTransition(x1, ev, x2) 00975 TransSet::Iterator vGenerator::FindTransition( 00976 const std::string& rX1, const std::string& rEv, const std::string& rX2) const 00977 { 00978 return mpTransRel->Find(StateIndex(rX1), EventIndex(rEv), StateIndex(rX2)); 00979 } 00980 00981 // iterator ExistsTransition(trans) 00982 bool vGenerator::ExistsTransition(const Transition& rTrans) const { 00983 return mpTransRel->Exists(rTrans); 00984 } 00985 00986 // iterator ExistsTransition(x1, ex x2) 00987 bool vGenerator::ExistsTransition(Idx x1, Idx ev, Idx x2) const { 00988 return mpTransRel->Exists(Transition(x1, ev, x2)); 00989 } 00990 00991 // iterator ExistsTransition(x1, ev, x2) 00992 bool vGenerator::ExistsTransition( 00993 const std::string& rX1, const std::string& rEv, const std::string& rX2) const 00994 { 00995 return mpTransRel->Exists(StateIndex(rX1), EventIndex(rEv), StateIndex(rX2)); 00996 } 00997 00998 00999 // idx InitState() const 01000 Idx vGenerator::InitState(void) const { 01001 #ifdef FAUDES_CHECKED 01002 if(mInitStates.Size()!=1) { 01003 std::stringstream errstr; 01004 errstr << "init state does not exist uniquely" << std::endl; 01005 throw Exception("vGenerator::InitSTate", errstr.str(), 92); 01006 } 01007 #endif 01008 return *mInitStates.Begin(); 01009 } 01010 01011 // iterator InitStatesBegin() const 01012 StateSet::Iterator vGenerator::InitStatesBegin(void) const { 01013 return mInitStates.Begin(); 01014 } 01015 01016 // iterator InitStatesEnd() const 01017 StateSet::Iterator vGenerator::InitStatesEnd(void) const { 01018 return mInitStates.End(); 01019 } 01020 01021 // iterator MarkedStatesBegin() 01022 StateSet::Iterator vGenerator::MarkedStatesBegin(void) const { 01023 return mMarkedStates.Begin(); 01024 } 01025 01026 // iterator MarkedStatesEnd() const 01027 StateSet::Iterator vGenerator::MarkedStatesEnd(void) const { 01028 return mMarkedStates.End(); 01029 } 01030 01031 // InjectAlphabet(newalphabet) 01032 void vGenerator::InjectAlphabet(const EventSet& rNewAlphabet) { 01033 FD_DG("vGenerator::InjectAlphabet() " << rNewAlphabet.ToString()); 01034 #ifdef FAUDES_CHECKED 01035 if(rNewAlphabet.SymbolTablep()!=mpEventSymbolTable) { 01036 std::stringstream errstr; 01037 errstr << "symboltable mismatch aka not implemented" << std::endl; 01038 throw Exception("vGenerator::InjectAlphabet", errstr.str(), 88); 01039 } 01040 #endif 01041 *mpAlphabet = rNewAlphabet; 01042 mpAlphabet->Name("Alphabet"); 01043 } 01044 01045 // RestrictAlphabet(newalphabet) 01046 void vGenerator::RestrictAlphabet(const EventSet& rNewAlphabet) { 01047 FD_DG("vGenerator::RestrictAlphabet() " << rNewAlphabet.ToString()); 01048 #ifdef FAUDES_CHECKED 01049 if(rNewAlphabet.SymbolTablep()!=mpEventSymbolTable) { 01050 std::stringstream errstr; 01051 errstr << "symboltable mismatch aka not implemented" << std::endl; 01052 throw Exception("vGenerator::RestrictAlphabet", errstr.str(), 88); 01053 } 01054 #endif 01055 mpAlphabet->RestrictSet(rNewAlphabet); 01056 } 01057 01058 // InsEvent(index) 01059 bool vGenerator::InsEvent(Idx index) { 01060 FD_DG("vGenerator(" << this << ")::InsEvent(" << index << ")"); 01061 return mpAlphabet->Insert(index); 01062 } 01063 01064 // InsEvent(rName) 01065 Idx vGenerator::InsEvent(const std::string& rName) { 01066 FD_DG("vGenerator(" << this << ")::InsEvent(\"" << rName << "\")"); 01067 return mpAlphabet->Insert(rName); 01068 } 01069 01070 // InsEvents(events) 01071 void vGenerator::InsEvents(const EventSet& events) { 01072 mpAlphabet->InsertSet(events); 01073 } 01074 01075 // DelEvent(index) 01076 bool vGenerator::DelEvent(Idx index) { 01077 FD_DG("vGenerator(" << this << ")::DelEvent(" << index << ")"); 01078 mpTransRel->EraseByEv(index); 01079 return mpAlphabet->Erase(index); 01080 } 01081 01082 // DelEvent(rName) 01083 bool vGenerator::DelEvent(const std::string& rName) { 01084 FD_DG("vGenerator(" << this << ")::DelEvent(\"" << rName << "\")"); 01085 Idx index = mpAlphabet->Index(rName); 01086 mpTransRel->EraseByEv(index); 01087 return mpAlphabet->Erase(index); 01088 } 01089 01090 // DelEvents(events) 01091 void vGenerator::DelEvents(const EventSet& rEvents) { 01092 FD_DG("vGenerator(" << this << ")::DelEvents(\"" 01093 << rEvents.ToString() << "\")"); 01094 EventSet::Iterator it; 01095 for (it = rEvents.Begin(); it != rEvents.End(); ++it) { 01096 DelEvent(*it); 01097 } 01098 } 01099 01100 // DelEventFromAlphabet(index) 01101 bool vGenerator::DelEventFromAlphabet(Idx index) { 01102 FD_DG("vGenerator(" << this << ")::DelEventFromAlphabet(" 01103 << index << ")"); 01104 return mpAlphabet->Erase(index); 01105 } 01106 01107 // InsState() 01108 Idx vGenerator::InsState(void) { 01109 FD_DG("vGenerator(" << this << ")::InsState()"); 01110 return mpStates->Insert(); 01111 } 01112 01113 // InsState(index) 01114 bool vGenerator::InsState(Idx index) { 01115 FD_DG("vGenerator(" << this << ")::InsState(" << index << ")"); 01116 return mpStates->Insert(index); 01117 } 01118 01119 // InsState(rName) 01120 Idx vGenerator::InsState(const std::string& rName) { 01121 FD_DG("vGenerator(" << this << ")::InsState(\"" << rName << "\")"); 01122 Idx index=mpStates->Insert(); 01123 StateName(index,rName); 01124 return index; 01125 } 01126 01127 // InjectState(index) 01128 void vGenerator::InjectState(Idx index) { 01129 FD_DG("vGenerator(" << this << ")::InjectState(\"" << SStr(index) << "\")"); 01130 mpStates->Insert(index); 01131 } 01132 01133 // InjectStates(rNewStates) 01134 void vGenerator::InjectStates(const StateSet& rNewStates) { 01135 FD_DG("vGenerator(" << this << ")::InjectStates(" << rNewStates.ToString() << ")"); 01136 *mpStates=rNewStates; 01137 mpStates->Name("States"); 01138 mpStateSymbolTable->RestrictDomain(*mpStates); 01139 FD_DG("vGenerator(" << this << ")::InjectStates(): report " << mpStates->ToString()); 01140 } 01141 01142 // InsInitState() 01143 Idx vGenerator::InsInitState(void) { 01144 FD_DG("vGenerator(" << this << ")::InsInitState()"); 01145 Idx index; 01146 index = InsState(); 01147 mInitStates.Insert(index); 01148 return index; 01149 } 01150 01151 // InsInitState(name) 01152 Idx vGenerator::InsInitState(const std::string& rName) { 01153 FD_DG("vGenerator(" << this << ")::InsInitState(\"" << rName << "\")"); 01154 Idx index; 01155 index = InsState(rName); 01156 mInitStates.Insert(index); 01157 return index; 01158 } 01159 01160 // InsInitState(name) 01161 bool vGenerator::InsInitState(Idx index) { 01162 bool res=InsState(index); 01163 mInitStates.Insert(index); 01164 return res; 01165 } 01166 01167 // InsMarkedState() 01168 Idx vGenerator::InsMarkedState(void) { 01169 FD_DG("vGenerator(" << this << ")::InsMarkedState()"); 01170 Idx index; 01171 index = InsState(); 01172 mMarkedStates.Insert(index); 01173 return index; 01174 } 01175 01176 // InsInitState(name) 01177 bool vGenerator::InsMarkedState(Idx index) { 01178 bool res=InsState(index); 01179 mMarkedStates.Insert(index); 01180 return res; 01181 } 01182 01183 // InsMarkedState(rName) 01184 Idx vGenerator::InsMarkedState(const std::string& rName) { 01185 FD_DG("vGenerator(" << this << ")::InsMarkedState(\"" << rName << "\")"); 01186 Idx index; 01187 index = InsState(rName); 01188 mMarkedStates.Insert(index); 01189 return index; 01190 } 01191 01192 // DelState(index) 01193 bool vGenerator::DelState(Idx index) { 01194 FD_DG("vGenerator(" << this << ")::DelState(" << index << ")"); 01195 // mInitStates 01196 mInitStates.Erase(index); 01197 // mstates 01198 mMarkedStates.Erase(index); 01199 // transrel 01200 mpTransRel->EraseByX1OrX2(index); 01201 // symbolic name 01202 mpStateSymbolTable->ClrEntry(index); 01203 // finally ... remove the state 01204 return mpStates->Erase(index); 01205 } 01206 01207 // DelState(rName) 01208 bool vGenerator::DelState(const std::string& rName) { 01209 FD_DG("vGenerator(" << this << ")::DelState(\"" << rName << "\")"); 01210 Idx index; 01211 index = StateIndex(rName); 01212 #ifdef FAUDES_CHECKED 01213 if (index == 0) { 01214 std::stringstream errstr; 01215 errstr << "state name \"" << rName << "\" not found in generator \"" 01216 << Name() << "\""; 01217 throw Exception("vGenerator::DelState(name)", errstr.str(), 90); 01218 } 01219 #endif 01220 return DelState(index); 01221 } 01222 01223 // DelStates(rDelStates) 01224 void vGenerator::DelStates(const StateSet& rDelStates) { 01225 FD_DG("vGenerator(" << this << ")::DelStates(" 01226 << rDelStates.ToString() << ")"); 01227 StateSet::Iterator cit; 01228 StateSet::Iterator cit_end; 01229 // symbolic state names 01230 if (StateNamesEnabled()) { 01231 for (cit = rDelStates.Begin(); cit != rDelStates.End(); ++cit) { 01232 mpStateSymbolTable->ClrEntry(*cit); 01233 } 01234 } 01235 // statesets 01236 mpStates->EraseSet(rDelStates); 01237 mInitStates.EraseSet(rDelStates); 01238 mMarkedStates.EraseSet(rDelStates); 01239 // mpTransRel: 01240 mpTransRel->EraseByX1OrX2(rDelStates); 01241 // original (slow) 01242 //for (cit = rDelStates.Begin(); cit != rDelStates.End(); ++cit) { 01243 // mpTransRel->EraseByX1OrX2(*cit); 01244 //} 01245 } 01246 01247 // DelStateFromStates(index) 01248 bool vGenerator::DelStateFromStates(Idx index) { 01249 FD_DG("vGenerator(" << this << ")::DelStateFromStates(" << index << ")"); 01250 // mStates + global 01251 return mpStates->Erase(index); 01252 } 01253 01254 // DelStateFromStates(pos) 01255 StateSet::Iterator vGenerator::DelStateFromStates(StateSet::Iterator pos) { 01256 FD_DG("vGenerator(" << this << ")::DelState(" << *pos << ")"); 01257 return mpStates->Erase(pos); 01258 } 01259 01260 // SetInitState(index) 01261 void vGenerator::SetInitState(Idx index) { 01262 FD_DG("vGenerator(" << this << ")::SetInitState(" << index << ")"); 01263 #ifdef FAUDES_CHECKED 01264 if (! mpStates->Exists(index)) { 01265 std::stringstream errstr; 01266 errstr << "vGenerator::SetMarkedState: index " << index 01267 << " not in stateset"; 01268 throw Exception("vGenerator::SetInitState(..)", errstr.str(), 91); 01269 } 01270 #endif 01271 mInitStates.Insert(index); 01272 } 01273 01274 // SetInitState(rName) 01275 void vGenerator::SetInitState(const std::string& rName) { 01276 FD_DG("vGenerator(" << this << ")::SetInitState(\"" << rName << "\")"); 01277 Idx index = StateIndex(rName); 01278 #ifdef FAUDES_CHECKED 01279 if (index == 0) { 01280 std::stringstream errstr; 01281 errstr << "State name \"" << rName << "\" not known in Generator"; 01282 throw Exception("vGenerator::SetInitState(..)", errstr.str(), 90); 01283 } 01284 #endif 01285 SetInitState(index); 01286 } 01287 01288 // InjectInitStates(rNewInitStates) 01289 void vGenerator::InjectInitStates(const StateSet& rNewInitStates) { 01290 FD_DG("vGenerator(" << this << ")::InjectInitStates(" 01291 << rNewInitStates.ToString() << ")"); 01292 mInitStates = rNewInitStates; 01293 mInitStates.Name("InitStates"); 01294 } 01295 01296 // ClrInitState(index) 01297 void vGenerator::ClrInitState(Idx index) { 01298 FD_DG("vGenerator(" << this << ")::ClrInitState(" << index << ")"); 01299 #ifdef FAUDES_CHECKED 01300 if (! mpStates->Exists(index)) { 01301 std::stringstream errstr; 01302 errstr << "vGenerator::SetMarkedState: index " << index 01303 << " not in stateset"; 01304 throw Exception("vGenerator::ClrInitState(..)", errstr.str(), 91); 01305 } 01306 #endif 01307 mInitStates.Erase(index); 01308 } 01309 01310 // ClrInitState(rName) 01311 void vGenerator::ClrInitState(const std::string& rName) { 01312 FD_DG("vGenerator(" << this << ")::ClrInitState(\"" << rName << "\")"); 01313 Idx index = StateIndex(rName); 01314 #ifdef FAUDES_CHECKED 01315 if (index == 0) { 01316 std::stringstream errstr; 01317 errstr << "State name \"" << rName << "\" not known in Generator"; 01318 throw Exception("vGenerator::ClrInitState(..)", errstr.str(), 90); 01319 } 01320 #endif 01321 ClrInitState(index); 01322 } 01323 01324 // ClrInitState(pos) 01325 StateSet::Iterator vGenerator::ClrInitState(StateSet::Iterator pos) { 01326 FD_DG("vGenerator(" << this << ")::ClrInitState(" << *pos << ")"); 01327 return mInitStates.Erase(pos); 01328 } 01329 01330 // ClearInitStates() 01331 void vGenerator::ClearInitStates(void) { 01332 mInitStates.Clear(); 01333 } 01334 01335 // SetMarkedState(index) 01336 void vGenerator::SetMarkedState(Idx index) { 01337 FD_DG("vGenerator(" << this << ")::SetMarkedState(" << index << ")"); 01338 #ifdef FAUDES_CHECKED 01339 if (! mpStates->Exists(index)) { 01340 std::stringstream errstr; 01341 errstr << "vGenerator::SetMarkedState: index " << index 01342 << " not in stateset"; 01343 throw Exception("vGenerator::SetMarkedState(..)", errstr.str(), 91); 01344 } 01345 #endif 01346 mMarkedStates.Insert(index); 01347 } 01348 01349 // SetMarkedState(rName) 01350 void vGenerator::SetMarkedState(const std::string& rName) { 01351 FD_DG("vGenerator(" << this << ")::SetMarkedState(\"" << rName << "\")"); 01352 Idx index = StateIndex(rName); 01353 #ifdef FAUDES_CHECKED 01354 if (index == 0) { 01355 std::stringstream errstr; 01356 errstr << "State name \"" << rName << "\" not known in Generator"; 01357 throw Exception("vGenerator::SetMarkedState(..)", errstr.str(), 90); 01358 } 01359 #endif 01360 SetMarkedState(index); 01361 } 01362 01363 // InjectMarkedStates(rNewMarkedStates) 01364 void vGenerator::InjectMarkedStates(const StateSet& rNewMarkedStates) { 01365 FD_DG("vGenerator(" << this << ")::InjectMarkedStates(" 01366 << rNewMarkedStates.ToString() << ")"); 01367 mMarkedStates = rNewMarkedStates; 01368 mMarkedStates.Name("MarkedStates"); 01369 } 01370 01371 // ClrMarkedState(index) 01372 void vGenerator::ClrMarkedState(Idx index) { 01373 FD_DG("vGenerator(" << this << ")::ClrMarkedState(" << index << ")"); 01374 #ifdef FAUDES_CHECKED 01375 if (! mpStates->Exists(index)) { 01376 std::stringstream errstr; 01377 errstr << "vGenerator::ClrMarkedState: index " << index 01378 << " not in stateset"; 01379 throw Exception("vGenerator::ClrMarkedState(..)", errstr.str(), 91); 01380 } 01381 #endif 01382 mMarkedStates.Erase(index); 01383 } 01384 01385 // ClrMarkedState(rName) 01386 void vGenerator::ClrMarkedState(const std::string& rName) { 01387 FD_DG("vGenerator(" << this << ")::ClrMarkedState(\"" << rName << "\")"); 01388 Idx index = StateIndex(rName); 01389 #ifdef FAUDES_CHECKED 01390 if (index == 0) { 01391 std::stringstream errstr; 01392 errstr << "State name \"" << rName << "\" not known in Generator"; 01393 throw Exception("vGenerator::ClrMarkedState(..)", errstr.str(), 90); 01394 } 01395 #endif 01396 ClrMarkedState(index); 01397 } 01398 01399 // ClrMarkedState(pos) 01400 StateSet::Iterator vGenerator::ClrMarkedState(StateSet::Iterator pos) { 01401 FD_DG("vGenerator(" << this << ")::ClrMarkedState(" << *pos << ")"); 01402 return mMarkedStates.Erase(pos); 01403 } 01404 01405 // ClearMarkedStates() 01406 void vGenerator::ClearMarkedStates(void) { 01407 mMarkedStates.Clear(); 01408 } 01409 01410 // InjectTransition(newtrans) 01411 void vGenerator::InjectTransition(const Transition& rTrans) { 01412 FD_DG("vGenerator::InjectTransition(" << TStr(rTrans) << ")"); 01413 mpTransRel->Insert(rTrans); 01414 } 01415 01416 // InjectTransRel(newtransrel) 01417 void vGenerator::InjectTransRel(const TransSet& rNewTransrel) { 01418 FD_DG("vGenerator::InjectTransRel(...)"); 01419 *mpTransRel=rNewTransrel; 01420 mpTransRel->Name("TransRel"); 01421 } 01422 01423 // SetTransition(rX1, rEv, rX2) 01424 bool vGenerator::SetTransition(const std::string& rX1, const std::string& rEv, const std::string& rX2) { 01425 FD_DG("vGenerator(" << this << ")::SetTransition(\"" 01426 << rX1 << "\", \"" << rEv << "\", \"" << rX2 << "\")"); 01427 Idx x1 = StateIndex(rX1); 01428 Idx x2 = StateIndex(rX2); 01429 #ifdef FAUDES_CHECKED 01430 if (x1 == 0) { 01431 FD_ERR("vGenerator::SetTransition: state " << rX1 01432 << " not in stateset"); 01433 std::stringstream errstr; 01434 errstr << "State name " << rX1 << " not found in Generator"; 01435 throw Exception("vGenerator::SetTransition(..)", errstr.str(), 90); 01436 } 01437 if (! mpAlphabet->Exists(rEv)) { 01438 FD_ERR("vGenerator::SetTransition: event " << rEv << " not in alphabet"); 01439 std::stringstream errstr; 01440 errstr << "Event name " << rEv << " not found in event domain of Generator"; 01441 throw Exception("vGenerator::SetTransition(..)", errstr.str(), 95); 01442 } 01443 if (x2 == 0) { 01444 FD_ERR("vGenerator::SetTransition: state " << rX2 << " not in stateset"); 01445 std::stringstream errstr; 01446 errstr << "State name " << rX2 << " not found in Generator"; 01447 throw Exception("vGenerator::SetTransition(..)", errstr.str(), 90); 01448 } 01449 #endif 01450 return SetTransition(Transition(x1, EventIndex(rEv), x2)); 01451 } 01452 01453 01454 // SetTransition(x1, ev, x2) 01455 bool vGenerator::SetTransition(Idx x1, Idx ev, Idx x2) { 01456 return SetTransition(Transition(x1,ev,x2)); 01457 } 01458 01459 // SetTransition(rTransition) 01460 bool vGenerator::SetTransition(const Transition& rTransition) { 01461 FD_DG("vGenerator(" << this << ")::SetTransition(" << rTransition.X1 << "," 01462 << rTransition.Ev << "," << rTransition.X2 << ")"); 01463 #ifdef FAUDES_CHECKED 01464 if (! mpStates->Exists(rTransition.X1)) { 01465 std::stringstream errstr; 01466 errstr << "vGenerator::SetTransition: state " << rTransition.X1 01467 << " not in stateset"; 01468 throw Exception("vGenerator::SetTransition(..)", errstr.str(), 95); 01469 } 01470 if (! mpAlphabet->Exists(rTransition.Ev)) { 01471 std::stringstream errstr; 01472 errstr << "vGenerator::SetTransition: event " << rTransition.Ev 01473 << " not in alphabet "; 01474 throw Exception("vGenerator::SetTransition(..)", errstr.str(), 95); 01475 } 01476 if (! mpStates->Exists(rTransition.X2)) { 01477 std::stringstream errstr; 01478 errstr << "vGenerator::SetTransition: state " << rTransition.X2 01479 << " not in stateset"; 01480 throw Exception("vGenerator::SetTransition(..)", errstr.str(), 95); 01481 } 01482 #endif 01483 return mpTransRel->Insert(rTransition); 01484 } 01485 01486 // ClrTransition.X1, ev, x2) 01487 void vGenerator::ClrTransition(Idx x1, Idx ev, Idx x2) { 01488 FD_DG("vGenerator(" << this << ")::ClrTransition(" 01489 << x1 << "," << ev << "," << x2 << ")"); 01490 mpTransRel->Erase(x1, ev, x2); 01491 } 01492 01493 // ClrTransition(rTransition) 01494 void vGenerator::ClrTransition(const Transition& rTransition) { 01495 FD_DG("vGenerator(" << this << ")::ClrTransition(" << TStr(rTransition) << ")"); 01496 mpTransRel->Erase(rTransition); 01497 } 01498 01499 // ClrTransition(it) 01500 TransSet::Iterator vGenerator::ClrTransition(TransSet::Iterator it) { 01501 FD_DG("vGenerator(" << this << ")::ClrTransition(" << TStr(*it)<< ")" ); 01502 return mpTransRel->Erase(it); 01503 } 01504 01505 // TransAttribute(trans, attr) 01506 void vGenerator::TransAttribute(const Transition& rTrans, const Type& rAttr) { 01507 FD_DG("vGenerator(" << this << ")::TransAttribute(" 01508 << TStr(rTrans) << ",\"" << rAttr.ToString() << "\")"); 01509 mpTransRel->Attribute(rTrans, rAttr); 01510 } 01511 01512 // TransAttributep(trans) 01513 AttributeVoid* vGenerator::TransAttributep(const Transition& rTrans) { 01514 return mpTransRel->Attributep(rTrans); 01515 } 01516 01517 01518 // TransAttribute(trans) 01519 const AttributeVoid& vGenerator::TransAttribute(const Transition& rTrans) const { 01520 return mpTransRel->Attribute(rTrans); 01521 } 01522 01523 // ClrTransAttribute(trans) 01524 void vGenerator::ClrTransAttribute(const Transition& rTrans) { 01525 mpTransRel->ClrAttribute(rTrans); 01526 } 01527 01528 01529 // ClearTransRel() 01530 void vGenerator::ClearTransRel(void) { 01531 mpTransRel->Clear(); 01532 } 01533 01534 // EventAttribute(index, attr) 01535 void vGenerator::EventAttribute(Idx index, const Type& rAttr) { 01536 FD_DG("vGenerator(" << this << ")::EventAttribute(" 01537 << EStr(index) << ",\"" << rAttr.ToString() << "\")"); 01538 mpAlphabet->Attribute(index, rAttr); 01539 } 01540 01541 01542 // EventAttributes(set) 01543 void vGenerator::EventAttributes(const EventSet& rEventSet) { 01544 FD_DG("vGenerator(" << this << ")::EventAttributes(" 01545 << rEventSet.ToString() << "\")"); 01546 mpAlphabet->Attributes(rEventSet); 01547 } 01548 01549 // ClrEventAttribute(index) 01550 void vGenerator::ClrEventAttribute(Idx index) { 01551 FD_DG("vGenerator(" << this << ")::ClrEventAttribute(\"" << EStr(index) << "\")"); 01552 mpAlphabet->ClrAttribute(index); 01553 } 01554 01555 // StateAttribute(index, attr) 01556 void vGenerator::StateAttribute(Idx index, const Type& rAttr) { 01557 FD_DG("vGenerator(" << this << ")::StateAttribute(" 01558 << SStr(index) << ",\"" << rAttr.ToString() << "\")"); 01559 mpStates->Attribute(index, rAttr); 01560 } 01561 01562 // ClrStateAttribute(index) 01563 void vGenerator::ClrStateAttribute(Idx index) { 01564 FD_DG("vGenerator(" << this << ")::ClrStateAttribute(\"" << index << "\")"); 01565 mpStates->ClrAttribute(index); 01566 } 01567 01568 // ExistsEvent(index) 01569 bool vGenerator::ExistsEvent(Idx index) const { 01570 return mpAlphabet->Exists(index); 01571 } 01572 01573 // ExistsEvent(rName) 01574 bool vGenerator::ExistsEvent(const std::string& rName) const { 01575 return mpAlphabet->Exists(rName); 01576 } 01577 01578 // FindEvent(index) const 01579 EventSet::Iterator vGenerator::FindEvent(Idx index) const { 01580 return mpAlphabet->Find(index); 01581 } 01582 01583 // FindEvent(rName) 01584 EventSet::Iterator vGenerator::FindEvent(const std::string& rName) const { 01585 return mpAlphabet->Find(rName); 01586 } 01587 01588 // ExistsState(index) 01589 bool vGenerator::ExistsState(Idx index) const { 01590 return mpStates->Exists(index); 01591 } 01592 01593 // ExistsName(name) 01594 bool vGenerator::ExistsState(const std::string& rName) const { 01595 return ExistsState(StateIndex(rName)); 01596 } 01597 01598 // FindState(rName) const 01599 StateSet::Iterator vGenerator::FindState(const std::string& rName) const { 01600 return mpStates->Find(mpStateSymbolTable->Index(rName)); 01601 } 01602 01603 // FindState(index) const 01604 StateSet::Iterator vGenerator::FindState(Idx index) const { 01605 return mpStates->Find(index); 01606 } 01607 01608 // ExistsInitState(index) 01609 bool vGenerator::ExistsInitState(Idx index) const { 01610 return mInitStates.Exists(index); 01611 } 01612 01613 // FindInitState(index) 01614 StateSet::Iterator vGenerator::FindInitState(Idx index) const { 01615 return mInitStates.Find(index); 01616 } 01617 01618 // ExistsMarkedState(index) 01619 bool vGenerator::ExistsMarkedState(Idx index) const { 01620 return mMarkedStates.Exists(index); 01621 } 01622 01623 // FindMarkedState(index) 01624 StateSet::Iterator vGenerator::FindMarkedState(Idx index) const { 01625 return mMarkedStates.Find(index); 01626 } 01627 01628 // EventAttribute(index) 01629 const AttributeVoid& vGenerator::EventAttribute(Idx index) const { 01630 return mpAlphabet->Attribute(index); 01631 } 01632 01633 // EventAttributep(index) 01634 AttributeVoid* vGenerator::EventAttributep(Idx index) { 01635 return mpAlphabet->Attributep(index); 01636 } 01637 01638 // EventAttribute(rName) 01639 const AttributeVoid& vGenerator::EventAttribute(const std::string& rName) const { 01640 return EventAttribute(EventIndex(rName)); 01641 } 01642 01643 // EventAttributep(rName) 01644 AttributeVoid* vGenerator::EventAttributep(const std::string& rName) { 01645 return EventAttributep(EventIndex(rName)); 01646 } 01647 01648 // StateAttribute(index) 01649 const AttributeVoid& vGenerator::StateAttribute(Idx index) const { 01650 return mpStates->Attribute(index); 01651 } 01652 01653 // StateAttributep(index) 01654 AttributeVoid* vGenerator::StateAttributep(Idx index) { 01655 return mpStates->Attributep(index); 01656 } 01657 01658 // GlobalAttribute(attr) 01659 void vGenerator::GlobalAttribute(const Type& rAttr) { 01660 FD_DG("vGenerator(" << this << ")::GlobalAttribute(" 01661 << rAttr.ToString() << "\")"); 01662 // set to void is ok for silient ignore 01663 if(typeid(rAttr)==typeid(AttributeVoid)) return; 01664 // error: 01665 std::stringstream errstr; 01666 errstr << "cannot cast global attribute " << rAttr.ToString() << " for generator " << Name(); 01667 throw Exception("vGenerator::GlobalAttribute", errstr.str(), 63); 01668 } 01669 01670 // GlobalAttributeTry(attr) 01671 void vGenerator::GlobalAttributeTry(const Type& rAttr) { 01672 FD_DG("vGenerator(" << this << ")::GlobalAttributeTry(" 01673 << rAttr.ToString() << "\")"); 01674 // ignore 01675 } 01676 01677 // GlobalAttribute() 01678 const AttributeVoid& vGenerator::GlobalAttribute(void) const { 01679 FD_DG("vGenerator(" << this << ")::GlobalAttribute()"); 01680 return *mpGlobalAttribute; 01681 } 01682 01683 // GlobalAttributep() 01684 AttributeVoid* vGenerator::GlobalAttributep(void) { 01685 FD_DG("vGenerator(" << this << ")::GlobalAttributep()"); 01686 return mpGlobalAttribute; 01687 } 01688 01689 01690 // Alphabet() 01691 const EventSet& vGenerator::Alphabet(void) const { 01692 return *mpAlphabet; 01693 } 01694 01695 // States() 01696 const StateSet& vGenerator::States(void) const { 01697 return *mpStates; 01698 } 01699 01700 // TransRel() 01701 const TransSet& vGenerator::TransRel(void) const { 01702 return *mpTransRel; 01703 } 01704 01705 01706 // TransRel(res) 01707 void vGenerator::TransRel(TransSetX1EvX2& res) const { mpTransRel->ReSort(res); } 01708 void vGenerator::TransRel(TransSetEvX1X2& res) const { mpTransRel->ReSort(res); } 01709 void vGenerator::TransRel(TransSetEvX2X1& res) const { mpTransRel->ReSort(res); } 01710 void vGenerator::TransRel(TransSetX2EvX1& res) const { mpTransRel->ReSort(res); } 01711 void vGenerator::TransRel(TransSetX2X1Ev& res) const { mpTransRel->ReSort(res); } 01712 void vGenerator::TransRel(TransSetX1X2Ev& res) const { mpTransRel->ReSort(res); } 01713 01714 01715 Transition vGenerator::TransitionByNames( 01716 const std::string& rX1, const std::string& rEv, const std::string& rX2) const { 01717 return Transition(StateIndex(rX1),EventIndex(rEv),StateIndex(rX2)); 01718 } 01719 01720 // InitStates() 01721 const StateSet& vGenerator::InitStates(void) const { 01722 return mInitStates; 01723 } 01724 01725 // MarkedStates() 01726 const StateSet& vGenerator::MarkedStates(void) const { 01727 return mMarkedStates; 01728 } 01729 01730 // MinimizeAlphabet() 01731 void vGenerator::MinimizeAlphabet(void) { 01732 mpAlphabet->NameSet::EraseSet(UnusedEvents()); 01733 } 01734 01735 // UsedEvents() 01736 EventSet vGenerator::UsedEvents(void) const { 01737 EventSet resultset = NewEventSet(); 01738 TransSet::Iterator it; 01739 for (it = mpTransRel->Begin(); it != mpTransRel->End(); ++it) { 01740 resultset.Insert(it->Ev); 01741 } 01742 return resultset; 01743 } 01744 01745 // UnusedEvents() 01746 EventSet vGenerator::UnusedEvents(void) const { 01747 return *mpAlphabet - UsedEvents(); 01748 } 01749 01750 // ActiveEventSet(x1) 01751 EventSet vGenerator::ActiveEventSet(Idx x1) const { 01752 EventSet result = NewEventSet(); 01753 TransSet::Iterator it; 01754 for (it = TransRelBegin(x1); it != TransRelEnd(x1); ++it) { 01755 result.Insert(it->Ev); 01756 } 01757 return result; 01758 } 01759 01760 // ActiveTransSet(x1) 01761 TransSet vGenerator::ActiveTransSet(Idx x1) const { 01762 TransSet result; 01763 TransSet::Iterator it; 01764 for (it = TransRelBegin(x1); it != TransRelEnd(x1); ++it) { 01765 result.Insert(*it); 01766 } 01767 return result; 01768 } 01769 01770 // TransRelStateSpace() 01771 StateSet vGenerator::TransRelStateSpace(void) const { 01772 StateSet states; 01773 TransSet::Iterator it; 01774 for (it=mpTransRel->Begin(); it != mpTransRel->End(); ++it) { 01775 states.Insert(it->X1); 01776 states.Insert(it->X2); 01777 } 01778 return states; 01779 } 01780 01781 // TransRelStateSpace(x1) 01782 StateSet vGenerator::TransRelStateSpace(Idx x1) const { 01783 StateSet states; 01784 TransSet::Iterator it = mpTransRel->Begin(x1); 01785 TransSet::Iterator it_end = mpTransRel->End(x1); 01786 for (; it != it_end; ++it) { 01787 states.Insert(it->X2); 01788 } 01789 return states; 01790 } 01791 01792 01793 // CheckAccessible(accessibleset, startState) 01794 void vGenerator::CheckAccessible(StateSet& accessibleset, Idx startState) const { 01795 if (! accessibleset.Exists(startState)) { 01796 accessibleset.Insert(startState); 01797 TransSet::Iterator it = TransRelBegin(startState); 01798 TransSet::Iterator it_end = TransRelEnd(startState); 01799 for (; it != it_end; ++it) { 01800 CheckAccessible(accessibleset, it->X2); 01801 } 01802 } 01803 } 01804 01805 // CheckCoaccessible(coaccessibleset, rtransrel, startState) 01806 void vGenerator::CheckCoaccessible(StateSet& coaccessibleset, const TransSetX2EvX1& rtrel, Idx startState) const { 01807 if (! coaccessibleset.Exists(startState)) { 01808 coaccessibleset.Insert(startState); 01809 TransSetX2EvX1::Iterator it = rtrel.BeginByX2(startState); 01810 TransSetX2EvX1::Iterator it_end = rtrel.EndByX2(startState); 01811 for (; it != it_end; ++it) { 01812 CheckCoaccessible(coaccessibleset, rtrel, it->X1); 01813 } 01814 } 01815 } 01816 01817 // AccessibleSet() 01818 StateSet vGenerator::AccessibleSet(void) const { 01819 StateSet accessibleset; 01820 StateSet::Iterator it; 01821 for (it = InitStatesBegin(); it != InitStatesEnd(); ++it) { 01822 CheckAccessible(accessibleset, *it); 01823 } 01824 accessibleset.Name("AccessibleSet"); 01825 return accessibleset; 01826 } 01827 01828 // Accessible() 01829 bool vGenerator::Accessible(void) { 01830 StateSet accessibleset = AccessibleSet(); 01831 StateSet not_accessible = *mpStates - accessibleset; 01832 DelStates(not_accessible); 01833 // return true if there is an initial state 01834 if (!mInitStates.Empty()) { 01835 FD_DF("vGenerator::accessible: generator is accessible"); 01836 return true; 01837 } 01838 else { 01839 FD_DF("vGenerator::accessible: generator is accessible but empty"); 01840 return false; 01841 } 01842 01843 } 01844 01845 // IsAccessible() 01846 bool vGenerator::IsAccessible(void) const { 01847 if (AccessibleSet() == *mpStates) { 01848 FD_DF("vGenerator::accessible: generator is accessible"); 01849 return true; 01850 } 01851 else { 01852 FD_DF("vGenerator::accessible: generator is not accessible"); 01853 return false; 01854 } 01855 } 01856 01857 // CoaccessibleSet() 01858 StateSet vGenerator::CoaccessibleSet(void) const { 01859 StateSet coaccessibleset; 01860 StateSet::Iterator it; 01861 // build reverse transition relation 01862 TransSetX2EvX1 rtrel; 01863 TransRel(rtrel); 01864 for (it = MarkedStatesBegin(); it != MarkedStatesEnd(); ++it) { 01865 CheckCoaccessible(coaccessibleset, rtrel, *it); 01866 } 01867 coaccessibleset.Name("CoaccessibleSet"); 01868 return coaccessibleset; 01869 } 01870 01871 // Coaccessible() 01872 bool vGenerator::Coaccessible(void) { 01873 StateSet coaccessibleset = CoaccessibleSet(); 01874 StateSet not_coaccessible = *mpStates - coaccessibleset; 01875 DelStates(not_coaccessible); 01876 // return true if there is a marked state 01877 if (! mMarkedStates.Empty()) { 01878 FD_DF("vGenerator::coaccessible: generator is coaccessible"); 01879 return true; 01880 } 01881 else { 01882 FD_DF("vGenerator::coaccessible: generator is not coaccessible"); 01883 return false; 01884 } 01885 } 01886 01887 // IsCoaccessible() 01888 bool vGenerator::IsCoaccessible(void) const { 01889 if (CoaccessibleSet() == *mpStates) { 01890 FD_DF("vGenerator::coaccessible: generator is coaccessible"); 01891 return true; 01892 } 01893 else { 01894 FD_DF("vGenerator::coaccessible: generator is not coaccessible"); 01895 return false; 01896 } 01897 } 01898 01899 // TrimSet() 01900 StateSet vGenerator::TrimSet(void) const { 01901 FD_DF("vGenerator::trimset: trim states: " 01902 << StateSet(AccessibleSet() * CoaccessibleSet()).ToString()); 01903 StateSet res=AccessibleSet() * CoaccessibleSet(); 01904 res.Name("TrimSet"); 01905 return res; 01906 } 01907 01908 // Trim() 01909 bool vGenerator::Trim(void) { 01910 FD_DF("vGenerator::trim: generator states: " << mpStates->ToString()); 01911 // better: compute sets and do one state delete 01912 bool accessiblebool = Accessible(); 01913 bool coaccessiblebool = Coaccessible(); 01914 FD_DF("vGenerator::trim: trim states: " << mpStates->ToString()); 01915 if (accessiblebool && coaccessiblebool) { 01916 FD_DF("vGenerator::Trim(): generator is nontrivial"); 01917 return true; 01918 } 01919 FD_DF("vGenerator::Trim(): generator is trivial"); 01920 return false; 01921 } 01922 01923 01924 // IsTrim() 01925 bool vGenerator::IsTrim(void) const { 01926 bool res=true; 01927 if(!IsAccessible()) res=false; 01928 else if(!IsCoaccessible()) res=false; 01929 FD_DF("vGenerator::IsTrim(): result " << res); 01930 return res; 01931 } 01932 01933 01934 // BlockingStates() 01935 StateSet vGenerator::BlockingStates(void) const { 01936 FD_DF("vGenerator::BlockingSet: blocking states: " 01937 << StateSet(AccessibleSet() - CoaccessibleSet()).ToString()); 01938 return AccessibleSet() - CoaccessibleSet(); 01939 } 01940 01941 01942 01943 // IsComplete 01944 bool vGenerator::IsComplete(const StateSet& rStates) const { 01945 FD_DG("IsComplete(" << Name() << ")"); 01946 01947 // loop over provided states 01948 StateSet::Iterator sit=rStates.Begin(); 01949 StateSet::Iterator sit_end=rStates.End(); 01950 for(;sit!=sit_end;sit++){ 01951 TransSet::Iterator tit=TransRelBegin(*sit); 01952 TransSet::Iterator tit_end=TransRelEnd(*sit); 01953 if(tit==tit_end) break; 01954 } 01955 // return true if no terminal state has been found 01956 return sit==sit_end; 01957 } 01958 01959 // IsComplete 01960 bool vGenerator::IsComplete(void) const { 01961 return IsComplete(States()); 01962 } 01963 01964 // Complete 01965 bool vGenerator::Complete(void) { 01966 // states to remove 01967 StateSet termset = TerminalStates(); 01968 // iterative search ... 01969 bool done; 01970 do { 01971 // ... over all states 01972 StateSet::Iterator sit = States().Begin(); 01973 StateSet::Iterator sit_end = States().End(); 01974 done=true; 01975 for(; sit!=sit_end; ++sit) { 01976 if(termset.Exists(*sit)) continue; 01977 TransSet::Iterator tit = TransRelBegin(*sit); 01978 TransSet::Iterator tit_end = TransRelEnd(*sit); 01979 for (; tit != tit_end; ++tit) { 01980 if(!termset.Exists(tit->X2)) break; 01981 } 01982 if(tit==tit_end) { 01983 termset.Insert(*sit); 01984 done=false; 01985 } 01986 } 01987 } while(!done); 01988 // remove those states 01989 DelStates(termset); 01990 // done 01991 return !InitStates().Empty(); 01992 } 01993 01994 01995 // TerminalStates() 01996 StateSet vGenerator::TerminalStates(const StateSet& rStates) const { 01997 FD_DG("Generator::TerminalStates(" << Name() << ")"); 01998 01999 // prepare result 02000 StateSet res; 02001 02002 // loop states 02003 StateSet::Iterator sit=rStates.Begin(); 02004 StateSet::Iterator sit_end=rStates.End(); 02005 for(;sit!=sit_end;sit++){ 02006 TransSet::Iterator tit=TransRelBegin(*sit); 02007 TransSet::Iterator tit_end=TransRelEnd(*sit); 02008 if(tit==tit_end) res.Insert(*sit); 02009 } 02010 // return terminal states 02011 res.Name("TerminalStates"); 02012 return res; 02013 } 02014 02015 // TerminalStates() 02016 StateSet vGenerator::TerminalStates(void) const { 02017 return TerminalStates(States()); 02018 } 02019 02020 02021 // OmegaTrim 02022 bool vGenerator::OmegaTrim(void) { 02023 02024 // note: this really is inefficient; at least we should 02025 // record the inverse transition relation for the coaccessile 02026 // iteration 02027 02028 // first we make the generator accessible 02029 Accessible(); 02030 // iterate coaccessible and complete until convergence in oserved 02031 while(1) { 02032 Idx osize=States().Size(); 02033 Coaccessible(); 02034 Complete(); 02035 if(States().Size()==osize) break; 02036 } 02037 // done 02038 return !InitStates().Empty() && !MarkedStates().Empty(); 02039 } 02040 02041 02042 // IsOmegaTrim() 02043 bool vGenerator::IsOmegaTrim(void) const { 02044 bool res=true; 02045 if(!IsAccessible()) res=false; 02046 else if(!IsCoaccessible()) res=false; 02047 else if(!IsComplete()) res=false; 02048 FD_DF("vGenerator::IsOmegaTrim(): result " << res); 02049 return res; 02050 } 02051 02052 02053 02054 // IsDeterministic() 02055 bool vGenerator::IsDeterministic(void) const { 02056 // if there is more than one initial state ... nondet 02057 if (InitStatesSize() != 1) { 02058 FD_DG("vGenerator::IsDeterministic: number of initial states not 1"); 02059 return false; 02060 } 02061 // if there is a state/event pair with non-unique successor ... nondet 02062 if (TransRelSize() < 2) return true; 02063 TransSet::Iterator it1; 02064 TransSet::Iterator it2; 02065 for (it1 = TransRelBegin(), it2 = it1++; it1 != TransRelEnd(); it2 = it1++) { 02066 if ((it1->X1 == it2->X1) && (it1->Ev == it2->Ev)) { 02067 FD_WP("IsDeterministic: nondeterministic generator. at least one state " 02068 << "contains more than on transition with same event: " 02069 << SStr(it1->X1) << ", event " << EStr(it1->Ev)); 02070 return false; 02071 } 02072 } 02073 // in all other cases generator is deterministic 02074 return true; 02075 } 02076 02077 // DoWrite() 02078 void vGenerator::DoWrite(TokenWriter& rTw, const std::string& rLabel, const Type* pContext) const { 02079 (void) pContext; 02080 // figure section 02081 std::string label=rLabel; 02082 if(label=="") label="Generator"; 02083 FD_DG("vGenerator(" << this << ")::DoWrite(): section " << label); 02084 // reindex for file output 02085 if(rTw.DestMode()==TokenWriter::File) SetMinStateIndexMap(); 02086 // write generator 02087 rTw.WriteBegin(label); 02088 rTw << mMyName; 02089 rTw << "\n"; 02090 rTw << "\n"; 02091 SWrite(rTw); 02092 rTw << "\n"; 02093 mpAlphabet->Write(rTw); 02094 rTw << "\n"; 02095 WriteStateSet(rTw, *mpStates); 02096 rTw << "\n"; 02097 WriteTransRel(rTw); 02098 rTw << "\n"; 02099 WriteStateSet(rTw, mInitStates); 02100 rTw << "\n"; 02101 WriteStateSet(rTw, mMarkedStates); 02102 rTw << "\n"; 02103 mpGlobalAttribute->Write(rTw); 02104 rTw << "\n"; 02105 rTw.WriteEnd(label); 02106 // end of reindex 02107 ClearMinStateIndexMap(); 02108 } 02109 02110 // DoDWrite() 02111 void vGenerator::DoDWrite(TokenWriter& rTw, const std::string& rLabel, const Type* pContext) const { 02112 (void) pContext; 02113 // figure section 02114 std::string label=rLabel; 02115 if(label=="") label="Generator"; 02116 FD_DG("vGenerator(" << this << ")::DoDWrite(): section " << label); 02117 // write generator 02118 rTw.WriteBegin(label); 02119 rTw << mMyName; 02120 rTw << "\n"; 02121 rTw << "\n"; 02122 SWrite(rTw); 02123 rTw << "\n"; 02124 mpAlphabet->DWrite(rTw); 02125 rTw << "\n"; 02126 DWriteStateSet(rTw, *mpStates); 02127 rTw << "\n"; 02128 DWriteTransRel(rTw); 02129 rTw << "\n"; 02130 DWriteStateSet(rTw, mInitStates); 02131 rTw << "\n"; 02132 DWriteStateSet(rTw, mMarkedStates); 02133 rTw << "\n"; 02134 mpGlobalAttribute->Write(rTw); 02135 rTw << "\n"; 02136 rTw.WriteEnd(label); 02137 rTw << "\n"; 02138 } 02139 02140 // WriteAlphabet() 02141 void vGenerator::WriteAlphabet(void) const { 02142 TokenWriter tw(TokenWriter::Stdout); 02143 WriteAlphabet(tw); 02144 } 02145 02146 // AlphabetToString() 02147 std::string vGenerator::AlphabetToString(void) const { 02148 TokenWriter tw(TokenWriter::String); 02149 WriteAlphabet(tw); 02150 return tw.Str(); 02151 } 02152 02153 // WriteAlphabet(rTw&) 02154 void vGenerator::WriteAlphabet(TokenWriter& rTw) const { 02155 mpAlphabet->Write(rTw); 02156 } 02157 02158 // WriteStateSet(rStateSet&) 02159 void vGenerator::WriteStateSet(const StateSet& rStateSet) const { 02160 TokenWriter tw(TokenWriter::Stdout); 02161 WriteStateSet(tw,rStateSet); 02162 } 02163 02164 // StateSetToString() 02165 std::string vGenerator::StateSetToString(const StateSet& rStateSet) const { 02166 TokenWriter tw(TokenWriter::String); 02167 WriteStateSet(tw,rStateSet); 02168 return tw.Str(); 02169 } 02170 02171 // StateSetToText() 02172 std::string vGenerator::StateSetToText(const StateSet& rStateSet) const { 02173 TokenWriter tw(TokenWriter::String); 02174 tw.Endl(true); 02175 WriteStateSet(tw,rStateSet); 02176 return tw.Str(); 02177 } 02178 02179 02180 // WriteStateSet(rTw&, rStateSet&) 02181 void vGenerator::WriteStateSet(TokenWriter& rTw, const StateSet& rStateSet) const { 02182 rTw.WriteBegin(rStateSet.Name()); 02183 // build reverse index map of states to write ( fileidx->idx ) 02184 // (this ensures named states to be written first; see SetMinStateIndexMap()) 02185 std::map<Idx,Idx> reversemap; 02186 std::map<Idx,Idx>::const_iterator minit; 02187 StateSet::Iterator sit; 02188 for (sit = rStateSet.Begin(); sit != rStateSet.End(); ++sit) { 02189 reversemap[MinStateIndex(*sit)] = *sit; 02190 } 02191 // iterate states to write 02192 for(minit = reversemap.begin(); minit != reversemap.end(); ++minit) { 02193 // identify anonymous block (consecutive state indices) 02194 std::map<Idx,Idx>::const_iterator conit=minit; 02195 Idx start = conit->first; 02196 Idx anoncount = 0; 02197 for(; conit != reversemap.end(); ++conit) { 02198 if(StateName(conit->second) != "") break; 02199 if(!StateAttribute(conit->second).IsDefault()) break; 02200 if(conit->first != start+anoncount) break; 02201 ++anoncount; 02202 } 02203 // write anonymous block 02204 if (anoncount > FD_CONSECUTIVE) { 02205 rTw.WriteBegin("Consecutive"); 02206 rTw << start; 02207 rTw << start+anoncount-1; 02208 rTw.WriteEnd("Consecutive"); 02209 minit=conit; 02210 } 02211 // break loop 02212 if(minit == reversemap.end() ) 02213 break; 02214 // write non anonymous state name/idx 02215 std::string statename = StateName(minit->second); 02216 if (statename != "") { 02217 rTw << statename; 02218 } else { 02219 rTw << minit->first; 02220 } 02221 // write state attribute 02222 const AttributeVoid& attr=rStateSet.Attribute(minit->second); 02223 attr.Write(rTw); 02224 } 02225 rTw.WriteEnd(rStateSet.Name()); 02226 } 02227 02228 02229 // DWriteStateSet(rTw&, rStateSet&) 02230 void vGenerator::DWriteStateSet(TokenWriter& rTw, const StateSet& rStateSet) const { 02231 rTw.WriteBegin(rStateSet.Name()); 02232 StateSet::Iterator lit; 02233 std::map<Idx,Idx>::const_iterator minit; 02234 for(lit = rStateSet.Begin(); lit != rStateSet.End(); ++lit) { 02235 rTw << SStr(*lit); 02236 const AttributeVoid& attr=rStateSet.Attribute(*lit); 02237 attr.Write(rTw); 02238 } 02239 rTw.WriteEnd(rStateSet.Name()); 02240 } 02241 02242 02243 // StatesToString() 02244 std::string vGenerator::StatesToString(void) const { 02245 return StateSetToString(*mpStates); 02246 } 02247 02248 // StatesToText() 02249 std::string vGenerator::StatesToText(void) const { 02250 return StateSetToText(*mpStates); 02251 } 02252 02253 // MarkedStatesToString() 02254 std::string vGenerator::MarkedStatesToString(void) const { 02255 return StateSetToString(mMarkedStates); 02256 } 02257 02258 // InitStatesToString() 02259 std::string vGenerator::InitStatesToString(void) const { 02260 return StateSetToString(mInitStates); 02261 } 02262 02263 02264 // WriteTransRel() 02265 void vGenerator::WriteTransRel(void) const { 02266 TokenWriter tw(TokenWriter::Stdout); 02267 WriteTransRel(tw); 02268 } 02269 02270 // TransRelToString() 02271 std::string vGenerator::TransRelToString(void) const { 02272 TokenWriter tw(TokenWriter::String); 02273 WriteTransRel(tw); 02274 return tw.Str(); 02275 } 02276 02277 // TransRelToText() 02278 std::string vGenerator::TransRelToText(void) const { 02279 TokenWriter tw(TokenWriter::String); 02280 tw.Endl(true); 02281 WriteTransRel(tw); 02282 return tw.Str(); 02283 } 02284 02285 // WriteTransRel(rTw&) 02286 void vGenerator::WriteTransRel(TokenWriter& rTw) const { 02287 TransSet::Iterator tit; 02288 int oldcolumns = rTw.Columns(); 02289 rTw.Columns(3); 02290 rTw.WriteBegin("TransRel"); 02291 bool smalltransrel = (Size() < FD_SMALLTRANSREL); 02292 02293 // loop all transitions 02294 for(tit = mpTransRel->Begin(); tit != mpTransRel->End(); ++tit) { 02295 02296 // write x1 02297 Idx x1=MinStateIndex(tit->X1); 02298 if (smalltransrel) { 02299 std::string x1name = StateName(tit->X1); 02300 if (x1name != "") { 02301 rTw << x1name; 02302 } else { 02303 rTw << x1; 02304 } 02305 } else { 02306 rTw << x1; 02307 } 02308 02309 // write ev 02310 rTw << EventName(tit->Ev); 02311 02312 // write x2 02313 Idx x2=MinStateIndex(tit->X2); 02314 if (smalltransrel) { 02315 std::string x2name = StateName(tit->X2); 02316 if (x2name != "") { 02317 rTw << x2name; 02318 } else { 02319 rTw << x2; 02320 } 02321 } else { 02322 rTw << x2; 02323 } 02324 02325 // write attributes 02326 TransAttribute(*tit).Write(rTw); 02327 02328 } 02329 rTw.WriteEnd("TransRel"); 02330 rTw.Columns(oldcolumns); 02331 } 02332 02333 // DWriteTransRel(rTw&) 02334 void vGenerator::DWriteTransRel(TokenWriter& rTw) const { 02335 TransSet::Iterator tit; 02336 int oldcolumns = rTw.Columns(); 02337 rTw.Columns(1); 02338 rTw.WriteBegin("TransRel"); 02339 for (tit = mpTransRel->Begin(); tit != mpTransRel->End(); ++tit) { 02340 rTw << TStr(*tit); 02341 mpTransRel->Attribute(*tit).Write(rTw); 02342 } 02343 rTw.WriteEnd("TransRel"); 02344 rTw.Columns(oldcolumns); 02345 } 02346 02347 02348 // DoSWrite(rTw&) 02349 void vGenerator::DoSWrite(TokenWriter& rTw) const 02350 { 02351 Type::DoSWrite(rTw); 02352 rTw.WriteComment(" States: " + ToStringInteger(Size()) ); 02353 rTw.WriteComment(" Init/Marked: " + ToStringInteger(mInitStates.Size()) 02354 + "/" + ToStringInteger(mMarkedStates.Size())); 02355 rTw.WriteComment(" Events: " + ToStringInteger(mpAlphabet->Size()) ); 02356 rTw.WriteComment(" Transitions: " + ToStringInteger(mpTransRel->Size()) ); 02357 rTw.WriteComment(" StateSymbols: " + ToStringInteger(mpStateSymbolTable->Size()) ); 02358 rTw.WriteComment(" Attrib. E/S/T: " + ToStringInteger(mpAlphabet->AttributesSize()) 02359 + "/" + ToStringInteger(mpStates->AttributesSize()) 02360 + "/" + ToStringInteger(mpTransRel->AttributesSize()) ); 02361 rTw.WriteComment(""); 02362 } 02363 02364 // DotWrite(rFileName) 02365 void vGenerator::DotWrite(const std::string& rFileName) const { 02366 FD_DG("vGenerator(" << this << ")::DotWrite(" << rFileName << ")"); 02367 SetMinStateIndexMap(); 02368 StateSet::Iterator lit; 02369 TransSet::Iterator tit; 02370 try { 02371 std::ofstream stream; 02372 stream.exceptions(std::ios::badbit|std::ios::failbit); 02373 stream.open(rFileName.c_str()); 02374 stream << "// dot output generated by libFAUDES vGenerator" << std::endl; 02375 stream << "digraph \"" << Name() << "\" {" << std::endl; 02376 stream << " rankdir=LR" << std::endl; 02377 stream << " node [shape=circle];" << std::endl; 02378 stream << std::endl; 02379 stream << " // initial states" << std::endl; 02380 int i = 1; 02381 for (lit = InitStatesBegin(); lit != InitStatesEnd(); ++lit) { 02382 std::string xname= StateName(*lit); 02383 if(xname=="") xname=ToStringInteger(MinStateIndex(*lit)); 02384 stream << " dot_dummyinit_" << i << " [shape=none, label=\"\" ];" << std::endl; 02385 stream << " dot_dummyinit_" << i << " -> \"" << xname << "\";" << std::endl; 02386 i++; 02387 } 02388 stream << std::endl; 02389 stream << " // mstates" << std::endl; 02390 for (lit = MarkedStatesBegin(); lit != MarkedStatesEnd(); ++lit) { 02391 std::string xname= StateName(*lit); 02392 if(xname=="") xname=ToStringInteger(MinStateIndex(*lit)); 02393 stream << " \"" << xname << "\" [shape=doublecircle];" << std::endl; 02394 } 02395 stream << std::endl; 02396 stream << " // rest of stateset" << std::endl; 02397 for (lit = StatesBegin(); lit != StatesEnd(); ++lit) { 02398 if (! (ExistsInitState(*lit) || ExistsMarkedState(*lit)) ) { 02399 std::string xname= StateName(*lit); 02400 if(xname=="") xname=ToStringInteger(MinStateIndex(*lit)); 02401 stream << " \"" << xname << "\";" << std::endl; 02402 } 02403 } 02404 stream << std::endl; 02405 stream << " // transition relation" << std::endl; 02406 for(tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 02407 std::string x1name= StateName(tit->X1); 02408 if(x1name=="") x1name=ToStringInteger(MinStateIndex(tit->X1)); 02409 std::string x2name= StateName(tit->X2); 02410 if(x2name=="") x2name=ToStringInteger(MinStateIndex(tit->X2)); 02411 stream << " \"" << x1name << "\" -> \"" << x2name 02412 << "\" [label=\"" << EventName(tit->Ev) << "\"];" << std::endl; 02413 } 02414 stream << "};" << std::endl; 02415 stream.close(); 02416 } 02417 catch (std::ios::failure&) { 02418 throw Exception("vGenerator::DotWrite", 02419 "Exception opening/writing dotfile \""+rFileName+"\"", 2); 02420 } 02421 ClearMinStateIndexMap(); 02422 } 02423 02424 // DDotWrite(rFileName) 02425 void vGenerator::DDotWrite(const std::string& rFileName) const { 02426 FD_DG("vGenerator(" << this << ")::DDotWrite(" << rFileName << ")"); 02427 StateSet::Iterator lit; 02428 TransSet::Iterator tit; 02429 try { 02430 std::ofstream stream; 02431 stream.exceptions(std::ios::badbit|std::ios::failbit); 02432 stream.open(rFileName.c_str()); 02433 stream << "digraph \"" << Name() << "\" {" << std::endl; 02434 stream << " rankdir=LR" << std::endl; 02435 stream << " node [shape=circle];" << std::endl; 02436 stream << std::endl; 02437 stream << " // istates" << std::endl; 02438 int i = 1; 02439 for (lit = InitStatesBegin(); lit != InitStatesEnd(); ++lit) { 02440 stream << " dot_dummyinit_" << i << " [shape=none, label=\"\" ];" << std::endl; 02441 stream << " dot_dummyinit_" << i << " -> \"" 02442 << SStr(*lit) << "\";" << std::endl; 02443 i++; 02444 } 02445 stream << std::endl; 02446 stream << " // mstates" << std::endl; 02447 for (lit = MarkedStatesBegin(); lit != MarkedStatesEnd(); ++lit) { 02448 stream << " \"" << SStr(*lit) << "\" [shape=doublecircle];" << std::endl; 02449 } 02450 stream << std::endl; 02451 stream << " // rest of stateset" << std::endl; 02452 for (lit = StatesBegin(); lit != StatesEnd(); ++lit) { 02453 // if not in mInitStates or mMarkedStates 02454 if (! (ExistsInitState(*lit) || ExistsMarkedState(*lit)) ) { 02455 stream << " \"" << SStr(*lit) << "\";" << std::endl; 02456 } 02457 } 02458 stream << std::endl; 02459 stream << " // transition relation" << std::endl; 02460 for (tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 02461 stream << " \"" << SStr(tit->X1) 02462 << "\" -> \"" << SStr(tit->X2) 02463 << "\" [label=\"" << EventName(tit->Ev) << "\"];" << std::endl; 02464 } 02465 stream << "};" << std::endl; 02466 stream.close(); 02467 } 02468 catch (std::ios::failure&) { 02469 throw Exception("vGenerator::DotWrite", 02470 "Exception opening/writing dotfile \""+rFileName+"\"", 2); 02471 } 02472 } 02473 02474 02475 // XDotWrite(rFileName) 02476 void vGenerator::XDotWrite(const std::string& rFileName) const { 02477 FD_DG("vGenerator(" << this << ")::XDotWrite(" << rFileName << ")"); 02478 StateSet::Iterator lit; 02479 TransSet::Iterator tit; 02480 try { 02481 std::ofstream stream; 02482 stream.exceptions(std::ios::badbit|std::ios::failbit); 02483 stream.open(rFileName.c_str()); 02484 stream << "digraph \"___" << Name() << "___\" {" << std::endl; 02485 stream << " rankdir=LR" << std::endl; 02486 stream << " node [shape=circle];" << std::endl; 02487 stream << std::endl; 02488 stream << " // stateset" << std::endl; 02489 for (lit = InitStatesBegin(); lit != InitStatesEnd(); ++lit) { 02490 stream << " \"s" << *lit << "\";" << std::endl; 02491 } 02492 for (lit = MarkedStatesBegin(); lit != MarkedStatesEnd(); ++lit) { 02493 stream << " \"s" << *lit << "\";" << std::endl; 02494 } 02495 for (lit = StatesBegin(); lit != StatesEnd(); ++lit) { 02496 if(ExistsInitState(*lit)) continue; 02497 if(ExistsMarkedState(*lit)) continue; 02498 stream << " \"s" << *lit << "\";" << std::endl; 02499 } 02500 stream << std::endl; 02501 stream << " // transition relation" << std::endl; 02502 for (tit = TransRelBegin(); tit != TransRelEnd(); ++tit) { 02503 stream << " \"s" << tit->X1 02504 << "\" -> \"s" << tit->X2 02505 << "\" [label=\"e" << tit->Ev << "\" " << "polyline" << "];" << std::endl; 02506 } 02507 stream << "};" << std::endl; 02508 stream.close(); 02509 } 02510 catch (std::ios::failure&) { 02511 throw Exception("vGenerator::XDotWrite", 02512 "Exception opening/writing dotfile \""+rFileName+"\"", 2); 02513 } 02514 } 02515 02516 // DoRead(tr) 02517 void vGenerator::DoRead(TokenReader& rTr, const std::string& rLabel, const Type* pContext) { 02518 (void) pContext; 02519 std::string label=rLabel; 02520 if(label=="") label="Generator"; 02521 FD_DG("vGenerator(" << this << ")::DoRead(): file " << rTr.FileName() << " section " << label); 02522 // Clear old stuff 02523 Clear(); 02524 // find Genertor in any of our current file formats 02525 rTr.SeekBegin(label); 02526 // get the Generator "name" token 02527 ReadGeneratorName(rTr); 02528 // read mAlphabet 02529 ReadAlphabet(rTr); 02530 // read stateset 02531 ReadStates(rTr); 02532 // read transrel 02533 ReadTransRel(rTr); 02534 // read istates 02535 ReadStateSet(rTr, "InitStates", mInitStates); 02536 // read mstates 02537 ReadStateSet(rTr, "MarkedStates", mMarkedStates); 02538 // read attribute 02539 mpGlobalAttribute->Read(rTr); 02540 // skip unknown global attributes 02541 AttributeVoid::Skip(rTr); 02542 // read end 02543 rTr.SeekEnd(label); 02544 FD_DG("vGenerator(" << this << ")::DoRead(): done"); 02545 } 02546 02547 // ReadGeneratorName(rFileName) 02548 void vGenerator::ReadGeneratorName(const std::string& rFileName) { 02549 TokenReader tr(rFileName); 02550 tr.SeekBegin("Generator"); // mimique old behaviour .. use "ReadBegin" instead 02551 ReadGeneratorName(tr); 02552 } 02553 02554 // ReadGeneratorName(tr) 02555 void vGenerator::ReadGeneratorName(TokenReader& rTr) { 02556 FD_DG("vGenerator(" << this << ")::ReadGeneratorName(\"" 02557 << rTr.FileName() << "\")"); 02558 mMyName=rTr.ReadString(); 02559 } 02560 02561 // ReadAlphabet(rFileName) 02562 void vGenerator::ReadAlphabet(const std::string& rFileName) { 02563 FD_DG("vGenerator(" << this << ")::ReadAlphabet(\"" << rFileName << "\")"); 02564 mpAlphabet->Read(rFileName,"Alphabet"); 02565 } 02566 02567 // ReadAlphabet(rTr) 02568 void vGenerator::ReadAlphabet(TokenReader& rTr) { 02569 FD_DG("vGenerator(" << this << ")::ReadAlphabet(\"" 02570 << rTr.FileName() << "\")"); 02571 mpAlphabet->Read(rTr,"Alphabet"); 02572 } 02573 02574 // ReadStates(rFileName) 02575 void vGenerator::ReadStates(const std::string& rFileName) { 02576 TokenReader tr(rFileName); 02577 ReadStates(tr); 02578 } 02579 02580 // ReadStates(tr) 02581 void vGenerator::ReadStates(TokenReader& rTr) { 02582 FD_DG("vGenerator(" << this << ")::ReadStates(\"" << rTr.FileName() << "\")"); 02583 // HELPERS: 02584 Token token; 02585 AttributeVoid* attrp = mpStates->Attribute().New(); 02586 FD_DG("vGenerator(" << this << ")::ReadStates(..): attribute type " << typeid(*attrp).name()); 02587 // ALGORITHM: 02588 mpStates->Clear(); 02589 mpStates->Name("States"); 02590 mStateSymbolTable.Clear(); 02591 rTr.SeekBegin("States"); 02592 while(rTr.Peek(token)) { 02593 // break end of section 02594 if (token.Type() == Token::End) { 02595 break; 02596 } 02597 // read state by index 02598 if (token.Type() == Token::Integer) { 02599 rTr.Get(token); 02600 Idx index = token.IntegerValue(); 02601 FD_DG("vGenerator(" << this << ")::ReadStates(\"" << rTr.FileName() << "\"): by index " << index); 02602 if(mpStates->Exists(index)) { 02603 delete attrp; 02604 std::stringstream errstr; 02605 errstr << "Token " << token.IntegerValue() << " appears twice in stateset" 02606 << rTr.FileLine(); 02607 throw Exception("vGenerator::ReadStates", errstr.str(), 80); 02608 } 02609 // read attribute 02610 attrp->Read(rTr,"",this); 02611 // skip unknown attributes 02612 AttributeVoid::Skip(rTr); 02613 // insert element with attribute 02614 InsState(index); 02615 StateAttribute(index,*attrp); 02616 continue; 02617 } 02618 // read state by name 02619 if (token.Type() == Token::String) { 02620 rTr.Get(token); 02621 FD_DG("vGenerator(" << this << ")::ReadStates(\"" << rTr.FileName() << "\"): by name " << token.StringValue()); 02622 if(ExistsState(token.StringValue())) { 02623 delete attrp; 02624 std::stringstream errstr; 02625 errstr << "Token " << token.StringValue() << " appears twice in stateset" 02626 << rTr.FileLine(); 02627 throw Exception("vGenerator::ReadStates", errstr.str(), 80); 02628 } 02629 // read attribute 02630 attrp->Read(rTr,"",this); 02631 // skip unknown attributes 02632 AttributeVoid::Skip(rTr); 02633 // insert element with attribute 02634 Idx index=InsState(token.StringValue()); 02635 StateAttribute(index,*attrp); 02636 continue; 02637 } 02638 // read consecutive block of anonymous states 02639 if (token.Type() == Token::Begin && token.StringValue() == "Consecutive") { 02640 rTr.ReadBegin("Consecutive"); 02641 Token token1,token2; 02642 rTr.Get(token1); 02643 rTr.Get(token2); 02644 FD_DG("vGenerator(" << this << ")::ReadStates(\"" << rTr.FileName() << "\"): consecutive range"); 02645 if ((token1.Type() != Token::Integer) || (token2.Type() != Token::Integer)) { 02646 delete attrp; 02647 std::stringstream errstr; 02648 errstr << "Invalid range of consecutive states" << rTr.FileLine(); 02649 throw Exception("vGenerator::ReadStates", errstr.str(), 80); 02650 } 02651 for(Idx index = (Idx) token1.IntegerValue(); index <= (Idx) token2.IntegerValue(); ++index) { 02652 if(mpStates->Exists(index)) { 02653 delete attrp; 02654 std::stringstream errstr; 02655 errstr << "Index " << index << " appears twice in stateset" 02656 << rTr.FileLine(); 02657 throw Exception("vGenerator::ReadStates", errstr.str(), 80); 02658 } 02659 InsState(index); 02660 } 02661 rTr.ReadEnd("Consecutive"); 02662 continue; 02663 } 02664 // cannot process token 02665 delete attrp; 02666 std::stringstream errstr; 02667 errstr << "Invalid token" << rTr.FileLine(); 02668 throw Exception("vGenerator::ReadStates", errstr.str(), 80); 02669 } 02670 rTr.SeekEnd("States"); 02671 // dispose attribute 02672 delete attrp; 02673 FD_DG("vGenerator(" << this << ")::ReadStates(\"" << rTr.FileName() << "\"): done"); 02674 } 02675 02676 02677 // ReadStateSet(tr, rLabel, rStateSet) 02678 void vGenerator::ReadStateSet(TokenReader& rTr, const std::string& rLabel, StateSet& rStateSet) const { 02679 FD_DG("vGenerator(" << this << ")::ReadStateSet(\"" << rLabel<< "\")"); 02680 // HELPERS: 02681 Token token; 02682 AttributeVoid* attrp = rStateSet.Attribute().New(); 02683 FD_DG("vGenerator(" << this << ")::ReadStateSet(..): attribute type " << typeid(*attrp).name()); 02684 // ALGORITHM: 02685 rStateSet.Clear(); 02686 rTr.SeekBegin(rLabel); 02687 rStateSet.Name(rLabel); 02688 while(rTr.Peek(token)) { 02689 // break end of section 02690 if (token.Type() == Token::End) { 02691 break; 02692 } 02693 // read state by index 02694 if (token.Type() == Token::Integer) { 02695 rTr.Get(token); 02696 Idx index = token.IntegerValue(); 02697 if(!ExistsState(index)) { 02698 delete attrp; 02699 std::stringstream errstr; 02700 errstr << "Token " << token.IntegerValue() << " not in stateset" 02701 << rTr.FileLine(); 02702 throw Exception("vGenerator::ReadStateSet", errstr.str(), 80); 02703 } 02704 // read attribute 02705 attrp->Read(rTr,"",this); 02706 // skip unknown attributes 02707 AttributeVoid::Skip(rTr); 02708 // insert element with attribute 02709 rStateSet.Insert(index); 02710 rStateSet.Attribute(index,*attrp); 02711 continue; 02712 } 02713 // read state by name 02714 if (token.Type() == Token::String) { 02715 rTr.Get(token); 02716 Idx index =StateIndex(token.StringValue()); 02717 if(index==0) { 02718 delete attrp; 02719 std::stringstream errstr; 02720 errstr << "Token " << token.StringValue() << " not in stateset" 02721 << rTr.FileLine(); 02722 throw Exception("vGenerator::ReadStateSet", errstr.str(), 80); 02723 } 02724 // read attribute 02725 attrp->Read(rTr,"",this); 02726 // skip unknown attributes 02727 AttributeVoid::Skip(rTr); 02728 // insert element with attribute 02729 rStateSet.Insert(index); 02730 rStateSet.Attribute(index,*attrp); 02731 continue; 02732 } 02733 // read consecutve block of anonymous states 02734 if (token.Type() == Token::Begin && token.StringValue() == "Consecutive") { 02735 rTr.ReadBegin("Consecutive"); 02736 Token token1,token2; 02737 rTr.Get(token1); 02738 rTr.Get(token2); 02739 if ((token1.Type() != Token::Integer) || (token2.Type() != Token::Integer)) { 02740 delete attrp; 02741 std::stringstream errstr; 02742 errstr << "Invalid range of consecutive states" << rTr.FileLine(); 02743 throw Exception("vGenerator::ReadStateSet", errstr.str(), 80); 02744 } 02745 for(Idx index = (Idx) token1.IntegerValue(); index <= (Idx) token2.IntegerValue(); ++index) { 02746 if(!ExistsState(index)) { 02747 std::stringstream errstr; 02748 errstr << "Token " << token.IntegerValue() << " not in stateset" 02749 << rTr.FileLine(); 02750 throw Exception("vGenerator::ReadStateSet", errstr.str(), 80); 02751 } 02752 rStateSet.Insert(index); 02753 } 02754 rTr.ReadEnd("Consecutive"); 02755 continue; 02756 } 02757 // cannot process token 02758 delete attrp; 02759 std::stringstream errstr; 02760 errstr << "Invalid token" << rTr.FileLine(); 02761 throw Exception("vGenerator::ReadStateSet", errstr.str(), 50); 02762 } 02763 rTr.SeekEnd(rLabel); 02764 // dispose attribute 02765 delete attrp; 02766 } 02767 02768 // ReadTransRel(rFileName) 02769 void vGenerator::ReadTransRel(const std::string& rFileName) { 02770 TokenReader tr(rFileName); 02771 ReadTransRel(tr); 02772 } 02773 02774 // ReadTransRel(tr) 02775 void vGenerator::ReadTransRel(TokenReader& rTr) { 02776 FD_DG("vGenerator(" << this << ")::ReadTransRel(\"" << rTr.FileName() << "\")"); 02777 AttributeVoid* attrp = mpTransRel->Attribute().New(); 02778 FD_DG("vGenerator(" << this << ")::ReadTransRel(..): attribute type " << typeid(*attrp).name()); 02779 try { 02780 Token token; 02781 Idx x1 = 0, ev = 0, x2 = 0; 02782 rTr.SeekBegin("TransRel"); 02783 // Read tokens 02784 while (rTr.Peek(token)) { 02785 // 0: end of transition relation 02786 if ((token.Type() == Token::End)) break; 02787 02788 // 1: the x1 token 02789 rTr >> token; 02790 if (token.Type() == Token::Integer) { 02791 x1=token.IntegerValue(); 02792 } else if (token.Type() == Token::String) { 02793 token.StringValue(); 02794 x1=StateIndex(token.StringValue()); 02795 } else break; 02796 02797 // 2: the event token 02798 rTr >> token; 02799 if (token.Type() == Token::Integer) { 02800 ev=token.IntegerValue(); 02801 } else if (token.Type() == Token::String) { 02802 token.StringValue(); 02803 ev=EventIndex(token.StringValue()); 02804 } else break; 02805 02806 // 3: the x1 token 02807 rTr >> token; 02808 if (token.Type() == Token::Integer) { 02809 x2=token.IntegerValue(); 02810 } else if (token.Type() == Token::String) { 02811 token.StringValue(); 02812 x2=StateIndex(token.StringValue()); 02813 } else break; 02814 02815 // 4: attributes 02816 attrp->Read(rTr,"",this); 02817 02818 // 5: skip unknown attributes 02819 AttributeVoid::Skip(rTr); 02820 02821 // check values 02822 if( (!ExistsState(x1)) || (!ExistsState(x2)) ){ 02823 std::stringstream errstr; 02824 errstr << "invalid state" << rTr.FileLine(); 02825 throw Exception("vGenerator::ReadTransRel", errstr.str(), 85); 02826 } 02827 if(!ExistsEvent(ev)) { 02828 std::stringstream errstr; 02829 errstr << "invalid event" << rTr.FileLine(); 02830 throw Exception("vGenerator::ReadTransRel", errstr.str(), 85); 02831 } 02832 02833 // insert transition 02834 Transition trans=Transition(x1,ev,x2); 02835 SetTransition(trans); 02836 TransAttribute(trans,*attrp); 02837 02838 } // end while 02839 rTr.SeekEnd("TransRel"); 02840 } 02841 catch (faudes::Exception&) { 02842 delete attrp; 02843 std::stringstream errstr; 02844 errstr << "Reading TransRel failed in " << rTr.FileLine(); 02845 throw Exception("vGenerator::ReadTransRel", errstr.str(), 50); 02846 } 02847 FD_DG("vGenerator(" << this << ")::ReadTransRel(\"" << rTr.FileName() << "\"): sone"); 02848 // dispose attribute 02849 delete attrp; 02850 } 02851 02852 02853 // EStr(index) 02854 std::string vGenerator::EStr(Idx index) const { 02855 return EventName(index); 02856 } 02857 02858 // SStr(index) 02859 std::string vGenerator::SStr(Idx index) const { 02860 std::string name = StateName(index); 02861 if(name == "") name=ToStringInteger(index); 02862 return name+"["+faudes::ToStringInteger(index)+"]"; 02863 } 02864 02865 // TStr(index) 02866 std::string vGenerator::TStr(const Transition& trans) const { 02867 return SStr(trans.X1) + "--(" + EStr(trans.Ev) + ")-->" + SStr(trans.X2); 02868 } 02869 02870 02871 // GraphWrite(rFileName,rOutFormat) 02872 void vGenerator::GraphWrite(const std::string& rFileName, const std::string& rOutFormat, 02873 const std::string& rDotExec) const { 02874 FD_DG("vGenerator::GraphWrite(...): " << typeid(*this).name()); 02875 // generate temp dot ibput file 02876 std::string dotin = CreateTempFile(); 02877 if(dotin == "") { 02878 std::stringstream errstr; 02879 errstr << "Exception opening temp file"; 02880 throw Exception("vGenerator::GraphWrite", errstr.str(), 2); 02881 } 02882 try{ 02883 DotWrite(dotin); 02884 } 02885 catch (faudes::Exception& exception) { 02886 RemoveFile(dotin); 02887 std::stringstream errstr; 02888 errstr << "Exception writing dot input file"; 02889 throw Exception("vGenerator::GraphWrite", errstr.str(), 2); 02890 } 02891 try{ 02892 faudes::ProcessDot(dotin,rFileName,rOutFormat,rDotExec); 02893 } 02894 catch (faudes::Exception& exception) { 02895 RemoveFile(dotin); 02896 std::stringstream errstr; 02897 errstr << "Exception processing dot file"; 02898 throw Exception("vGenerator::GraphWrite", errstr.str(), 3); 02899 } 02900 RemoveFile(dotin); 02901 } 02902 02903 // rti wrapper 02904 bool IsAccessible(const vGenerator& rGen) { 02905 return rGen.IsAccessible(); 02906 } 02907 02908 // rti wrapper 02909 bool IsCoaccessible(const vGenerator& rGen) { 02910 return rGen.IsCoaccessible(); 02911 } 02912 02913 // rti wrapper 02914 bool IsTrim(const vGenerator& rGen) { 02915 return rGen.IsTrim(); 02916 } 02917 02918 // rti wrapper 02919 bool IsOmegaTrim(const vGenerator& rGen) { 02920 return rGen.IsOmegaTrim(); 02921 } 02922 02923 // rti wrapper 02924 bool IsComplete(const vGenerator& rGen) { 02925 return rGen.IsComplete(); 02926 } 02927 02928 // rti wrapper 02929 bool IsComplete(const vGenerator& rGen, const StateSet& rStateSet) { 02930 return rGen.IsComplete(rStateSet); 02931 } 02932 02933 // rti wrapper 02934 bool IsDeterministic(const vGenerator& rGen) { 02935 return rGen.IsDeterministic(); 02936 } 02937 02938 02939 // rti wrapper 02940 void Accessible(vGenerator& rGen) { 02941 rGen.Accessible(); 02942 } 02943 02944 // rti wrapper 02945 void Accessible(const vGenerator& rGen, vGenerator& rRes) { 02946 rRes=rGen; 02947 rRes.Accessible(); 02948 } 02949 02950 // rti wrapper 02951 void Coaccessible(vGenerator& rGen) { 02952 rGen.Coaccessible(); 02953 } 02954 02955 // rti wrapper 02956 void Coaccessible(const vGenerator& rGen, vGenerator& rRes) { 02957 rRes=rGen; 02958 rRes.Coaccessible(); 02959 } 02960 02961 // rti wrapper 02962 void Complete(vGenerator& rGen) { 02963 rGen.Complete(); 02964 } 02965 02966 // rti wrapper 02967 void Complete(const vGenerator& rGen, vGenerator& rRes) { 02968 rRes=rGen; 02969 rRes.Complete(); 02970 } 02971 02972 // rti wrapper 02973 void Trim(vGenerator& rGen) { 02974 rGen.Trim(); 02975 } 02976 02977 // rti wrapper 02978 void Trim(const vGenerator& rGen, vGenerator& rRes) { 02979 rRes=rGen; 02980 rRes.Trim(); 02981 } 02982 02983 // rti wrapper 02984 void OmegaTrim(vGenerator& rGen) { 02985 rGen.OmegaTrim(); 02986 } 02987 02988 // rti wrapper 02989 void OmegaTrim(const vGenerator& rGen, vGenerator& rRes) { 02990 rRes=rGen; 02991 rRes.OmegaTrim(); 02992 } 02993 02994 // rti wrapper 02995 void MarkAllStates(vGenerator& rGen) { 02996 rGen.InjectMarkedStates(rGen.States()); 02997 } 02998 02999 } // name space 03000 03001 |
libFAUDES 2.16b --- 2010-9-8 --- c++ source docu by doxygen 1.6.3