Adding ufcs to math with type of pointer

This commit is contained in:
davu 2023-03-17 22:48:54 +01:00 committed by Jan Jurzitza
parent e65e86a744
commit 95e484a202
6 changed files with 76 additions and 17 deletions

View File

@ -658,7 +658,11 @@ ScopeSymbolPair generateAutocompleteTreesProd(string source, string filename, si
version (linux)
{
enum string ufcsExampleCode =
unittest
{
enum string ufcsExampleCode =
q{class Incrementer
{
int run(int x)
@ -676,9 +680,6 @@ void doIncrement()
life.
}};
unittest
{
import dsymbol.ufcs;
writeln("Getting UFCS Symbols For life");
ModuleCache cache;
@ -701,9 +702,19 @@ void doIncrement()
life.
}};
unittest
unittest
{
import dsymbol.ufcs;
enum string ufcsTemplateExampleCode =
q{int increment(T)(T x)
{
return x++;
}
void doIncrement()
{
int life = 42;
life.
}};
writeln("Getting Templated UFCS Symbols For life");
ModuleCache cache;
@ -715,4 +726,23 @@ unittest
}
unittest
{
enum string ufcsPointerExampleCode =
q{void increment(int* x) { }
void doIncrement(int* x, int* y)
{
y.
}};
writeln("Getting Ptr UFCS completion");
ModuleCache cache;
// position of variable life
size_t cursorPos = 65;
auto pair = generateAutocompleteTreesProd(ufcsPointerExampleCode, randomDFilename, cursorPos, cache);
assert(pair.ufcsSymbols[0].name == "increment");
assert(pair.ufcsSymbols[1].name == "doIncrement");
}
}

View File

@ -42,9 +42,9 @@ enum string[string] INTEGER_PROMOTIONS = [
enum MAX_RECURSION_DEPTH = 50;
private DSymbol* deduceSymbolType(DSymbol* symbol)
private const(DSymbol)* deduceSymbolType(const(DSymbol)* symbol)
{
DSymbol* symbolType = symbol.type;
const(DSymbol)* symbolType = symbol.type;
while (symbolType !is null && (symbolType.qualifier == SymbolQualifier.func
|| symbolType.kind == CompletionKind.functionName
|| symbolType.kind == CompletionKind.importSymbol
@ -57,6 +57,7 @@ private DSymbol* deduceSymbolType(DSymbol* symbol)
//look at next type to deduce
symbolType = symbolType.type;
}
return symbolType;
}
@ -170,9 +171,6 @@ private void getUFCSSymbols(T, Y)(ref T localAppender, ref Y globalAppender, Sco
DSymbol*[] getUFCSSymbolsForCursor(Scope* completionScope, ref const(Token)[] tokens, size_t cursorPosition)
{
DSymbol* cursorSymbol;
DSymbol* cursorSymbolType;
TokenCursorResult tokenCursorResult = getCursorToken(tokens, cursorPosition);
if (tokenCursorResult.completionContext is CompletionContext.UnknownCompletion)
@ -181,7 +179,7 @@ DSymbol*[] getUFCSSymbolsForCursor(Scope* completionScope, ref const(Token)[] to
return [];
}
cursorSymbol = completionScope.getFirstSymbolByNameAndCursor(
const(DSymbol)* cursorSymbol = completionScope.getFirstSymbolByNameAndCursor(
tokenCursorResult.symbolIdentifierName, cursorPosition);
if (cursorSymbol is null)
@ -196,7 +194,7 @@ DSymbol*[] getUFCSSymbolsForCursor(Scope* completionScope, ref const(Token)[] to
return [];
}
cursorSymbolType = deduceSymbolType(cursorSymbol);
const(DSymbol)* cursorSymbolType = deduceSymbolType(cursorSymbol);
if (cursorSymbolType is null)
{
@ -220,7 +218,7 @@ DSymbol*[] getUFCSSymbolsForCursor(Scope* completionScope, ref const(Token)[] to
}
private DSymbol*[] getUFCSSymbolsForDotCompletion(DSymbol* symbolType, Scope* completionScope, size_t cursorPosition)
private DSymbol*[] getUFCSSymbolsForDotCompletion(const(DSymbol)* symbolType, Scope* completionScope, size_t cursorPosition)
{
// local appender
FilteredAppender!(a => a.isCallableWithArg(symbolType), DSymbol*[]) localAppender;
@ -232,7 +230,7 @@ private DSymbol*[] getUFCSSymbolsForDotCompletion(DSymbol* symbolType, Scope* co
return localAppender.data ~ globalAppender.data;
}
private DSymbol*[] getUFCSSymbolsForParenCompletion(DSymbol* symbolType, Scope* completionScope, istring searchWord, size_t cursorPosition)
private DSymbol*[] getUFCSSymbolsForParenCompletion(const(DSymbol)* symbolType, Scope* completionScope, istring searchWord, size_t cursorPosition)
{
// local appender
FilteredAppender!(a => a.isCallableWithArg(symbolType) && a.name.among(searchWord), DSymbol*[]) localAppender;
@ -280,7 +278,16 @@ private bool matchAliasThis(const(DSymbol)* beforeDotType, const(DSymbol)* incom
}
bool isNonConstrainedTemplate(const(DSymbol)* incomingSymbol){
return incomingSymbol.functionParameters.front.type !is null && incomingSymbol.functionParameters.front.type.kind is CompletionKind.typeTmpParam;
return incomingSymbol.functionParameters.front.type !is null
&& incomingSymbol.functionParameters.front.type.kind is CompletionKind.typeTmpParam;
}
private bool matchesWithTypeOfPointer(const(DSymbol)* incomingSymbol, const(DSymbol)* cursorSymbolType) {
return incomingSymbol.functionParameters.front.type.qualifier == SymbolQualifier.pointer
&& cursorSymbolType.qualifier == SymbolQualifier.pointer
&& incomingSymbol.functionParameters.front.type.type is cursorSymbolType.type;
}
/**
@ -294,7 +301,7 @@ bool isNonConstrainedTemplate(const(DSymbol)* incomingSymbol){
*/
bool isCallableWithArg(const(DSymbol)* incomingSymbol, const(DSymbol)* beforeDotType, bool isGlobalScope = false, int recursionDepth = 0)
{
if (incomingSymbol is null
if (incomingSymbol is null
|| beforeDotType is null
|| isGlobalScope && incomingSymbol.protection is tok!"private" // don't show private functions if we are in global scope
|| recursionDepth > MAX_RECURSION_DEPTH)
@ -306,6 +313,7 @@ bool isCallableWithArg(const(DSymbol)* incomingSymbol, const(DSymbol)* beforeDot
{
return beforeDotType is incomingSymbol.functionParameters.front.type
|| isNonConstrainedTemplate(incomingSymbol)
|| matchesWithTypeOfPointer(incomingSymbol, beforeDotType)
|| willImplicitBeUpcasted(beforeDotType, incomingSymbol)
|| matchAliasThis(beforeDotType, incomingSymbol, recursionDepth);

View File

@ -0,0 +1,10 @@
identifiers
alignof k
doIncrement F
increment F
init k
mangleof k
max k
min k
sizeof k
stringof k

View File

@ -0,0 +1,5 @@
void increment(int* x) { }
void doIncrement(int* x, int* y)
{
y.
}

View File

@ -0,0 +1,5 @@
set -e
set -u
../../bin/dcd-client $1 -c65 file.d > actual_pointer_test.txt
diff actual_pointer_test.txt expected_pointer_test.txt

View File

@ -10,6 +10,7 @@ struct IntAliased {
}
void u(Foo foo) {}
void ufcsHelloPtr(Foo* foo) {}
void ufcsHello(ref Foo foo) {}
void ufcsBar(Foo foo, string mama) {}
void ufcsBarRef(ref Foo foo, string mama) {}