From dcc89a6f6173792e64b8312a8080f05500abe8de Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Enrico=20Tr=C3=B6ger?= Date: Tue, 9 Jun 2009 21:02:46 +0000 Subject: [PATCH] Parse Pascal calltips (closes #2802640). git-svn-id: https://geany.svn.sourceforge.net/svnroot/geany/trunk@3849 ea778897-0a13-0410-b9d1-a72fbfd435f5 --- ChangeLog | 6 ++++ tagmanager/pascal.c | 84 ++++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 86 insertions(+), 4 deletions(-) diff --git a/ChangeLog b/ChangeLog index 59362f1a..045c23ed 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2009-06-09 Enrico Tröger + + * tagmanager/pascal.c: + Parse Pascal calltips (closes #2802640). + + 2009-06-09 Nick Treleaven * src/filetypes.c, src/ui_utils.c: diff --git a/tagmanager/pascal.c b/tagmanager/pascal.c index ce9079f2..fac7e66c 100644 --- a/tagmanager/pascal.c +++ b/tagmanager/pascal.c @@ -20,6 +20,7 @@ #include "entry.h" #include "parse.h" #include "read.h" +#include "main.h" #include "vstring.h" /* @@ -30,7 +31,7 @@ typedef enum { } pascalKind; static kindOption PascalKinds [] = { - { TRUE, 'f', "function", "functions"}, + { TRUE, 'f', "function", "functions"}, { TRUE, 'f', "function", "procedures"} }; @@ -39,7 +40,8 @@ static kindOption PascalKinds [] = { */ static void createPascalTag (tagEntryInfo* const tag, - const vString* const name, const int kind) + const vString* const name, const int kind, + const char *arglist, const char *vartype) { if (PascalKinds [kind].enabled && name != NULL && vStringLength (name) > 0) { @@ -47,6 +49,8 @@ static void createPascalTag (tagEntryInfo* const tag, tag->kindName = PascalKinds [kind].name; tag->kind = PascalKinds [kind].letter; + tag->extensionFields.arglist = arglist; + tag->extensionFields.varType = vartype; } else initTagEntry (tag, NULL); @@ -79,6 +83,69 @@ static boolean tail (const char *cp) return result; } +static void parseArglist(const char *buf, char **arglist, char **vartype) +{ + char *c, *start, *end; + int level; + + if (NULL == buf || NULL == arglist) + return; + + c = strdup(buf); + /* parse argument list which can be missing like in "function ginit:integer;" */ + if (NULL != (start = strchr(c, '('))) + { + for (level = 1, end = start + 1; level > 0; ++end) + { + if ('\0' == *end) + break; + else if ('(' == *end) + ++ level; + else if (')' == *end) + -- level; + } + } + else /* if no argument list was found, continue looking for a return value */ + { + start = "()"; + end = c; + } + + /* parse return type if requested by passing a non-NULL vartype argument */ + if (NULL != vartype) + { + char *var, *var_start; + + *vartype = NULL; + + if (NULL != (var = strchr(end, ':'))) + { + var++; /* skip ':' */ + while (isspace((int) *var)) + ++var; + + if (starttoken(*var)) + { + var_start = var; + var++; + while (intoken(*var)) + var++; + if (endtoken(*var)) + { + *var = '\0'; + *vartype = strdup(var_start); + } + } + } + } + + *end = '\0'; + *arglist = strdup(start); + + eFree(c); +} + + /* Algorithm adapted from from GNU etags. * Locates tags for procedures & functions. Doesn't do any type- or * var-definitions. It does look for the keyword "extern" or "forward" @@ -89,6 +156,8 @@ static void findPascalTags (void) { vString *name = vStringNew (); tagEntryInfo tag; + char *arglist = NULL; + char *vartype = NULL; pascalKind kind = K_FUNCTION; /* each of these flags is TRUE iff: */ boolean incomment = FALSE; /* point is inside a comment */ @@ -208,7 +277,11 @@ static void findPascalTags (void) for (cp = dbp ; *cp != '\0' && !endtoken (*cp) ; cp++) continue; vStringNCopyS (name, (const char*) dbp, cp - dbp); - createPascalTag (&tag, name, kind); + eFree(arglist); + if (kind == K_FUNCTION) + eFree(vartype); + parseArglist((const char*) cp, &arglist, (kind == K_FUNCTION) ? &vartype : NULL); + createPascalTag (&tag, name, kind, arglist, vartype); dbp = cp; /* set dbp to e-o-token */ get_tagname = FALSE; found_tag = TRUE; @@ -254,8 +327,11 @@ static void findPascalTags (void) } break; } - } /* while not eof */ + } /* while not eof */ } + eFree(arglist); + eFree(vartype); + vStringDelete(name); } extern parserDefinition* PascalParser (void)