Skip to content

Commit

Permalink
fbc: nested types - fix static fields and typos
Browse files Browse the repository at this point in the history
- Add new FB_UDTOPT_HASNESTED flag to track when
  a UDT has nested named types.  This can help determine
  if searching or checking inside a type's member's
  is necessary or not.
- symbIsParentNamespace(): add early out if type has no
  nested named types.  This effectively reverts the check
  to similar logic before nested named types were added.
- in hIsStructAllowed() don't assume that types don't
  have nested named types.  Test FB_UDTOPT_HASNESTED
  instead.  This fixes access to static fields when
  defining the static variable outside of the type.
- fix typo in hPatchByvalParamsToSelf() -> param
- in hPatchByvalParamsToSelf()/hPatchByvalResultToSelf(),
  only recurse in to types if  FB_UDTOPT_HASNESTED is set
  • Loading branch information
jayrm committed Oct 21, 2022
1 parent ecfdb3e commit 944b969
Show file tree
Hide file tree
Showing 5 changed files with 73 additions and 49 deletions.
2 changes: 1 addition & 1 deletion changelog.txt
Expand Up @@ -42,7 +42,7 @@ Version 1.10.0
- makefile: 'DISABLE_GAS64_DEBUG=1' makefile configuration option to disable debugging comments in gas64 asm files
- gfxlib2: add FB.GET_SCANLINE_SIZE to fbgfx.bi and ScreenControl() to get current internal scan line size multiplier
- gfxlib2: SCREENCONTROL: add getters for GL parameters - new GET_GL_* constants in fbgfx.bi
- fbc: allow a TYPE or UNION to be declared inside another TYPE or UNION to allow declaration of inner named types. Support c++ name mangling parameters of inner types.
- fbc: allow a TYPE or UNION to be declared inside another TYPE or UNION to allow declaration of nested named types. Support c++ name mangling parameters of named nested types. Support definition of variables declared in a named nested type.
- Name mangling for c++ 'char' through BYTE/UBYTE parameters using the form "[unsigned] byte alias "char". Data type size is still 8 byte signed/unsigned from fbc side, but will mangled as 'char'; neither signed nor unsigned for the c++ side.
- Support 'SOURCE_DATE_EPOCH' environment variable for controlling the instrinsic __DATE__, __DATE_ISO__, __TIME__ macros. This in turn controls __FB_BUILD_DATE__ and __FB_BUILD_DATE_ISO__ macros when building the compiler. Report error message on malformed values.
- fbc -nolib a,b,c command line option for selectively excluding specific libraries when linking (more fine-grained control than -nodeflibs, and not only for default libraries)
Expand Down
62 changes: 33 additions & 29 deletions src/compiler/parser-decl-struct.bas
Expand Up @@ -879,6 +879,7 @@ decl_inner:
'' allow named UNION|TYPE to be nested in another UNION|TYPE
else
hBeginNesting( s )
symbSetUdtHasNested( s )
cTypeDecl( attrib )

end if
Expand Down Expand Up @@ -1203,10 +1204,8 @@ private sub hPatchByvalParamsToSelf( byval parent as FBSYMBOL ptr )
param = symbGetProcHeadParam( sym )
while( param )
'' BYVAL AS ParentUDT?
if( (symbGetType( param ) = FB_DATATYPE_STRUCT) and _
(symbIsParentNamespace( symbGetType( sym ), symbGetSubtype( sym ), parent)) ) then

if( symbGetParamMode( param ) = FB_PARAMMODE_BYVAL ) then
if( symbGetParamMode( param ) = FB_PARAMMODE_BYVAL ) then
if( symbIsParentNamespace( symbGetType( param ), symbGetSubtype( param ), parent) ) then
symbRecalcLen( param )
end if
end if
Expand All @@ -1218,14 +1217,17 @@ private sub hPatchByvalParamsToSelf( byval parent as FBSYMBOL ptr )
sym = sym->next
wend

'' recurse in to nested types
sym = symbGetUDTSymbtb( parent ).head
while( sym )
if( symbIsStruct( sym ) ) then
hPatchByvalParamsToSelf( sym )
end if
sym = sym->next
wend
'' recurse in to nested types only if the type
'' is expected to have nested types
if( symbGetUdtHasNested( parent ) ) then
sym = symbGetUDTSymbtb( parent ).head
while( sym )
if( symbIsStruct( sym ) ) then
hPatchByvalParamsToSelf( sym )
end if
sym = sym->next
wend
end if

end sub

Expand All @@ -1236,28 +1238,30 @@ private sub hPatchByvalResultToSelf( byval parent as FBSYMBOL ptr )
while( sym )

'' Function or static variable? Using parent UDT as Byval (result) data type?
if( (symbGetType( sym ) = FB_DATATYPE_STRUCT) and _
(symbIsParentNamespace( symbGetType( sym ), symbGetSubtype( sym ), parent)) and _
(not symbIsRef( sym )) ) then

if( symbIsProc( sym ) ) then
symbProcRecalcRealType( sym )
'' (FBSYMBOL->lgt is 0 for procedures anyways, no need to update)
elseif( symbIsVar( sym ) ) then
symbRecalcLen( sym )
if( not symbIsRef( sym ) ) then
if( symbIsParentNamespace( symbGetType( sym ), symbGetSubtype( sym ), parent ) ) then
if( symbIsProc( sym ) ) then
symbProcRecalcRealType( sym )
'' (FBSYMBOL->lgt is 0 for procedures anyways, no need to update)
elseif( symbIsVar( sym ) ) then
symbRecalcLen( sym )
end if
end if
end if

