Commit 8ee676ca 8ee676ca15768d386ec3596235968e40abee2ae1 by Sergey Poznyakoff

Start switching lexers to the new line tracker facility

* include/mailutils/locus.h (MU_LOCUS_POINT_INITIALIZER): New define
(MU_LOCUS_RANGE_INITIALIZER): New define
(mu_locus_point_set_file, mu_locus_point_init)
(mu_locus_point_deinit, mu_locus_point_copy)
(mu_locus_range_deinit): New protos
* libmailutils/locus/locus.c: New file.
* libmailutils/locus/Makefile.am: Add new file.
* libmailutils/locus/linetrack.c (mu_linetrack_at_bol): New function.
(mu_linetrack_locus): New function.
(mu_linetrack_advance): Use mu_locus_point_set_file to set the mu_file
field.
* libmailutils/tests/linetrack.c: Initialize and deinitialize locus
range.
* mimeview/mimetypes.l: switch to line tracker
* mimeview/mimeview.h: Use defines from yyloc.h
1 parent 1ba98c36
......@@ -11,12 +11,17 @@ struct mu_locus_point
unsigned mu_col;
};
#define MU_LOCUS_POINT_INITIALIZER { NULL, 0, 0 }
struct mu_locus_range
{
struct mu_locus_point beg;
struct mu_locus_point end;
};
#define MU_LOCUS_RANGE_INITIALIZER \
{ MU_LOCUS_POINT_INITIALIZER, MU_LOCUS_POINT_INITIALIZER }
typedef struct mu_linetrack *mu_linetrack_t;
struct mu_linetrack_stat
......@@ -30,6 +35,14 @@ struct mu_linetrack_stat
int mu_ident_ref (char const *name, char const **refname);
int mu_ident_deref (char const *);
int mu_locus_point_set_file (struct mu_locus_point *pt, const char *filename);
int mu_locus_point_init (struct mu_locus_point *pt, const char *filename);
void mu_locus_point_deinit (struct mu_locus_point *pt);
int mu_locus_point_copy (struct mu_locus_point *dest,
struct mu_locus_point const *src);
void mu_locus_range_deinit (struct mu_locus_range *lr);
static inline int
mu_locus_point_same_file (struct mu_locus_point const *a,
struct mu_locus_point const *b)
......@@ -56,7 +69,10 @@ void mu_linetrack_advance (mu_linetrack_t trk,
struct mu_locus_range *loc,
char const *text, size_t leng);
int mu_linetrack_retreat (mu_linetrack_t trk, size_t n);
int mu_linetrack_locus (struct mu_linetrack *trk, struct mu_locus_point *lp);
int mu_linetrack_stat (mu_linetrack_t trk, struct mu_linetrack_stat *st);
int mu_linetrack_at_bol (struct mu_linetrack *trk);
void mu_stream_print_locus_range (mu_stream_t stream,
......
......@@ -20,7 +20,8 @@ noinst_LTLIBRARIES = liblocus.la
liblocus_la_SOURCES = \
ident.c\
debug.c\
linetrack.c
linetrack.c\
locus.c
AM_CPPFLAGS = @MU_LIB_COMMON_INCLUDES@ -I/libmailutils
......
......@@ -145,7 +145,13 @@ mu_linetrack_stat (struct mu_linetrack *trk, struct mu_linetrack_stat *st)
return 0;
}
int
mu_linetrack_at_bol (struct mu_linetrack *trk)
{
return *cols_tos_ptr (trk) == 0;
}
void
mu_linetrack_advance (struct mu_linetrack *trk,
struct mu_locus_range *loc,
......@@ -155,8 +161,9 @@ mu_linetrack_advance (struct mu_linetrack *trk,
if (text == NULL || leng == 0)
return;
loc->beg.mu_file = loc->end.mu_file = trk->file_name;
mu_locus_point_set_file (&loc->beg, trk->file_name);
mu_locus_point_set_file (&loc->end, trk->file_name);
loc->beg.mu_line = trk->hline + trk->tos;
ptr = cols_tos_ptr (trk);
loc->beg.mu_col = *ptr + 1;
......@@ -174,7 +181,7 @@ mu_linetrack_advance (struct mu_linetrack *trk,
}
else
{
/* Text ends with a newline. Keep the previos line number. */
/* Text ends with a newline. Keep the previous line number. */
loc->end.mu_line = trk->hline + trk->tos - 1;
loc->end.mu_col = cols_peek (trk, trk->tos - 1) - 1;
if (loc->end.mu_col + 1 == loc->beg.mu_col)
......@@ -186,6 +193,13 @@ mu_linetrack_advance (struct mu_linetrack *trk,
}
int
mu_linetrack_locus (struct mu_linetrack *trk, struct mu_locus_point *lp)
{
lp->mu_line = trk->hline + trk->tos;
return mu_locus_point_init (lp, trk->file_name);
}
int
mu_linetrack_retreat (struct mu_linetrack *trk, size_t n)
{
struct mu_linetrack_stat st;
......
#include <stdlib.h>
#include <errno.h>
#include <mailutils/types.h>
#include <mailutils/locus.h>
#include <mailutils/error.h>
int
mu_locus_point_set_file (struct mu_locus_point *pt, const char *filename)
{
int rc;
char const *ref;
rc = mu_ident_ref (filename, &ref);
if (rc)
return rc;
mu_ident_deref (pt->mu_file);
pt->mu_file = ref;
return 0;
}
int
mu_locus_point_init (struct mu_locus_point *pt, const char *filename)
{
pt->mu_line = 0;
pt->mu_col = 0;
return mu_locus_point_set_file (pt, filename);
}
void
mu_locus_point_deinit (struct mu_locus_point *pt)
{
mu_ident_deref (pt->mu_file);
memset (pt, 0, sizeof *pt);
}
int
mu_locus_point_copy (struct mu_locus_point *dest,
struct mu_locus_point const *src)
{
dest->mu_col = src->mu_col;
dest->mu_line = src->mu_line;
return mu_locus_point_init (dest, src->mu_file);
}
void
mu_locus_range_deinit (struct mu_locus_range *lr)
{
mu_locus_point_deinit (&lr->beg);
mu_locus_point_deinit (&lr->end);
}
......@@ -29,7 +29,7 @@ main (int argc, char **argv)
MU_ASSERT (mu_linetrack_create (&trk, argv[1], max_lines));
while ((rc = mu_stream_getline (mu_strin, &buf, &size, &n)) == 0 && n > 0)
{
struct mu_locus_range lr;
struct mu_locus_range lr = MU_LOCUS_RANGE_INITIALIZER;
char *tok;
n = mu_rtrim_class (buf, MU_CTYPE_SPACE);
......@@ -57,6 +57,7 @@ main (int argc, char **argv)
free (tok);
mu_stream_lprintf (mu_strout, &lr, "%s\n", buf);
}
mu_locus_range_deinit (&lr);
}
return 0;
}
......
......@@ -29,9 +29,9 @@
#include <mimetypes-decl.h>
#include <mailutils/io.h>
static struct mu_locus loc;
static int newline;
static mu_linetrack_t trk;
struct mu_locus_point string_beg;
static mu_opool_t pool;
static unsigned
......@@ -42,53 +42,18 @@ digit_to_number (char c)
c-'a'+10);
}
static struct mu_locus prev_loc;
static struct mu_locus string_beg;
static int prev_newline;
static void
advance_locus (void)
{
prev_loc = loc;
prev_newline = newline;
if (newline)
{
loc.mu_line++;
loc.mu_col = 1;
}
yylloc.beg = loc;
loc.mu_col += yyleng;
yylloc.end = loc;
yylloc.end.mu_col--;
#if 0
printf ("+%2d> %u:%u-%u:%u: %s\n",
yyleng,
yylloc.beg.mu_line, yylloc.beg.mu_col,
yylloc.end.mu_line, yylloc.end.mu_col, yytext);
#endif
newline = yytext[yyleng-1] == '\n';
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_SET_LOCUS, &loc);
}
static void
retreat_locus (void)
{
loc = prev_loc;
newline = prev_newline;
}
static void
finish_string (void)
{
mu_opool_append_char (pool, 0);
yylval.string.ptr = mu_opool_finish (pool, &yylval.string.len);
yylval.string.len--;
yylloc.end = yylloc.beg;
mu_locus_point_copy (&yylloc.end, &yylloc.beg);
yylloc.end.mu_col--;
yylloc.beg = string_beg;
mu_locus_point_copy (&yylloc.beg, &string_beg);
mu_locus_point_deinit (&string_beg);
if (mu_debug_level_p (MU_DEBCAT_APP, MU_DEBUG_TRACE5))
{
size_t i;
......@@ -106,7 +71,15 @@ finish_string (void)
#endif
}
#define YY_USER_ACTION advance_locus ();
#define YY_USER_ACTION \
do \
{ \
mu_linetrack_advance (trk, &yylloc, yytext, yyleng); \
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM, \
MU_IOCTL_LOGSTREAM_SET_LOCUS_RANGE, &yylloc); \
} \
while (0);
%}
%x RULE ARGS ASTRING
......@@ -178,8 +151,8 @@ WS [ \t][ \t]*
return EOL;
}
. {
string_beg = yylloc.beg;
retreat_locus ();
mu_locus_point_copy (&string_beg, &yylloc.beg);
mu_linetrack_retreat (trk, 1);
yyless (0);
BEGIN (ASTRING);
}
......@@ -217,8 +190,8 @@ WS [ \t][ \t]*
mu_opool_append (pool, yytext, yyleng);
}
. {
retreat_locus ();
. {
mu_linetrack_retreat (trk, 1);
yyless (0);
BEGIN (ARGS);
finish_string ();
......@@ -232,7 +205,8 @@ mimetypes_open (const char *name)
{
struct stat st;
int mode;
char *filename;
yy_flex_debug = mu_debug_level_p (MU_DEBCAT_MIME, MU_DEBUG_TRACE4);
if (stat (name, &st))
......@@ -242,28 +216,26 @@ mimetypes_open (const char *name)
}
if (S_ISDIR (st.st_mode))
loc.mu_file = mu_make_file_name (name, "mime.types");
filename = mu_make_file_name (name, "mime.types");
else
loc.mu_file = mu_strdup (name);
loc.mu_line = 1;
loc.mu_col = 1;
newline = 0;
yyin = fopen (loc.mu_file, "r");
filename = mu_strdup (name);
yyin = fopen (filename, "r");
if (!yyin)
{
mu_error (_("cannot open `%s': %s"), loc.mu_file, mu_strerror (errno));
free (loc.mu_file);
mu_error (_("cannot open `%s': %s"), filename, mu_strerror (errno));
free (filename);
return -1;
}
MU_ASSERT (mu_linetrack_create (&trk, filename, 3));
free (filename);
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_GET_MODE, &mode);
mode |= MU_LOGMODE_LOCUS;
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_SET_MODE, &mode);
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_SET_LOCUS, &loc);
mu_opool_create (&pool, MU_OPOOL_ENOMEMABRT);
return 0;
......@@ -275,16 +247,14 @@ mimetypes_close ()
int mode;
fclose (yyin);
/* FIXME: Don't free (loc.mu_file), because it is referenced by
mu_locus structures in the parse tree */
mu_linetrack_destroy (&trk);
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_GET_MODE, &mode);
mode &= ~MU_LOGMODE_LOCUS;
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_SET_MODE, &mode);
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_SET_LOCUS, NULL);
MU_IOCTL_LOGSTREAM_SET_LOCUS_RANGE, NULL);
}
int
......@@ -319,17 +289,8 @@ mimetypes_malloc (size_t size)
void
lex_next_rule (void)
{
int bol = 0;
int c;
if (newline)
{
loc.mu_col = 0;
loc.mu_line++;
newline = 0;
bol = 1;
}
if (yy_flex_debug)
{
YY_LOCATION_PRINT (stderr, yylloc);
......@@ -337,31 +298,27 @@ lex_next_rule (void)
}
while ((c = input ()) != EOF)
{
loc.mu_col++;
char ch = c;
mu_linetrack_advance (trk, &yylloc, &ch, 1);
if (c == '\n')
{
loc.mu_line++;
loc.mu_col = 0;
bol = 1;
continue;
}
else if (bol)
else if (mu_linetrack_at_bol (trk) && !(c == ' ' || c == '\t'))
{
bol = 0;
if (!(c == ' ' || c == '\t'))
{
unput (c);
break;
}
}
mu_linetrack_retreat (trk, 1);
unput (c);
break;
}
}
if (yy_flex_debug)
{
yylloc.beg = yylloc.end = loc;
YY_LOCATION_PRINT (stderr, yylloc);
struct mu_locus_range lr = MU_LOCUS_RANGE_INITIALIZER;
mu_linetrack_locus (trk, &lr.beg);
YY_LOCATION_PRINT (stderr, lr);
fprintf (stderr, ": finished error recovery\n");
mu_locus_point_deinit (&lr.beg);
}
BEGIN (RULE);
unput ('\n');
loc.mu_col = 0;
loc.mu_line--;
}
}
......
......@@ -22,6 +22,8 @@
# include <strings.h>
#endif
#include <mailutils/mailutils.h>
#include <mailutils/locus.h>
#include <mailutils/yyloc.h>
#include <fnmatch.h>
struct mimetypes_string
......@@ -48,29 +50,3 @@ const char *get_file_type (void);
extern char const *mimeview_file;
extern mu_stream_t mimeview_stream;
struct mu_locus_range
{
struct mu_locus beg;
struct mu_locus end;
};
#define YYLTYPE struct mu_locus_range
#define YYLLOC_DEFAULT(Current, Rhs, N) \
do \
{ \
if (N) \
{ \
(Current).beg = YYRHSLOC(Rhs, 1).beg; \
(Current).end = YYRHSLOC(Rhs, N).end; \
} \
else \
{ \
(Current).beg = YYRHSLOC(Rhs, 0).end; \
(Current).end = (Current).beg; \
} \
} while (0)
#define YY_LOCATION_PRINT(File, Loc) \
fprintf(File, "%s:%u.%u-%u.%u", \
(Loc).beg.mu_file, \
(Loc).beg.mu_line, (Loc).beg.mu_col, \
(Loc).end.mu_line, (Loc).end.mu_col)
......