trandecl.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 557 行 · 第 1/2 页
C
557 行
/****************************************************************************
*
* 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 <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "wic.h"
static char * NAME_PREFIX = "STRUN"; // struct/union
typedef enum {
DECL_INFO,
DECL_TREE_ELEM
} DeclTreeElemType;
struct DeclTreeElem {
DeclTreeElemType type;
union {
pDeclInfo decl;
pDeclTree list;
};
};
pDeclTreeElem createDeclTreeElem(DeclTreeElemType type, void *data) {
pDeclTreeElem newElem = wicMalloc(sizeof *newElem);
newElem->type = type;
if (type == DECL_TREE_ELEM) {
newElem->list = data;
} else if (type == DECL_INFO) {
newElem->decl = data;
} else {
assert(0);
}
return newElem;
}
static void zapDeclTreeElem(void *_elem) {
pDeclTreeElem elem = _elem;
if (elem == NULL) {
return;
}
switch(elem->type) {
case DECL_INFO:
zapDeclInfo(elem->decl);
break;
case DECL_TREE_ELEM:
zapSLList(elem->list, zapDeclTreeElem);
break;
default:
assert(0);
}
wicFree(elem);
}
char *_get1stDclrName(pDclrList list) {
pDclr dclr;
rewindCurrSLListPos(list);
if (!getCurrSLListPosElem(list, &dclr)) {
reportError(FATAL_INTERNAL, "In _get1stDclrName");
}
assert(dclr != NULL);
assert(dclr->id != NULL);
return getDclrName(dclr);
}
char *_createUnnamedDeclStructDclrList(pDeclInfo decl) {
static char noname[] = { "noname " };
static unsigned int counter = 1;
pTokPos endPos;
sprintf(noname+6, "%d", counter); // 6 is strlen("noname")
counter++;
if (decl->repr.s->body == NULL) {
endPos = decl->repr.s->name->pos;
} else {
endPos = decl->repr.s->body->endPos;
}
decl->dclrList = createDclrList (
createDclr(
createIDTokenAfter(
noname,
endPos
)
)
);
return noname;
}
static char *_nameUnnamedStruct(pDeclInfo decl, char *baseName, int level){
// Name the sturct/union if it does not have name;
// Return NULL if error occures; Return a named struct otherwise.
char *name;
char *retVal;
int addBase = 1;
if (decl->storage == STG_TYPEDEF) {
zapToken(decl->repr.s->name); decl->repr.s->name = NULL;
addBase = 0;
}
if (decl->repr.s->name == NULL) {
if (decl->dclrList == NULL) {
if (level > 0) {
name = _createUnnamedDeclStructDclrList(decl);
} else {
name = "INVALID";
reportError(RERR_INCOMPLETE_TYPE);
}
} else {
name = _get1stDclrName(decl->dclrList);
}
} else {
name = getTokenIdName(decl->repr.s->name);
if (decl->dclrList == NULL && level > 0) {
name = _createUnnamedDeclStructDclrList(decl);
}
}
if (decl->repr.s->name == NULL) {
if (addBase) {
retVal = wicMalloc(strlen(baseName) + strlen(name) + 2);
sprintf(retVal, "%s_%s", baseName, name);
} else {
retVal = wicStrdup(name);
}
decl->repr.s->name = createIDTokenAfter(
retVal,
dupTokPos(decl->repr.s->typePos, NULL)
);
}
retVal = getTokenIdName(decl->repr.s->name);
return retVal;
}
static int _nameUnnamed(pDeclInfo decl, char *baseName, int level) {
char *name;
switch (decl->type) {
case DIT_ENUM:
case DIT_SCALAR:
return 1;
case DIT_STRUCT_OR_UNION:
assert(decl->repr.s != NULL);
name = _nameUnnamedStruct(decl, baseName, level);
if (name == NULL) {
reportError(RERR_INCOMPLETE_TYPE);
return 0;
}
if (decl->repr.s->body != NULL) {
pDeclList list = decl->repr.s->body->declList;
pDeclInfo node;
assert(list != NULL);
rewindCurrSLListPos(list);
while (getCurrSLListPosElem(list, &node)) {
incCurrSLListPos(list);
_nameUnnamed(node, name, level+1);
}
}
return 1;
case DIT_NULL:
reportError(RERR_INCOMPLETE_TYPE);
return 0;
default:
assert(0);
}
return 1;
}
static pDeclTree _unNestDecl(pDeclInfo decl) {
pDeclTree retVal = NULL;
switch (decl->type) {
case DIT_SCALAR:
retVal = createSLList();
addSLListElem(retVal, createDeclTreeElem(DECL_INFO, decl));
break;
case DIT_STRUCT_OR_UNION:
{
pDeclStructBody body;
pDeclTree prepend = createSLList();
body = decl->repr.s->body;
if (body != NULL) {
pDeclInfo node;
pDeclTreeElem node1, node2;
pDeclTree inside;
rewindCurrSLListPos(body->declList);
while (getCurrSLListPosElem(body->declList, &node)) {
inside = _unNestDecl(node);
rewindCurrSLListPos(inside);
if (!getCurrSLListPosElem(inside, &node1)) {
reportError(FATAL_INTERNAL, "In _unNestDecl");
}
incCurrSLListPos(inside);
if (getCurrSLListPosElem(inside, &node2))
{
addSLListElem(prepend, node1);
setCurrSLListPosElem(body->declList, node2->decl);
}
incCurrSLListPos(body->declList);
}
if (decl->dclrList != NULL) {
pDeclInfo newDecl;
assert(decl->repr.s->typePos != NULL);
newDecl = dupDeclInfo(decl, decl->repr.s->typePos);
zapDeclStructBody(newDecl->repr.s->body);
newDecl->repr.s->body = NULL;
zapSLList(decl->dclrList, zapDclr);
decl->dclrList = NULL;
addSLListElem(prepend, createDeclTreeElem(DECL_INFO, decl));
retVal = createSLList();
addSLListElem(retVal,
createDeclTreeElem(DECL_TREE_ELEM, prepend) );
addSLListElem(retVal, createDeclTreeElem(DECL_INFO, newDecl));
} else {
addSLListElem(prepend, createDeclTreeElem(DECL_INFO, decl));
retVal = prepend;
}
} else {
retVal = createSLList();
addSLListElem(retVal, createDeclTreeElem(DECL_INFO, decl));
}
break;
}
case DIT_ENUM:
{
pDeclEnum e;
pDclrList saveDclrList;
e = decl->repr.e;
assert(e != NULL);
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?