ctree.c

来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 737 行 · 第 1/2 页

C
737
字号
/****************************************************************************
*
*                            Open Watcom Project
*
*    Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
*  ========================================================================
*
*    This file contains Original Code and/or Modifications of Original
*    Code as defined in and that are subject to the Sybase Open Watcom
*    Public License version 1.0 (the 'License'). You may not use this file
*    except in compliance with the License. BY USING THIS FILE YOU AGREE TO
*    ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
*    provided with the Original Code and Modifications, and is also
*    available at www.sybase.com/developer/opensource.
*
*    The Original Code and all software distributed under the License are
*    distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
*    EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
*    ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
*    MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
*    NON-INFRINGEMENT. Please see the License for the specific language
*    governing rights and limitations under the License.
*
*  ========================================================================
*
* Description:  WHEN YOU FIGURE OUT WHAT THIS FILE DOES, PLEASE
*               DESCRIBE IT HERE!
*
****************************************************************************/


#include <stdarg.h>
#include <stdio.h>
#include <string.h>
#include "wic.h"

static pLabel _createLabel(LabelType type, void *data) {
    pLabel newLabel = wicMalloc(sizeof(Label));
    newLabel->type = type;
    newLabel->repr.data = data;
    return newLabel;
}

pLabel createTokenLabel(pToken token) {
    return _createLabel(LABT_TOKEN, token);
}

pLabel createListLabel(pSLList list) {
    return _createLabel(LABT_LIST, list);
}

pLabel createDeclInfoLabel(pDeclInfo dinfo) {
    return _createLabel(LABT_DECL_INFO, dinfo);
}

int isExternDecl(pDeclInfo decl) {
    if (decl == NULL) {
        return 0;
    } else {
        return decl->storage == STG_EXTERN;
    }
}

pLabel createDeclListLabel(pDeclList declList) {
    return _createLabel(LABT_DECL_LIST, declList);
}

pLabel createConstr0Label(LabelConstrType type) {
    pLabel newLabel = _createLabel(LABT_CONSTRUCT_ROOT, NULL);
    newLabel->repr.constr.type = type;
    newLabel->repr.constr.numTokens = 0;
    return newLabel;
}

pLabel createConstr1Label(LabelConstrType type, pToken t0) {
    pLabel newLabel = _createLabel(LABT_CONSTRUCT_ROOT, NULL);
    newLabel->repr.constr.type = type;
    newLabel->repr.constr.numTokens = 1;
    newLabel->repr.constr.tokens = wicMalloc(sizeof(pToken) * 1);
    newLabel->repr.constr.tokens[0] = t0;
    return newLabel;
}

pLabel createConstr2Label(LabelConstrType type, pToken t0, pToken t1) {
    pLabel newLabel = _createLabel(LABT_CONSTRUCT_ROOT, NULL);
    newLabel->repr.constr.type = type;
    newLabel->repr.constr.numTokens = 2;
    newLabel->repr.constr.tokens = wicMalloc(sizeof(pToken) * 2);
    newLabel->repr.constr.tokens[0] = t0;
    newLabel->repr.constr.tokens[1] = t1;
    return newLabel;
}

pLabel createConstr3Label(LabelConstrType type, pToken t0, pToken t1,
                          pToken t2) {
    pLabel newLabel = _createLabel(LABT_CONSTRUCT_ROOT, NULL);
    newLabel->repr.constr.type = type;
    newLabel->repr.constr.numTokens = 3;
    newLabel->repr.constr.tokens = wicMalloc(sizeof(pToken) * 3);
    newLabel->repr.constr.tokens[0] = t0;
    newLabel->repr.constr.tokens[1] = t1;
    newLabel->repr.constr.tokens[2] = t2;
    return newLabel;
}

pLabel createConstr4Label(LabelConstrType type, pToken t0, pToken t1,
                          pToken t2, pToken t3) {
    pLabel newLabel = _createLabel(LABT_CONSTRUCT_ROOT, NULL);
    newLabel->repr.constr.type = type;
    newLabel->repr.constr.numTokens = 4;
    newLabel->repr.constr.tokens = wicMalloc(sizeof(pToken) * 4);
    newLabel->repr.constr.tokens[0] = t0;
    newLabel->repr.constr.tokens[1] = t1;
    newLabel->repr.constr.tokens[2] = t2;
    newLabel->repr.constr.tokens[3] = t3;
    return newLabel;
}

pCTree createCTreeRoot(pLabel label) {
    pCTree newTree;

    newTree = wicMalloc(sizeof(CTree));
    newTree->label = label;
    newTree->child1 = NULL;
    newTree->child2 = NULL;
    return newTree;
}

