aboutsummaryrefslogtreecommitdiffstats
path: root/wiretap/candump_scanner.l
blob: b74f14cc17feac3131666b9558d9dc5a9e02d29a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
/* candump_scanner.l
 *
 * Wiretap Library
 * Copyright (c) 1998 by Gilbert Ramirez <gram@alumni.rice.edu>
 *
 * Support for candump log file format
 * Copyright (c) 2019 by Maksim Salau <maksim.salau@gmail.com>
 *
 * SPDX-License-Identifier: GPL-2.0-or-later
 */

%option reentrant
%option noyywrap
%option noinput
%option nounput
%option batch
%option never-interactive
%option prefix="candump_"
%option extra-type="candump_state_t *"
%option yylineno
%option nodefault

%option noyy_scan_buffer
%option noyy_scan_bytes
%option noyy_scan_string

/*
 * We have to override the memory allocators so that we don't get
 * "unused argument" warnings from the yyscanner argument (which
 * we don't use, as we have a global memory allocator).
 *
 * We provide, as macros, our own versions of the routines generated by Flex,
 * which just call malloc()/realloc()/free() (as the Flex versions do),
 * discarding the extra argument.
 */
%option noyyalloc
%option noyyrealloc
%option noyyfree

%{

#include <ws_diag_control.h>
#include <wiretap/file_wrappers.h>
#include "candump_parser.h"
#include "candump_priv.h"

#ifndef HAVE_UNISTD_H
#define YY_NO_UNISTD_H
#endif

static int candump_yyinput(void *buf, candump_state_t *state)
{
    int c = file_getc(state->fh);

    if (c == EOF)
    {
        state->err = file_error(state->fh, &state->err_info);
        return YY_NULL;
    }

    *(char *)buf = c;

    return 1;
}

#define YY_INPUT(buf, result, max_size) \
    do { (result) = candump_yyinput((buf), yyextra); } while (0)

/* Count bytes read. This is required in order to rewind the file
 * to the beginning of the next packet, since flex reads more bytes
 * before executing the action that does yyterminate(). */
#define YY_USER_ACTION do { yyextra->file_bytes_read += yyleng; } while (0);

/*
 * Sleazy hack to suppress compiler warnings in yy_fatal_error().
 */
#define YY_EXIT_FAILURE ((void)yyscanner, 2)

/*
 * Macros for the allocators, to discard the extra argument.
 */
#define candump_alloc(size, yyscanner)          (void *)malloc(size)
#define candump_realloc(ptr, size, yyscanner)   (void *)realloc((char *)(ptr), (size))
#define candump_free(ptr, yyscanner)            free((char *)(ptr))

DIAG_OFF_FLEX

%}

INT [0-9]
HEX [0-9A-Fa-f]

%%

[ \t]                   { return TOKEN_SPACE; };
[\r\n][ \t\r\n]*        { yyterminate(); }

\({INT}+\.{INT}+\)      {
                            yyextra->token.v0 = strtoul(yytext + 1, NULL, 10);
                            yyextra->token.v1 = strtoul(strchr(yytext, '.') + 1, NULL, 10);
                            return TOKEN_TIMESTAMP;
                        }

R{INT}                  {
                            yyextra->token.v0 = strtoul(yytext + 1, NULL, 10);
                            return TOKEN_RTR;
                        }

R                       {
                            yyextra->token.v0 = 0;
                            return TOKEN_RTR;
                        }

{HEX}{8}#               {
                            yyextra->token.v0 = strtoul(yytext, NULL, 16);
                            return TOKEN_EXT_ID;
                        }

{HEX}{3}#               {
                            yyextra->token.v0 = strtoul(yytext, NULL, 16);
                            return TOKEN_STD_ID;
                        }

{HEX}{HEX}              {
                            yyextra->token.v0 = strtoul(yytext, NULL, 16);
                            return TOKEN_BYTE;
                        }

#{HEX}                  {
                            yyextra->token.v0 = strtoul(yytext + 1, NULL, 16);
                            return TOKEN_FLAGS;
                        }

.                       { return TOKEN_UNKNOWN; }

%%

DIAG_ON_FLEX