public IndexedMethod findMethodDeclaration( PythonParserResult info, org.python.antlr.ast.Call call, AstPath path, Set<IndexedMethod>[] alternativesHolder) { PythonParserResult parseResult = PythonAstUtils.getParseResult(info); PythonIndex index = PythonIndex.get(info.getSnapshot().getSource().getFileObject()); Set<IndexedElement> functions = null; // TODO - do more accurate lookup of types here! // (a) For functions, look in imported symbols first! // (b) For methods, try to resolve the lhs type first and search within specific types! String callName = PythonAstUtils.getCallName(call); if (callName == null) { return null; } if (call.getInternalFunc() instanceof Attribute) { // Method/member access functions = index.getAllMembers(callName, QuerySupport.Kind.EXACT, parseResult, false); } else { functions = index.getAllElements(callName, QuerySupport.Kind.EXACT, parseResult, false); } if (functions != null && functions.size() > 0) { Set<IndexedElement> eligible = new HashSet<IndexedElement>(); for (IndexedElement element : functions) { if (element instanceof IndexedMethod) { eligible.add(element); } } int astOffset = call.getCharStartIndex(); int lexOffset = PythonLexerUtils.getLexerOffset(info, astOffset); IndexedElement candidate = findBestMatch( info, callName, eligible, (BaseDocument) info.getSnapshot().getSource().getDocument(false), astOffset, lexOffset, path, call, index); assert candidate instanceof IndexedMethod; // Filtered into earlier already return (IndexedMethod) candidate; } return null; }
public Object visitCall(Call node) throws Exception { if (node.getInternalStarargs() != null) // unknown arg length function call { String argsSym = getUnique("args$"); for (expr ex : node.getInternalArgs()) { visit(ex); } addLine("PUSH $newList"); addLine("CALL " + node.getInternalArgs().size()); addLine("POP " + argsSym); visit(node.getInternalStarargs()); addLine("PUSH " + argsSym); addLine("SELECTMEMBER extend"); addLine("PUSHMEMBER"); addLine("CALL 1"); addLine("POP $"); addLine("PUSH " + argsSym); visit(node.getInternalFunc()); addLine("CALL"); } else // normal function call { for (expr ex : node.getInternalArgs()) { visit(ex); } visit(node.getInternalFunc()); addLine("CALL " + node.getInternalArgs().size()); } return null; }