Пример #1
0
 // Resolve this array initializer list.
 // Provide with the type that we expect each element in the list to be
 public void Resolve(ISemanticResolver s, TypeEntry tExpected)
 {
     // Each node must either be an expression or a nested array initializer list
     //foreach(Node n in List)
     for(int i = 0; i < m_list.Length; i++)
     {
         Node n = m_list[i]; 
         if (n is Exp)
         {
             Exp e = (Exp) n;
             Exp.ResolveExpAsRight(ref e, s);
             m_list[i] = e;
             
             s.EnsureAssignable(e, tExpected.CLRType);
         } 
         
         else if (n is ArrayInitializer)
         {
             Debug.Assert(tExpected.IsArray); // @todo -legit
             
             ArrayInitializer a = (ArrayInitializer) n;
             TypeEntry tNested = tExpected.AsArrayType.ElemType;
             
             a.Resolve(s, tNested);
         }
         
         else 
         {
             // Error
             Debug.Assert(false); // @todo - legit
         }
     
     }
 }
Пример #2
0
 // Semantic resolution.
 // This is where we check for Set-Property transformations (where an
 // assignment gets changed into a methodcall)
 protected override Exp ResolveExpAsRight(ISemanticResolver s)
 {
     // Resolve the leftside of the operator                
     Exp.ResolveExpAsLeft(ref m_oeLeft, s);
     
     
     // Event transform  actually occurs in the assignment node.
     // A.e = A.e + d --> A.add_e(d)            
     // We have to do this before we resolve the RHS of the operator (Since we
     // can't resolve events as a RHS).
     if (m_oeLeft is EventExp)
     {   
         EventExp nodeEvent = (EventExp)m_oeLeft;
         EventExpEntry e = nodeEvent.Symbol;         
         
         // Here we just do some asserts.
         BinaryExp b = this.m_expRight as BinaryExp;
         Debug.Assert(b != null, "bad formed event +=,-=");  
      
         // By now, we know we have something of the form A = B + C   
         // Make sure that A=B. Since we resolved A as left, must resolve B as left too.
         Exp eTempLeft = b.Left;
         Exp.ResolveExpAsLeft(ref eTempLeft, s);
         Debug.Assert(eTempLeft is EventExp);
         Debug.Assert(Object.ReferenceEquals(((EventExp) eTempLeft).Symbol, e)); // symbols should be exact references
         
         // Resolve C (the delegate that we're adding to the event)
         Exp eTempRight = b.Right;
         Exp.ResolveExpAsRight(ref eTempRight, s);            
         Debug.Assert(AST.DelegateDecl.IsDelegate(eTempRight.CLRType), "Event only ops w/ delegates"); // @todo -legit/            
         
         Debug.Assert(b.Op == BinaryExp.BinaryOp.cAdd || b.Op == BinaryExp.BinaryOp.cSub);
             
         
         MethodExpEntry m2 = (b.Op == BinaryExp.BinaryOp.cAdd) ? e.AddMethod : e.RemoveMethod;
             
         Exp e2 = new MethodCallExp(
             nodeEvent.InstanceExp,
             m2,
             new ArgExp[] {
                 new ArgExp(EArgFlow.cIn, eTempRight)
             },
             s
         );
                 
         Exp.ResolveExpAsRight(ref e2, s);
         return e2;            
     }
     
     Exp.ResolveExpAsRight(ref m_expRight, s);
                     
     
     // Check for calling add_, remove on events
     // a.E += X 
     // a.E = a.E + X (parser transforms)
     // if E is a delegate, and RHS is structured like E + X
     // then transform to a.add_E(X) or a.remove_E(x)
     
     // @todo - use the EventInfo to get exact add / remove functions
     if (DelegateDecl.IsDelegate(m_oeLeft.CLRType))
     {   
         // Events can only exist on a class
         AST.FieldExp f = m_oeLeft as FieldExp;
         if (f == null)
             goto NotAnEvent;
             
         Exp eInstance = f.InstanceExp; // ok if static                
         
         BinaryExp rhs = m_expRight as BinaryExp;
         if (rhs == null)
             goto NotAnEvent;            
         
         // Check if RHS is a.E + X
         if ((rhs.Left != m_oeLeft) || (rhs.Right.CLRType != rhs.Left.CLRType))
             goto NotAnEvent;
         
                     
         string stEventName = f.Symbol.Name;
         string stOpName;
         if (rhs.Op == BinaryExp.BinaryOp.cAdd)
             stOpName = "add_" + stEventName;
         else if (rhs.Op == BinaryExp.BinaryOp.cSub)
             stOpName = "remove_" + stEventName;                        
         else
             goto NotAnEvent;                
          
         // a.add_E(X);    
         Exp e = new MethodCallExp(
             eInstance,
             new Identifier(stOpName),
             new ArgExp[] {
                 new ArgExp(EArgFlow.cIn, rhs.Right)
             }
         );            
         
         Exp.ResolveExpAsRight(ref e, s);
         e.SetLocation(this.Location);    
         return e;
                     
         
     NotAnEvent:
         ;            
     }
     
     // Check for set-indexer
     if (m_oeLeft is ArrayAccessExp)
     {
         ArrayAccessExp a = m_oeLeft as ArrayAccessExp;
         if (a.IsIndexer) 
         {
             // Leftside: get_Item(idx, value);
             System.Type [] alParams = new Type [] {
                 a.ExpIndex.CLRType,
                 m_expRight.CLRType
             };
         
             TypeEntry t = s.ResolveCLRTypeToBlueType(a.Left.CLRType);            
             MethodExpEntry m = t.LookupIndexer(a.Left.Location, s, alParams, true);
             
             Exp e = new MethodCallExp(
                 a.Left,
                 m,
                 new ArgExp[] { 
                     new ArgExp(EArgFlow.cIn, a.ExpIndex),
                     new ArgExp(EArgFlow.cIn, m_expRight) 
                 },
                 s);
             
             Exp.ResolveExpAsRight(ref e, s);
             e.SetLocation(this.Location);    
             return e;
         }        
     }
     
     // Check for transforming properties into MethodCalls
     if (m_oeLeft is PropertyExp)
     {
         PropertyExp p = (PropertyExp) m_oeLeft;
         
         Exp e = new MethodCallExp(
             p.InstanceExp, 
             p.Symbol.SymbolSet, 
             new ArgExp[] { 
                 new ArgExp(EArgFlow.cIn, m_expRight) 
             },
             s);
             
         Exp.ResolveExpAsRight(ref e, s);
         e.SetLocation(this.Location);
         return e;
     }
     
     CalcCLRType(s);
 
     // Ensure type match        
     s.EnsureAssignable(m_expRight, m_oeLeft.CLRType);        
     
     return this;
 }
