home *** CD-ROM | disk | FTP | other *** search
- /*****************************************************************************/
-
- #include "smcPCH.h"
- #pragma hdrstop
-
- #include "parser.h"
- #include "treeops.h"
-
- /*****************************************************************************
- *
- * The low-level tree node allocation routines.
- */
-
- #ifndef FAST
-
- Tree parser::parseAllocNode()
- {
- Tree node;
-
- node = (Tree)parseAllocPriv.nraAlloc(sizeof(*node));
-
- #ifdef DEBUG
- node->tnLineNo = -1;
- // node->tnColumn = -1;
- #endif
-
- return node;
- }
-
- #endif
-
- /*****************************************************************************
- *
- * Allocate a parse tree node with the given operator.
- */
-
- Tree parser::parseCreateNode(treeOps op)
- {
- Tree tree = parseAllocNode();
-
- #ifndef NDEBUG
- memset(tree, 0xDD, sizeof(*tree));
- #endif
-
- tree->tnOper = op;
- tree->tnFlags = 0;
-
- tree->tnLineNo = parseScan->scanGetTokenLno();
- // tree->tnColumn = parseScan->scanGetTokenCol();
-
- return tree;
- }
-
- /*****************************************************************************/
-
- Tree parser::parseCreateBconNode(int val)
- {
- Tree node = parseCreateNode(TN_CNS_INT);
-
- node->tnVtyp = TYP_BOOL;
- node->tnIntCon.tnIconVal = val;
-
- return node;
- }
-
- Tree parser::parseCreateIconNode(__int32 ival, var_types typ)
- {
- Tree node = parseCreateNode(TN_CNS_INT);
-
- node->tnVtyp = typ;
- node->tnIntCon.tnIconVal = ival;
-
- if (typ != TYP_UNDEF)
- return node;
-
- node->tnOper = TN_ERROR;
- node->tnType = parseStab->stIntrinsicType(typ);
-
- return node;
- }
-
- Tree parser::parseCreateLconNode(__int64 lval, var_types typ)
- {
- Tree node = parseCreateNode(TN_CNS_LNG);
-
- assert(typ == TYP_LONG || typ == TYP_ULONG);
-
- node->tnVtyp = typ;
- node->tnLngCon.tnLconVal = lval;
-
- return node;
- }
-
- Tree parser::parseCreateFconNode(float fval)
- {
- Tree node = parseCreateNode(TN_CNS_FLT);
-
- node->tnVtyp = TYP_FLOAT;
- node->tnFltCon.tnFconVal = fval;
-
- return node;
- }
-
- Tree parser::parseCreateDconNode(double dval)
- {
- Tree node = parseCreateNode(TN_CNS_DBL);
-
- node->tnVtyp = TYP_DOUBLE;
- node->tnDblCon.tnDconVal = dval;
-
- return node;
- }
-
- Tree parser::parseCreateSconNode(stringBuff sval,
- size_t slen,
- unsigned type,
- int wide,
- Tree addx)
- {
- Tree node;
- size_t olen;
- size_t tlen;
- stringBuff buff;
- unsigned flag;
-
- static
- unsigned tpfl[] =
- {
- 0,
- TNF_STR_ASCII,
- TNF_STR_WIDE,
- TNF_STR_STR,
- };
-
- assert(type < arraylen(tpfl));
-
- flag = tpfl[type];
-
- if (addx)
- {
- unsigned oldf = addx->tnFlags & (TNF_STR_ASCII|TNF_STR_WIDE|TNF_STR_STR);
-
- assert(addx->tnOper == TN_CNS_STR);
-
- if (flag != oldf)
- {
- if (tpfl)
- parseComp->cmpError(ERRsyntax);
- else
- flag = oldf;
- }
-
- node = addx;
- olen = addx->tnStrCon.tnSconLen;
- tlen = slen + olen;
- }
- else
- {
- node = parseCreateNode(TN_CNS_STR);
- tlen = slen;
- }
-
- #if MGDDATA
-
- UNIMPL(!"save str");
-
- #else
-
- stringBuff dest;
-
- buff = dest = (char *)parseAllocPriv.nraAlloc(roundUp(tlen + 1));
-
- if (addx)
- {
- memcpy(dest, node->tnStrCon.tnSconVal, olen);
- dest += olen;
- }
-
- memcpy(dest, sval, slen + 1);
-
- #endif
-
- node->tnVtyp = TYP_REF;
- node->tnStrCon.tnSconVal = buff;
- node->tnStrCon.tnSconLen = tlen;
- node->tnStrCon.tnSconLCH = wide;
-
- node->tnFlags |= flag;
-
- return node;
- }
-
- Tree parser::parseCreateErrNode(unsigned errNum)
- {
- Tree node = parseCreateNode(TN_ERROR);
-
- if (errNum != ERRnone) parseComp->cmpError(errNum);
-
- node->tnVtyp = TYP_UNDEF;
- node->tnType = parseStab->stIntrinsicType(TYP_UNDEF);
-
- return node;
- }
-
- /*****************************************************************************/
- #ifdef DEBUG
- /*****************************************************************************/
-
- #ifndef __SMC__
- const char * treeNodeName(treeOps op); // moved into macros.cpp
- #endif
-
- inline
- void treeNodeIndent(unsigned level)
- {
- printf("%*c", 1+level*3, ' ');
- }
-
- void parser::parseDispTreeNode(Tree tree, unsigned indent, const char *name)
- {
- treeNodeIndent(indent);
- printf("[%08X] ", tree);
-
- if (tree && tree->tnType
- && (NatUns)tree->tnType != 0xCCCCCCCC
- && (NatUns)tree->tnType != 0xDDDDDDDD
- && tree->tnOper != TN_LIST)
- {
- printf("(type=%s)", parseStab->stTypeName(tree->tnType, NULL));
- }
-
- assert(tree || name);
-
- if (!name)
- {
- name = (tree->tnOper < TN_COUNT) ? treeNodeName(tree->tnOperGet())
- : "<ERROR>";
- }
-
- printf("%12s ", name);
-
- assert(tree == 0 || tree->tnOper < TN_COUNT);
- }
-
- void parser::parseDispTree(Tree tree, unsigned indent)
- {
- unsigned kind;
-
- if (tree == NULL)
- {
- treeNodeIndent(indent);
- printf("[%08X] <NULL>\n", tree);
- return;
- }
-
- assert((int)tree != 0xDDDDDDDD); /* Value used to initalize nodes */
-
- /* Make sure we're not stuck in a recursive tree */
-
- assert(indent < 32);
-
- if (tree->tnOper >= TN_COUNT)
- {
- parseDispTreeNode(tree, indent); NO_WAY(!"bogus operator");
- }
-
- kind = tree->tnOperKind();
-
- /* Is this a constant node? */
-
- if (kind & TNK_CONST)
- {
- parseDispTreeNode(tree, indent);
-
- switch (tree->tnOper)
- {
- case TN_CNS_INT: printf(" %ld" , tree->tnIntCon.tnIconVal); break;
- case TN_CNS_LNG: printf(" %Ld" , tree->tnLngCon.tnLconVal); break;
- case TN_CNS_FLT: printf(" %f" , tree->tnFltCon.tnFconVal); break;
- case TN_CNS_DBL: printf(" %lf" , tree->tnDblCon.tnDconVal); break;
- case TN_CNS_STR: printf(" '%s'", tree->tnStrCon.tnSconVal); break;
- }
-
- printf("\n");
- return;
- }
-
- /* Is this a leaf node? */
-
- if (kind & TNK_LEAF)
- {
- parseDispTreeNode(tree, indent);
-
- switch (tree->tnOper)
- {
- case TN_NAME:
- printf("'%s'", tree->tnName.tnNameId->idSpelling());
- break;
-
- case TN_THIS:
- case TN_NULL:
- case TN_BASE:
- case TN_DBGBRK:
- break;
-
- default:
- NO_WAY(!"don't know how to display this leaf node");
- }
-
- printf("\n");
- return;
- }
-
- /* Is it a 'simple' unary/binary operator? */
-
- if (kind & TNK_SMPOP)
- {
- if (tree->tnOp.tnOp2)
- parseDispTree(tree->tnOp.tnOp2, indent + 1);
-
- parseDispTreeNode(tree, indent);
-
- /* Check for a few special cases */
-
- switch (tree->tnOper)
- {
- case TN_NEW:
- case TN_CAST:
- if (!(tree->tnFlags & TNF_BOUND))
- printf(" type='%s'", parseStab->stTypeName(tree->tnType, NULL));
- break;
-
- default:
- break;
- }
-
- printf("\n");
-
- if (tree->tnOp.tnOp1)
- parseDispTree(tree->tnOp.tnOp1, indent + 1);
-
- return;
- }
-
- /* See what kind of a special operator we have here */
-
- switch (tree->tnOper)
- {
- Tree name;
- Tree init;
-
- case TN_BLOCK:
-
- if (tree->tnBlock.tnBlkDecl)
- parseDispTree(tree->tnBlock.tnBlkDecl, indent + 1);
-
- parseDispTreeNode(tree, indent);
- printf(" parent=[%08X]", tree->tnBlock.tnBlkParent);
- printf( " decls=[%08X]", tree->tnBlock.tnBlkDecl );
- printf("\n");
-
- if (tree->tnBlock.tnBlkStmt)
- parseDispTree(tree->tnBlock.tnBlkStmt, indent + 1);
-
- break;
-
- case TN_VAR_DECL:
-
- init = NULL;
- name = tree->tnDcl.tnDclInfo;
-
- parseDispTreeNode(tree, indent);
- printf(" next=[%08X] ", tree->tnDcl.tnDclNext);
-
- if (name)
- {
- if (name->tnOper == TN_LIST)
- {
- init = name->tnOp.tnOp2;
- name = name->tnOp.tnOp1;
- }
-
- assert(name && name->tnOper == TN_NAME);
-
- printf("'%s'\n", name->tnName.tnNameId->idSpelling());
-
- if (init)
- parseDispTree(init, indent + 1);
- }
- else
- {
- SymDef vsym = tree->tnDcl.tnDclSym;
-
- assert(vsym && vsym->sdSymKind == SYM_VAR);
-
- printf("[sym=%08X] '%s'\n", vsym, vsym->sdSpelling());
- }
-
- break;
-
- case TN_FNC_SYM:
- case TN_FNC_PTR:
-
- if (tree->tnFncSym.tnFncObj)
- parseDispTree(tree->tnFncSym.tnFncObj, indent + 1);
-
- parseDispTreeNode(tree, indent);
- printf("'%s'\n", tree->tnFncSym.tnFncSym->sdSpelling());
-
- if (tree->tnFncSym.tnFncArgs)
- parseDispTree(tree->tnFncSym.tnFncArgs, indent + 1);
- return;
-
- case TN_LCL_SYM:
-
- parseDispTreeNode(tree, indent);
- if (tree->tnLclSym.tnLclSym->sdIsImplicit)
- printf(" TEMP(%d)\n", tree->tnLclSym.tnLclSym->sdVar.sdvILindex);
- else
- printf(" sym='%s'\n", parseStab->stTypeName(NULL, tree->tnLclSym.tnLclSym, NULL, NULL, true));
- break;
-
- case TN_VAR_SYM:
- case TN_PROPERTY:
-
- if (tree->tnVarSym.tnVarObj)
- parseDispTree(tree->tnVarSym.tnVarObj, indent + 1);
-
- parseDispTreeNode(tree, indent);
- printf(" sym='%s'\n", parseStab->stTypeName(NULL, tree->tnVarSym.tnVarSym, NULL, NULL, true));
- break;
-
- case TN_BFM_SYM:
-
- if (tree->tnBitFld.tnBFinst)
- parseDispTree(tree->tnBitFld.tnBFinst, indent + 1);
-
- parseDispTreeNode(tree, indent);
- printf(" offs=%04X BF=[%u/%u] sym='%s'\n", tree->tnBitFld.tnBFoffs,
- tree->tnBitFld.tnBFlen,
- tree->tnBitFld.tnBFpos,
- parseStab->stTypeName(NULL, tree->tnBitFld.tnBFmsym, NULL, NULL, true));
- break;
-
- case TN_ANY_SYM:
-
- parseDispTreeNode(tree, indent);
- printf(" sym='%s'\n", parseStab->stTypeName(NULL, tree->tnSym.tnSym, NULL, NULL, true));
- break;
-
- case TN_ERROR:
-
- parseDispTreeNode(tree, indent);
- printf("\n");
- break;
-
- case TN_SLV_INIT:
- parseDispTreeNode(tree, indent);
- printf(" at line #%u [offs=%04X]\n", tree->tnInit.tniSrcPos.dsdSrcLno,
- tree->tnInit.tniSrcPos.dsdBegPos);
- break;
-
- case TN_NONE:
- parseDispTreeNode(tree, indent);
- if (tree->tnType)
- printf(" type='%s'", parseStab->stTypeName(tree->tnType, NULL));
- printf("\n");
- break;
-
- default:
- parseDispTreeNode(tree, indent);
-
- printf("<DON'T KNOW HOW TO DISPLAY THIS NODE>\n");
- return;
- }
- }
-
- /*****************************************************************************/
- #endif//DEBUG
- /*****************************************************************************/
- /*****************************************************************************/
-