ref: f36eb04aeec2b5b81c55dadc8effac349b6369fc
parent: d81fc84632ff5d9bdbec8914c4255c2a247052cf
author: Tor Andersson <tor@ccxvii.net>
date: Sat Jan 11 13:05:33 EST 2014
Track newlines properly.
--- a/jslex.c
+++ b/jslex.c
@@ -90,37 +90,6 @@
return TK_IDENTIFIER;
}
-#define GET() (*(*sp)++)
-#define UNGET() ((*sp)--)
-#define PEEK() (**sp)
-#define NEXT() ((*sp)++)
-#define NEXTPEEK() (NEXT(), PEEK())
-#define LOOK(x) (PEEK() == x ? (NEXT(), 1) : 0)
-
-static void textinit(js_State *J)
-{
- if (!J->buf.text) {
- J->buf.cap = 4096;
- J->buf.text = malloc(J->buf.cap);
- }
- J->buf.len = 0;
-}
-
-static inline void textpush(js_State *J, int c)
-{
- if (J->buf.len >= J->buf.cap) {
- J->buf.cap = J->buf.cap * 2;
- J->buf.text = realloc(J->buf.text, J->buf.cap);
- }
- J->buf.text[J->buf.len++] = c;
-}
-
-static inline char *textend(js_State *J)
-{
- textpush(J, 0);
- return J->buf.text;
-}
-
static inline int iswhite(int c)
{
return c == 0x9 || c == 0xB || c == 0xC || c == 0x20 || c == 0xA0 || c == 0xFEFF;
@@ -162,8 +131,52 @@
return 0;
}
-static inline void lexlinecomment(const char **sp)
+#define PEEK() (**sp)
+#define NEXT() get(J, sp)
+#define GET() get(J, sp)
+#define UNGET() ((*sp)--)
+#define NEXTPEEK() (NEXT(), PEEK())
+#define LOOK(x) (PEEK() == x ? (NEXT(), 1) : 0)
+
+static inline int get(js_State *J, const char **sp)
{
+ int c = *(*sp)++;
+ /* consume CR LF as one unit */
+ if (c == '\r' && PEEK() == '\n')
+ (*sp)++;
+ if (isnewline(c)) {
+ J->line++;
+ J->newline = 1;
+ }
+ return c;
+}
+
+static void textinit(js_State *J)
+{
+ if (!J->buf.text) {
+ J->buf.cap = 4096;
+ J->buf.text = malloc(J->buf.cap);
+ }
+ J->buf.len = 0;
+}
+
+static inline void textpush(js_State *J, int c)
+{
+ if (J->buf.len >= J->buf.cap) {
+ J->buf.cap = J->buf.cap * 2;
+ J->buf.text = realloc(J->buf.text, J->buf.cap);
+ }
+ J->buf.text[J->buf.len++] = c;
+}
+
+static inline char *textend(js_State *J)
+{
+ textpush(J, 0);
+ return J->buf.text;
+}
+
+static inline void lexlinecomment(js_State *J, const char **sp)
+{
int c = PEEK();
while (c && !isnewline(c)) {
c = NEXTPEEK();
@@ -174,11 +187,6 @@
{
while (1) {
int c = GET();
- if (isnewline(c)) {
- if (c == '\r' && PEEK() == '\n')
- NEXT();
- J->line++;
- }
if (c == '*') {
while (c == '*')
c = GET();
@@ -190,7 +198,7 @@
}
}
-static inline double lexhex(const char **sp)
+static inline double lexhex(js_State *J, const char **sp)
{
double n = 0;
int c = PEEK();
@@ -201,7 +209,7 @@
return n;
}
-static inline double lexinteger(const char **sp)
+static inline double lexinteger(js_State *J, const char **sp)
{
double n = 0;
int c = PEEK();
@@ -212,7 +220,7 @@
return n;
}
-static inline double lexfraction(const char **sp)
+static inline double lexfraction(js_State *J, const char **sp)
{
double n = 0;
double d = 1;
@@ -225,15 +233,15 @@
return n / d;
}
-static inline double lexexponent(const char **sp)
+static inline double lexexponent(js_State *J, const char **sp)
{
if (LOOK('e') || LOOK('E')) {
if (LOOK('-'))
- return -lexinteger(sp);
+ return -lexinteger(J, sp);
else if (LOOK('+'))
- return lexinteger(sp);
+ return lexinteger(J, sp);
else
- return lexinteger(sp);
+ return lexinteger(J, sp);
}
return 0;
}
@@ -246,7 +254,7 @@
*sp += 2;
if (!ishex(PEEK()))
return jsP_error(J, "0x not followed by hexademical digit");
- J->number = lexhex(sp);
+ J->number = lexhex(J, sp);
return TK_NUMBER;
}
@@ -253,10 +261,10 @@
if ((*sp)[0] == '0' && isdec((*sp)[1]))
return jsP_error(J, "number with leading zero");
- n = lexinteger(sp);
+ n = lexinteger(J, sp);
if (LOOK('.'))
- n += lexfraction(sp);
- n *= pow(10, lexexponent(sp));
+ n += lexfraction(J, sp);
+ n *= pow(10, lexexponent(J, sp));
if (isidentifierstart(PEEK()))
return jsP_error(J, "number with letter suffix");
@@ -270,11 +278,8 @@
int c = GET();
int x = 0;
- if (isnewline(c)) {
- if (c == '\r' && PEEK() == '\n')
- NEXT();
+ if (isnewline(c))
return 0;
- }
switch (c) {
case 'u':
@@ -425,11 +430,6 @@
c = GET();
if (isnewline(c)) {
- /* consume CR LF as one unit */
- if (c == '\r' && PEEK() == '\n')
- NEXT();
- J->line++;
- J->newline = 1;
if (isnlthcontext(J->lasttoken))
return ';';
continue;
@@ -437,7 +437,7 @@
if (c == '/') {
if (LOOK('/')) {
- lexlinecomment(sp);
+ lexlinecomment(J, sp);
continue;
} else if (LOOK('*')) {
if (lexcomment(J, sp))
@@ -452,6 +452,7 @@
}
}
+ // TODO: \uXXXX escapes
if (isidentifierstart(c)) {
textinit(J);
textpush(J, c);
--- a/jsparse.c
+++ b/jsparse.c
@@ -814,7 +814,7 @@
{
va_list ap;
- fprintf(stderr, "syntax error: %s:%d: ", J->filename, J->line);
+ fprintf(stderr, "%s:%d: error: ", J->filename, J->line);
va_start(ap, fmt);
vfprintf(stderr, fmt, ap);
va_end(ap);