Пример #3
0
 // Semantic resolution
 // "a X= b" is semantically equivalent to "a = a X b"
 protected override Exp ResolveExpAsRight(ISemanticResolver s)
 {
     // Note that the left side ("a") of "a X= b" is both a 
     // Left & Right side value
     ResolveExpAsLeft(ref this.m_eLeft, s);
     ResolveExpAsRight(ref this.m_expRight, s);
    
     
     CalcCLRType(s);
 
     // Ensure type match
     s.EnsureAssignable(m_expRight, Left.CLRType);
     
     return this;
 }
Пример #4
0
 // Semantic resolution
 protected override Exp ResolveExpAsRight(ISemanticResolver s)
 {
     ResolveExpAsRight(ref this.m_expTest, s);
     ResolveExpAsRight(ref this.m_expTrue, s);
     ResolveExpAsRight(ref this.m_expFalse, s);
     
     s.EnsureAssignable(m_expTest, typeof(bool));
             
     CalcCLRType(s);
     return this;
 }
Пример #5
0
 // Semantic resolution
 protected override Exp ResolveExpAsRight(ISemanticResolver s)
 {
     // We have a problem. If our arg is a property, then we need to 
     // transform this x++ --> x = x + 1
     // But we can't always transform since we can overload the ++, -- operators.
     // So resolve our arg, see if it's a property, and then transform if it is.
     
     // Since we update the Arg, we must resolve it as a left value
     Exp.ResolveExpAsLeft(ref this.m_exp, s);
     
     // First check if we have an overload
     
     
     // Check if we're a property
     if (m_exp is PropertyExp)
     {
         Exp e = null;
         int iDelta = IsInc ? 1 : -1;
         
         e = new AssignStmtExp(
             m_exp, 
             new BinaryExp(
                 m_exp,
                 new IntExp(iDelta, this.m_filerange),
                 BinaryExp.BinaryOp.cAdd
             )
         );
         
         Exp.ResolveExpAsRight(ref e, s);
         return e;
     }
             
     CalcCLRType(s);
 
     // Ensure type match, unless we have an overload.
     s.EnsureAssignable(Arg, typeof(int));
     
     return this;
 }
