static void jsY_unescape(js_State *J) { if (jsY_accept(J, '\\')) { if (jsY_accept(J, 'u')) { int x = 0; if (!jsY_ishex(J->lexchar)) goto error; x |= jsY_tohex(J->lexchar) << 12; jsY_next(J); if (!jsY_ishex(J->lexchar)) goto error; x |= jsY_tohex(J->lexchar) << 8; jsY_next(J); if (!jsY_ishex(J->lexchar)) goto error; x |= jsY_tohex(J->lexchar) << 4; jsY_next(J); if (!jsY_ishex(J->lexchar)) goto error; x |= jsY_tohex(J->lexchar); J->lexchar = x; return; } error: jsY_error(J, "unexpected escape sequence"); } }
static double lexhex(js_State *J) { double n = 0; if (!jsY_ishex(J->lexchar)) jsY_error(J, "malformed hexadecimal number"); while (jsY_ishex(J->lexchar)) { n = n * 16 + jsY_tohex(J->lexchar); jsY_next(J); } return n; }
static void Decode(js_State *J, const char *str, const char *reserved) { js_Buffer *sb = NULL; int a, b; while (*str) { int c = (unsigned char) *str++; if (c != '%') js_putc(J, &sb, c); else { if (!str[0] || !str[1]) js_urierror(J, "truncated escape sequence"); a = *str++; b = *str++; if (!jsY_ishex(a) || !jsY_ishex(b)) js_urierror(J, "invalid escape sequence"); c = jsY_tohex(a) << 4 | jsY_tohex(b); if (!strchr(reserved, c)) js_putc(J, &sb, c); else { js_putc(J, &sb, '%'); js_putc(J, &sb, a); js_putc(J, &sb, b); } } } js_putc(J, &sb, 0); if (js_try(J)) { js_free(J, sb); js_throw(J); } js_pushstring(J, sb ? sb->s : ""); js_endtry(J); js_free(J, sb); }
static int lexescape(js_State *J) { int x = 0; /* already consumed '\' */ if (jsY_accept(J, '\n')) return 0; switch (J->lexchar) { case 'u': jsY_next(J); if (!jsY_ishex(J->lexchar)) return 1; else { x |= jsY_tohex(J->lexchar) << 12; jsY_next(J); } if (!jsY_ishex(J->lexchar)) return 1; else { x |= jsY_tohex(J->lexchar) << 8; jsY_next(J); } if (!jsY_ishex(J->lexchar)) return 1; else { x |= jsY_tohex(J->lexchar) << 4; jsY_next(J); } if (!jsY_ishex(J->lexchar)) return 1; else { x |= jsY_tohex(J->lexchar); jsY_next(J); } textpush(J, x); break; case 'x': jsY_next(J); if (!jsY_ishex(J->lexchar)) return 1; else { x |= jsY_tohex(J->lexchar) << 4; jsY_next(J); } if (!jsY_ishex(J->lexchar)) return 1; else { x |= jsY_tohex(J->lexchar); jsY_next(J); } textpush(J, x); break; case '0': textpush(J, 0); jsY_next(J); break; case '\\': textpush(J, '\\'); jsY_next(J); break; case '\'': textpush(J, '\''); jsY_next(J); break; case '"': textpush(J, '"'); jsY_next(J); break; case 'b': textpush(J, '\b'); jsY_next(J); break; case 'f': textpush(J, '\f'); jsY_next(J); break; case 'n': textpush(J, '\n'); jsY_next(J); break; case 'r': textpush(J, '\r'); jsY_next(J); break; case 't': textpush(J, '\t'); jsY_next(J); break; case 'v': textpush(J, '\v'); jsY_next(J); break; default: textpush(J, J->lexchar); jsY_next(J); break; } return 0; }