bs-platform
Version:
bucklescript compiler, ocaml standard libary by bucklescript and its required runtime support
302 lines (277 loc) • 9.8 kB
JavaScript
'use strict';
var Caml_builtin_exceptions = require("./caml_builtin_exceptions.js");
/***********************************************************************/
/* */
/* Objective Caml */
/* */
/* Xavier Leroy, projet Cristal, INRIA Rocquencourt */
/* */
/* Copyright 1996 Institut National de Recherche en Informatique et */
/* en Automatique. All rights reserved. This file is distributed */
/* under the terms of the GNU Library General Public License, with */
/* the special exception on linking described in file ../LICENSE. */
/* */
/***********************************************************************/
/* $Id: lexing.c 6045 2004-01-01 16:42:43Z doligez $ */
/* The table-driven automaton for lexers generated by camllex. */
function caml_lex_array(s) {
var l = s.length / 2;
var a = new Array(l);
// when s.charCodeAt(2 * i + 1 ) > 128 (0x80)
// a[i] < 0
// for(var i = 0 ; i <= 0xffff; ++i) { if (i << 16 >> 16 !==i){console.log(i<<16>>16, 'vs',i)}}
//
for (var i = 0; i < l; i++)
a[i] = (s.charCodeAt(2 * i) | (s.charCodeAt(2 * i + 1) << 8)) << 16 >> 16;
return a;
}
;
function caml_lex_engine_aux (tbl,start_state,lexbuf,exn){
// Lexing.lexbuf
var lex_buffer = 1;
var lex_buffer_len = 2;
var lex_start_pos = 4;
var lex_curr_pos = 5;
var lex_last_pos = 6;
var lex_last_action = 7;
var lex_eof_reached = 8;
// Lexing.lex_tables
var lex_base = 0;
var lex_backtrk = 1;
var lex_default = 2;
var lex_trans = 3;
var lex_check = 4;
if (!tbl.lex_default) {
tbl.lex_base = caml_lex_array(tbl[lex_base]);
tbl.lex_backtrk = caml_lex_array(tbl[lex_backtrk]);
tbl.lex_check = caml_lex_array(tbl[lex_check]);
tbl.lex_trans = caml_lex_array(tbl[lex_trans]);
tbl.lex_default = caml_lex_array(tbl[lex_default]);
}
var c;
var state = start_state;
//var buffer = bytes_of_string(lexbuf[lex_buffer]);
var buffer = lexbuf[lex_buffer];
if (state >= 0) {
/* First entry */
lexbuf[lex_last_pos] = lexbuf[lex_start_pos] = lexbuf[lex_curr_pos];
lexbuf[lex_last_action] = -1;
}
else {
/* Reentry after refill */
state = -state - 1;
}
for (;;) {
/* Lookup base address or action number for current state */
var base = tbl.lex_base[state];
if (base < 0)
return -base - 1;
/* See if it's a backtrack point */
var backtrk = tbl.lex_backtrk[state];
if (backtrk >= 0) {
lexbuf[lex_last_pos] = lexbuf[lex_curr_pos];
lexbuf[lex_last_action] = backtrk;
}
/* See if we need a refill */
if (lexbuf[lex_curr_pos] >= lexbuf[lex_buffer_len]) {
if (lexbuf[lex_eof_reached] === 0)
return -state - 1;
else
c = 256;
}
else {
/* Read next input char */
c = buffer[lexbuf[lex_curr_pos]];
lexbuf[lex_curr_pos]++;
}
/* Determine next state */
if (tbl.lex_check[base + c] === state) {
state = tbl.lex_trans[base + c];
}
else {
state = tbl.lex_default[state];
}
/* If no transition on this char, return to last backtrack point */
if (state < 0) {
lexbuf[lex_curr_pos] = lexbuf[lex_last_pos];
if (lexbuf[lex_last_action] == -1)
throw exn
else
return lexbuf[lex_last_action];
}
else {
/* Erase the EOF condition only if the EOF pseudo-character was
consumed by the automaton (i.e. there was no backtrack above)
*/
if (c == 256)
lexbuf[lex_eof_reached] = 0;
}
}
};
var empty_token_lit = "lexing: empty token";
function caml_lex_engine(tbls, i, buf) {
return caml_lex_engine_aux(tbls, i, buf, [
Caml_builtin_exceptions.failure,
empty_token_lit
]);
}
/***********************************************/
/* New lexer engine, with memory of positions */
/***********************************************/
/**
* s -> Lexing.lex_tables.lex_code
* mem -> Lexing.lexbuf.lex_mem (* int array *)
*/
function caml_lex_run_mem(s, i, mem, curr_pos) {
for (;;) {
var dst = s.charCodeAt(i);
i++;
if (dst == 0xff)
return;
var src = s.charCodeAt(i);
i++;
if (src == 0xff)
mem[dst] = curr_pos;
else
mem[dst] = mem[src];
}
}
/**
* s -> Lexing.lex_tables.lex_code
* mem -> Lexing.lexbuf.lex_mem (* int array *)
*/
function caml_lex_run_tag(s, i, mem) {
for (;;) {
var dst = s.charCodeAt(i);
i++;
if (dst == 0xff)
return;
var src = s.charCodeAt(i);
i++;
if (src == 0xff)
mem[dst] = -1;
else
mem[dst] = mem[src];
}
}
;
function caml_new_lex_engine_aux (tbl,start_state,lexbuf,exn){
// Lexing.lexbuf
var lex_buffer = 1;
var lex_buffer_len = 2;
var lex_start_pos = 4;
var lex_curr_pos = 5;
var lex_last_pos = 6;
var lex_last_action = 7;
var lex_eof_reached = 8;
var lex_mem = 9;
// Lexing.lex_tables
var lex_base = 0;
var lex_backtrk = 1;
var lex_default = 2;
var lex_trans = 3;
var lex_check = 4;
var lex_base_code = 5;
var lex_backtrk_code = 6;
var lex_default_code = 7;
var lex_trans_code = 8;
var lex_check_code = 9;
var lex_code = 10;
if (!tbl.lex_default) {
tbl.lex_base = caml_lex_array(tbl[lex_base]);
tbl.lex_backtrk = caml_lex_array(tbl[lex_backtrk]);
tbl.lex_check = caml_lex_array(tbl[lex_check]);
tbl.lex_trans = caml_lex_array(tbl[lex_trans]);
tbl.lex_default = caml_lex_array(tbl[lex_default]);
}
if (!tbl.lex_default_code) {
tbl.lex_base_code = caml_lex_array(tbl[lex_base_code]);
tbl.lex_backtrk_code = caml_lex_array(tbl[lex_backtrk_code]);
tbl.lex_check_code = caml_lex_array(tbl[lex_check_code]);
tbl.lex_trans_code = caml_lex_array(tbl[lex_trans_code]);
tbl.lex_default_code = caml_lex_array(tbl[lex_default_code]);
}
if (tbl.lex_code == null) {
//tbl.lex_code = caml_bytes_of_string(tbl[lex_code]);
tbl.lex_code = (tbl[lex_code]);
}
var c, state = start_state;
//var buffer = caml_bytes_of_string(lexbuf[lex_buffer]);
var buffer = lexbuf[lex_buffer];
if (state >= 0) {
/* First entry */
lexbuf[lex_last_pos] = lexbuf[lex_start_pos] = lexbuf[lex_curr_pos];
lexbuf[lex_last_action] = -1;
}
else {
/* Reentry after refill */
state = -state - 1;
}
for (;;) {
/* Lookup base address or action number for current state */
var base = tbl.lex_base[state];
if (base < 0) {
var pc_off = tbl.lex_base_code[state];
caml_lex_run_tag(tbl.lex_code, pc_off, lexbuf[lex_mem]);
return -base - 1;
}
/* See if it's a backtrack point */
var backtrk = tbl.lex_backtrk[state];
if (backtrk >= 0) {
var pc_off = tbl.lex_backtrk_code[state];
caml_lex_run_tag(tbl.lex_code, pc_off, lexbuf[lex_mem]);
lexbuf[lex_last_pos] = lexbuf[lex_curr_pos];
lexbuf[lex_last_action] = backtrk;
}
/* See if we need a refill */
if (lexbuf[lex_curr_pos] >= lexbuf[lex_buffer_len]) {
if (lexbuf[lex_eof_reached] == 0)
return -state - 1;
else
c = 256;
}
else {
/* Read next input char */
c = buffer[lexbuf[lex_curr_pos]];
lexbuf[lex_curr_pos]++;
}
/* Determine next state */
var pstate = state;
if (tbl.lex_check[base + c] == state)
state = tbl.lex_trans[base + c];
else
state = tbl.lex_default[state];
/* If no transition on this char, return to last backtrack point */
if (state < 0) {
lexbuf[lex_curr_pos] = lexbuf[lex_last_pos];
if (lexbuf[lex_last_action] == -1)
throw exn;
else
return lexbuf[lex_last_action];
}
else {
/* If some transition, get and perform memory moves */
var base_code = tbl.lex_base_code[pstate], pc_off;
if (tbl.lex_check_code[base_code + c] == pstate)
pc_off = tbl.lex_trans_code[base_code + c];
else
pc_off = tbl.lex_default_code[pstate];
if (pc_off > 0)
caml_lex_run_mem(tbl.lex_code, pc_off, lexbuf[lex_mem], lexbuf[lex_curr_pos]);
/* Erase the EOF condition only if the EOF pseudo-character was
consumed by the automaton (i.e. there was no backtrack above)
*/
if (c == 256)
lexbuf[lex_eof_reached] = 0;
}
}
};
function caml_new_lex_engine(tbl, i, buf) {
return caml_new_lex_engine_aux(tbl, i, buf, [
Caml_builtin_exceptions.failure,
empty_token_lit
]);
}
exports.caml_lex_engine = caml_lex_engine;
exports.caml_new_lex_engine = caml_new_lex_engine;
/* Not a pure module */