sym = sym->next
wend

'' recurse in to nested types
sym = symbGetUDTSymbtb( parent ).head
while( sym )
if( symbIsStruct( sym ) ) then
hPatchByvalResultToSelf( sym )
end if
sym = sym->next
wend
'' recurse in to nested types only if the type
'' is expected to have nested types
if( symbGetUdtHasNested( parent ) ) then
sym = symbGetUDTSymbtb( parent ).head
while( sym )
if( symbIsStruct( sym ) ) then
hPatchByvalResultToSelf( sym )
end if
sym = sym->next
wend
end if

end sub
6 changes: 6 additions & 0 deletions src/compiler/parser-identifier.bas
Expand Up @@ -174,6 +174,12 @@ private function hIsStructAllowed _
return FALSE
end if

'' if the struct has nested types, don't do any other checks
'' since the type name could be used as a namespace prefix
if( symbGetUdtHasNested( sym ) ) then
return TRUE
end if

'' Ordinary/non-class struct? Won't ever be used as namespace prefix,
'' since it doesn't have any methods/static member vars
if( symbGetIsUnique( sym ) = FALSE ) then
Expand Down
10 changes: 10 additions & 0 deletions src/compiler/symb.bas
Expand Up @@ -2331,11 +2331,21 @@ function symbIsParentNamespace _
return FALSE
end if

if( subtype = NULL ) then
return FALSE
end if

if( start_ns ) then
context = start_ns
else
context = symbGetCurrentNamespc( )
end if

'' no nested types? check current namespace / context only
if( symbGetUdtHasNested( subtype ) = FALSE ) then
return ( context = subtype )
end if

while( context <> @symbGetGlobalNamespc( ) )
if( symbGetClass( context ) = FB_SYMBCLASS_STRUCT ) then
if( context = subtype ) then
Expand Down
42 changes: 23 additions & 19 deletions src/compiler/symb.bi
Expand Up @@ -474,25 +474,26 @@ end type

'' structure
enum FB_UDTOPT
FB_UDTOPT_ISUNION = &h0001
FB_UDTOPT_ISANON = &h0002
FB_UDTOPT_HASPTRFIELD = &h0004
FB_UDTOPT_HASCTORFIELD = &h0008
FB_UDTOPT_HASDTORFIELD = &h0010
FB_UDTOPT_HASRECBYVALPARAM = &h0020
FB_UDTOPT_HASRECBYVALRES = &h0040
FB_UDTOPT_HASGETPROPERTY = &h0080
FB_UDTOPT_HASSETPROPERTY = &h0100
FB_UDTOPT_HASIDXGETPROPERTY = &h0200
FB_UDTOPT_HASIDXSETPROPERTY = &h0400
FB_UDTOPT_HASKWDFIELD = &h0800
FB_UDTOPT_HASINITEDFIELD = &h1000
FB_UDTOPT_HASANONUNION = &h2000
FB_UDTOPT_HASSTATICVAR = &h4000
FB_UDTOPT_HASBITFIELD = &h8000
FB_UDTOPT_ISWSTRING = &h10000
FB_UDTOPT_ISZSTRING = &h20000
FB_UDTOPT_VALISTTYPEMASK = &hf00000
FB_UDTOPT_ISUNION = &h00000001
FB_UDTOPT_ISANON = &h00000002
FB_UDTOPT_HASPTRFIELD = &h00000004
FB_UDTOPT_HASCTORFIELD = &h00000008
FB_UDTOPT_HASDTORFIELD = &h00000010
FB_UDTOPT_HASRECBYVALPARAM = &h00000020
FB_UDTOPT_HASRECBYVALRES = &h00000040
FB_UDTOPT_HASGETPROPERTY = &h00000080
FB_UDTOPT_HASSETPROPERTY = &h00000100
FB_UDTOPT_HASIDXGETPROPERTY = &h00000200
FB_UDTOPT_HASIDXSETPROPERTY = &h00000400
FB_UDTOPT_HASKWDFIELD = &h00000800
FB_UDTOPT_HASINITEDFIELD = &h00001000
FB_UDTOPT_HASANONUNION = &h00002000
FB_UDTOPT_HASSTATICVAR = &h00004000
FB_UDTOPT_HASBITFIELD = &h00008000
FB_UDTOPT_ISWSTRING = &h00010000
FB_UDTOPT_ISZSTRING = &h00020000
FB_UDTOPT_HASNESTED = &h00040000
FB_UDTOPT_VALISTTYPEMASK = &h00f00000
end enum

type FB_STRUCT_DBG
Expand Down Expand Up @@ -2375,6 +2376,9 @@ declare function symbCloneSimpleStruct( byval sym as FBSYMBOL ptr ) as FBSYMBOL
#define symbSetUdtIsWstring( s ) (s)->udt.options or= FB_UDTOPT_ISWSTRING
#define symbGetUdtIsWstring( s ) (((s)->udt.options and FB_UDTOPT_ISWSTRING) <> 0 )

#define symbSetUdtHasNested( s ) (s)->udt.options or= FB_UDTOPT_HASNESTED
#define symbGetUdtHasNested( s ) (((s)->udt.options and FB_UDTOPT_HASNESTED) <> 0)

#define symbGetUDTIsUnionOrAnon(s) (((s)->udt.options and (FB_UDTOPT_ISUNION or FB_UDTOPT_ISANON)) <> 0)

#define symbGetUDTAlign(s) s->udt.align
Expand Down

0 comments on commit 944b969

Please sign in to comment.