Kaydet (Commit) 1438a99e authored tarafından Colomban Wendling's avatar Colomban Wendling

Merge pull request #889 from b4n/c/return-type

C, C++, C#, D: Improve return type and var type recognition.
......@@ -518,7 +518,8 @@ static const keywordDesc KeywordTable [] = {
*/
static void createTags (const unsigned int nestLevel, statementInfo *const parent);
static void copyToken (tokenInfo *const dest, const tokenInfo *const src);
static const char *getVarType (const statementInfo *const st);
static const char *getVarType (const statementInfo *const st,
const tokenInfo *const token);
/*
* FUNCTION DEFINITIONS
......@@ -1186,6 +1187,7 @@ static const char* accessField (const statementInfo *const st)
}
static void addOtherFields (tagEntryInfo* const tag, const tagType type,
const tokenInfo *const nameToken,
const statementInfo *const st, vString *const scope)
{
/* For selected tag types, append an extension flag designating the
......@@ -1254,40 +1256,90 @@ static void addOtherFields (tagEntryInfo* const tag, const tagType type,
if (((TOKEN_NAME == st->firstToken->type) || isDataTypeKeyword(st->firstToken))
&& (0 != strcmp(vStringValue(st->firstToken->name), tag->name)))
{
tag->extensionFields.varType = getVarType(st);
tag->extensionFields.varType = getVarType(st, nameToken);
}
}
}
static const char *getVarType (const statementInfo *const st)
static const char *getVarType (const statementInfo *const st,
const tokenInfo *const nameToken)
{
static vString *vt = NULL;
unsigned int i;
unsigned int end = st->tokenIndex;
boolean seenType = FALSE;
if (! st->gotArgs)
return vStringValue(st->firstToken->name); /* ignore non-functions */
switch (st->declaration) {
case DECL_BASE:
case DECL_FUNCTION:
case DECL_FUNCTION_TEMPLATE:
break;
default:
return vStringValue(st->firstToken->name);
}
if (vt == NULL)
vt = vStringNew();
else
vStringClear(vt);
/* find the end of the type signature in the token list */
for (i = 0; i < st->tokenIndex; i++)
{
const tokenInfo *const t = st->token[i];
/* stop if we find the token used to generate the tag name, or
* a name token in the middle yet not preceded by a scope separator */
if ((t == nameToken ||
(t->type == nameToken->type &&
t->keyword == nameToken->keyword &&
t->lineNumber == nameToken->lineNumber &&
strcmp(vStringValue(t->name), vStringValue(nameToken->name)) == 0)) ||
(t->type == TOKEN_NAME && seenType &&
(i > 0 && st->token[i - 1]->type != TOKEN_DOUBLE_COLON)))
{
break;
}
if (t->type != TOKEN_DOUBLE_COLON)
end = i + 1;
if (t->type == TOKEN_NAME)
seenType = TRUE;
else if (t->type == TOKEN_KEYWORD && isDataTypeKeyword(t))
seenType = TRUE;
}
/* ugly historic workaround when we can't figure out the type */
if (end < 2 && ! st->gotArgs)
return vStringValue(st->firstToken->name);
for (i = 0; i < end; i++)
{
tokenInfo *t = st->token[i];
switch (t->type)
{
case TOKEN_NAME: /* user typename */
if (strcmp(vStringValue(t->name), vStringValue(st->firstToken->name)) != 0)
continue;
break;
case TOKEN_KEYWORD:
if (t->keyword != KEYWORD_EXTERN && t->keyword != KEYWORD_STATIC) /* uninteresting keywords */
if ((t->keyword != KEYWORD_EXTERN && t->keyword != KEYWORD_STATIC) && /* uninteresting keywords */
(st->gotArgs ||
/* ignore uninteresting keywords for non-functions */
(t->keyword != KEYWORD_PUBLIC &&
t->keyword != KEYWORD_PRIVATE &&
t->keyword != KEYWORD_PROTECTED &&
t->keyword != KEYWORD_FINAL &&
t->keyword != KEYWORD_TYPEDEF &&
/* hack for D static conditions */
t->keyword != KEYWORD_IF)))
{
break;
}
continue;
case TOKEN_STAR: vStringCatS(vt, " *"); continue;
case TOKEN_ARRAY: vStringCatS(vt, "[]"); continue;
case TOKEN_DOUBLE_COLON:
vStringCatS(vt, "::");
continue;
default: continue;
}
if (vStringLength(vt) > 0)
......@@ -1426,7 +1478,7 @@ static void makeTag (const tokenInfo *const token,
e.type = type;
findScopeHierarchy (scope, st);
addOtherFields (&e, type, st, scope);
addOtherFields (&e, type, token, st, scope);
#ifdef DEBUG_C
printTagEntry(&e);
......
......@@ -301,6 +301,7 @@ test_sources = \
ui5.controller.js \
union.f \
value.f \
var-and-return-type.cpp \
whitespaces.php \
$(NULL)
test_results = $(test_sources:=.tags)
......
# format=tagmanager
a64bit_fields0int
a64bit_fields0unsigned int
anon_struct_020480
anon_struct_120480
anon_struct_220480
b64bit_fields0int
b64bit_fields0unsigned int
bad264anon_struct_10BYTE
bit_fields20480
bitfield_flags40960anon_struct_1
c64bit_fields0int
c64bit_fields0unsigned int
exp64anon_struct_00
frac064anon_struct_00
frac164anon_struct_00
group64anon_struct_10BYTE
lower64shortname_info0char
lower64shortname_info0unsigned char
mystruct40960anon_struct_2
personal64anon_struct_10BYTE
private64anon_struct_20BYTE
......
# format=tagmanager
f116()0std
f216()0const std
f316()std0std const
f1Ì16Í()Ö0Ïstd::string
f2Ì16Í()Ö0Ïconst std::string
f3Ì16Í()ÎstdÖ0Ïstd::string const
# format=tagmanager
m116()C::C0C *C
m216()C::C0C *const C
m316()C::C0C const *C
m416()C::C0C const *const C
m116()C::C0C::T *
m216()C::C0C::T *const
m316()C::C0C::T const *
m416()C::C0C::T const *const
# format=tagmanager
MajorVersion64mud0std
MinorVersion64mud0std
MajorVersion64mud0std::string
MinorVersion64mud0std::string
mud2560
......@@ -4,8 +4,8 @@ B
M3_INIT131072(a, b, c)0
STRINGIFY131072(x)0
STRINGIFY_INTERN131072(x)0
buf64str0char
len64str0int
buf64str0char *
len64str0unsigned int
main16(void)0int
matrix340960int
size64str0int
......
......@@ -7,8 +7,8 @@ F
M3_INIT131072(a, b, c)0
STRINGIFY131072(x)0
STRINGIFY_INTERN131072(x)0
buf64str0char
len64str0int
buf64str0char *
len64str0unsigned int
main16(void)0int
matrix340960int
size64str0int
......
......@@ -2,4 +2,4 @@
IndexerClass10
Main128()MainClass0public void
MainClass10
myArray8IndexerClass0int
myArray8IndexerClass0int[]
......@@ -3,4 +3,4 @@ IMyInterface
IndexerClass10
Main128()MainClass0public void
MainClass10
myArray8IndexerClass0int
myArray8IndexerClass0int[]
......@@ -3,7 +3,7 @@ ConstTest
Main128()ConstTest0public void
MyClass1ConstTest0
MyClass128(int p1, int p2)ConstTest.MyClass0
c18ConstTest.MyClass0int
c28ConstTest.MyClass0int
c18ConstTest.MyClass0const int
c28ConstTest.MyClass0const int
x8ConstTest.MyClass0int
y8ConstTest.MyClass0int
......@@ -14,6 +14,6 @@ Main
Sphere1TestClass0
Sphere128(double r)TestClass.Sphere0
TestClass10
pi8TestClass.Dimensions0double
pi8TestClass.Dimensions0const double
x8TestClass.Dimensions0double
y8TestClass.Dimensions0double
......@@ -2,4 +2,4 @@
Main128()Test0public void
Test10
Test128(int _i)Test0
i8Test0int
i8Test0volatile int
......@@ -13,7 +13,7 @@ bar
bar1024()Interface0public AliasInt
conditional163840T
foo4Enum0
globalVar163840__gshared
globalVar163840__gshared int
i163840int
main16(string[] args)0void
obj163840Object
......
const volatile unsigned int func1();
const volatile unsigned int var1 = 0;
struct type1 {
unsigned int memb1;
struct type1 *next;
};
const struct type1 func2();
const struct type1 var2 = { 0, 0 };
typedef type1 type1_t;
const type1_t func3();
const type1_t var3 = { 0, 0 };
struct type1 func4();
struct type1 var4 = { 0, 0 };
type1_t func5();
type1_t var5 = { 0, 0 };
typedef unsigned long int type2_t;
/* scoped stuff */
#include <string>
const std::string func6();
const std::string var6 = "hello";
std::string func7();
std::string var7 = "hello";
/* this shows a different bug in the parser, adding scope std to the symbol.
* ignore this for now.
std::string const func8();
std::string const var8 = "hello";
*/
# format=tagmanager
func11024()0const volatile unsigned int
func21024()0type1
func31024()0const type1_t
func41024()0type1
func51024()0type1_t
func61024()0const std::string
func71024()0std::string
memb164type10unsigned int
next64type10type1
type120480
type1_t40960type1
type2_t40960unsigned long int
var1163840const volatile unsigned int
var2163840type1
var3163840const type1_t
var4163840type1
var5163840type1_t
var6163840const std::string
var7163840std::string
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment