//------------------------------------------------------------ // FieldWithType.Convert // /// <summary> /// If swt is FieldWithType, convert to FieldWithType and return it. /// Otherwise, create a FieldWithType instance by swt and return it. /// </summary> /// <param name="swt"></param> /// <returns></returns> //------------------------------------------------------------ static internal FieldWithType Convert(SymWithType swt) { FieldWithType fwt = swt as FieldWithType; if (fwt != null) { return(fwt); } return(new FieldWithType(swt)); }
//------------------------------------------------------------ // FieldWithType.Set (2) // /// <summary></summary> /// <param name="fwt"></param> //------------------------------------------------------------ internal void Set(FieldWithType fwt) { if (fwt != null) { this.Set(fwt.FieldSym, fwt.AggTypeSym); } else { this.Set(null, null); } }
//------------------------------------------------------------ // FUNCBREC.CreateAutoImplementedGetAccessor // /// <summary></summary> /// <param name="methodSym"></param> /// <returns></returns> //------------------------------------------------------------ internal EXPR CreateAutoImplementedGetAccessor(METHSYM methodSym) { CreateNewScope(); SCOPESYM scopeSym = this.currentScopeSym; this.currentScopeSym.ScopeFlags = SCOPEFLAGS.NONE; this.currentBlockExpr = NewExprBlock(treeNode); this.currentBlockExpr.ScopeSym = this.currentScopeSym; SymWithType symWithType = new SymWithType(); AGGTYPESYM parentAts = methodSym.ParentAggSym.GetThisType(); symWithType.Set( methodSym.PropertySym.BackFieldSym, parentAts); EXPR fieldExpr = BindToField( null, BindThisImplicit(null), FieldWithType.Convert(symWithType), BindFlagsEnum.RValueRequired); //TYPESYM retTypeSym = methodSym.ReturnTypeSym; EXPRRETURN returnExpr = NewExpr(null, EXPRKIND.RETURN, null) as EXPRRETURN; returnExpr.ObjectExpr = fieldExpr; this.currentBlockExpr.StatementsExpr = returnExpr; EXPRBLOCK blockExpr = this.currentBlockExpr; this.currentBlockExpr = blockExpr.OwingBlockExpr; CloseScope(); CorrectAnonMethScope(blockExpr.ScopeSym); return(blockExpr); }
//------------------------------------------------------------ // FUNCBREC.BindObjectInitializer // /// <summary></summary> /// <param name="newNode"></param> /// <param name="typeSym"></param> /// <param name="locVarSym"></param> /// <param name="objectExpr"></param> /// <param name="builder"></param> /// <returns></returns> //------------------------------------------------------------ internal EXPR BindObjectInitializer( NEWNODE newNode, TYPESYM typeSym, LOCVARSYM locVarSym, EXPR objectExpr, StatementListBuilder builder) { DebugUtil.Assert(newNode != null && typeSym != null && builder != null); DebugUtil.Assert( (locVarSym != null && objectExpr == null) || (locVarSym == null && objectExpr != null)); BindFlagsEnum bindFlags = BindFlagsEnum.RValueRequired; string localFormat = "<{0}><{1}>__local"; //-------------------------------------------------------- // Bind the local variable. //-------------------------------------------------------- if (locVarSym == null) { string typeName = typeSym.IsAGGTYPESYM ? (typeSym as AGGTYPESYM).GetAggregate().Name : typeSym.Name; string locName = String.Format(localFormat, typeName, (this.localCount)++); locVarSym = Compiler.LocalSymbolManager.CreateLocalSym( SYMKIND.LOCVARSYM, locName, this.currentScopeSym) as LOCVARSYM; locVarSym.TypeSym = typeSym; locVarSym.LocSlotInfo.HasInit = true; locVarSym.DeclTreeNode = newNode; StoreInCache(newNode, locName, locVarSym, null, true); } EXPR locVarExpr = BindToLocal( newNode, locVarSym, bindFlags | BindFlagsEnum.MemberSet); //-------------------------------------------------------- // If objectExpr is not null, assign it to the local variable. //-------------------------------------------------------- if (objectExpr != null) { EXPR assignLocExpr = BindAssignment( newNode, locVarExpr, objectExpr, false); builder.Add(SetNodeStmt(newNode, MakeStmt(newNode, assignLocExpr, 0))); } //-------------------------------------------------------- // Assign each value. //-------------------------------------------------------- DECLSTMTNODE decNode = newNode.InitialNode as DECLSTMTNODE; DebugUtil.Assert(decNode != null); BASENODE node = decNode.VariablesNode; while (node != null) { VARDECLNODE varDecl; if (node.Kind == NODEKIND.LIST) { varDecl = node.AsLIST.Operand1 as VARDECLNODE; node = node.AsLIST.Operand2; } else { varDecl = node as VARDECLNODE; node = null; } BINOPNODE assignNode = varDecl.ArgumentsNode as BINOPNODE; if (assignNode == null || assignNode.Operator != OPERATOR.ASSIGN || assignNode.Operand1 == null || assignNode.Operand1.Kind != NODEKIND.NAME || assignNode.Operand2 == null) { continue; } //---------------------------------------------------- // LHS //---------------------------------------------------- NAMENODE nameNode = assignNode.Operand1 as NAMENODE; DebugUtil.Assert(nameNode != null); bindFlags = BindFlagsEnum.MemberSet; MemberLookup mem = new MemberLookup(); EXPR leftExpr = null; if (mem.Lookup( Compiler, typeSym, locVarExpr, this.parentDeclSym, nameNode.Name, 0, MemLookFlagsEnum.UserCallable)) { SymWithType swt = mem.FirstSymWithType; DebugUtil.Assert(swt != null && swt.IsNotNull); switch (swt.Sym.Kind) { case SYMKIND.MEMBVARSYM: leftExpr = BindToField( assignNode, locVarExpr, FieldWithType.Convert(swt), bindFlags); break; case SYMKIND.PROPSYM: leftExpr = BindToProperty( assignNode, locVarExpr, PropWithType.Convert(swt), bindFlags, null, null); break; default: leftExpr = NewError(nameNode, null); break; } } else { mem.ReportErrors(nameNode); leftExpr = NewError(nameNode, null); } //---------------------------------------------------- // Collection initializer //---------------------------------------------------- if (assignNode.Operand2.Kind == NODEKIND.ARRAYINIT) { if (!leftExpr.TypeSym.IsARRAYSYM) { BindCollectionInitializer( newNode, (assignNode.Operand2 as UNOPNODE).Operand, leftExpr.TypeSym, //typeSym, null, //locVarSym, leftExpr, null, builder); continue; } } //---------------------------------------------------- // RHS //---------------------------------------------------- EXPR rightExpr = BindExpr( assignNode.Operand2, BindFlagsEnum.RValueRequired); //---------------------------------------------------- // Assign //---------------------------------------------------- EXPR assignExpr = BindAssignment( assignNode, leftExpr, rightExpr, false); builder.Add(SetNodeStmt(decNode, MakeStmt(decNode, assignExpr, 0))); } return(locVarExpr); }
//------------------------------------------------------------ // FUNCBREC.CreateAutoImplementedSetAccessor // /// <summary></summary> /// <param name="methodSym"></param> /// <returns></returns> //------------------------------------------------------------ internal EXPR CreateAutoImplementedSetAccessor(METHSYM methodSym) { CreateNewScope(); SCOPESYM scopeSym = this.currentScopeSym; this.currentScopeSym.ScopeFlags = SCOPEFLAGS.NONE; this.currentBlockExpr = NewExprBlock(treeNode); this.currentBlockExpr.ScopeSym = this.currentScopeSym; //-------------------------------------------------------- // Back filed //-------------------------------------------------------- SymWithType fieldSwt = new SymWithType(); AGGTYPESYM parentAts = methodSym.ParentAggSym.GetThisType(); fieldSwt.Set( methodSym.PropertySym.BackFieldSym, parentAts); EXPR fieldExpr = BindToField( null, BindThisImplicit(null), FieldWithType.Convert(fieldSwt), BindFlagsEnum.RValueRequired); //-------------------------------------------------------- // Parameter "value" //-------------------------------------------------------- // The SYM instance of parameter "value" is a LOCVARSYM instance, // and is created in CLSDREC.FillMethInfoCommon. LOCVARSYM locSym = Compiler.LocalSymbolManager.LookupLocalSym( Compiler.NameManager.GetPredefinedName(PREDEFNAME.VALUE), this.OuterScopeSym, SYMBMASK.LOCVARSYM) as LOCVARSYM; DebugUtil.Assert(locSym != null); SymWithType valueSwt = new SymWithType(); valueSwt.Set(locSym, null); EXPR valueExpr = BindToLocal(null, locSym, BindFlagsEnum.RValueRequired); //-------------------------------------------------------- // BackField = value //-------------------------------------------------------- EXPR assignExpr = NewExprBinop( null, EXPRKIND.ASSG, fieldExpr.TypeSym, fieldExpr, valueExpr); //-------------------------------------------------------- // Statement //-------------------------------------------------------- EXPRSTMTAS stmt = NewExpr(null, EXPRKIND.STMTAS, null) as EXPRSTMTAS; stmt.Expr = assignExpr; //-------------------------------------------------------- // Block //-------------------------------------------------------- this.currentBlockExpr.StatementsExpr = stmt; EXPRBLOCK blockExpr = this.currentBlockExpr; this.currentBlockExpr = blockExpr.OwingBlockExpr; CloseScope(); CorrectAnonMethScope(blockExpr.ScopeSym); return(blockExpr); }