Skip to content

Commit

Permalink
fix for production output (generated parsers):
Browse files Browse the repository at this point in the history
- added the option `-T` (`--output-debug-tables`) which you can add to the jison command line options when you wish to *keep* the (otherwise unused) `nonterminals_` table, which lists the entire grammar verbatim.

- strip the `nonterminals_` table output from the output when the above option is not set; prep code to have the table produce more / additional debug/diagnostics data when the user **does** want the table to be included in the output.
  • Loading branch information
GerHobbelt committed Mar 22, 2016
1 parent 67e35ad commit 1ab3fef
Showing 1 changed file with 30 additions and 8 deletions.
38 changes: 30 additions & 8 deletions lib/jison.js
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ var Production = typal.construct({
this.precedence = 0;
},
toString: function Production_toString() {
return this.symbol + ' -> ' + this.handle.join(' ');
return this.symbol + (this.nullable ? '~' : '') + (this.precedence ? ' @' + this.precedence : '') + ' -> ' + this.handle.join(' ');
}
});

Expand Down Expand Up @@ -962,7 +962,7 @@ lookaheadMixin.firstSets = function firstSets() {
nonterminals = this.nonterminals,
self = this,
cont = true,
symbol,firsts;
symbol, firsts;

// loop until no further changes have been made
while (cont) {
Expand Down Expand Up @@ -1106,8 +1106,13 @@ lrGeneratorMixin.Item = typal.construct({
toString: function () {
var temp = this.production.handle.slice(0);
temp[this.dotPosition] = '.' + (temp[this.dotPosition] || '');
return this.production.symbol + ' -> ' + temp.join(' ') +
(this.follows.length === 0 ? '' : ' #lookaheads= ' + this.follows.join(' '));
var s = this.production.symbol + ' -> ' + temp.join(' ');
var padlen = Math.max(4, 40 - s.length);
var pad = new Array(padlen);
if (this.follows.length) {
s = s + pad.join(' ') + '#lookaheads= ' + this.follows.join(' ');
}
return s;
}
});

Expand Down Expand Up @@ -2147,7 +2152,11 @@ lrGeneratorMixin.generateModule_ = function generateModule_() {
return nt;
}

function produceProductionsForDebugging(tbl, sym) {
function produceProductionsForDebugging(tbl, sym, options) {
if (!options.outputDebugTables) {
return undefined;
}

var prods = {};
for (var nonterm in tbl) {
var entry = tbl[nonterm];
Expand All @@ -2156,9 +2165,9 @@ lrGeneratorMixin.generateModule_ = function generateModule_() {
var item_tbl = entry.productions._items;
for (var i = 0, len = item_tbl.length; i < len; i++) {
var p = item_tbl[i];
item_prods[p.id] = p.handle.map(function (t) {
var rulestr = p.handle.map(function (t) {
if (!t) {
t = '<epsilon>';
t = '%epsilon';
}
// `$eof` is a synonym of `$end` for bison compatibility;
// this is the only place where two symbol names may map to a single symbol ID number
Expand All @@ -2169,6 +2178,11 @@ lrGeneratorMixin.generateModule_ = function generateModule_() {
}
return t;
}).join(' ');
item_prods[p.id] = {
handle: rulestr,
first: [0],
follow: [0]
};
}
prods[nonterm] = item_prods;
}
Expand Down Expand Up @@ -2196,6 +2210,7 @@ lrGeneratorMixin.generateModule_ = function generateModule_() {
_: 1,
noMain: 1,
compressTables: 1,
outputDebugTables: 1,
file: 1,
outfile: 1,
inputPath: 1,
Expand Down Expand Up @@ -2237,6 +2252,10 @@ lrGeneratorMixin.generateModule_ = function generateModule_() {
if (descrLst) {
descrLst = descrLst.replace(/"([0-9]+)":/g, '$1:');
}
var rulesLst = JSON.stringify(produceProductionsForDebugging(this.nonterminals, this.symbols_, this.options), null, 2);
if (rulesLst) {
rulesLst = rulesLst.replace(/"([0-9]+)":/g, '$1:');
}

var moduleCode = '{\n';
moduleCode += [
Expand All @@ -2248,8 +2267,11 @@ lrGeneratorMixin.generateModule_ = function generateModule_() {
'options: ' + produceOptions(this.options),
'symbols_: ' + JSON.stringify(produceSymbolTable(this.symbols_), null, 2),
'terminals_: ' + JSON.stringify(this.terminals_, null, 2).replace(/"([0-9]+)":/g, '$1:'),
'nonterminals_: ' + JSON.stringify(produceProductionsForDebugging(this.nonterminals, this.symbols_), null, 2).replace(/"([0-9]+)":/g, '$1:'),
].concat(
rulesLst ?
'nonterminals_: ' + rulesLst :
[]
).concat(
descrLst ?
'terminal_descriptions_: ' + descrLst :
[]
Expand Down

0 comments on commit 1ab3fef

Please sign in to comment.