Пример #6
0
    // Semantic resolution
    public override void ResolveStatement(ISemanticResolver s)
    {        
        Exp.ResolveExpAsRight(ref this.m_expTest, s);

        m_loopcount++;
        BodyStmt.ResolveStatement(s);
        m_loopcount--;

        //s.EnsureDerivedType(s.ResolveCLRTypeToBlueType(typeof(bool)), TestExp);
        s.EnsureAssignable(TestExp, typeof(bool));
    }
Пример #7
0
 // Semantic resolution
 public override void ResolveStatement(ISemanticResolver s)
 {
     if (m_oeException != null)
     {
         Exp.ResolveExpAsRight(ref m_oeException, s);
         //Debug.Assert(m_oeException.SymbolMode == ObjExp.Mode.cExpEntry);
         
         // Must derive from System.Exception            
         s.EnsureAssignable(m_oeException, typeof(System.Exception));
     }
 }
Пример #8
0
 public void ResolveHandler(ISemanticResolver s)
 {           
     // Catch blocks can declare an identifier        
     if (IdVarName != null)
     {
         m_var = new LocalVarDecl(IdVarName, m_type);
         Body.InjectLocalVar(m_var);
     }
     
     this.m_type.ResolveType(s);
     Body.ResolveStatement(s);
     
     // Catch type must be of type System.Exception
     if (m_var != null)
     {
         s.EnsureAssignable(m_var.Symbol.m_type.CLRType, typeof(System.Exception), IdVarName.Location);
     }
     
     // Catch type must be of type System.Exception
     //TypeEntry tSystem_Exception =s.ResolveCLRTypeToBlueType(typeof(System.Exception));
     //s.EnsureDerivedType(tSystem_Exception, m_type.TypeRec, new FileRange());
     
 }
Пример #9
0
 // Semantic resolution
 public override void ResolveStatement(ISemanticResolver s)
 {
     MethodExpEntry m = s.GetCurrentMethod();
     if (m_exp != null) 
     {
         Exp.ResolveExpAsRight(ref m_exp, s);
     
         // Ensure that expression we're returning matches the method's
         // return type            
         //s.EnsureDerivedType(m.RetType, m_exp);
         s.EnsureAssignable(m_exp, m.RetType.CLRType);
     } 
     else 
     {
         // If we're not returning an expression, then our return type should be void
         if (m.RetType.CLRType != typeof(void))
         {
             ThrowError(SymbolError.NoReturnTypeExpected(this));
             /*
             s.ThrowError(SemanticChecker.Code.cNoReturnTypeExpected,
                 this.Location, 
                 "Functions with void return type can't return an expression"
                 );
             */
         }        
     }
 }