Пример #1
0
        public OperatorImplementationTable CreateOperatorImplementationsTable()
        {
            var table = new OperatorImplementationTable();

            foreach (var entry in _baseOperatorImplementations)
            {
                table.Add(entry.Key, entry.Value);
            }
            return(table);
        }
Пример #2
0
/*
 *  public virtual FunctionBindingInfo GetFunctionBindingInfo(string name, AstNodeList  parameters) {
 *    return FunctionBindings.Find(name, parameters.Count);
 *  }
 *  //Utility methods for adding library functions
 *  public FunctionBindingInfo AddFunction(string name, int paramCount) {
 *    return null;
 *  }
 *  public FunctionBindingInfo AddFunction(string name, int paramCount, FunctionFlags flags) {
 *    FunctionBindingInfo info = new FunctionBindingInfo(name, paramCount, null, flags);
 *    FunctionBindings.Add(name, info);
 *    return info;
 *  }
 */

        #region Operator implementations
        // When an implementation for exact type pair is not found, we find implementation for base type and create
        // implementation for exact types using type converters
        public virtual OperatorImplementation AddOperatorImplementation(OperatorImplementationTable implementations, OperatorDispatchKey forKey)
        {
            Type baseType = GetBaseTypeForExpression(forKey.OpSymbol, forKey.Arg1Type, forKey.Arg2Type);

            if (baseType == null)
            {
                return(null);
            }
            TypeConverter arg1Converter = GetConverter(forKey.Arg1Type, baseType);
            TypeConverter arg2Converter = GetConverter(forKey.Arg2Type, baseType);
            //Get base method for the operator and common type
            var baseKey = OperatorDispatchKey.CreateFromTypes(forKey.OpSymbol, baseType, baseType);
            OperatorImplementation baseImpl;

            if (!_baseOperatorImplementations.TryGetValue(baseKey, out baseImpl))
            {
                throw new Exception(string.Format(Resources.ErrOpNotDefinedForTypes, forKey.OpSymbol, forKey.Arg1Type, forKey.Arg2Type));
            }
            var impl = new OperatorImplementation(forKey, baseType, baseImpl.BaseMethod, arg1Converter, arg2Converter, baseImpl.ResultConverter);

            implementations[forKey] = impl;
            return(impl);
        }
Пример #3
0
 public DynamicCallDispatcher(EvaluationContext context)
 {
     _context = context;
     _runtime = _context.Runtime;
     OperatorImplementations = _runtime.CreateOperatorImplementationsTable();
 }
Пример #4
0
        public virtual void InitOperatorImplementations()
        {
            _baseOperatorImplementations = new OperatorImplementationTable();

            // note that arithmetics on byte, sbyte, int16, uint16 are performed in Int32 format (the way it's done in c# I guess)
            // so the result is always Int32
            // we don't force the result back to original type - I don't think it's necessary
            // For each operator, we add a series of implementation methods for same-type operands. They are saved as DispatchRecords in
            // operator dispatchers. This happens at initialization time. Dispatch records for mismatched argument types (ex: int + double)
            // are created on-the-fly at execution time.
            string op;

            op = "+";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x + (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x + (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x + (Int16)y);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x + (UInt16)y);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x + (Int32)y));
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x + (UInt32)y));
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x + (Int64)y));
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x + (UInt64)y));
            AddImplementation(op, typeof(Single), (x, y) => (Single)x + (Single)y);
            AddImplementation(op, typeof(double), (x, y) => (double)x + (double)y);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x + (BigInteger)y);
            AddImplementation(op, typeof(Complex), (x, y) => (Complex)x + (Complex)y);
            AddImplementation(op, typeof(string), (x, y) => (string)x + (string)y);

            op = "-";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x - (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x - (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x - (Int16)y);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x - (UInt16)y);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x - (Int32)y));
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x - (UInt32)y));
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x - (Int64)y));
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x - (UInt64)y));
            AddImplementation(op, typeof(Single), (x, y) => (Single)x - (Single)y);
            AddImplementation(op, typeof(double), (x, y) => (double)x - (double)y);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x - (BigInteger)y);
            AddImplementation(op, typeof(Complex), (x, y) => (Complex)x - (Complex)y);

            op = "*";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x * (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x * (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => checked ((Int16)x * (Int16)y));
            AddImplementation(op, typeof(UInt16), (x, y) => checked ((UInt16)x * (UInt16)y));
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x * (Int32)y));
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x * (UInt32)y));
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x * (Int64)y));
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x * (UInt64)y));
            AddImplementation(op, typeof(Single), (x, y) => (Single)x * (Single)y);
            AddImplementation(op, typeof(double), (x, y) => (double)x * (double)y);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x * (BigInteger)y);
            AddImplementation(op, typeof(Complex), (x, y) => (Complex)x * (Complex)y);

            op = "/";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x / (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x / (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => checked ((Int16)x / (Int16)y));
            AddImplementation(op, typeof(UInt16), (x, y) => checked ((UInt16)x / (UInt16)y));
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x / (Int32)y));
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x / (UInt32)y));
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x / (Int64)y));
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x / (UInt64)y));
            AddImplementation(op, typeof(Single), (x, y) => (Single)x / (Single)y);
            AddImplementation(op, typeof(double), (x, y) => (double)x / (double)y);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x / (BigInteger)y);
            AddImplementation(op, typeof(Complex), (x, y) => (Complex)x / (Complex)y);

            op = "&";
            AddImplementation(op, typeof(bool), (x, y) => (bool)x & (bool)y);
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x & (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x & (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x & (Int16)y);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x & (UInt16)y);
            AddImplementation(op, typeof(Int32), (x, y) => (Int32)x & (Int32)y);
            AddImplementation(op, typeof(UInt32), (x, y) => (UInt32)x & (UInt32)y);
            AddImplementation(op, typeof(Int64), (x, y) => (Int64)x & (Int64)y);
            AddImplementation(op, typeof(UInt64), (x, y) => (UInt64)x & (UInt64)y);

            op = "|";
            AddImplementation(op, typeof(bool), (x, y) => (bool)x | (bool)y);
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x | (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x | (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x | (Int16)y);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x | (UInt16)y);
            AddImplementation(op, typeof(Int32), (x, y) => (Int32)x | (Int32)y);
            AddImplementation(op, typeof(UInt32), (x, y) => (UInt32)x | (UInt32)y);
            AddImplementation(op, typeof(Int64), (x, y) => (Int64)x | (Int64)y);
            AddImplementation(op, typeof(UInt64), (x, y) => (UInt64)x | (UInt64)y);

            op = "^"; //XOR
            AddImplementation(op, typeof(bool), (x, y) => (bool)x ^ (bool)y);
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x ^ (sbyte)y);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x ^ (byte)y);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x ^ (Int16)y);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x ^ (UInt16)y);
            AddImplementation(op, typeof(Int32), (x, y) => (Int32)x ^ (Int32)y);
            AddImplementation(op, typeof(UInt32), (x, y) => (UInt32)x ^ (UInt32)y);
            AddImplementation(op, typeof(Int64), (x, y) => (Int64)x ^ (Int64)y);
            AddImplementation(op, typeof(UInt64), (x, y) => (UInt64)x ^ (UInt64)y);

            //Note that && and || are special forms, not binary operators

            op = "<";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x < (sbyte)y, BoolResultConverter);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x < (byte)y, BoolResultConverter);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x < (Int16)y, BoolResultConverter);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x < (UInt16)y, BoolResultConverter);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x < (Int32)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x < (UInt32)y), BoolResultConverter);
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x < (Int64)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x < (UInt64)y), BoolResultConverter);
            AddImplementation(op, typeof(Single), (x, y) => (Single)x < (Single)y, BoolResultConverter);
            AddImplementation(op, typeof(double), (x, y) => (double)x < (double)y, BoolResultConverter);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x < (BigInteger)y, BoolResultConverter);

            op = ">";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x > (sbyte)y, BoolResultConverter);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x > (byte)y, BoolResultConverter);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x > (Int16)y, BoolResultConverter);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x > (UInt16)y, BoolResultConverter);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x > (Int32)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x > (UInt32)y), BoolResultConverter);
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x > (Int64)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x > (UInt64)y), BoolResultConverter);
            AddImplementation(op, typeof(Single), (x, y) => (Single)x > (Single)y, BoolResultConverter);
            AddImplementation(op, typeof(double), (x, y) => (double)x > (double)y, BoolResultConverter);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x > (BigInteger)y, BoolResultConverter);

            op = "<=";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x <= (sbyte)y, BoolResultConverter);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x <= (byte)y, BoolResultConverter);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x <= (Int16)y, BoolResultConverter);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x <= (UInt16)y, BoolResultConverter);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x <= (Int32)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x <= (UInt32)y), BoolResultConverter);
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x <= (Int64)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x <= (UInt64)y), BoolResultConverter);
            AddImplementation(op, typeof(Single), (x, y) => (Single)x <= (Single)y, BoolResultConverter);
            AddImplementation(op, typeof(double), (x, y) => (double)x <= (double)y, BoolResultConverter);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x <= (BigInteger)y, BoolResultConverter);

            op = ">=";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x >= (sbyte)y, BoolResultConverter);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x >= (byte)y, BoolResultConverter);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x >= (Int16)y, BoolResultConverter);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x >= (UInt16)y, BoolResultConverter);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x >= (Int32)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x >= (UInt32)y), BoolResultConverter);
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x >= (Int64)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x >= (UInt64)y), BoolResultConverter);
            AddImplementation(op, typeof(Single), (x, y) => (Single)x >= (Single)y, BoolResultConverter);
            AddImplementation(op, typeof(double), (x, y) => (double)x >= (double)y, BoolResultConverter);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x >= (BigInteger)y, BoolResultConverter);

            op = "==";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x == (sbyte)y, BoolResultConverter);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x == (byte)y, BoolResultConverter);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x == (Int16)y, BoolResultConverter);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x == (UInt16)y, BoolResultConverter);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x == (Int32)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x == (UInt32)y), BoolResultConverter);
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x == (Int64)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x == (UInt64)y), BoolResultConverter);
            AddImplementation(op, typeof(Single), (x, y) => (Single)x == (Single)y, BoolResultConverter);
            AddImplementation(op, typeof(double), (x, y) => (double)x == (double)y, BoolResultConverter);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x == (BigInteger)y, BoolResultConverter);

            op = "!=";
            AddImplementation(op, typeof(sbyte), (x, y) => (sbyte)x != (sbyte)y, BoolResultConverter);
            AddImplementation(op, typeof(byte), (x, y) => (byte)x != (byte)y, BoolResultConverter);
            AddImplementation(op, typeof(Int16), (x, y) => (Int16)x != (Int16)y, BoolResultConverter);
            AddImplementation(op, typeof(UInt16), (x, y) => (UInt16)x != (UInt16)y, BoolResultConverter);
            AddImplementation(op, typeof(Int32), (x, y) => checked ((Int32)x != (Int32)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt32), (x, y) => checked ((UInt32)x != (UInt32)y), BoolResultConverter);
            AddImplementation(op, typeof(Int64), (x, y) => checked ((Int64)x != (Int64)y), BoolResultConverter);
            AddImplementation(op, typeof(UInt64), (x, y) => checked ((UInt64)x != (UInt64)y), BoolResultConverter);
            AddImplementation(op, typeof(Single), (x, y) => (Single)x != (Single)y, BoolResultConverter);
            AddImplementation(op, typeof(double), (x, y) => (double)x != (double)y, BoolResultConverter);
            AddImplementation(op, typeof(BigInteger), (x, y) => (BigInteger)x != (BigInteger)y, BoolResultConverter);
        }//method