3
* Copyright (c) 2003, Peter Strand <peter@zarquon.se>
5
* This source code is released for free distribution under the terms of the
6
* GNU General Public License.
8
* This module contains functions for generating tags for Haskell language
13
* Does not handle operators or infix definitions like:
23
#include "general.h" /* must always come first */
36
K_TYPE, K_CONSTRUCTOR, K_FUNCTION, K_MODULE
39
static kindOption HaskellKinds [] = {
40
{ TRUE, 't', "typedef", "types" },
41
{ TRUE, 'c', "macro", "type constructors" },
42
{ TRUE, 'f', "function", "functions" },
43
{ TRUE, 'm', "namespace", "modules"}
47
typedef const unsigned char *custr;
50
* FUNCTION DEFINITIONS
54
static void skip_rest_of_line(void)
59
} while (c != EOF && c != '\n');
62
static int get_line(char *buf)
69
} while (c != EOF && c != '\n' && i < 1000);
74
static int get_next_char(void)
85
if (c == '-' && nxt == '-') {
87
return get_next_char();
89
if (c == '{' && nxt == '-') {
94
} while (! (c == EOF || (last == '-' && c == '}')));
95
return get_next_char();
100
static void add_tag(const char *token, haskellKind kind, vString *name)
103
for (i = 0; token[i] != '\0'; ++i)
104
vStringPut(name, token[i]);
106
vStringTerminate(name);
107
makeSimpleTag(name, HaskellKinds, kind);
111
static int isident(char c)
113
return isalnum(c) || c == '_' || c == '\'' || c == '$';
116
static int get_token(char *token, int n)
120
while (c != EOF && isident(c) && i < 1000) {
136
enum Find_State { Find_Eq, Find_Constr, Get_Extr, Find_Extr, Find_Bar };
138
static int inside_datatype(vString *name)
140
enum Find_State st = Find_Eq;
151
if (! (c == ' ' || c == '\t')) {
158
else if (st == Find_Constr)
162
} while (isspace(c));
168
if (!get_token(token, 1))
170
add_tag(token, K_CONSTRUCTOR, name);
173
else if (st == Find_Extr)
180
else if (c == '\n') {
182
if (! (c == ' ' || c == '\t')) {
186
else if (!isspace(c))
189
else if (st == Get_Extr)
193
} while (isspace(c));
198
add_tag(token, K_FUNCTION, name);
207
else if (st == Find_Bar)
213
if (! (c == ' ' || c == '\t')) {
217
} while (c != EOF && c != '|');
224
static void findHaskellTags (int is_literate)
226
vString *name = vStringNew ();
227
char token[1001], arg[1001];
229
int in_tex_lit_code = 0;
244
if (is_literate && !in_tex_lit_code) {
259
} else if (c == '\\') {
260
int n = get_line(token);
261
if (strncmp(token, "begin{code}", 11) == 0) {
266
if (n > 0 && token[n-1] != '\n')
278
if (is_literate && in_tex_lit_code && c == '\\') {
279
if (strncmp(token, "end{code}", 9) == 0) {
292
if (!get_token(token, 1)) {
297
if ((c = fileGetc()) == EOF)
299
} while (c == ' ' || c == '\t');
302
if (strcmp(token, "data") == 0 || strcmp(token, "newtype") == 0) {
303
add_tag(arg, K_TYPE, name);
304
c = inside_datatype(name);
307
if (strcmp(token, "type") == 0)
308
add_tag(arg, K_TYPE, name);
309
else if (strcmp(token, "module") == 0)
310
add_tag(arg, K_MODULE, name);
311
else if (strcmp(token, "instance") == 0 ||
312
strcmp(token, "foreign") == 0 ||
313
strcmp(token, "import") == 0)
317
add_tag(token, K_FUNCTION, name);
325
static void findNormalHaskellTags (void)
330
static void findLiterateHaskellTags (void)
335
extern parserDefinition* HaskellParser (void)
337
static const char *const extensions [] = { "hs", NULL };
338
parserDefinition* def = parserNew ("Haskell");
340
def->kinds = HaskellKinds;
341
def->kindCount = KIND_COUNT(HaskellKinds);
342
def->extensions = extensions;
343
def->parser = findNormalHaskellTags;
347
extern parserDefinition* LiterateHaskellParser (void)
349
static const char *const extensions [] = { "lhs", NULL };
350
parserDefinition* def = parserNew ("Literate Haskell");
351
def->kinds = HaskellKinds;
352
def->kindCount = KIND_COUNT(HaskellKinds);
353
def->extensions = extensions;
354
def->parser = findLiterateHaskellTags;
358
/* vi:set expandtab tabstop=8 shiftwidth=4: */