public static void Compile(string name, TypeBuilder dataClass, ITypedExpression typedExpression, DataDeclaration data, IMetadataContainer container, IRuntimeContainer runtimeContainer) { var method = dataClass.DefineMethod(name, MethodAttributes.Public | MethodAttributes.Static, null, Type.EmptyTypes); if (data.TypeParameters.Any()) { method.DefineGenericParameters(data.TypeParameters.ToArray()); } var converter = new TypeConverter(runtimeContainer, method.GetGenericArguments()); var converted = converter.Convert(data.Type); method.SetReturnType(converted); var body = method.GetILGenerator(); typedExpression.AcceptVisitor(new DataCompiler(body, method.GetGenericArguments(), runtimeContainer)); body.Emit(OpCodes.Ret); container.Add(name, data); runtimeContainer.Add(name, method); RemoveFirstParameter(name, dataClass, method, new IType[0], data.Type, data.TypeParameters, runtimeContainer); }
/// <summary> /// Try convert <paramref name="argument"/> to specified type {T}. /// </summary> private static IExpression <T> TryConvertExpression <T>(string name, int argI, ITypedExpression argument, ref IList <string> errors) { IExpression <T> arg = argument as IExpression <T>; if (arg == null) { if (typeof(T) == typeof(double)) { AddError(ref errors, string.Format("{0} function argument {1} must be a number type, but was '{2}'", name, argI + 1, argument.ResultType.Name)); } else { AddError(ref errors, string.Format("{0} function argument {1} must be of type '{2}', but was '{3}'", name, argI + 1, typeof(T).Name, argument.ResultType.Name)); } } return(arg); }
public static ITypedExpression Sum(ITypedExpression left, ITypedExpression right, IType l1, IType l2, IType r1, IType r2) { return new TypedExpressions.Case ( new TypedExpressions.Composition(new TypedExpressions.Inl(l2, r2), left, l1, l2, new Types.SumType(l2, r2)), new TypedExpressions.Composition(new TypedExpressions.Inr(l2, r2), right, r1, r2, new Types.SumType(l2, r2)), l1, r1, new Types.SumType(l2, r2) ); }