Change message for variables that might be used in mixin expressions

This commit is contained in:
Hackerpilot 2014-11-17 14:53:37 -08:00
parent 3d365aafee
commit 504fcc830e
1 changed files with 41 additions and 9 deletions

View File

@ -9,8 +9,7 @@ import std.d.ast;
import std.d.lexer; import std.d.lexer;
import analysis.base; import analysis.base;
import std.container; import std.container;
import std.regex : Regex, regex, matchAll;
import std.stdio;
/** /**
* Checks for unused variables. * Checks for unused variables.
@ -22,6 +21,7 @@ class UnusedVariableCheck : BaseAnalyzer
this(string fileName) this(string fileName)
{ {
super(fileName); super(fileName);
re = regex("[\\p{Alphabetic}_][\\w_]*");
} }
override void visit(const Module mod) override void visit(const Module mod)
@ -71,7 +71,6 @@ class UnusedVariableCheck : BaseAnalyzer
mixin PartsUseVariables!FunctionCallExpression; mixin PartsUseVariables!FunctionCallExpression;
mixin PartsUseVariables!NewExpression; mixin PartsUseVariables!NewExpression;
mixin PartsUseVariables!TemplateArgumentList; mixin PartsUseVariables!TemplateArgumentList;
mixin PartsUseVariables!MixinExpression;
mixin PartsUseVariables!ArgumentList; mixin PartsUseVariables!ArgumentList;
mixin PartsUseVariables!Initializer; mixin PartsUseVariables!Initializer;
mixin PartsUseVariables!IndexExpression; mixin PartsUseVariables!IndexExpression;
@ -201,13 +200,38 @@ class UnusedVariableCheck : BaseAnalyzer
interestDepth--; interestDepth--;
} }
override void visit(const MixinExpression mix)
{
interestDepth++;
mixinDepth++;
mix.accept(this);
mixinDepth--;
interestDepth--;
}
override void visit(const PrimaryExpression primary) override void visit(const PrimaryExpression primary)
{ {
if (interestDepth > 0 && primary.identifierOrTemplateInstance !is null if (interestDepth > 0)
{
if (primary.identifierOrTemplateInstance !is null
&& primary.identifierOrTemplateInstance.identifier != tok!"") && primary.identifierOrTemplateInstance.identifier != tok!"")
{ {
variableUsed(primary.identifierOrTemplateInstance.identifier.text); variableUsed(primary.identifierOrTemplateInstance.identifier.text);
} }
if (mixinDepth > 0 && primary.primary == tok!"stringLiteral"
|| primary.primary == tok!"wstringLiteral"
|| primary.primary == tok!"dstringLiteral")
{
foreach (part; matchAll(primary.primary.text, re))
{
size_t treeIndex = tree.length - 1;
auto uu = UnUsed(part.hit);
auto r = tree[treeIndex].equalRange(&uu);
if (!r.empty)
r.front.uncertain = true;
}
}
}
primary.accept(this); primary.accept(this);
} }
@ -328,11 +352,14 @@ class UnusedVariableCheck : BaseAnalyzer
foreach (uu; tree[$ - 1]) foreach (uu; tree[$ - 1])
{ {
if (!uu.isRef && tree.length > 1) if (!uu.isRef && tree.length > 1)
{
string certainty = uu.uncertain ? " might not be used." : " is never used.";
string errorMessage = (uu.isParameter ? "Parameter " : "Variable ")
~ uu.name ~ certainty;
addErrorMessage(uu.line, uu.column, addErrorMessage(uu.line, uu.column,
uu.isParameter ? "dscanner.suspicious.unused_parameter" uu.isParameter ? "dscanner.suspicious.unused_parameter"
: "dscanner.suspicious.unused_variable", : "dscanner.suspicious.unused_variable", errorMessage);
(uu.isParameter ? "Parameter " : "Variable ") }
~ uu.name ~ " is never used.");
} }
tree = tree[0 .. $ - 1]; tree = tree[0 .. $ - 1];
} }
@ -349,16 +376,21 @@ class UnusedVariableCheck : BaseAnalyzer
size_t column; size_t column;
bool isParameter; bool isParameter;
bool isRef; bool isRef;
bool uncertain;
} }
RedBlackTree!(UnUsed*, "a.name < b.name")[] tree; RedBlackTree!(UnUsed*, "a.name < b.name")[] tree;
uint interestDepth; uint interestDepth;
uint mixinDepth;
bool isOverride; bool isOverride;
bool inAggregateScope; bool inAggregateScope;
bool blockStatementIntroducesScope = true; bool blockStatementIntroducesScope = true;
Regex!char re;
} }