2005-11-22 12:26:26 +00:00
|
|
|
/*
|
2007-12-04 15:44:45 +00:00
|
|
|
* $Id$
|
2006-01-11 18:50:44 +00:00
|
|
|
*
|
|
|
|
* Copyright (c) 2000-2001, Jérôme Plût
|
|
|
|
* Copyright (c) 2006, Enrico Tröger
|
|
|
|
*
|
|
|
|
* This source code is released for free distribution under the terms of the
|
|
|
|
* GNU General Public License.
|
|
|
|
*
|
|
|
|
* This module contains functions for generating tags for source files
|
|
|
|
* for the TeX formatting system.
|
|
|
|
*/
|
2005-11-22 12:26:26 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* INCLUDE FILES
|
|
|
|
*/
|
|
|
|
#include "general.h" /* must always come first */
|
|
|
|
|
|
|
|
#include <ctype.h>
|
2006-01-11 18:50:44 +00:00
|
|
|
#include <string.h>
|
2005-11-22 12:26:26 +00:00
|
|
|
|
|
|
|
#include "parse.h"
|
|
|
|
#include "read.h"
|
|
|
|
#include "vstring.h"
|
|
|
|
|
|
|
|
/*
|
|
|
|
* DATA DEFINITIONS
|
|
|
|
*/
|
|
|
|
typedef enum {
|
2006-01-23 13:41:08 +00:00
|
|
|
K_COMMAND,
|
|
|
|
K_ENVIRONMENT,
|
|
|
|
K_SECTION,
|
|
|
|
K_SUBSECTION,
|
|
|
|
K_SUBSUBSECTION,
|
2006-12-05 16:03:18 +00:00
|
|
|
K_CHAPTER,
|
2006-01-23 13:41:08 +00:00
|
|
|
K_LABEL
|
2006-01-11 18:50:44 +00:00
|
|
|
} TeXKind;
|
2005-11-22 12:26:26 +00:00
|
|
|
|
2006-01-11 18:50:44 +00:00
|
|
|
static kindOption TeXKinds[] = {
|
2006-01-16 17:47:11 +00:00
|
|
|
{ TRUE, 'f', "function", "command definitions" },
|
|
|
|
{ TRUE, 'c', "class", "environment definitions" },
|
|
|
|
{ TRUE, 'm', "member", "labels, sections and bibliography" },
|
|
|
|
{ TRUE, 'd', "macro", "subsections" },
|
|
|
|
{ TRUE, 'v', "variable", "subsubsections" },
|
2006-12-05 16:03:18 +00:00
|
|
|
{ TRUE, 'n', "namespace", "chapters"},
|
2006-01-23 13:41:08 +00:00
|
|
|
{ TRUE, 's', "struct", "labels and bibliography" }
|
2005-11-22 12:26:26 +00:00
|
|
|
};
|
|
|
|
|
2006-01-11 18:50:44 +00:00
|
|
|
#define TEX_BRACES (1<<0)
|
|
|
|
#define TEX_BSLASH (1<<1)
|
|
|
|
#define TEX_LABEL (1<<2)
|
|
|
|
|
2005-11-22 12:26:26 +00:00
|
|
|
/*
|
|
|
|
* FUNCTION DEFINITIONS
|
|
|
|
*/
|
|
|
|
|
2007-01-24 19:52:12 +00:00
|
|
|
static int getWord(const char * ref, const char **ptr)
|
2005-11-22 12:26:26 +00:00
|
|
|
{
|
2007-01-24 19:52:12 +00:00
|
|
|
const char *p = *ptr;
|
2006-01-11 18:50:44 +00:00
|
|
|
|
2007-01-24 19:52:12 +00:00
|
|
|
while ((*ref != '\0') && (*p != '\0') && (*ref == *p))
|
|
|
|
ref++, p++;
|
2006-01-11 18:50:44 +00:00
|
|
|
|
|
|
|
|
2007-01-24 19:52:12 +00:00
|
|
|
if (*ref)
|
|
|
|
return FALSE;
|
|
|
|
|
2008-02-27 13:17:29 +00:00
|
|
|
if (*p == '*') /* to allow something like \section*{foobar} */
|
2007-01-24 19:52:12 +00:00
|
|
|
p++;
|
|
|
|
|
|
|
|
*ptr = p;
|
|
|
|
return TRUE;
|
2005-11-22 12:26:26 +00:00
|
|
|
}
|
|
|
|
|
2006-01-23 13:41:08 +00:00
|
|
|
static void createTag(int flags, TeXKind kind, const char * l)
|
2006-01-11 18:50:44 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
vString *name = vStringNew ();
|
2006-01-11 18:50:44 +00:00
|
|
|
|
2006-01-23 13:41:08 +00:00
|
|
|
while ((*l == ' '))
|
2006-01-11 18:50:44 +00:00
|
|
|
l++;
|
2006-01-23 13:41:08 +00:00
|
|
|
if (flags & (TEX_BRACES | TEX_LABEL))
|
|
|
|
{
|
2006-01-11 18:50:44 +00:00
|
|
|
if ((*(l++)) != '{')
|
|
|
|
goto no_tag;
|
|
|
|
}
|
|
|
|
if (flags & TEX_BSLASH)
|
|
|
|
{
|
|
|
|
if ((*(l++)) != '\\')
|
|
|
|
goto no_tag;
|
|
|
|
}
|
|
|
|
if (flags & TEX_LABEL)
|
|
|
|
{
|
|
|
|
do
|
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
vStringPut(name, (int) *l);
|
2006-01-11 18:50:44 +00:00
|
|
|
++l;
|
|
|
|
} while ((*l != '\0') && (*l != '}'));
|
2006-01-23 13:41:08 +00:00
|
|
|
vStringTerminate(name);
|
2007-01-24 19:52:12 +00:00
|
|
|
if (name->buffer[0] != '}')
|
|
|
|
makeSimpleTag(name, TeXKinds, kind);
|
2006-01-11 18:50:44 +00:00
|
|
|
}
|
2006-01-23 13:41:08 +00:00
|
|
|
else if (isalpha((int) *l) || *l == '@')
|
2006-01-11 18:50:44 +00:00
|
|
|
{
|
|
|
|
do
|
|
|
|
{
|
|
|
|
vStringPut (name, (int) *l);
|
|
|
|
++l;
|
2006-01-23 13:41:08 +00:00
|
|
|
} while (isalpha((int) *l) || *l == '@');
|
|
|
|
vStringTerminate(name);
|
|
|
|
makeSimpleTag(name, TeXKinds, kind);
|
2006-01-11 18:50:44 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
vStringPut(name, (int) *l);
|
|
|
|
vStringTerminate(name);
|
|
|
|
makeSimpleTag(name, TeXKinds, kind);
|
2006-01-11 18:50:44 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
no_tag:
|
2006-01-23 13:41:08 +00:00
|
|
|
vStringDelete(name);
|
2006-01-11 18:50:44 +00:00
|
|
|
}
|
|
|
|
|
2006-01-23 13:41:08 +00:00
|
|
|
static void findTeXTags(void)
|
2005-11-22 12:26:26 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
const char *line;
|
2005-11-22 12:26:26 +00:00
|
|
|
|
2006-01-23 13:41:08 +00:00
|
|
|
while ((line = (const char*)fileReadLine()) != NULL)
|
2005-11-22 12:26:26 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
const char *cp = line;
|
2008-02-27 13:17:29 +00:00
|
|
|
/*int escaped = 0;*/
|
2006-01-11 18:50:44 +00:00
|
|
|
|
|
|
|
for (; *cp != '\0'; cp++)
|
|
|
|
{
|
|
|
|
if (*cp == '%')
|
2007-01-24 19:52:12 +00:00
|
|
|
break;
|
2006-01-11 18:50:44 +00:00
|
|
|
if (*cp == '\\')
|
|
|
|
{
|
|
|
|
cp++;
|
|
|
|
|
|
|
|
/* \newcommand{\command} */
|
2006-01-23 13:41:08 +00:00
|
|
|
if (getWord("newcommand", &cp)
|
|
|
|
|| getWord("providecommand", &cp)
|
|
|
|
|| getWord("renewcommand", &cp)
|
2006-01-11 18:50:44 +00:00
|
|
|
)
|
|
|
|
{
|
|
|
|
createTag (TEX_BRACES|TEX_BSLASH, K_COMMAND, cp);
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* \DeclareMathOperator{\command} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("DeclareMathOperator", &cp))
|
2006-01-11 18:50:44 +00:00
|
|
|
{
|
|
|
|
if (*cp == '*')
|
|
|
|
cp++;
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_BRACES|TEX_BSLASH, K_COMMAND, cp);
|
2006-01-11 18:50:44 +00:00
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* \def\command */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("def", &cp))
|
2006-01-11 18:50:44 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_BSLASH, K_COMMAND, cp);
|
2006-01-11 18:50:44 +00:00
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* \newenvironment{name} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if ( getWord("newenvironment", &cp)
|
2006-01-23 13:41:08 +00:00
|
|
|
|| getWord("newtheorem", &cp)
|
2006-10-30 23:00:26 +00:00
|
|
|
|| getWord("begin", &cp)
|
2006-01-11 18:50:44 +00:00
|
|
|
)
|
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_BRACES, K_ENVIRONMENT, cp);
|
2006-01-11 18:50:44 +00:00
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* \bibitem[label]{key} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("bibitem", &cp))
|
2006-01-11 18:50:44 +00:00
|
|
|
{
|
|
|
|
while (*cp == ' ')
|
|
|
|
cp++;
|
|
|
|
if (*(cp++) != '[')
|
|
|
|
break;
|
|
|
|
while ((*cp != '\0') && (*cp != ']'))
|
|
|
|
cp++;
|
|
|
|
if (*(cp++) != ']')
|
|
|
|
break;
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_LABEL, K_LABEL, cp);
|
2006-01-11 18:50:44 +00:00
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* \label{key} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("label", &cp))
|
2006-01-11 18:50:44 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_LABEL, K_LABEL, cp);
|
2006-01-11 18:50:44 +00:00
|
|
|
continue;
|
|
|
|
}
|
2006-01-16 17:47:11 +00:00
|
|
|
/* \section{key} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("section", &cp))
|
2006-01-23 13:41:08 +00:00
|
|
|
{
|
|
|
|
createTag(TEX_LABEL, K_SECTION, cp);
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
/* \subsection{key} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("subsection", &cp))
|
2006-01-16 17:47:11 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_LABEL, K_SUBSECTION, cp);
|
2006-01-16 17:47:11 +00:00
|
|
|
continue;
|
|
|
|
}
|
2006-01-23 13:41:08 +00:00
|
|
|
/* \subsubsection{key} */
|
2006-10-30 23:00:26 +00:00
|
|
|
else if (getWord("subsubsection", &cp))
|
2006-01-16 17:47:11 +00:00
|
|
|
{
|
2006-01-23 13:41:08 +00:00
|
|
|
createTag(TEX_LABEL, K_SUBSUBSECTION, cp);
|
2006-01-16 17:47:11 +00:00
|
|
|
continue;
|
|
|
|
}
|
2006-12-05 16:03:18 +00:00
|
|
|
/* \chapter{key} */
|
|
|
|
else if (getWord("chapter", &cp))
|
|
|
|
{
|
|
|
|
createTag(TEX_LABEL, K_CHAPTER, cp);
|
|
|
|
continue;
|
|
|
|
}
|
2006-01-11 18:50:44 +00:00
|
|
|
}
|
|
|
|
}
|
2005-11-22 12:26:26 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2006-05-16 19:04:04 +00:00
|
|
|
extern parserDefinition* LaTeXParser (void)
|
2005-11-22 12:26:26 +00:00
|
|
|
{
|
2006-04-27 22:52:09 +00:00
|
|
|
static const char *const extensions [] = { "tex", "sty", "idx", NULL };
|
|
|
|
parserDefinition * def = parserNew ("LaTeX");
|
2006-01-11 18:50:44 +00:00
|
|
|
def->kinds = TeXKinds;
|
|
|
|
def->kindCount = KIND_COUNT (TeXKinds);
|
|
|
|
def->extensions = extensions;
|
|
|
|
def->parser = findTeXTags;
|
|
|
|
return def;
|
2005-11-22 12:26:26 +00:00
|
|
|
}
|
|
|
|
|