summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorsanine <sanine.not@pm.me>2023-01-18 13:03:34 -0600
committersanine <sanine.not@pm.me>2023-01-18 13:03:34 -0600
commit82f47550fe3327cce6f2e0e1bf62e81d9ebcf90c (patch)
tree18c15c14a3f1623a4343d36a2f518ee6f51f204a
parent8d5389d66ef79b58a0fff32fa2b01b4206bfb311 (diff)
begin reentrant refactor
-rw-r--r--yy/in.xml126
-rw-r--r--yy/kalmia.h2
-rw-r--r--yy/kalmia.l92
-rw-r--r--yy/kalmia.y71
-rw-r--r--yy/main.c22
-rw-r--r--yy/makefile15
6 files changed, 250 insertions, 78 deletions
diff --git a/yy/in.xml b/yy/in.xml
new file mode 100644
index 0000000..ddd1543
--- /dev/null
+++ b/yy/in.xml
@@ -0,0 +1,126 @@
+<?xml version="1.0" encoding="utf-8"?>
+<COLLADA xmlns="http://www.collada.org/2008/03/COLLADASchema" version="1.5.0">
+ <asset>
+ <created>2005-11-14T02:16:38Z</created>
+ <modified>2005-11-15T11:36:38Z</modified>
+ <revision>1.0</revision>
+ </asset>
+ <library_effects>
+ <effect id="whitePhong">
+ <profile_COMMON>
+ <technique sid="phong1">
+ <phong>
+ <emission>
+ <color>1.0 1.0 1.0 1.0</color>
+ </emission>
+ <ambient>
+ <color>1.0 1.0 1.0 1.0</color>
+ </ambient>
+ <diffuse>
+ <color>1.0 1.0 1.0 1.0</color>
+ </diffuse>
+ <specular>
+ <color>1.0 1.0 1.0 1.0</color>
+ </specular>
+ <shininess>
+ <float>20.0</float>
+ </shininess>
+ <reflective>
+ <color>1.0 1.0 1.0 1.0</color>
+ </reflective>
+ <reflectivity>
+ <float>0.5</float>
+ </reflectivity>
+ <transparent>
+ <color>1.0 1.0 1.0 1.0</color>
+ </transparent>
+ <transparency>
+ <float>1.0</float>
+ </transparency>
+ </phong>
+ </technique>
+ </profile_COMMON>
+ </effect>
+ </library_effects>
+ <library_materials>
+ <material id="whiteMaterial">
+ <instance_effect url="#whitePhong"/>
+ </material>
+ </library_materials>
+ <library_geometries>
+ <geometry id="box" name="box">
+ <mesh>
+ <source id="box-Pos">
+ <float_array id="box-Pos-array" count="24">
+ -0.5 0.5 0.5
+ 0.5 0.5 0.5
+ -0.5 -0.5 0.5
+ 0.5 -0.5 0.5
+ -0.5 0.5 -0.5
+ 0.5 0.5 -0.5
+ -0.5 -0.5 -0.5
+ 0.5 -0.5 -0.5
+ </float_array>
+ <technique_common>
+ <accessor source="#box-Pos-array" count="8" stride="3">
+ <param name="X" type="float" />
+ <param name="Y" type="float" />
+ <param name="Z" type="float" />
+ </accessor>
+ </technique_common>
+ </source>
+ <source id="box-0-Normal">
+ <float_array id="box-0-Normal-array" count="18">
+ 1.0 0.0 0.0
+ -1.0 0.0 0.0
+ 0.0 1.0 0.0
+ 0.0 -1.0 0.0
+ 0.0 0.0 1.0
+ 0.0 0.0 -1.0
+ </float_array>
+ <technique_common>
+ <accessor source="#box-0-Normal-array" count="6" stride="3">
+ <param name="X" type="float"/>
+ <param name="Y" type="float"/>
+ <param name="Z" type="float"/>
+ </accessor>
+ </technique_common>
+ </source>
+ <vertices id="box-Vtx">
+ <input semantic="POSITION" source="#box-Pos"/>
+ </vertices>
+ <polygons count="6" material="WHITE">
+ <input semantic="VERTEX" source="#box-Vtx" offset="0"/>
+ <input semantic="NORMAL" source="#box-0-Normal" offset="1"/>
+ <p>0 4 2 4 3 4 1 4</p>
+ <p>0 2 1 2 5 2 4 2</p>
+ <p>6 3 7 3 3 3 2 3</p>
+ <p>0 1 4 1 6 1 2 1</p>
+ <p>3 0 7 0 5 0 1 0</p>
+ <p>5 5 7 5 6 5 4 5</p>
+ </polygons>
+ </mesh>
+ </geometry>
+ </library_geometries>
+ <library_visual_scenes>
+ <visual_scene id="DefaultScene">
+ <node id="Box" name="Box">
+ <translate> 0 0 0</translate>
+ <rotate> 0 0 1 0</rotate>
+ <rotate> 0 1 0 0</rotate>
+ <rotate> 1 0 0 0</rotate>
+ <scale> 1 1 1</scale>
+ <instance_geometry url="#box">
+ <bind_material>
+ <technique_common>
+ <instance_material symbol="WHITE" target="#whiteMaterial"/>
+ </technique_common>
+ </bind_material>
+ </instance_geometry>
+ </node>
+ </visual_scene>
+ </library_visual_scenes>
+ <scene>
+ <instance_visual_scene url="#DefaultScene"/>
+ </scene>
+</COLLADA>
diff --git a/yy/kalmia.h b/yy/kalmia.h
new file mode 100644
index 0000000..6259956
--- /dev/null
+++ b/yy/kalmia.h
@@ -0,0 +1,2 @@
+#include "kalmia.tab.h"
+#include "kalmia.lex.h"
diff --git a/yy/kalmia.l b/yy/kalmia.l
index 2472bdc..916f576 100644
--- a/yy/kalmia.l
+++ b/yy/kalmia.l
@@ -1,26 +1,39 @@
-%{
-#include <stdio.h>
-#include "y.tab.h"
-
-char *copy_str(char *);
-int line_num;
+%option noinput nounput noyywrap 8bit nodefault
+%option reentrant bison-bridge bison-locations
+%start STRING
+%{
+#include <string.h>
+#include "kalmia.tab.h"
+#define YY_USER_ACTION \
+ yylloc->first_line = yylloc->last_line; \
+ yylloc->first_column = yylloc->last_column; \
+ if (*yytext == '\n') { \
+ yylloc->last_line += 1; \
+ yylloc->last_column = 0; \
+ } \
+ else { \
+ yylloc->last_column += yyleng; \
+ }
%}
S \x20\x0a\x0d\x09
DATE [0-9]{4}\-[0-9]{2}\-[0-9]{2}T[0-9]{2}:[0-9]{2}:[0-9]{2}[A-Z]*
+ATTR ([\x20\x0a\x0d\x09]*)?"="
-
-%start STRING
-
%%
-<INITIAL>"<?xml".*"?>" { return PROLOG; }
-<INITIAL>[\x20\x0a\x0d\x09] { if (*yytext == '\n') { line_num += 1; } }
+<INITIAL>"<?xml".*"?>" {
+ /* xml prologue */
+ return PROLOG;
+}
+<INITIAL>[\x20\x0a\x0d\x09] {
+ /* ignore whitespace */
+}
<INITIAL>"<" { return S_TAG_OPEN; }
@@ -29,24 +42,49 @@ DATE [0-9]{4}\-[0-9]{2}\-[0-9]{2}T[0-9]{2}:[0-9]{2}:[0-9]{2}[A-Z]*
<INITIAL>"/>" { return EMPTY_TAG_CLOSE; }
-<INITIAL>[a-zA-Z_:][a-zA-Z0-9\.\-_:]* { yylval.sval = copy_str(yytext); return NAME; }
-
-<INITIAL>"=" { return *yytext; }
+<INITIAL>[a-zA-Z_:][a-zA-Z0-9\.\-_:]* {
+ /* generic tag name */
+ yylval->sval = strdup(yytext); return NAME;
+}
+<INITIAL>[a-zA-Z_:][a-zA-Z0-9\.\-_:]*/([\x20\x0a\x0d\x09])*"=" {
+ /* generic attribute key */
+ yylval->sval = strdup(yytext);
+ return ATTR;
+}
+<INITIAL>"=" {
+ /* attribute "=" */
+ return *yytext;
+}
-<INITIAL>"\"" { BEGIN(STRING); return *yytext; }
-<STRING>"\"" { BEGIN(INITIAL); return *yytext; }
-<STRING>[^"] { yylval.cval = *yytext; return CHAR; }
-<INITIAL>-?[0-9]+ { yylval.lval = strtol(yytext, NULL, 10); return INTEGER; }
-<INITIAL>-?[0-9]+\.?[0-9]* { yylval.dval = strtod(yytext, NULL); return DOUBLE; }
-<INITIAL>{DATE} { return DATE; }
+<INITIAL>"\"" {
+ /* begin a string */
+ BEGIN(STRING);
+ return *yytext;
+}
+<STRING>"\"" {
+ /* end a string */
+ BEGIN(INITIAL);
+ return *yytext;
+}
+<STRING>[^"]+ {
+ /* within a string */
+ yylval->sval = strdup(yytext);
+ return TEXT;
+}
-%%
-char * copy_str(char *str)
-{
- size_t len = strlen(str) + 1;
- char *copy = malloc(sizeof(char) * len);
- strncpy(copy, str, len);
- return copy;
+<INITIAL>-?[0-9]+ {
+ /* integers */
+ yylval->lval = strtol(yytext, NULL, 10);
+ return INTEGER;
+}
+<INITIAL>-?[0-9]+\.?[0-9]* {
+ /* doubles */
+ yylval->dval = strtod(yytext, NULL);
+ return DOUBLE;
+}
+<INITIAL>{DATE} {
+ /* dates */
+ return DATE;
}
diff --git a/yy/kalmia.y b/yy/kalmia.y
index 5d808e2..8afc101 100644
--- a/yy/kalmia.y
+++ b/yy/kalmia.y
@@ -1,12 +1,18 @@
-%{
-#include <stdio.h>
-int yyerror(const char *);
-int yylex();
-
-char attr_buf[1024];
-int attr_i;
-%}
+%define api.pure full
+%locations
+%define parse.error verbose
+%param { yyscan_t scanner }
+%code top {
+ #include <stdio.h>
+}
+%code requires {
+ typedef void* yyscan_t;
+}
+%code {
+ int yylex(YYSTYPE *yylvalp, YYLTYPE *yyllocp, yyscan_t scanner);
+ int yyerror(YYLTYPE *yyllocp, yyscan_t unused, const char *msg);
+}
%union {
long lval;
@@ -18,15 +24,13 @@ int attr_i;
%token PROLOG
%token S_TAG_OPEN E_TAG_OPEN TAG_CLOSE EMPTY_TAG_CLOSE
%token <sval> NAME
-%token <cval> CHAR
+%token <sval> ATTR
+%token <sval> TEXT
%token <lval> INTEGER
%token <dval> DOUBLE
%token DATE;
-%define parse.error verbose
-
-
%%
@@ -68,51 +72,28 @@ attributes:
;
attribute:
- NAME '=' '"' chars '"' { attr_buf[attr_i] = 0; printf("attribute: %s=%s\n", $1, attr_buf); attr_i = 0; }
- ;
-
-chars:
- | CHAR { attr_buf[attr_i] = $1; attr_i += 1; }
- | chars CHAR { attr_buf[attr_i] = $2; attr_i += 1; }
+ ATTR '=' '"' TEXT '"' { printf("attribute: %s=%s\n", $1, $4); }
;
integers:
- INTEGER
- | integers INTEGER
+ INTEGER { printf("%d\n", $1); }
+ | integers INTEGER { printf("%d\n", $2); }
;
doubles:
- DOUBLE
- | doubles DOUBLE
+ DOUBLE { printf("%f\n", $1); }
+ | doubles DOUBLE { printf("%f\n", $2); }
;
%%
-
-extern FILE *yyin;
-extern int line_num;
-
-int main()
-{
- attr_i = 0;
- line_num = 0;
- yyin = fopen("in.xml", "r");
- if (yyin == NULL) {
- fprintf(stderr, "could not open file!\n");
- return -1;
- }
- do {
- yyparse();
- } while (!feof(yyin));
-
- return 0;
-}
-
-
-int yyerror(const char *msg)
+int yyerror(YYLTYPE *yyllocp, yyscan_t unused, const char *msg);
{
- fprintf(stderr, "parse error on line %d: %s\n", line_num, msg);
+ fprintf(
+ stderr, "[%d:%d]: %s\n",
+ yyllocp->first_line, yyllocp->first_column, msg
+ );
return 1;
}
diff --git a/yy/main.c b/yy/main.c
new file mode 100644
index 0000000..d53a598
--- /dev/null
+++ b/yy/main.c
@@ -0,0 +1,22 @@
+#include <stdio.h>
+#include "kalmia.h"
+
+int main(int argc, char **argv)
+{
+ if (argc < 2) {
+ fprintf(stderr, "You must specify a file to parse!\n");
+ return -1;
+ }
+ FILE *in = fopen(argv[1], "r");
+ if (in == NULL) {
+ fprintf(stderr, "Could not open file \"%s\"\n", argv[1]);
+ return -1;
+ }
+
+ yyscan_t scanner;
+ yylex_init(&scanner);
+ yyset_in(in, scanner);
+ yyparse(scanner);
+ yylex_destroy(scanner);
+ return 0;
+}
diff --git a/yy/makefile b/yy/makefile
index cd482dc..5f33c4f 100644
--- a/yy/makefile
+++ b/yy/makefile
@@ -1,10 +1,13 @@
all: kalmia
-y.tab.c: kalmia.y
- yacc -d kalmia.y
+kalmia.tab.c: kalmia.y
+ bison -o "$@" --header=kalmia.tab.h kalmia.y
-lex.yy.c: kalmia.l
- lex kalmia.l
+kalmia.lex.c: kalmia.l
+ flex -o "$@" --header-file "kalmia.lex.h" kalmia.l
-kalmia: y.tab.c lex.yy.c
- gcc -o kalmia y.tab.c lex.yy.c -lfl
+kalmia: kalmia.tab.c kalmia.lex.c main.c kalmia.h
+ gcc -o kalmia main.c kalmia.tab.c kalmia.lex.c -lfl
+
+clean:
+ rm kalmia.lex.c kalmia.lex.h kalmia.tab.c kalmia.tab.h kalmia