Skip to content

Commit adb7d59

Browse files
committed
Allow external variables in functions
1 parent e42760e commit adb7d59

File tree

2 files changed

+37
-8
lines changed

2 files changed

+37
-8
lines changed

lib/binary_parser.ts

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -583,8 +583,8 @@ export class Parser {
583583
return this;
584584
}
585585

586-
getCode() {
587-
const ctx = new Context();
586+
private getContext(importPath?: string) {
587+
const ctx = new Context(importPath);
588588

589589
ctx.pushCode(
590590
'var dataView = new DataView(buffer.buffer, buffer.byteOffset, buffer.length);'
@@ -602,7 +602,11 @@ export class Parser {
602602
ctx.pushCode('return vars;');
603603
}
604604

605-
return ctx.code;
605+
return ctx;
606+
}
607+
608+
getCode() {
609+
return this.getContext().code;
606610
}
607611

608612
private addRawCode(ctx: Context) {
@@ -651,10 +655,14 @@ export class Parser {
651655
}
652656

653657
compile() {
658+
const importPath = 'imports';
659+
const ctx = this.getContext(importPath);
654660
this.compiled = new Function(
661+
importPath,
655662
'TextDecoder',
656-
`return function (buffer, constructorFn) { ${this.getCode()} };`
663+
`return function (buffer, constructorFn) { ${ctx.code} };`
657664
)(
665+
ctx.imports,
658666
typeof TextDecoder === 'undefined'
659667
? require('util').TextDecoder
660668
: TextDecoder
@@ -811,7 +819,8 @@ export class Parser {
811819

812820
switch (typeof this.options.assert) {
813821
case 'function':
814-
ctx.pushCode(`if (!(${this.options.assert}).call(vars, ${varName})) {`);
822+
const func = ctx.addImport(this.options.assert);
823+
ctx.pushCode(`if (!${func}.call(vars, ${varName})) {`);
815824
break;
816825
case 'number':
817826
ctx.pushCode(`if (${this.options.assert} !== ${varName}) {`);
@@ -961,8 +970,9 @@ export class Parser {
961970
ctx.pushCode(`var ${cur} = 0;`);
962971
ctx.pushCode(`while (offset < buffer.length) {`);
963972
ctx.pushCode(`${cur} = dataView.getUint8(offset);`);
973+
const func = ctx.addImport(pred);
964974
ctx.pushCode(
965-
`if (${pred}.call(this, ${cur}, buffer.subarray(offset))) break;`
975+
`if (${func}.call(this, ${cur}, buffer.subarray(offset))) break;`
966976
);
967977
ctx.pushCode(`offset += 1;`);
968978
ctx.pushCode(`}`);
@@ -1046,8 +1056,9 @@ export class Parser {
10461056

10471057
if (typeof this.options.readUntil === 'function') {
10481058
const pred = this.options.readUntil;
1059+
const func = ctx.addImport(pred);
10491060
ctx.pushCode(
1050-
`while (!(${pred}).call(this, ${item}, buffer.subarray(offset)));`
1061+
`while (!${func}.call(this, ${item}, buffer.subarray(offset)));`
10511062
);
10521063
}
10531064
}
@@ -1131,7 +1142,8 @@ export class Parser {
11311142
formatter: Function
11321143
) {
11331144
if (typeof formatter === 'function') {
1134-
ctx.pushCode(`${varName} = (${formatter}).call(this, ${varName});`);
1145+
const func = ctx.addImport(formatter);
1146+
ctx.pushCode(`${varName} = ${func}.call(this, ${varName});`);
11351147
}
11361148
}
11371149

lib/context.ts

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,13 @@ export class Context {
66
bitFields: Parser[] = [];
77
tmpVariableCount = 0;
88
references: { [key: string]: { resolved: boolean; requested: boolean } } = {};
9+
importPath: string;
10+
imports: any[] = [];
11+
reverseImports = new Map<any, number>();
12+
13+
constructor(importPath?: string) {
14+
this.importPath = importPath;
15+
}
916

1017
generateVariable(name?: string) {
1118
const arr = [];
@@ -62,6 +69,16 @@ export class Context {
6269
this.scopes.pop();
6370
}
6471

72+
addImport(im: any) {
73+
if (!this.importPath) return `(${im})`;
74+
let id = this.reverseImports.get(im);
75+
if (!id) {
76+
id = this.imports.push(im) - 1;
77+
this.reverseImports.set(im, id);
78+
}
79+
return `${this.importPath}[${id}]`;
80+
}
81+
6582
addReference(alias: string) {
6683
if (this.references[alias]) return;
6784
this.references[alias] = { resolved: false, requested: false };

0 commit comments

Comments
 (0)