package org.eclipse.cdt.codan.extension; import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.IASTBinaryExpression; import org.eclipse.cdt.core.dom.ast.IASTDeclarator; import org.eclipse.cdt.core.dom.ast.IASTExpression; import org.eclipse.cdt.core.dom.ast.IASTIdExpression; import org.eclipse.cdt.core.dom.ast.IASTInitializer; import org.eclipse.cdt.core.dom.ast.IASTInitializerExpression; import org.eclipse.cdt.core.dom.ast.IASTLiteralExpression; import org.eclipse.cdt.core.dom.ast.IASTName; import org.eclipse.cdt.core.dom.ast.IASTNode; import org.eclipse.cdt.core.dom.ast.IBinding; import org.eclipse.cdt.core.dom.ast.IVariable; /******************************************************************************* * Copyright (c) 2009 Elliott Baron * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Elliott Baron - initial API and implementation *******************************************************************************/ public class VariableAssignmentVisitor extends ASTVisitor { private ExecutionState es; public VariableAssignmentVisitor(ExecutionState es) { this.es = es; shouldVisitInitializers = true; shouldVisitExpressions = true; } @Override public int visit(IASTInitializer initializer) { IASTNode parent = initializer.getParent(); if (parent instanceof IASTDeclarator) { if (initializer instanceof IASTInitializerExpression) { IASTDeclarator decl = (IASTDeclarator) parent; IASTExpression expr = ((IASTInitializerExpression) initializer).getExpression(); parseAssignment(parent, decl.getName(), expr); } return PROCESS_SKIP; } return PROCESS_CONTINUE; } @Override public int visit(IASTExpression expression) { if (expression instanceof IASTBinaryExpression) { IASTBinaryExpression binExpr = (IASTBinaryExpression) expression; int op = binExpr.getOperator(); // Check operator is an assignment operator if (op == IASTBinaryExpression.op_assign) { // FIXME other ops IASTExpression o1 = binExpr.getOperand1(); if (o1 instanceof IASTIdExpression) { IASTName name = ((IASTIdExpression) o1).getName(); parseAssignment(binExpr, name, binExpr.getOperand2()); } return PROCESS_SKIP; } } return PROCESS_CONTINUE; } private void parseAssignment(IASTNode parent, IASTName name, IASTExpression valueExpr) { IBinding binding = name.resolveBinding(); if (binding instanceof IVariable) { IVariable var = (IVariable) binding; Boolean truth = getTruthValue(valueExpr); if (truth != null) { es.addTruthAssignment(var, truth); } } } private Boolean getTruthValue(IASTExpression valueExpr) { Boolean result = null; // Handle assignment from literals if (valueExpr instanceof IASTLiteralExpression) { int kind = ((IASTLiteralExpression) valueExpr).getKind(); String value = String.valueOf(((IASTLiteralExpression) valueExpr).getValue()); switch (kind) { case IASTLiteralExpression.lk_integer_constant: // 0 = False, > 0 = True result = !value.equals("0"); } } // TODO other variable assignments return result; } }