pCTree createNULLCTree(void) {
    return NULL;
}

pCTree createCTree1(pLabel label, pCTree child) {
    pCTree newTree;

    newTree = createCTreeRoot(label);
    newTree->child1 = child;
    return newTree;
}

pCTree createCTree2(pLabel label, pCTree child1, pCTree child2) {
    pCTree newTree;

    newTree = createCTreeRoot(label);
    newTree->child1 = child1;
    newTree->child2 = child2;
    return newTree;
}

pLabel getCTreeLabel(pCTree tree) {
    return tree->label;
}

pLabel getCTreeChild1Label(pCTree tree) {
    return tree->child1->label;
}

pLabel getCTreeChild2Label(pCTree tree) {
    return tree->child2->label;
}

pCTree getCTreeChild1(pCTree tree) {
    return tree->child1;
}

pCTree getCTreeChild2(pCTree tree) {
    return tree->child2;
}

/*************************************************************************/

pDclrList createDclrList(pDclr elem) {
    pDclrList list = createSLList();
    addSLListElem(list, elem);
    return list;
}

pDclrList addDclrList(pDclrList list, pDclr elem) {
    addSLListElem(list, elem);
    return list;
}

static void _addScalarTypeToDeclInfo(pDeclInfo dinfo, YScalarType tokCode);

static pDeclInfo _createDeclInfo(DeclInfoType type) {
    pDeclInfo newDInfo;

    newDInfo = wicMalloc(sizeof *newDInfo);

    newDInfo->begPunct = NULL;
    newDInfo->qualifier = STY_NULL;
    newDInfo->storage = STG_NULL;
    newDInfo->prefixPos = NULL;
    newDInfo->dclrList = NULL;
    newDInfo->dclr = NULL;
    newDInfo->type = type;
    return newDInfo;
};

pDeclInfo createQualifierDeclInfo(TypeQualifier qualifier, pTokPos pos) {
    pDeclInfo newDecl = _createDeclInfo(DIT_NULL);
    newDecl->qualifier = qualifier;
    newDecl->prefixPos = combine2TokPos(newDecl->prefixPos, pos);
    return newDecl;
}

pDeclInfo createStgClassDeclInfo(StgClass stgClass, pToken pos) {
    pDeclInfo newDecl = _createDeclInfo(DIT_NULL);
    newDecl->storage = stgClass;
    newDecl->prefixPos = combine2TokPos(newDecl->prefixPos, pos->pos);
    pos->pos = NULL;
    zapToken(pos);
    return newDecl;
}

pDeclInfo createDeclInfoENUM(pDeclEnum e) {
    pDeclInfo newDecl = _createDeclInfo(DIT_ENUM);
    newDecl->repr.e = e;
    return newDecl;
}

pDeclInfo createDeclInfoSTRUCT(pDeclStructInfo s) {
    pDeclInfo newDecl = _createDeclInfo(DIT_STRUCT_OR_UNION);
    newDecl->repr.s = s;
    return newDecl;
}

pDeclInfo createDeclInfoSCALAR(YScalarType tokCode, pTokPos pos) {
    pDeclInfo newDecl = _createDeclInfo(DIT_SCALAR);
    newDecl->repr.scalar.scalar = SCL_NULL;
    newDecl->repr.scalar.scalarCombo = STM_NULL;
    newDecl->repr.scalar.scalarPos = pos;
    _addScalarTypeToDeclInfo(newDecl, tokCode);
    return newDecl;
}

void initNoTypeDecl(pDeclInfo decl) {
    if (decl->type == DIT_NULL) {
        decl->type = DIT_SCALAR;
        decl->repr.scalar.scalar = SCL_NULL;
        decl->repr.scalar.scalarCombo = STM_NULL;
        decl->repr.scalar.scalarPos = NULL;
        _addScalarTypeToDeclInfo(decl, STM_INT);
    }
}

