enums implemented

git-svn-id: http://picoc.googlecode.com/svn/trunk@180 21eae674-98b7-11dd-bd71-f92a316d2d60
This commit is contained in:
zik.saleeba 2009-03-09 22:36:01 +00:00
parent 2f5a46681e
commit 23bce9d38a
7 changed files with 88 additions and 3 deletions

View file

@ -350,6 +350,7 @@ int ParseStatement(struct ParseState *Parser)
case TokenVoidType:
case TokenStructType:
case TokenUnionType:
case TokenEnumType:
*Parser = PreState;
ParseDeclaration(Parser, Token);
break;

View file

@ -115,7 +115,7 @@ struct ValueType
struct ValueType *FromType; /* the type we're derived from (or NULL) */
struct ValueType *DerivedTypeList; /* first in a list of types derived from this one */
struct ValueType *Next; /* next item in the derived type list */
struct Table *Members; /* members of a struct, union or enum */
struct Table *Members; /* members of a struct or union */
};
/* function definition */
@ -170,7 +170,6 @@ struct Value
char ValOnHeap; /* the AnyValue is on the heap (but this Value is on the stack) */
char ValOnStack; /* the AnyValue is on the stack along with this Value */
char IsLValue; /* is modifiable and is allocated somewhere we can usefully modify it */
char TempToken; /* temporary token used in expression evaluation */
};
/* hash table data structure */

View file

@ -4,6 +4,7 @@
/* get a line of interactive input */
char *PlatformGetLine(char *Buf, int MaxLen)
{
fflush(stdout);
return fgets(Buf, MaxLen, stdin);
}

18
tests/17_enum.c Normal file
View file

@ -0,0 +1,18 @@
enum fred
{
a,
b,
c,
d,
e = 54,
f = 73,
g,
h
} frod;
printf("%d %d %d %d %d %d %d %d\n", a, b, c, d, e, f, g, h);
printf("%d\n", frod);
frod = 12;
printf("%d\n", frod);
frod = e;
printf("%d\n", frod);

4
tests/17_enum.expect Normal file
View file

@ -0,0 +1,4 @@
0 1 2 3 54 73 74 75
0
12
54

View file

@ -12,7 +12,8 @@ TESTS= 00_assignment.test \
12_hashdefine.test \
13_integer_literals.test \
14_if.test \
16_nesting.test
16_nesting.test \
17_enum.test
%.test: %.expect %.c
@echo Test: $*...

61
type.c
View file

@ -175,6 +175,60 @@ void TypeParseStruct(struct ParseState *Parser, struct ValueType **Typ, int IsSt
LexGetToken(Parser, NULL, TRUE);
}
/* parse an enum declaration */
void TypeParseEnum(struct ParseState *Parser, struct ValueType **Typ)
{
struct Value *LexValue;
struct Value InitValue;
enum LexToken Token;
struct ValueType *EnumType;
int EnumValue = 0;
char *EnumIdentifier;
if (TopStackFrame != NULL)
ProgramFail(Parser, "enum definitions can only be globals");
if (LexGetToken(Parser, &LexValue, TRUE) != TokenIdentifier)
ProgramFail(Parser, "enum name required");
*Typ = &IntType;
EnumType = TypeGetMatching(Parser, &UberType, TypeEnum, 0, LexValue->Val->Identifier);
Token = LexGetToken(Parser, NULL, FALSE);
if (Token != TokenLeftBrace)
{ /* use the already defined enum */
if ((*Typ)->Members == NULL)
ProgramFail(Parser, "enum '%s' isn't defined", LexValue->Val->Identifier);
return;
}
LexGetToken(Parser, NULL, TRUE);
(*Typ)->Members = &GlobalTable;
memset(&InitValue, '\0', sizeof(struct Value));
InitValue.Typ = &IntType;
InitValue.Val = (union AnyValue *)&EnumValue;
do {
if (LexGetToken(Parser, &LexValue, TRUE) != TokenIdentifier)
ProgramFail(Parser, "identifier expected");
EnumIdentifier = LexValue->Val->Identifier;
if (LexGetToken(Parser, NULL, FALSE) == TokenAssign)
{
LexGetToken(Parser, NULL, TRUE);
EnumValue = ExpressionParseInt(Parser);
}
VariableDefine(Parser, EnumIdentifier, &InitValue);
Token = LexGetToken(Parser, NULL, TRUE);
if (Token != TokenComma && Token != TokenRightBrace)
ProgramFail(Parser, "comma expected");
EnumValue++;
} while (Token == TokenComma);
}
/* parse a type - just the basic type */
int TypeParseFront(struct ParseState *Parser, struct ValueType **Typ)
{
@ -198,6 +252,13 @@ int TypeParseFront(struct ParseState *Parser, struct ValueType **Typ)
TypeParseStruct(Parser, Typ, Token == TokenStructType);
break;
case TokenEnumType:
if (*Typ != NULL)
ProgramFail(Parser, "bad type declaration");
TypeParseEnum(Parser, Typ);
break;
default: *Parser = Before; return FALSE;
}