瀏覽代碼

Fixed various Struct init issues. Fixes #436.

woollybah 6 年之前
父節點
當前提交
418efeb967
共有 4 個文件被更改,包括 31 次插入30 次删除
  1. 21 7
      ctranslator.bmx
  2. 3 19
      decl.bmx
  3. 1 1
      options.bmx
  4. 6 3
      parser.bmx

+ 21 - 7
ctranslator.bmx

@@ -1626,7 +1626,7 @@ t:+"NULLNULLNULL"
 			End If
 
 			If expr.instanceExpr Then
-				If expr.classDEcl.IsStruct() Then
+				If expr.classDecl.IsStruct() Then
 					t = ctorMunged + "_ObjectNew" + TransArgs( expr.args,expr.ctor)
 				Else
 					t = "_" + ctorMunged + "_ObjectNew" + TransArgs( expr.args,expr.ctor, Bra(expr.instanceExpr.Trans()) + "->clas" )
@@ -1652,7 +1652,8 @@ t:+"NULLNULLNULL"
 
 		If expr.expr.length = 1 Then
 			If TObjectType(expr.ty) And TObjectType(expr.ty).classdecl.IsStruct() And Not IsPointerType(expr.ty) Then
-				Return "bbArrayNew1DStruct" + Bra(TransArrayType(expr.ty) + ", " + expr.expr[0].Trans() + ", sizeof" + Bra(TransObject(TObjectType(expr.ty).classdecl)))
+				Return "bbArrayNew1DStruct" + Bra(TransArrayType(expr.ty) + ", " + expr.expr[0].Trans() + ", sizeof" + ..
+						Bra(TransObject(TObjectType(expr.ty).classdecl)) + ", _" + TObjectType(expr.ty).classdecl.munged + "_New")
 			Else
 				Return "bbArrayNew1D" + Bra(TransArrayType(expr.ty) + ", " + expr.expr[0].Trans())
 			End If
@@ -1669,7 +1670,8 @@ t:+"NULLNULLNULL"
 			Next
 
 			If TObjectType(expr.ty) And TObjectType(expr.ty).classdecl.IsStruct() And Not IsPointerType(expr.ty) Then
-				Return "bbArrayNewStruct" + Bra(TransArrayType(expr.ty) + ", sizeof" + Bra(TransObject(TObjectType(expr.ty).classdecl)) + ", " + expr.expr.length + ", " + s)
+				Return "bbArrayNewStruct" + Bra(TransArrayType(expr.ty) + ", sizeof" + Bra(TransObject(TObjectType(expr.ty).classdecl)) + ..
+						", " + expr.expr.length + ", " + s)
 			Else
 				Return "bbArrayNew" + Bra(TransArrayType(expr.ty) + ", " + expr.expr.length + ", " + s)
 			End If
@@ -4587,6 +4589,8 @@ End Rem
 			' field initialisation
 			For Local decl:TFieldDecl=EachIn classDecl.Decls()
 			
+				Local doEmit:Int = True
+			
 				If Not decl.IsSemanted() Then
 					decl.Semant()
 				End If
@@ -4628,18 +4632,28 @@ End Rem
 						End If
 					End If
 				Else
-					If TNumericType(decl.ty) Or TObjectType(decl.ty) Or IsPointerType(decl.ty, 0, TType.T_POINTER) Then
-						fld :+ "= 0;"
+					If TNumericType(decl.ty) Or IsPointerType(decl.ty, 0, TType.T_POINTER) Then
+						doEmit = False
+					Else If TObjectType(decl.ty) Then
+						If TObjectType(decl.ty).classDecl.IsStruct() Then
+							fld :+ "= " + TObjectType(decl.ty).classDecl.munged + "_New_ObjectNew();"
+						Else
+							fld :+ "= &bbNullObject;"
+						End If
 					Else If TFunctionPtrType(decl.ty) Then
 						fld :+ "= &brl_blitz_NullFunctionError;"
 					Else If TStringType(decl.ty) Then
 						fld :+ "= &bbEmptyString;"
 					Else If TArrayType(decl.ty) Then
 						fld :+ "= &bbEmptyArray;"
+					Else If TEnumType(decl.ty) Then
+						fld :+ "= " + TEnumType(decl.ty).decl.values[0].Value() + ";"
 					End If
 				End If
 	
-				Emit fld
+				If doEmit Then
+					Emit fld
+				End If
 			Next
 		
 		End If
@@ -4757,7 +4771,7 @@ End Rem
 		t = TransObject(classdecl) + " o"
 
 		If classDecl.IsStruct() Then
-			Emit t + ";"
+			Emit t + " = {0};"
 		Else
 			t :+ " = "
 			If ClassHasObjectField(classDecl) Then

+ 3 - 19
decl.bmx

@@ -512,28 +512,12 @@ Type TValDecl Extends TDecl
 					init=declInit.Copy().SemantAndCast(ty)
 					
 					' check if struct has been initialised
-					If TObjectType(ty) And TObjectType(ty).classDecl.IsStruct() Then
+					If TObjectType(ty) And TObjectType(ty).classDecl.IsStruct() And Not TObjectType(ty).classDecl.IsExtern() Then
 					
 						' new not used
 						If TConstExpr(init) And Not TConstExpr(init).value Then
-							
-							Local found:Int = False
-							' struct contains any objects?
-							For Local fld:TFieldDecl = EachIn TObjectType(ty).classDecl._decls
-								If Not fld.IsSemanted() Then
-									fld.Semant()
-								End If
-							
-								If TObjectType(fld.ty) Or TStringType(fld.ty) Or TArrayType(fld.ty) Then
-									found = True
-									Exit
-								End If
-							Next
-						
-							' we need to initialise object fields, so we'll call the default constructor
-							If found Then
-								init = New TNewObjectExpr.Create(ty, Null).Semant()
-							End If
+							' always call the default constructor to init all the fields correctly
+							init = New TNewObjectExpr.Create(ty, Null).Semant()
 						End If
 					End If
 				End If

+ 1 - 1
options.bmx

@@ -25,7 +25,7 @@ SuperStrict
 
 Import "base.configmap.bmx"
 
-Const version:String = "0.104"
+Const version:String = "0.105"
 
 Const BUILDTYPE_APP:Int = 0
 Const BUILDTYPE_MODULE:Int = 1

+ 6 - 3
parser.bmx

@@ -2419,8 +2419,10 @@ End Rem
 				'Wend
 				init=New TNewArrayExpr.Create( ty,ln)
 				ty=New TArrayType.Create( ty, ln.length )
-			Else If toke<>"const"
-				init=New TConstExpr.Create( ty,"" )
+			Else If toke <> "const"
+				If toke="global" Or toke="local" Then
+					init=New TConstExpr.Create( ty,"" )
+				End If
 			Else
 				Err "Constants must be initialized."
 			EndIf
@@ -2431,7 +2433,8 @@ End Rem
 		Local decl:TValDecl
 
 		Select toke
-		Case "global" decl=New TGlobalDecl.Create( id,ty,init,attrs )
+		Case "global"
+			decl=New TGlobalDecl.Create( id,ty,init,attrs )
 		Case "field"
 			decl=New TFieldDecl.Create( id,ty,init,attrs )