/* private Expression ml(Expression m, IEnumerable<Expression> args) * { * var mt = m.type as MapType; * return ml(m, args, new DataType[0], mt.range); * }*/ private Expression ml(Expression m, IEnumerable <Expression> args, IType[] typeArgs, IType resultType) { Debug.Assert(m.type is MapType); var mt = m.type as MapType; Debug.Assert(args.Count() == mt.domain.Count()); Debug.Assert(typeArgs.Count() == mt.typeParameters.Count()); Expression[] mlArgs = new Expression[1] { m }.Concat(args).ToArray(); return(new BasicFAE( BasicMapRead.mapRead(typeArgs, (from a in mlArgs select a.type).ToArray(), resultType), new ExpressionList(mlArgs) )); }
public static MapRead mu2ml(MapWrite mu) { var mlArgTypes = TypeTuple.make(mu.argumentTypes.Take(mu.argumentTypes.Count() - 1)); return(BasicMapRead.mapRead(mu.typeArguments.Skip(1).ToArray(), mlArgTypes, mu.argumentTypes.Last())); }
//////////////////////////////////////////////////////////////////////////////////// private Expression makeExpression(NAryExpr fae, bool old) { if (fae.Fun is TypeCoercion) { return(makeExpression(fae.Args[0], old)); } var arguments = new ExpressionList((from Expr e in fae.Args select makeExpression(e, old)).ToArray()); Function function; if (fae.Fun is MapSelect) { var typeArguments = new IType[fae.TypeParameters.FormalTypeParams.Count]; for (int i = 0; i < fae.TypeParameters.FormalTypeParams.Count; i++) { typeArguments[i] = makeType(fae.TypeParameters[fae.TypeParameters.FormalTypeParams[i]]); } var argumentTypes = TypeTuple.make(from a in arguments select a.type); function = BasicMapRead.mapRead( typeArguments, argumentTypes, makeType(fae.Type) ); } else if (fae.Fun is MapStore) { var typeArguments = new IType[fae.TypeParameters.FormalTypeParams.Count]; for (int i = 0; i < fae.TypeParameters.FormalTypeParams.Count; i++) { typeArguments[i] = makeType(fae.TypeParameters[fae.TypeParameters.FormalTypeParams[i]]); } function = BasicMapWrite.makeMapWrite(typeArguments, (from a in arguments select a.type).ToArray(), makeType(fae.ShallowType)); } else if (fae.Fun.FunctionName == "==" || fae.Fun.FunctionName == "!=") { if (arguments[0].type.isEquivalent(arguments[1].type)) { function = BFunction.eq(arguments[0].type); } else { Debug.Assert(!arguments[0].type.isGround || !arguments[1].type.isGround); function = BFunction.eq(arguments[0].type, arguments[1].type); } if (fae.Fun.FunctionName == "!=") { arguments = new ExpressionList( new BasicFAE( function, arguments ) ); function = scope.getFunction("!", TypeTuple.make()); } } else if (fae.Fun.FunctionName == "<:") { function = scope.getFunction(fae.Fun.FunctionName, TypeTuple.make(new[] { arguments[0].type })); } else if (fae.Fun.FunctionName == BFunctionTemplate.iteName) { function = scope.getFunction(fae.Fun.FunctionName, TypeTuple.make(new[] { arguments[1].type })); } else if (fae.Fun.FunctionName == @"-" && fae.Fun.ArgumentCount == 1) { arguments = new ExpressionList(new[] { new BasicLiteralExpression(IntegerValue.make(0)), arguments[0] }); function = scope.getFunction(@"-", TypeTuple.make()); } else { var typeArguments = TypeTuple.make((fae.TypeParameters == null) ? new IType[0] : (from ftp in fae.TypeParameters.FormalTypeParams select scope.typeFactory.makeTypeI(fae.TypeParameters[ftp], context))); function = scope.getFunction(fae.Fun.FunctionName, typeArguments); } var result = new BoogieFunctionApplicationExpression(fae, function, arguments); Debug.Assert(result.type.ToStringN() == makeType(fae.Type == null ? fae.ShallowType : fae.Type).ToStringN()); Debug.Assert(result != null); foreach (var fv in result.freeVariables) { Debug.Assert(context.lookupVariableByOwnName(fv.name) == fv); } foreach (var ftv in result.freeTypeVariables) { Debug.Assert(ReferenceEquals(context.lookupTypeVariable(ftv.name), ftv)); } return(result); }