Now handles forward declared structures correctly.
Issue #166 git-svn-id: http://picoc.googlecode.com/svn/trunk@583 21eae674-98b7-11dd-bd71-f92a316d2d60
This commit is contained in:
parent
35e64fa8c1
commit
9ec50b6e49
|
@ -515,6 +515,7 @@ void TypeParseIdentPart(struct ParseState *Parser, struct ValueType *BasicTyp, s
|
|||
void TypeParse(struct ParseState *Parser, struct ValueType **Typ, char **Identifier, int *IsStatic);
|
||||
struct ValueType *TypeGetMatching(Picoc *pc, struct ParseState *Parser, struct ValueType *ParentType, enum BaseType Base, int ArraySize, const char *Identifier, int AllowDuplicates);
|
||||
struct ValueType *TypeCreateOpaqueStruct(Picoc *pc, struct ParseState *Parser, const char *StructName, int Size);
|
||||
int TypeIsForwardDeclared(struct ParseState *Parser, struct ValueType *Typ);
|
||||
|
||||
/* heap.c */
|
||||
void HeapInit(Picoc *pc, int StackSize);
|
||||
|
|
18
tests/56_cross_structure.c
Normal file
18
tests/56_cross_structure.c
Normal file
|
@ -0,0 +1,18 @@
|
|||
#include <stdio.h>
|
||||
|
||||
struct s1;
|
||||
|
||||
struct s2
|
||||
{
|
||||
struct s1 *s;
|
||||
};
|
||||
|
||||
struct s1
|
||||
{
|
||||
struct s2 *s;
|
||||
};
|
||||
|
||||
void main()
|
||||
{
|
||||
printf("ok\n");
|
||||
}
|
1
tests/56_cross_structure.expect
Normal file
1
tests/56_cross_structure.expect
Normal file
|
@ -0,0 +1 @@
|
|||
ok
|
|
@ -49,7 +49,8 @@ TESTS= 00_assignment.test \
|
|||
51_static.test \
|
||||
52_unnamed_enum.test \
|
||||
54_goto.test \
|
||||
55_array_initialiser.test
|
||||
55_array_initialiser.test \
|
||||
56_cross_structure.test
|
||||
|
||||
%.test: %.expect %.c
|
||||
@echo Test: $*...
|
||||
|
|
18
type.c
18
type.c
|
@ -198,15 +198,18 @@ void TypeParseStruct(struct ParseState *Parser, struct ValueType **Typ, int IsSt
|
|||
StructIdentifier = PlatformMakeTempName(pc, TempNameBuf);
|
||||
}
|
||||
|
||||
*Typ = TypeGetMatching(pc, Parser, &Parser->pc->UberType, IsStruct ? TypeStruct : TypeUnion, 0, StructIdentifier, Token != TokenLeftBrace);
|
||||
*Typ = TypeGetMatching(pc, Parser, &Parser->pc->UberType, IsStruct ? TypeStruct : TypeUnion, 0, StructIdentifier, TRUE);
|
||||
if (Token == TokenLeftBrace && (*Typ)->Members != NULL)
|
||||
ProgramFail(Parser, "data type '%t' is already defined", *Typ);
|
||||
|
||||
Token = LexGetToken(Parser, NULL, FALSE);
|
||||
if (Token != TokenLeftBrace)
|
||||
{
|
||||
/* use the already defined structure */
|
||||
#if 0
|
||||
if ((*Typ)->Members == NULL)
|
||||
ProgramFail(Parser, "structure '%s' isn't defined", LexValue->Val->Identifier);
|
||||
|
||||
#endif
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -527,3 +530,14 @@ void TypeParse(struct ParseState *Parser, struct ValueType **Typ, char **Identif
|
|||
TypeParseIdentPart(Parser, BasicType, Typ, Identifier);
|
||||
}
|
||||
|
||||
/* check if a type has been fully defined - otherwise it's just a forward declaration */
|
||||
int TypeIsForwardDeclared(struct ParseState *Parser, struct ValueType *Typ)
|
||||
{
|
||||
if (Typ->Base == TypeArray)
|
||||
return TypeIsForwardDeclared(Parser, Typ->FromType);
|
||||
|
||||
if ( (Typ->Base == TypeStruct || Typ->Base == TypeUnion) && Typ->Members == NULL)
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
|
|
@ -185,6 +185,10 @@ struct Value *VariableDefineButIgnoreIdentical(struct ParseState *Parser, char *
|
|||
int DeclLine;
|
||||
int DeclColumn;
|
||||
|
||||
/* is the type a forward declaration? */
|
||||
if (TypeIsForwardDeclared(Parser, Typ))
|
||||
ProgramFail(Parser, "type '%t' isn't defined", Typ);
|
||||
|
||||
if (IsStatic)
|
||||
{
|
||||
char MangledName[LINEBUFFER_MAX];
|
||||
|
|
Loading…
Reference in a new issue