1
/*******************************************************************************
2
* Copyright (c) 2005, 2010 IBM Corporation and others.
3
* All rights reserved. This program and the accompanying materials
4
* are made available under the terms of the Eclipse Public License v1.0
5
* which accompanies this distribution, and is available at
6
* http://www.eclipse.org/legal/epl-v10.html
9
* IBM Rational Software - Initial API and implementation
10
* Markus Schorn (Wind River Systems)
11
*******************************************************************************/
12
package org.eclipse.cdt.internal.core.dom.parser.c;
14
import org.eclipse.cdt.core.dom.ILinkage;
15
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
16
import org.eclipse.cdt.core.dom.ast.IASTDeclaration;
17
import org.eclipse.cdt.core.dom.ast.IASTDeclarator;
18
import org.eclipse.cdt.core.dom.ast.IASTEqualsInitializer;
19
import org.eclipse.cdt.core.dom.ast.IASTExpression;
20
import org.eclipse.cdt.core.dom.ast.IASTInitializer;
21
import org.eclipse.cdt.core.dom.ast.IASTInitializerClause;
22
import org.eclipse.cdt.core.dom.ast.IASTName;
23
import org.eclipse.cdt.core.dom.ast.IASTNode;
24
import org.eclipse.cdt.core.dom.ast.IASTSimpleDeclaration;
25
import org.eclipse.cdt.core.dom.ast.IBinding;
26
import org.eclipse.cdt.core.dom.ast.IScope;
27
import org.eclipse.cdt.core.dom.ast.IType;
28
import org.eclipse.cdt.core.dom.ast.IValue;
29
import org.eclipse.cdt.core.parser.util.ArrayUtil;
30
import org.eclipse.cdt.internal.core.dom.Linkage;
31
import org.eclipse.cdt.internal.core.dom.parser.ASTQueries;
32
import org.eclipse.cdt.internal.core.dom.parser.IInternalVariable;
33
import org.eclipse.cdt.internal.core.dom.parser.Value;
34
import org.eclipse.core.runtime.PlatformObject;
37
* Binding for a global or a local variable, serves as base class for fields.
39
public class CVariable extends PlatformObject implements IInternalVariable, ICInternalBinding {
40
private IASTName[] declarations = null;
41
private IType type = null;
43
public CVariable(IASTName name) {
44
declarations = new IASTName[] { name };
47
public IASTNode getPhysicalNode() {
48
return declarations[0];
51
public void addDeclaration(IASTName name) {
52
if (name != null && name.isActive()) {
53
declarations = (IASTName[]) ArrayUtil.append(IASTName.class, declarations, name);
60
* @see org.eclipse.cdt.core.dom.ast.IVariable#getType()
62
public IType getType() {
63
if (type == null && declarations[0].getParent() instanceof IASTDeclarator)
64
type = CVisitor.createType((IASTDeclarator) declarations[0].getParent());
71
* @see org.eclipse.cdt.core.dom.ast.IBinding#getName()
73
public String getName() {
74
return declarations[0].toString();
77
public char[] getNameCharArray() {
78
return declarations[0].toCharArray();
84
* @see org.eclipse.cdt.core.dom.ast.IBinding#getScope()
86
public IScope getScope() {
87
IASTDeclarator declarator = (IASTDeclarator) declarations[0].getParent();
88
return CVisitor.getContainingScope(declarator.getParent());
91
public boolean isStatic() {
92
return hasStorageClass(IASTDeclSpecifier.sc_static);
95
public boolean hasStorageClass(int storage) {
96
if (declarations == null)
99
for (int i = 0; i < declarations.length && declarations[i] != null; i++) {
100
final IASTName name = declarations[i];
102
IASTNode parent = name.getParent();
103
while (!(parent instanceof IASTDeclaration))
104
parent = parent.getParent();
106
if (parent instanceof IASTSimpleDeclaration) {
107
IASTDeclSpecifier declSpec = ((IASTSimpleDeclaration) parent).getDeclSpecifier();
108
if (declSpec.getStorageClass() == storage) {
119
* @see org.eclipse.cdt.core.dom.ast.IVariable#isExtern()
121
public boolean isExtern() {
122
return hasStorageClass(IASTDeclSpecifier.sc_extern);
128
* @see org.eclipse.cdt.core.dom.ast.IVariable#isAuto()
130
public boolean isAuto() {
131
return hasStorageClass(IASTDeclSpecifier.sc_auto);
137
* @see org.eclipse.cdt.core.dom.ast.IVariable#isRegister()
139
public boolean isRegister() {
140
return hasStorageClass(IASTDeclSpecifier.sc_register);
143
public ILinkage getLinkage() {
144
return Linkage.C_LINKAGE;
147
public IASTNode[] getDeclarations() {
151
public IASTNode getDefinition() {
152
return getPhysicalNode();
155
public IBinding getOwner() {
156
if (declarations == null || declarations.length == 0)
159
return CVisitor.findDeclarationOwner(declarations[0], true);
162
public IValue getInitialValue() {
163
return getInitialValue(Value.MAX_RECURSION_DEPTH);
166
public IValue getInitialValue(int maxDepth) {
167
if (declarations != null) {
168
for (IASTName decl : declarations) {
171
final IValue val = getInitialValue(decl, maxDepth);
179
private IValue getInitialValue(IASTName name, int maxDepth) {
180
IASTDeclarator dtor = findDeclarator(name);
182
IASTInitializer init = dtor.getInitializer();
183
if (init instanceof IASTEqualsInitializer) {
184
final IASTInitializerClause initClause = ((IASTEqualsInitializer) init)
185
.getInitializerClause();
186
if (initClause instanceof IASTExpression) {
187
return Value.create((IASTExpression) initClause, maxDepth);
191
return Value.UNKNOWN;
196
private IASTDeclarator findDeclarator(IASTName name) {
197
IASTNode node = name.getParent();
198
if (!(node instanceof IASTDeclarator))
201
return ASTQueries.findOutermostDeclarator((IASTDeclarator) node);