static void _addScalarTypeToDeclInfo(pDeclInfo dinfo, YScalarType tokCode) {
    int i;

    static struct {
        ScalarType     id;
        YScalarType    combo;
    } listOfScalarTypes[] = {
        { SCL_CHAR,              STM_CHAR },
        { SCL_SCHAR,             STM_CHAR | STM_SIGNED },
        { SCL_UCHAR,             STM_CHAR | STM_UNSIGNED },
        { SCL_SSHORT,            STM_SHORT },
        { SCL_SSHORT,            STM_SHORT | STM_INT },
        { SCL_SSHORT,            STM_SHORT | STM_SIGNED },
        { SCL_SSHORT,            STM_SHORT | STM_SIGNED | STM_INT },
        { SCL_USHORT,            STM_SHORT | STM_UNSIGNED },
        { SCL_USHORT,            STM_SHORT | STM_UNSIGNED | STM_INT },
        { SCL_SINT,              STM_SIGNED },
        { SCL_SINT,              STM_INT },
        { SCL_SINT,              STM_INT | STM_SIGNED },
        { SCL_UINT,              STM_INT | STM_UNSIGNED },
        { SCL_UINT,              STM_UNSIGNED },
        { SCL_SLONG,             STM_LONG },
        { SCL_SLONG,             STM_LONG | STM_SIGNED },
        { SCL_ULONG,             STM_LONG | STM_UNSIGNED },
        { SCL_SLONG,             STM_LONG | STM_INT },
        { SCL_SLONG,             STM_LONG | STM_INT | STM_SIGNED },
        { SCL_ULONG,             STM_LONG | STM_INT | STM_UNSIGNED },
        { SCL_FLOAT,             STM_FLOAT },
        { SCL_DOUBLE,            STM_DOUBLE },
        { SCL_VOID,              STM_VOID },
        { SCL_LDOUBLE,           STM_LONG | STM_DOUBLE },
        { SCL_WCHAR,             STM_LONG | STM_CHAR },
        { SCL_DOT_DOT_DOT,       STM_DOT_DOT_DOT },
        { SCL_NULL,              STM_NULL }
    };

    assert(dinfo->type == DIT_SCALAR);

    tokCode |= dinfo->repr.scalar.scalarCombo;
    i = 0;
    while (listOfScalarTypes[i].id != 0) {
        if (listOfScalarTypes[i].combo == tokCode) {
            dinfo->repr.scalar.scalar = listOfScalarTypes[i].id;
            dinfo->repr.scalar.scalarCombo = tokCode;
            return;
        }
        i++;
    }
    reportError(RERR_INV_TYPE_COMBO);
}

pDeclInfo combine2DeclInfo(pDeclInfo d1, pDeclInfo d2) {
    assert(d1 != NULL); assert(d2 != NULL);
    assert(d1 != d2);
    assert(d1->dclrList == NULL); assert(d2->dclrList == NULL);

    d1->prefixPos = combine2TokPos(d1->prefixPos, d2->prefixPos);
    d2->prefixPos = NULL;
    if (d1->storage == STG_NULL) {
        if (d2->storage != STG_NULL) {
            d1->storage = d2->storage;
        }
    } else if (d2->storage != STG_NULL) {
        reportError(RERR_INV_TYPE_COMBO);
    }

    if (d1->qualifier != STY_NULL && d1->qualifier == d2->qualifier) {
        reportError(RERR_INV_TYPE_COMBO);
    } else {
        d1->qualifier |= d2->qualifier;
    }

    if (d1->type == DIT_NULL) {
        d1->type = d2->type;
        switch (d2->type) {
            case DIT_NULL:
                break;

            case DIT_SCALAR:
                d1->repr.scalar.scalar = SCL_NULL;
                d1->repr.scalar.scalarCombo = STM_NULL;
                d1->repr.scalar.scalarPos =
                                    d2->repr.scalar.scalarPos;
                                    d2->repr.scalar.scalarPos = NULL;
                _addScalarTypeToDeclInfo(d1, d2->repr.scalar.scalarCombo);
                break;

            case DIT_STRUCT_OR_UNION:
                d1->repr.s = d2->repr.s; d2->repr.s = NULL;
                break;

            case DIT_ENUM:
                d1->repr.e = d2->repr.e;   d2->repr.e = NULL;
                break;

            default:
                assert(0);
        }
    } else if (d1->type == DIT_SCALAR && d2->type == DIT_SCALAR) {
        _addScalarTypeToDeclInfo(d1, d2->repr.scalar.scalarCombo);
    } else {
        reportError(RERR_INV_TYPE_COMBO);
    }

    d1->dclr = combine2Dclr(d1->dclr, d2->dclr);    d2->dclr = NULL;

    zapDeclInfo(d2);
    return d1;
}

pDeclStructInfo createDeclStructInfo(pToken typeTok,
                                     pToken name, pDeclStructBody body) {
    pDeclStructInfo newSI;

    newSI = wicMalloc(sizeof *newSI);
    if (typeTok->data->code == Y_STRUCT) {
        newSI->type = DSIT_STRUCT;
    } else if (typeTok->data->code == Y_UNION) {
        newSI->type = DSIT_UNION;
    } else {
        assert(0);
    }

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?