This commit is contained in:
Hackerpilot 2014-09-14 19:15:29 +00:00
parent e3281599e8
commit 78ad6a0af7
7 changed files with 170 additions and 2 deletions

View File

@ -151,6 +151,48 @@ function M.gotoDeclaration()
end
end
function M.searchForSymbol()
local button = -1
local sybolName = ""
if buffer.selection_empty then
button, symbolName = ui.dialogs.inputbox{
title = "Search for Symbol",
informative_text = "Name:"
}
if button == -1 then return end
else
symbolName = buffer:get_sel_text()
end
local result = runDCDClient("--search " .. symbolName)
local resultList = {}
local posDict = {}
local i = 0
for line in result:gmatch("(.-)\n") do
local path, kind, position = line:match("([%w_/.]+)\t(%w)\t(%d+)")
table.insert(resultList, symbolName)
table.insert(resultList, kind)
table.insert(resultList, path)
table.insert(resultList, position)
posDict[i + 1] = {path, tonumber(position)}
i = i + 1
end
for j, item in ipairs(resultList) do print (item) end
local button2, index = ui.dialogs.filteredlist{
title = "Go to symbol",
columns = {"Name", "Type", "File", "Position"},
items = resultList,
search_column = 3
}
if button2 ~= -1 then
if (posDict[index][1] ~= "stdin") then
io.open_file(posDict[index][1])
end
buffer:goto_pos(tonumber(posDict[index][2]))
buffer:word_right_end_extend()
end
end
events.connect(events.CALL_TIP_CLICK, function(arrow)
if buffer:get_lexer() ~= "dmd" then return end
if arrow == 1 then

View File

@ -32,6 +32,8 @@ import std.d.lexer;
import messages;
import string_interning;
import std.range : isOutputRange;
/**
* Any special information about a variable declaration symbol.
*/
@ -128,6 +130,21 @@ public:
return app.data();
}
/**
* Adds all parts and parts of parts with the given name to the given output
* range.
*/
void getAllPartsNamed(OR)(string name, ref OR outputRange)
if (isOutputRange!(OR, ACSymbol*))
{
foreach (part; parts[])
{
if (part.name == name)
outputRange.put(part);
part.getAllPartsNamed(name, outputRange);
}
}
/**
* Symbol's name
*/

View File

@ -115,6 +115,71 @@ public AutocompleteResponse complete(const AutocompleteRequest request)
}
}
/**
*
*/
public AutocompleteResponse symbolSearch(const AutocompleteRequest request)
{
import containers.ttree;
LexerConfig config;
config.fileName = "";
auto cache = StringCache(StringCache.defaultBucketCount);
const(Token)[] tokenArray = getTokensForParser(cast(ubyte[]) request.sourceCode,
config, &cache);
auto allocator = scoped!(CAllocatorImpl!(BlockAllocator!(1024*16)));
Scope* completionScope = generateAutocompleteTrees(tokenArray, allocator);
scope(exit) typeid(Scope).destroy(completionScope);
static struct SearchResults
{
void put(ACSymbol* symbol)
{
tree.insert(SearchResult(symbol));
}
static struct SearchResult
{
ACSymbol* symbol;
int opCmp(ref const SearchResult other) const pure nothrow
{
if (other.symbol.symbolFile < symbol.symbolFile)
return -1;
if (other.symbol.symbolFile > symbol.symbolFile)
return 1;
if (other.symbol.location < symbol.location)
return -1;
return other.symbol.location > symbol.location;
}
}
TTree!(SearchResult) tree;
}
SearchResults results;
foreach (symbol; completionScope.symbols[])
{
symbol.getAllPartsNamed(request.searchName, results);
}
foreach (s; ModuleCache.getAllSymbols())
{
s.symbol.getAllPartsNamed(request.searchName, results);
}
AutocompleteResponse response;
foreach (result; results.tree[])
{
response.locations ~= result.symbol.location;
response.completionKinds ~= result.symbol.kind;
response.completions ~= result.symbol.symbolFile;
}
return response;
}
/******************************************************************************/
private:

View File

@ -44,13 +44,14 @@ int main(string[] args)
bool symbolLocation;
bool doc;
bool query;
string search;
try
{
getopt(args, "cursorPos|c", &cursorPos, "I", &importPaths,
"port|p", &port, "help|h", &help, "shutdown", &shutdown,
"clearCache", &clearCache, "symbolLocation|l", &symbolLocation,
"doc|d", &doc, "query|q", &query);
"doc|d", &doc, "query|q", &query, "search|s", &search);
}
catch (Exception e)
{
@ -113,7 +114,7 @@ int main(string[] args)
return 0;
}
}
else if (cursorPos == size_t.max)
else if (search == null && cursorPos == size_t.max)
{
// cursor position is a required argument
printHelp(args[0]);
@ -151,11 +152,14 @@ int main(string[] args)
request.importPaths = importPaths;
request.sourceCode = sourceCode;
request.cursorPosition = cursorPos;
request.searchName = search;
if (symbolLocation)
request.kind |= RequestKind.symbolLocation;
else if (doc)
request.kind |= RequestKind.doc;
else if(search)
request.kind |= RequestKind.search;
else
request.kind |= RequestKind.autocomplete;
@ -171,12 +175,16 @@ int main(string[] args)
printLocationResponse(response);
else if (doc)
printDocResponse(response);
else if (search !is null)
printSearchResponse(response);
else
printCompletionResponse(response);
return 0;
}
private:
void printHelp(string programName)
{
writefln(
@ -211,6 +219,10 @@ Options:
Gets documentation comments associated with the symbol at the cursor
location.
--search | -s symbolName
Searches for symbolName in both stdin / the given file name as well as
others files cached by the server.
--query | -q
Query the server statis. Returns 0 if the server is running. Returns
1 if the server could not be contacted.
@ -299,3 +311,12 @@ void printCompletionResponse(AutocompleteResponse response)
writeln(line);
}
}
void printSearchResponse(const AutocompleteResponse response)
{
foreach(i; 0 .. response.completions.length)
{
writefln("%s\t%s\t%s", response.completions[i], response.completionKinds[i],
response.locations[i]);
}
}

View File

@ -130,6 +130,8 @@ enum RequestKind : ubyte
doc = 0b00100000,
/// Query server status
query = 0b01000000,
/// Search for symbol
search = 0b10000000,
}
/**
@ -161,6 +163,11 @@ struct AutocompleteRequest
* The cursor position
*/
size_t cursorPosition;
/**
* Name of symbol searched for
*/
string searchName;
}
/**
@ -198,4 +205,9 @@ struct AutocompleteResponse
* completion type is a function argument list.
*/
char[] completionKinds;
/**
* Symbol locations for symbol searches.
*/
size_t[] locations;
}

View File

@ -244,6 +244,11 @@ struct ModuleCache
return importPaths[];
}
static auto getAllSymbols()
{
return cache[];
}
/// Count of autocomplete symbols that have been allocated
static uint symbolsAllocated;

View File

@ -202,6 +202,12 @@ int main(string[] args)
Log.error("Could not get symbol location", e.msg);
}
}
else if (request.kind & RequestKind.search)
{
AutocompleteResponse response = symbolSearch(request);
ubyte[] responseBytes = msgpack.pack(response);
s.send(responseBytes);
}
Log.info("Request processed in ", requestWatch.peek().to!("msecs", float), " milliseconds");
}
return 0;