private void ProcessPrefixPostfixOperators(ExpressionSyntax operand, OpCode opCode, bool isPrefix) { Visit(operand); InjectRequiredConversions(operand); var assignmentVisitor = new AssignmentVisitor(Context, ilVar); var operandInfo = Context.SemanticModel.GetSymbolInfo(operand); if (operandInfo.Symbol != null && operandInfo.Symbol.Kind != SymbolKind.Field && operandInfo.Symbol.Kind != SymbolKind.Property) // Fields / Properties requires more complex handling to load the owning reference. { if (!isPrefix) // For *postfix* operators we duplicate the value *before* applying the operator... { AddCilInstruction(ilVar, OpCodes.Dup); } AddCilInstruction(ilVar, OpCodes.Ldc_I4_1); AddCilInstruction(ilVar, opCode); if (isPrefix) // For prefix operators we duplicate the value *after* applying the operator... { AddCilInstruction(ilVar, OpCodes.Dup); } //assign (top of stack to the operand) assignmentVisitor.InstructionPrecedingValueToLoad = Context.CurrentLine; operand.Accept(assignmentVisitor); return; } var tempLocalName = MethodExtensions.LocalVariableNameFor("tmp_", "tmp_".UniqueId().ToString()); AddCecilExpression($"var {tempLocalName} = new VariableDefinition({Context.TypeResolver.Resolve(Context.SemanticModel.GetTypeInfo(operand).Type)});"); AddCecilExpression($"{Context.DefinitionVariables.GetLastOf(MemberKind.Method).VariableName}.Body.Variables.Add({tempLocalName});"); if (isPrefix) { AddCilInstruction(ilVar, OpCodes.Ldc_I4_1); AddCilInstruction(ilVar, opCode); } AddCilInstruction(ilVar, OpCodes.Stloc, tempLocalName); AddCilInstruction(ilVar, OpCodes.Ldloc, tempLocalName); assignmentVisitor.InstructionPrecedingValueToLoad = Context.CurrentLine; AddCilInstruction(ilVar, OpCodes.Ldloc, tempLocalName); if (!isPrefix) { AddCilInstruction(ilVar, OpCodes.Ldc_I4_1); AddCilInstruction(ilVar, opCode); } // assign (top of stack to the operand) operand.Accept(assignmentVisitor); }
public override void VisitAssignmentExpression(AssignmentExpressionSyntax node) { var leftNodeMae = node.Left as MemberAccessExpressionSyntax; CSharpSyntaxNode exp = leftNodeMae != null ? leftNodeMae.Name : node.Left; if (Context.SemanticModel.GetSymbolInfo(exp).Symbol?.Kind == SymbolKind.Property) // check if the left hand side of the assignment is a property and handle that as a method (set) call. { HandleMethodInvocation(node.Left, node.Right); return; } var visitor = new AssignmentVisitor(Context, ilVar, node); visitor.InstructionPrecedingValueToLoad = Context.CurrentLine; Visit(node.Right); if (!valueTypeNoArgObjCreation) { visitor.Visit(node.Left); } }