在Eclipse中如何访问局部变量及头文件变量的ICElements?
Great question! You're already off to a solid start using ITranslationUnit to access global variables and functions. Let's expand that approach to cover local variables inside functions and elements from included headers using Eclipse CDT's AST (Abstract Syntax Tree) API.
1. Accessing Local Variables Inside Functions
Local variables live within function bodies and nested code blocks, so you'll need to traverse the AST to dig into function definitions and their inner nodes. Here's a practical implementation:
First, retrieve the AST from your ITranslationUnit, then use an ASTVisitor to traverse function definitions and their child elements:
import org.eclipse.cdt.core.dom.ast.ASTVisitor; import org.eclipse.cdt.core.dom.ast.IASTCompoundStatement; import org.eclipse.cdt.core.dom.ast.IASTFunctionDefinition; import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit; import org.eclipse.cdt.core.dom.ast.IASTVariableDeclaration; import org.eclipse.cdt.core.model.ITranslationUnit; import org.eclipse.cdt.ui.CUIPlugin; // Assume you already have the input (e.g., IFileEditorInput) ITranslationUnit tu = CUIPlugin.getDefault().getWorkingCopyManager().getWorkingCopy(input); if (tu != null) { IASTTranslationUnit astTu = tu.getAST(); astTu.accept(new ASTVisitor() { // Target function definitions in the AST @Override public int visit(IASTFunctionDefinition functionDef) { // Get the function's body (the compound statement wrapped in { ... }) IASTCompoundStatement functionBody = functionDef.getBody(); if (functionBody != null) { // Traverse the function body to find local variables functionBody.accept(new ASTVisitor() { @Override public int visit(IASTVariableDeclaration varDecl) { // Extract the local variable name String varName = varDecl.getDeclarator().getName().toString(); System.out.println("Found local variable: " + varName); // Optional: Access additional details like variable type or modifiers // IASTType varType = varDecl.getType(); return PROCESS_CONTINUE; // Keep traversing other nodes in the function } }); } return PROCESS_CONTINUE; // Move on to check other functions } }); }
This will automatically find variables in nested blocks (like inside if or for statements) since the ASTVisitor recursively traverses all child nodes.
2. Accessing Elements from Included Header Files
Header file elements aren't directly part of the main .c file's AST by default—you need to resolve include directives and parse the header files separately. Here's how to do it:
import org.eclipse.cdt.core.dom.ast.IASTIncludeDirective; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IWorkspaceRoot; import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.runtime.Path; // Continuing with the same IASTTranslationUnit astTu from above astTu.accept(new ASTVisitor() { @Override public int visit(IASTIncludeDirective includeDirective) { // Extract the path from the include directive (e.g., "myheader.h" or <stdio.h>) String includePath = includeDirective.getName().toString(); // Resolve the header file in the workspace (adjust for system headers below) IWorkspaceRoot workspaceRoot = ResourcesPlugin.getWorkspace().getRoot(); IFile headerFile = workspaceRoot.getFile(new Path(includePath)); if (headerFile.exists()) { // Get the ITranslationUnit for the header file ITranslationUnit headerTu = CUIPlugin.getDefault().getWorkingCopyManager() .getWorkingCopy(headerFile.getFullPath().toString()); if (headerTu != null) { IASTTranslationUnit headerAst = headerTu.getAST(); // Traverse the header's AST to find variables and function declarations headerAst.accept(new ASTVisitor() { // Handle global variables in the header @Override public int visit(IASTVariableDeclaration varDecl) { String varName = varDecl.getDeclarator().getName().toString(); System.out.println("Found header variable: " + varName); return PROCESS_CONTINUE; } // Handle function declarations in the header @Override public int visit(IASTFunctionDeclaration funcDecl) { String funcName = funcDecl.getDeclarator().getName().toString(); System.out.println("Found header function declaration: " + funcName); return PROCESS_CONTINUE; } }); } } return PROCESS_CONTINUE; } });
Important Notes for Header Files:
- System Headers: For system headers (like
<stdio.h>), you'll need to use CDT's include path resolution instead of the workspace root. Retrieve the project's include paths viaICProjectto locate system headers correctly. - Non-Working Copies: If the header isn't open in the editor, use
CModelManagerto get the translation unit instead of relying on the working copy manager.
Required Dependencies
Ensure your plugin includes these CDT bundles in its dependencies:
org.eclipse.cdt.coreorg.eclipse.cdt.uiorg.eclipse.core.resources
内容的提问来源于stack exchange,提问作者Maruthamalai A




