1*16467b97STreehugger RobotANTLR_BEGIN_NAMESPACE() 2*16467b97STreehugger Robot 3*16467b97STreehugger Robottemplate<class ImplTraits> 4*16467b97STreehugger RobotANTLR_INLINE CommonTreeAdaptor<ImplTraits>::CommonTreeAdaptor(DebuggerType*) 5*16467b97STreehugger Robot{ 6*16467b97STreehugger Robot} 7*16467b97STreehugger Robot 8*16467b97STreehugger Robottemplate<class ImplTraits> 9*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::nilNode() 10*16467b97STreehugger Robot{ 11*16467b97STreehugger Robot return this->create(NULL); 12*16467b97STreehugger Robot} 13*16467b97STreehugger Robot 14*16467b97STreehugger Robottemplate<class ImplTraits> 15*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::dupTree( TreeType* tree) 16*16467b97STreehugger Robot{ 17*16467b97STreehugger Robot return this->dupTreeTT(tree, NULL); 18*16467b97STreehugger Robot} 19*16467b97STreehugger Robot 20*16467b97STreehugger Robottemplate<class ImplTraits> 21*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::dupTreeTT( TreeType* t, TreeType* parent) 22*16467b97STreehugger Robot{ 23*16467b97STreehugger Robot TreeType* newTree; 24*16467b97STreehugger Robot TreeType* child; 25*16467b97STreehugger Robot TreeType* newSubTree; 26*16467b97STreehugger Robot ANTLR_UINT32 n; 27*16467b97STreehugger Robot ANTLR_UINT32 i; 28*16467b97STreehugger Robot 29*16467b97STreehugger Robot if (t == NULL) 30*16467b97STreehugger Robot return NULL; 31*16467b97STreehugger Robot 32*16467b97STreehugger Robot newTree = t->dupNode(); 33*16467b97STreehugger Robot 34*16467b97STreehugger Robot // Ensure new subtree root has parent/child index set 35*16467b97STreehugger Robot // 36*16467b97STreehugger Robot this->setChildIndex( newTree, t->getChildIndex() ); 37*16467b97STreehugger Robot this->setParent(newTree, parent); 38*16467b97STreehugger Robot n = this->getChildCount(t); 39*16467b97STreehugger Robot 40*16467b97STreehugger Robot for (i=0; i < n; i++) 41*16467b97STreehugger Robot { 42*16467b97STreehugger Robot child = this->getChild(t, i); 43*16467b97STreehugger Robot newSubTree = this->dupTreeTT(child, t); 44*16467b97STreehugger Robot this->addChild(newTree, newSubTree); 45*16467b97STreehugger Robot } 46*16467b97STreehugger Robot return newTree; 47*16467b97STreehugger Robot} 48*16467b97STreehugger Robot 49*16467b97STreehugger Robottemplate<class ImplTraits> 50*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::addChild( TreeType* t, TreeType* child) 51*16467b97STreehugger Robot{ 52*16467b97STreehugger Robot if (t != NULL && child != NULL) 53*16467b97STreehugger Robot { 54*16467b97STreehugger Robot t->addChild(child); 55*16467b97STreehugger Robot } 56*16467b97STreehugger Robot} 57*16467b97STreehugger Robot 58*16467b97STreehugger Robottemplate<class ImplTraits> 59*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::addChildToken( TreeType* t, CommonTokenType* child) 60*16467b97STreehugger Robot{ 61*16467b97STreehugger Robot if (t != NULL && child != NULL) 62*16467b97STreehugger Robot { 63*16467b97STreehugger Robot this->addChild(t, this->create(child)); 64*16467b97STreehugger Robot } 65*16467b97STreehugger Robot} 66*16467b97STreehugger Robot 67*16467b97STreehugger Robottemplate<class ImplTraits> 68*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::setParent( TreeType* child, TreeType* parent) 69*16467b97STreehugger Robot{ 70*16467b97STreehugger Robot child->setParent(parent); 71*16467b97STreehugger Robot} 72*16467b97STreehugger Robot 73*16467b97STreehugger Robottemplate<class ImplTraits> 74*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::getParent( TreeType* child) 75*16467b97STreehugger Robot{ 76*16467b97STreehugger Robot return child->getParent(); 77*16467b97STreehugger Robot} 78*16467b97STreehugger Robot 79*16467b97STreehugger Robottemplate<class ImplTraits> 80*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::errorNode( CommonTokenType* tnstream, CommonTokenType* startToken, CommonTokenType* stopToken) 81*16467b97STreehugger Robot{ 82*16467b97STreehugger Robot // Use the supplied common tree node stream to get another tree from the factory 83*16467b97STreehugger Robot // TODO: Look at creating the erronode as in Java, but this is complicated by the 84*16467b97STreehugger Robot // need to track and free the memory allocated to it, so for now, we just 85*16467b97STreehugger Robot // want something in the tree that isn't a NULL pointer. 86*16467b97STreehugger Robot // 87*16467b97STreehugger Robot return this->createTypeText( CommonTokenType::TOKEN_INVALID, "Tree Error Node"); 88*16467b97STreehugger Robot 89*16467b97STreehugger Robot} 90*16467b97STreehugger Robot 91*16467b97STreehugger Robottemplate<class ImplTraits> 92*16467b97STreehugger Robotbool CommonTreeAdaptor<ImplTraits>::isNilNode( TreeType* t) 93*16467b97STreehugger Robot{ 94*16467b97STreehugger Robot return t->isNilNode(); 95*16467b97STreehugger Robot} 96*16467b97STreehugger Robot 97*16467b97STreehugger Robottemplate<class ImplTraits> 98*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::becomeRoot( TreeType* newRootTree, TreeType* oldRootTree) 99*16467b97STreehugger Robot{ 100*16467b97STreehugger Robot TreeType* saveRoot; 101*16467b97STreehugger Robot 102*16467b97STreehugger Robot /* Protect against tree rewrites if we are in some sort of error 103*16467b97STreehugger Robot * state, but have tried to recover. In C we can end up with a null pointer 104*16467b97STreehugger Robot * for a tree that was not produced. 105*16467b97STreehugger Robot */ 106*16467b97STreehugger Robot if (newRootTree == NULL) 107*16467b97STreehugger Robot { 108*16467b97STreehugger Robot return oldRootTree; 109*16467b97STreehugger Robot } 110*16467b97STreehugger Robot 111*16467b97STreehugger Robot /* root is just the new tree as is if there is no 112*16467b97STreehugger Robot * current root tree. 113*16467b97STreehugger Robot */ 114*16467b97STreehugger Robot if (oldRootTree == NULL) 115*16467b97STreehugger Robot { 116*16467b97STreehugger Robot return newRootTree; 117*16467b97STreehugger Robot } 118*16467b97STreehugger Robot 119*16467b97STreehugger Robot /* Produce ^(nil real-node) 120*16467b97STreehugger Robot */ 121*16467b97STreehugger Robot if (newRootTree->isNilNode()) 122*16467b97STreehugger Robot { 123*16467b97STreehugger Robot if (newRootTree->getChildCount() > 1) 124*16467b97STreehugger Robot { 125*16467b97STreehugger Robot /* TODO: Handle tree exceptions 126*16467b97STreehugger Robot */ 127*16467b97STreehugger Robot fprintf(stderr, "More than one node as root! TODO: Create tree exception handling\n"); 128*16467b97STreehugger Robot return newRootTree; 129*16467b97STreehugger Robot } 130*16467b97STreehugger Robot 131*16467b97STreehugger Robot /* The new root is the first child, keep track of the original newRoot 132*16467b97STreehugger Robot * because if it was a Nil Node, then we can reuse it now. 133*16467b97STreehugger Robot */ 134*16467b97STreehugger Robot saveRoot = newRootTree; 135*16467b97STreehugger Robot newRootTree = newRootTree->getChild(0); 136*16467b97STreehugger Robot 137*16467b97STreehugger Robot // Reclaim the old nilNode() 138*16467b97STreehugger Robot // 139*16467b97STreehugger Robot saveRoot->reuse(); 140*16467b97STreehugger Robot } 141*16467b97STreehugger Robot 142*16467b97STreehugger Robot /* Add old root into new root. addChild takes care of the case where oldRoot 143*16467b97STreehugger Robot * is a flat list (nill rooted tree). All children of oldroot are added to 144*16467b97STreehugger Robot * new root. 145*16467b97STreehugger Robot */ 146*16467b97STreehugger Robot newRootTree->addChild(oldRootTree); 147*16467b97STreehugger Robot 148*16467b97STreehugger Robot // If the oldroot tree was a nil node, then we know at this point 149*16467b97STreehugger Robot // it has become orphaned by the rewrite logic, so we tell it to do 150*16467b97STreehugger Robot // whatever it needs to do to be reused. 151*16467b97STreehugger Robot // 152*16467b97STreehugger Robot if (oldRootTree->isNilNode()) 153*16467b97STreehugger Robot { 154*16467b97STreehugger Robot // We have taken an old Root Tree and appended all its children to the new 155*16467b97STreehugger Robot // root. In addition though it was a nil node, which means the generated code 156*16467b97STreehugger Robot // will not reuse it again, so we will reclaim it here. First we want to zero out 157*16467b97STreehugger Robot // any pointers it was carrying around. We are just the baseTree handler so we 158*16467b97STreehugger Robot // don't know necessarilly know how to do this for the real node, we just ask the tree itself 159*16467b97STreehugger Robot // to do it. 160*16467b97STreehugger Robot // 161*16467b97STreehugger Robot oldRootTree->reuse(); 162*16467b97STreehugger Robot } 163*16467b97STreehugger Robot /* Always returns new root structure 164*16467b97STreehugger Robot */ 165*16467b97STreehugger Robot return newRootTree; 166*16467b97STreehugger Robot} 167*16467b97STreehugger Robot 168*16467b97STreehugger Robottemplate<class ImplTraits> 169*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::becomeRootToken(CommonTokenType* newRoot, TreeType* oldRoot) 170*16467b97STreehugger Robot{ 171*16467b97STreehugger Robot return this->becomeRoot(this->create(newRoot), oldRoot); 172*16467b97STreehugger Robot} 173*16467b97STreehugger Robot 174*16467b97STreehugger Robottemplate<class ImplTraits> 175*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::create( CommonTokenType* payload) 176*16467b97STreehugger Robot{ 177*16467b97STreehugger Robot return new TreeType(payload); 178*16467b97STreehugger Robot} 179*16467b97STreehugger Robot 180*16467b97STreehugger Robottemplate<class ImplTraits> 181*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::createTypeToken( ANTLR_UINT32 tokenType, 182*16467b97STreehugger Robot CommonTokenType* fromToken) 183*16467b97STreehugger Robot{ 184*16467b97STreehugger Robot /* Create the new token 185*16467b97STreehugger Robot */ 186*16467b97STreehugger Robot fromToken = this->createTokenFromToken(fromToken); 187*16467b97STreehugger Robot 188*16467b97STreehugger Robot /* Set the type of the new token to that supplied 189*16467b97STreehugger Robot */ 190*16467b97STreehugger Robot fromToken->setType(tokenType); 191*16467b97STreehugger Robot 192*16467b97STreehugger Robot /* Return a new node based upon this token 193*16467b97STreehugger Robot */ 194*16467b97STreehugger Robot return this->create(fromToken); 195*16467b97STreehugger Robot 196*16467b97STreehugger Robot} 197*16467b97STreehugger Robot 198*16467b97STreehugger Robottemplate<class ImplTraits> 199*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::createTypeTokenText( ANTLR_UINT32 tokenType, CommonTokenType* fromToken, const ANTLR_UINT8* text) 200*16467b97STreehugger Robot{ 201*16467b97STreehugger Robot /* Create the new token 202*16467b97STreehugger Robot */ 203*16467b97STreehugger Robot fromToken = this->createTokenFromToken(fromToken); 204*16467b97STreehugger Robot 205*16467b97STreehugger Robot /* Set the type of the new token to that supplied 206*16467b97STreehugger Robot */ 207*16467b97STreehugger Robot fromToken->setType(tokenType); 208*16467b97STreehugger Robot 209*16467b97STreehugger Robot /* Set the text of the token accordingly 210*16467b97STreehugger Robot */ 211*16467b97STreehugger Robot fromToken->setText(text); 212*16467b97STreehugger Robot 213*16467b97STreehugger Robot /* Return a new node based upon this token 214*16467b97STreehugger Robot */ 215*16467b97STreehugger Robot return this->create(fromToken); 216*16467b97STreehugger Robot} 217*16467b97STreehugger Robot 218*16467b97STreehugger Robottemplate<class ImplTraits> 219*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::createTypeText( ANTLR_UINT32 tokenType, const ANTLR_UINT8* text) 220*16467b97STreehugger Robot{ 221*16467b97STreehugger Robot CommonTokenType* fromToken; 222*16467b97STreehugger Robot 223*16467b97STreehugger Robot /* Create the new token 224*16467b97STreehugger Robot */ 225*16467b97STreehugger Robot fromToken = this->createToken(tokenType, text); 226*16467b97STreehugger Robot 227*16467b97STreehugger Robot /* Return a new node based upon this token 228*16467b97STreehugger Robot */ 229*16467b97STreehugger Robot return this->create(fromToken); 230*16467b97STreehugger Robot} 231*16467b97STreehugger Robot 232*16467b97STreehugger Robottemplate<class ImplTraits> 233*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::dupNode( TreeType* treeNode) 234*16467b97STreehugger Robot{ 235*16467b97STreehugger Robot return (treeNode == NULL) ? NULL : treeNode->dupNode(); 236*16467b97STreehugger Robot} 237*16467b97STreehugger Robot 238*16467b97STreehugger Robottemplate<class ImplTraits> 239*16467b97STreehugger RobotANTLR_UINT32 CommonTreeAdaptor<ImplTraits>::getType( TreeType* t) 240*16467b97STreehugger Robot{ 241*16467b97STreehugger Robot return t->getType(); 242*16467b97STreehugger Robot} 243*16467b97STreehugger Robot 244*16467b97STreehugger Robottemplate<class ImplTraits> 245*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::StringType CommonTreeAdaptor<ImplTraits>::getText( TreeType* t) 246*16467b97STreehugger Robot{ 247*16467b97STreehugger Robot return t->getText(); 248*16467b97STreehugger Robot} 249*16467b97STreehugger Robot 250*16467b97STreehugger Robottemplate<class ImplTraits> 251*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::getChild( TreeType* t, ANTLR_UINT32 i) 252*16467b97STreehugger Robot{ 253*16467b97STreehugger Robot return t->getChild(i); 254*16467b97STreehugger Robot} 255*16467b97STreehugger Robot 256*16467b97STreehugger Robottemplate<class ImplTraits> 257*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::setChild( TreeType* t, ANTLR_UINT32 i, TreeType* child) 258*16467b97STreehugger Robot{ 259*16467b97STreehugger Robot t->setChild(i, child); 260*16467b97STreehugger Robot} 261*16467b97STreehugger Robot 262*16467b97STreehugger Robottemplate<class ImplTraits> 263*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::deleteChild( TreeType* t, ANTLR_UINT32 i) 264*16467b97STreehugger Robot{ 265*16467b97STreehugger Robot t->deleteChild(i); 266*16467b97STreehugger Robot} 267*16467b97STreehugger Robot 268*16467b97STreehugger Robottemplate<class ImplTraits> 269*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::setChildIndex( TreeType* t, ANTLR_INT32 i) 270*16467b97STreehugger Robot{ 271*16467b97STreehugger Robot t->setChildIndex(i); 272*16467b97STreehugger Robot} 273*16467b97STreehugger Robot 274*16467b97STreehugger Robottemplate<class ImplTraits> 275*16467b97STreehugger RobotANTLR_INT32 CommonTreeAdaptor<ImplTraits>::getChildIndex( TreeType * t) 276*16467b97STreehugger Robot{ 277*16467b97STreehugger Robot return t->getChildIndex(); 278*16467b97STreehugger Robot} 279*16467b97STreehugger Robot 280*16467b97STreehugger Robottemplate<class ImplTraits> 281*16467b97STreehugger RobotANTLR_UINT32 CommonTreeAdaptor<ImplTraits>::getChildCount( TreeType* t) 282*16467b97STreehugger Robot{ 283*16467b97STreehugger Robot return t->getChildCount(); 284*16467b97STreehugger Robot} 285*16467b97STreehugger Robot 286*16467b97STreehugger Robottemplate<class ImplTraits> 287*16467b97STreehugger RobotANTLR_UINT64 CommonTreeAdaptor<ImplTraits>::getUniqueID( TreeType* node ) 288*16467b97STreehugger Robot{ 289*16467b97STreehugger Robot return reinterpret_cast<ANTLR_UINT64>(node); 290*16467b97STreehugger Robot} 291*16467b97STreehugger Robot 292*16467b97STreehugger Robottemplate<class ImplTraits> 293*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::CommonTokenType* 294*16467b97STreehugger Robot CommonTreeAdaptor<ImplTraits>::createToken( ANTLR_UINT32 tokenType, const ANTLR_UINT8* text) 295*16467b97STreehugger Robot{ 296*16467b97STreehugger Robot CommonTokenType* newToken = new CommonTokenType; 297*16467b97STreehugger Robot 298*16467b97STreehugger Robot if (newToken != NULL) 299*16467b97STreehugger Robot { 300*16467b97STreehugger Robot newToken->set_tokText( (const char*) text ); 301*16467b97STreehugger Robot newToken->setType(tokenType); 302*16467b97STreehugger Robot } 303*16467b97STreehugger Robot return newToken; 304*16467b97STreehugger Robot 305*16467b97STreehugger Robot} 306*16467b97STreehugger Robot 307*16467b97STreehugger Robottemplate<class ImplTraits> 308*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::CommonTokenType* 309*16467b97STreehugger Robot CommonTreeAdaptor<ImplTraits>::createTokenFromToken( CommonTokenType* fromToken) 310*16467b97STreehugger Robot{ 311*16467b97STreehugger Robot CommonTokenType* newToken; 312*16467b97STreehugger Robot 313*16467b97STreehugger Robot newToken = new CommonTokenType; 314*16467b97STreehugger Robot 315*16467b97STreehugger Robot if (newToken != NULL) 316*16467b97STreehugger Robot { 317*16467b97STreehugger Robot // Create the text using our own string factory to avoid complicating 318*16467b97STreehugger Robot // commontoken. 319*16467b97STreehugger Robot // 320*16467b97STreehugger Robot StringType text = fromToken->getText(); 321*16467b97STreehugger Robot newToken->set_tokText( text ); 322*16467b97STreehugger Robot newToken->setLine( fromToken->getLine() ); 323*16467b97STreehugger Robot newToken->setTokenIndex( fromToken->getTokenIndex() ); 324*16467b97STreehugger Robot newToken->setCharPositionInLine( fromToken->getCharPositionInLine() ); 325*16467b97STreehugger Robot newToken->setChannel( fromToken->getChannel() ); 326*16467b97STreehugger Robot newToken->setType( fromToken->getType() ); 327*16467b97STreehugger Robot } 328*16467b97STreehugger Robot 329*16467b97STreehugger Robot return newToken; 330*16467b97STreehugger Robot} 331*16467b97STreehugger Robot 332*16467b97STreehugger Robottemplate<class ImplTraits> 333*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::CommonTokenType* 334*16467b97STreehugger Robot CommonTreeAdaptor<ImplTraits>::getToken( TreeType* t) 335*16467b97STreehugger Robot{ 336*16467b97STreehugger Robot return t->getToken(); 337*16467b97STreehugger Robot} 338*16467b97STreehugger Robot 339*16467b97STreehugger Robottemplate<class ImplTraits> 340*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::setTokenBoundaries( TreeType* t, CommonTokenType* startToken, CommonTokenType* stopToken) 341*16467b97STreehugger Robot{ 342*16467b97STreehugger Robot ANTLR_MARKER start; 343*16467b97STreehugger Robot ANTLR_MARKER stop; 344*16467b97STreehugger Robot 345*16467b97STreehugger Robot TreeType* ct; 346*16467b97STreehugger Robot 347*16467b97STreehugger Robot if (t == NULL) 348*16467b97STreehugger Robot { 349*16467b97STreehugger Robot return; 350*16467b97STreehugger Robot } 351*16467b97STreehugger Robot 352*16467b97STreehugger Robot if ( startToken != NULL) 353*16467b97STreehugger Robot { 354*16467b97STreehugger Robot start = startToken->getTokenIndex(); 355*16467b97STreehugger Robot } 356*16467b97STreehugger Robot else 357*16467b97STreehugger Robot { 358*16467b97STreehugger Robot start = 0; 359*16467b97STreehugger Robot } 360*16467b97STreehugger Robot 361*16467b97STreehugger Robot if ( stopToken != NULL) 362*16467b97STreehugger Robot { 363*16467b97STreehugger Robot stop = stopToken->getTokenIndex(); 364*16467b97STreehugger Robot } 365*16467b97STreehugger Robot else 366*16467b97STreehugger Robot { 367*16467b97STreehugger Robot stop = 0; 368*16467b97STreehugger Robot } 369*16467b97STreehugger Robot 370*16467b97STreehugger Robot ct = t; 371*16467b97STreehugger Robot 372*16467b97STreehugger Robot ct->set_startIndex(start); 373*16467b97STreehugger Robot ct->set_stopIndex(stop); 374*16467b97STreehugger Robot} 375*16467b97STreehugger Robot 376*16467b97STreehugger Robottemplate<class ImplTraits> 377*16467b97STreehugger RobotANTLR_MARKER CommonTreeAdaptor<ImplTraits>::getTokenStartIndex( TreeType* t) 378*16467b97STreehugger Robot{ 379*16467b97STreehugger Robot return t->get_tokenStartIndex(); 380*16467b97STreehugger Robot} 381*16467b97STreehugger Robot 382*16467b97STreehugger Robottemplate<class ImplTraits> 383*16467b97STreehugger RobotANTLR_MARKER CommonTreeAdaptor<ImplTraits>::getTokenStopIndex( TreeType* t) 384*16467b97STreehugger Robot{ 385*16467b97STreehugger Robot return t->get_tokenStopIndex(); 386*16467b97STreehugger Robot} 387*16467b97STreehugger Robot 388*16467b97STreehugger Robottemplate<class ImplTraits> 389*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::StringType CommonTreeAdaptor<ImplTraits>::makeDot( TreeType* theTree) 390*16467b97STreehugger Robot{ 391*16467b97STreehugger Robot // The string we are building up 392*16467b97STreehugger Robot // 393*16467b97STreehugger Robot StringType dotSpec; 394*16467b97STreehugger Robot char buff[64]; 395*16467b97STreehugger Robot StringType text; 396*16467b97STreehugger Robot 397*16467b97STreehugger Robot dotSpec = "digraph {\n\n" 398*16467b97STreehugger Robot "\tordering=out;\n" 399*16467b97STreehugger Robot "\tranksep=.4;\n" 400*16467b97STreehugger Robot "\tbgcolor=\"lightgrey\"; node [shape=box, fixedsize=false, fontsize=12, fontname=\"Helvetica-bold\", fontcolor=\"blue\"\n" 401*16467b97STreehugger Robot "\twidth=.25, height=.25, color=\"black\", fillcolor=\"white\", style=\"filled, solid, bold\"];\n\n" 402*16467b97STreehugger Robot "\tedge [arrowsize=.5, color=\"black\", style=\"bold\"]\n\n"; 403*16467b97STreehugger Robot 404*16467b97STreehugger Robot if (theTree == NULL) 405*16467b97STreehugger Robot { 406*16467b97STreehugger Robot // No tree, so create a blank spec 407*16467b97STreehugger Robot // 408*16467b97STreehugger Robot dotSpec->append("n0[label=\"EMPTY TREE\"]\n"); 409*16467b97STreehugger Robot return dotSpec; 410*16467b97STreehugger Robot } 411*16467b97STreehugger Robot 412*16467b97STreehugger Robot sprintf(buff, "\tn%p[label=\"", theTree); 413*16467b97STreehugger Robot dotSpec.append(buff); 414*16467b97STreehugger Robot text = this->getText(theTree); 415*16467b97STreehugger Robot for (std::size_t j = 0; j < text.size(); j++) 416*16467b97STreehugger Robot { 417*16467b97STreehugger Robot switch(text[j]) 418*16467b97STreehugger Robot { 419*16467b97STreehugger Robot case '"': 420*16467b97STreehugger Robot dotSpec.append("\\\""); 421*16467b97STreehugger Robot break; 422*16467b97STreehugger Robot 423*16467b97STreehugger Robot case '\n': 424*16467b97STreehugger Robot dotSpec.append("\\n"); 425*16467b97STreehugger Robot break; 426*16467b97STreehugger Robot 427*16467b97STreehugger Robot case '\r': 428*16467b97STreehugger Robot dotSpec.append("\\r"); 429*16467b97STreehugger Robot break; 430*16467b97STreehugger Robot 431*16467b97STreehugger Robot default: 432*16467b97STreehugger Robot dotSpec += text[j]; 433*16467b97STreehugger Robot break; 434*16467b97STreehugger Robot } 435*16467b97STreehugger Robot } 436*16467b97STreehugger Robot dotSpec->append("\"]\n"); 437*16467b97STreehugger Robot 438*16467b97STreehugger Robot // First produce the node defintions 439*16467b97STreehugger Robot // 440*16467b97STreehugger Robot this->defineDotNodes(theTree, dotSpec); 441*16467b97STreehugger Robot dotSpec.append("\n"); 442*16467b97STreehugger Robot this->defineDotEdges(theTree, dotSpec); 443*16467b97STreehugger Robot 444*16467b97STreehugger Robot // Terminate the spec 445*16467b97STreehugger Robot // 446*16467b97STreehugger Robot dotSpec.append("\n}"); 447*16467b97STreehugger Robot 448*16467b97STreehugger Robot // Result 449*16467b97STreehugger Robot // 450*16467b97STreehugger Robot return dotSpec; 451*16467b97STreehugger Robot} 452*16467b97STreehugger Robot 453*16467b97STreehugger Robottemplate<class ImplTraits> 454*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::replaceChildren( TreeType* parent, ANTLR_INT32 startChildIndex, ANTLR_INT32 stopChildIndex, TreeType* t) 455*16467b97STreehugger Robot{ 456*16467b97STreehugger Robot if (parent != NULL) 457*16467b97STreehugger Robot parent->replaceChildren(startChildIndex, stopChildIndex, t); 458*16467b97STreehugger Robot} 459*16467b97STreehugger Robot 460*16467b97STreehugger Robottemplate<class ImplTraits> 461*16467b97STreehugger RobotCommonTreeAdaptor<ImplTraits>::~CommonTreeAdaptor() 462*16467b97STreehugger Robot{ 463*16467b97STreehugger Robot} 464*16467b97STreehugger Robot 465*16467b97STreehugger Robottemplate<class ImplTraits> 466*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::defineDotNodes(TreeType* t, const StringType& dotSpec) 467*16467b97STreehugger Robot{ 468*16467b97STreehugger Robot // How many nodes are we talking about? 469*16467b97STreehugger Robot // 470*16467b97STreehugger Robot int nCount; 471*16467b97STreehugger Robot int i; 472*16467b97STreehugger Robot TreeType* child; 473*16467b97STreehugger Robot char buff[64]; 474*16467b97STreehugger Robot StringType text; 475*16467b97STreehugger Robot int j; 476*16467b97STreehugger Robot 477*16467b97STreehugger Robot // Count the nodes 478*16467b97STreehugger Robot // 479*16467b97STreehugger Robot nCount = this->getChildCount(t); 480*16467b97STreehugger Robot 481*16467b97STreehugger Robot if (nCount == 0) 482*16467b97STreehugger Robot { 483*16467b97STreehugger Robot // This will already have been included as a child of another node 484*16467b97STreehugger Robot // so there is nothing to add. 485*16467b97STreehugger Robot // 486*16467b97STreehugger Robot return; 487*16467b97STreehugger Robot } 488*16467b97STreehugger Robot 489*16467b97STreehugger Robot // For each child of the current tree, define a node using the 490*16467b97STreehugger Robot // memory address of the node to name it 491*16467b97STreehugger Robot // 492*16467b97STreehugger Robot for (i = 0; i<nCount; i++) 493*16467b97STreehugger Robot { 494*16467b97STreehugger Robot 495*16467b97STreehugger Robot // Pick up a pointer for the child 496*16467b97STreehugger Robot // 497*16467b97STreehugger Robot child = this->getChild(t, i); 498*16467b97STreehugger Robot 499*16467b97STreehugger Robot // Name the node 500*16467b97STreehugger Robot // 501*16467b97STreehugger Robot sprintf(buff, "\tn%p[label=\"", child); 502*16467b97STreehugger Robot dotSpec->append(buff); 503*16467b97STreehugger Robot text = this->getText(child); 504*16467b97STreehugger Robot for (j = 0; j < text.size(); j++) 505*16467b97STreehugger Robot { 506*16467b97STreehugger Robot switch(text[j]) 507*16467b97STreehugger Robot { 508*16467b97STreehugger Robot case '"': 509*16467b97STreehugger Robot dotSpec.append("\\\""); 510*16467b97STreehugger Robot break; 511*16467b97STreehugger Robot 512*16467b97STreehugger Robot case '\n': 513*16467b97STreehugger Robot dotSpec.append("\\n"); 514*16467b97STreehugger Robot break; 515*16467b97STreehugger Robot 516*16467b97STreehugger Robot case '\r': 517*16467b97STreehugger Robot dotSpec.append("\\r"); 518*16467b97STreehugger Robot break; 519*16467b97STreehugger Robot 520*16467b97STreehugger Robot default: 521*16467b97STreehugger Robot dotSpec += text[j]; 522*16467b97STreehugger Robot break; 523*16467b97STreehugger Robot } 524*16467b97STreehugger Robot } 525*16467b97STreehugger Robot dotSpec.append("\"]\n"); 526*16467b97STreehugger Robot 527*16467b97STreehugger Robot // And now define the children of this child (if any) 528*16467b97STreehugger Robot // 529*16467b97STreehugger Robot this->defineDotNodes(child, dotSpec); 530*16467b97STreehugger Robot } 531*16467b97STreehugger Robot 532*16467b97STreehugger Robot // Done 533*16467b97STreehugger Robot // 534*16467b97STreehugger Robot return; 535*16467b97STreehugger Robot} 536*16467b97STreehugger Robot 537*16467b97STreehugger Robottemplate<class ImplTraits> 538*16467b97STreehugger Robotvoid CommonTreeAdaptor<ImplTraits>::defineDotEdges(TreeType* t, const StringType& dotSpec) 539*16467b97STreehugger Robot{ 540*16467b97STreehugger Robot // How many nodes are we talking about? 541*16467b97STreehugger Robot // 542*16467b97STreehugger Robot int nCount; 543*16467b97STreehugger Robot if (t == NULL) 544*16467b97STreehugger Robot { 545*16467b97STreehugger Robot // No tree, so do nothing 546*16467b97STreehugger Robot // 547*16467b97STreehugger Robot return; 548*16467b97STreehugger Robot } 549*16467b97STreehugger Robot 550*16467b97STreehugger Robot // Count the nodes 551*16467b97STreehugger Robot // 552*16467b97STreehugger Robot nCount = this->getChildCount(t); 553*16467b97STreehugger Robot 554*16467b97STreehugger Robot if (nCount == 0) 555*16467b97STreehugger Robot { 556*16467b97STreehugger Robot // This will already have been included as a child of another node 557*16467b97STreehugger Robot // so there is nothing to add. 558*16467b97STreehugger Robot // 559*16467b97STreehugger Robot return; 560*16467b97STreehugger Robot } 561*16467b97STreehugger Robot 562*16467b97STreehugger Robot // For each child, define an edge from this parent, then process 563*16467b97STreehugger Robot // and children of this child in the same way 564*16467b97STreehugger Robot // 565*16467b97STreehugger Robot for (int i=0; i<nCount; i++) 566*16467b97STreehugger Robot { 567*16467b97STreehugger Robot TreeType* child; 568*16467b97STreehugger Robot char buff[128]; 569*16467b97STreehugger Robot StringType text; 570*16467b97STreehugger Robot 571*16467b97STreehugger Robot // Next child 572*16467b97STreehugger Robot // 573*16467b97STreehugger Robot child = this->getChild(t, i); 574*16467b97STreehugger Robot 575*16467b97STreehugger Robot // Create the edge relation 576*16467b97STreehugger Robot // 577*16467b97STreehugger Robot sprintf(buff, "\t\tn%p -> n%p\t\t// ", t, child); 578*16467b97STreehugger Robot 579*16467b97STreehugger Robot dotSpec.append(buff); 580*16467b97STreehugger Robot 581*16467b97STreehugger Robot // Document the relationship 582*16467b97STreehugger Robot // 583*16467b97STreehugger Robot text = this->getText(t); 584*16467b97STreehugger Robot for (std::size_t j = 0; j < text.size(); j++) 585*16467b97STreehugger Robot { 586*16467b97STreehugger Robot switch(text[j]) 587*16467b97STreehugger Robot { 588*16467b97STreehugger Robot case '"': 589*16467b97STreehugger Robot dotSpec.append("\\\""); 590*16467b97STreehugger Robot break; 591*16467b97STreehugger Robot 592*16467b97STreehugger Robot case '\n': 593*16467b97STreehugger Robot dotSpec.append("\\n"); 594*16467b97STreehugger Robot break; 595*16467b97STreehugger Robot 596*16467b97STreehugger Robot case '\r': 597*16467b97STreehugger Robot dotSpec.append("\\r"); 598*16467b97STreehugger Robot break; 599*16467b97STreehugger Robot 600*16467b97STreehugger Robot default: 601*16467b97STreehugger Robot dotSpec += text[j]; 602*16467b97STreehugger Robot break; 603*16467b97STreehugger Robot } 604*16467b97STreehugger Robot } 605*16467b97STreehugger Robot 606*16467b97STreehugger Robot dotSpec.append(" -> "); 607*16467b97STreehugger Robot 608*16467b97STreehugger Robot text = this->getText(child); 609*16467b97STreehugger Robot for (std::size_t j = 0; j < text.size(); j++) 610*16467b97STreehugger Robot { 611*16467b97STreehugger Robot switch(text[j]) 612*16467b97STreehugger Robot { 613*16467b97STreehugger Robot case '"': 614*16467b97STreehugger Robot dotSpec.append("\\\""); 615*16467b97STreehugger Robot break; 616*16467b97STreehugger Robot 617*16467b97STreehugger Robot case '\n': 618*16467b97STreehugger Robot dotSpec.append("\\n"); 619*16467b97STreehugger Robot break; 620*16467b97STreehugger Robot 621*16467b97STreehugger Robot case '\r': 622*16467b97STreehugger Robot dotSpec.append("\\r"); 623*16467b97STreehugger Robot break; 624*16467b97STreehugger Robot 625*16467b97STreehugger Robot default: 626*16467b97STreehugger Robot dotSpec += text[j]; 627*16467b97STreehugger Robot break; 628*16467b97STreehugger Robot } 629*16467b97STreehugger Robot } 630*16467b97STreehugger Robot dotSpec.append("\n"); 631*16467b97STreehugger Robot 632*16467b97STreehugger Robot // Define edges for this child 633*16467b97STreehugger Robot // 634*16467b97STreehugger Robot this->defineDotEdges(child, dotSpec); 635*16467b97STreehugger Robot } 636*16467b97STreehugger Robot 637*16467b97STreehugger Robot // Done 638*16467b97STreehugger Robot // 639*16467b97STreehugger Robot return; 640*16467b97STreehugger Robot} 641*16467b97STreehugger Robot 642*16467b97STreehugger Robottemplate<class ImplTraits> 643*16467b97STreehugger Robottypename CommonTreeAdaptor<ImplTraits>::TreeType* CommonTreeAdaptor<ImplTraits>::rulePostProcessing( TreeType* root) 644*16467b97STreehugger Robot{ 645*16467b97STreehugger Robot TreeType* saveRoot; 646*16467b97STreehugger Robot 647*16467b97STreehugger Robot // Keep track of the root we are given. If it is a nilNode, then we 648*16467b97STreehugger Robot // can reuse it rather than orphaning it! 649*16467b97STreehugger Robot // 650*16467b97STreehugger Robot saveRoot = root; 651*16467b97STreehugger Robot 652*16467b97STreehugger Robot if (root != NULL && root->isNilNode()) 653*16467b97STreehugger Robot { 654*16467b97STreehugger Robot if (root->getChildCount() == 0) 655*16467b97STreehugger Robot { 656*16467b97STreehugger Robot root = NULL; 657*16467b97STreehugger Robot } 658*16467b97STreehugger Robot else if (root->getChildCount() == 1) 659*16467b97STreehugger Robot { 660*16467b97STreehugger Robot root = root->getChild(0); 661*16467b97STreehugger Robot root->setParent(NULL); 662*16467b97STreehugger Robot root->setChildIndex(-1); 663*16467b97STreehugger Robot 664*16467b97STreehugger Robot // The root we were given was a nil node, wiht one child, which means it has 665*16467b97STreehugger Robot // been abandoned and would be lost in the node factory. However 666*16467b97STreehugger Robot // nodes can be flagged as resuable to prevent this terrible waste 667*16467b97STreehugger Robot // 668*16467b97STreehugger Robot saveRoot->reuse(); 669*16467b97STreehugger Robot } 670*16467b97STreehugger Robot } 671*16467b97STreehugger Robot return root; 672*16467b97STreehugger Robot} 673*16467b97STreehugger Robot 674*16467b97STreehugger Robottemplate<class ImplTraits> 675*16467b97STreehugger RobotDebugTreeAdaptor<ImplTraits>::DebugTreeAdaptor( DebuggerType* debugger ) 676*16467b97STreehugger Robot{ 677*16467b97STreehugger Robot m_debugger = debugger; 678*16467b97STreehugger Robot} 679*16467b97STreehugger Robot 680*16467b97STreehugger Robottemplate<class ImplTraits> 681*16467b97STreehugger Robotvoid DebugTreeAdaptor<ImplTraits>::setDebugEventListener( DebuggerType* debugger) 682*16467b97STreehugger Robot{ 683*16467b97STreehugger Robot m_debugger = debugger; 684*16467b97STreehugger Robot} 685*16467b97STreehugger Robot 686*16467b97STreehugger Robottemplate<class ImplTraits> 687*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::nilNode() 688*16467b97STreehugger Robot{ 689*16467b97STreehugger Robot TreeType* t = this->create(NULL); 690*16467b97STreehugger Robot m_debugger->createNode(t); 691*16467b97STreehugger Robot return t; 692*16467b97STreehugger Robot} 693*16467b97STreehugger Robot 694*16467b97STreehugger Robottemplate<class ImplTraits> 695*16467b97STreehugger Robotvoid DebugTreeAdaptor<ImplTraits>::addChild(TreeType* t, TreeType* child) 696*16467b97STreehugger Robot{ 697*16467b97STreehugger Robot if (t != NULL && child != NULL) 698*16467b97STreehugger Robot { 699*16467b97STreehugger Robot t->addChild(child); 700*16467b97STreehugger Robot m_debugger->addChild(t, child); 701*16467b97STreehugger Robot } 702*16467b97STreehugger Robot} 703*16467b97STreehugger Robot 704*16467b97STreehugger Robottemplate<class ImplTraits> 705*16467b97STreehugger Robotvoid DebugTreeAdaptor<ImplTraits>::addChildToken(TreeType* t, CommonTokenType* child) 706*16467b97STreehugger Robot{ 707*16467b97STreehugger Robot TreeType* tc; 708*16467b97STreehugger Robot if (t != NULL && child != NULL) 709*16467b97STreehugger Robot { 710*16467b97STreehugger Robot tc = this->create(child); 711*16467b97STreehugger Robot this->addChild(t, tc); 712*16467b97STreehugger Robot m_debugger->addChild(t, tc); 713*16467b97STreehugger Robot } 714*16467b97STreehugger Robot} 715*16467b97STreehugger Robot 716*16467b97STreehugger Robottemplate<class ImplTraits> 717*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::becomeRoot( TreeType* newRootTree, TreeType* oldRootTree ) 718*16467b97STreehugger Robot{ 719*16467b97STreehugger Robot TreeType* t; 720*16467b97STreehugger Robot t = this->becomeRoot(newRootTree, oldRootTree); 721*16467b97STreehugger Robot m_debugger->becomeRoot(newRootTree, oldRootTree); 722*16467b97STreehugger Robot return t; 723*16467b97STreehugger Robot} 724*16467b97STreehugger Robot 725*16467b97STreehugger Robottemplate<class ImplTraits> 726*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::becomeRootToken(TreeType* newRoot, TreeType* oldRoot) 727*16467b97STreehugger Robot{ 728*16467b97STreehugger Robot TreeType* t; 729*16467b97STreehugger Robot t = this->becomeRoot(this->create(newRoot), oldRoot); 730*16467b97STreehugger Robot m_debugger->becomeRoot(t, oldRoot); 731*16467b97STreehugger Robot return t; 732*16467b97STreehugger Robot} 733*16467b97STreehugger Robot 734*16467b97STreehugger Robottemplate<class ImplTraits> 735*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::createTypeToken(ANTLR_UINT32 tokenType, CommonTokenType* fromToken) 736*16467b97STreehugger Robot{ 737*16467b97STreehugger Robot TreeType* t; 738*16467b97STreehugger Robot t = this->createTypeToken(tokenType, fromToken); 739*16467b97STreehugger Robot m_debugger->createNode(t); 740*16467b97STreehugger Robot return t; 741*16467b97STreehugger Robot} 742*16467b97STreehugger Robot 743*16467b97STreehugger Robottemplate<class ImplTraits> 744*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::createTypeTokenText(ANTLR_UINT32 tokenType, CommonTokenType* fromToken, ANTLR_UINT8* text) 745*16467b97STreehugger Robot{ 746*16467b97STreehugger Robot TreeType* t; 747*16467b97STreehugger Robot t = this->createTypeTokenText(tokenType, fromToken, text); 748*16467b97STreehugger Robot m_debugger->createNode(t); 749*16467b97STreehugger Robot return t; 750*16467b97STreehugger Robot} 751*16467b97STreehugger Robot 752*16467b97STreehugger Robottemplate<class ImplTraits> 753*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::createTypeText( ANTLR_UINT32 tokenType, ANTLR_UINT8* text) 754*16467b97STreehugger Robot{ 755*16467b97STreehugger Robot TreeType* t; 756*16467b97STreehugger Robot t = this->createTypeText(tokenType, text); 757*16467b97STreehugger Robot m_debugger->createNode(t); 758*16467b97STreehugger Robot return t; 759*16467b97STreehugger Robot} 760*16467b97STreehugger Robot 761*16467b97STreehugger Robottemplate<class ImplTraits> 762*16467b97STreehugger Robottypename DebugTreeAdaptor<ImplTraits>::TreeType* DebugTreeAdaptor<ImplTraits>::dupTree( TreeType* tree) 763*16467b97STreehugger Robot{ 764*16467b97STreehugger Robot TreeType* t; 765*16467b97STreehugger Robot 766*16467b97STreehugger Robot // Call the normal dup tree mechanism first 767*16467b97STreehugger Robot // 768*16467b97STreehugger Robot t = this->dupTreeTT(tree, NULL); 769*16467b97STreehugger Robot 770*16467b97STreehugger Robot // In order to tell the debugger what we have just done, we now 771*16467b97STreehugger Robot // simulate the tree building mechanism. THis will fire 772*16467b97STreehugger Robot // lots of debugging events to the client and look like we 773*16467b97STreehugger Robot // duped the tree.. 774*16467b97STreehugger Robot // 775*16467b97STreehugger Robot this->simulateTreeConstruction( t); 776*16467b97STreehugger Robot 777*16467b97STreehugger Robot return t; 778*16467b97STreehugger Robot} 779*16467b97STreehugger Robot 780*16467b97STreehugger Robottemplate<class ImplTraits> 781*16467b97STreehugger Robotvoid DebugTreeAdaptor<ImplTraits>::simulateTreeConstruction(TreeType* tree) 782*16467b97STreehugger Robot{ 783*16467b97STreehugger Robot ANTLR_UINT32 n; 784*16467b97STreehugger Robot ANTLR_UINT32 i; 785*16467b97STreehugger Robot TreeType* child; 786*16467b97STreehugger Robot 787*16467b97STreehugger Robot // Send the create node event 788*16467b97STreehugger Robot // 789*16467b97STreehugger Robot m_debugger->createNode(tree); 790*16467b97STreehugger Robot 791*16467b97STreehugger Robot n = this->getChildCount(tree); 792*16467b97STreehugger Robot for (i = 0; i < n; i++) 793*16467b97STreehugger Robot { 794*16467b97STreehugger Robot child = this->getChild(tree, i); 795*16467b97STreehugger Robot this->simulateTreeConstruction(child); 796*16467b97STreehugger Robot m_debugger->addChild(tree, child); 797*16467b97STreehugger Robot } 798*16467b97STreehugger Robot} 799*16467b97STreehugger Robot 800*16467b97STreehugger Robot 801*16467b97STreehugger RobotANTLR_END_NAMESPACE() 802