Skip to content

Commit

Permalink
Introduce "snapshot" opcode replacing inefficient function chaining a…
Browse files Browse the repository at this point in the history
…pproach
  • Loading branch information
asmblah committed Feb 25, 2024
1 parent 440186c commit 6a01707
Show file tree
Hide file tree
Showing 117 changed files with 3,059 additions and 988 deletions.
544 changes: 359 additions & 185 deletions src/transpilerSpec.js

Large diffs are not rendered by default.

28 changes: 14 additions & 14 deletions test/integration/transpiler/constructs/emptyTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,11 @@ describe('Transpiler empty(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getVariable = core.getVariable, isEmpty = core.isEmpty;' +
'return isEmpty()(getVariable("a_var"));' +
'});'
'}'
);
});

Expand All @@ -58,11 +58,11 @@ describe('Transpiler empty(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getElement = core.getElement, getVariable = core.getVariable, isEmpty = core.isEmpty;' +
'return isEmpty()(getElement(getVariable("myArray"), 21));' +
'});'
'}'
);
});

Expand All @@ -88,11 +88,11 @@ describe('Transpiler empty(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getInstanceProperty = core.getInstanceProperty, getVariable = core.getVariable, isEmpty = core.isEmpty;' +
'return isEmpty()(getInstanceProperty(getVariable("myObject"))("myProp"));' +
'});'
'return isEmpty()(getInstanceProperty(getVariable("myObject"), "myProp"));' +
'}'
);
});

Expand All @@ -117,11 +117,11 @@ describe('Transpiler empty(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getClassNameOrThrow = core.getClassNameOrThrow, getStaticProperty = core.getStaticProperty, isEmpty = core.isEmpty;' +
'return isEmpty()(getStaticProperty(getClassNameOrThrow())("myProp"));' +
'});'
'return isEmpty()(getStaticProperty(getClassNameOrThrow(), "myProp"));' +
'}'
);
});
});
6 changes: 3 additions & 3 deletions test/integration/transpiler/constructs/evalTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,11 @@ describe('Transpiler eval(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var eval = core.eval, getVariable = core.getVariable;' +
'return eval(getVariable("myCode"));' +
'});'
'}'
);
});
});
18 changes: 9 additions & 9 deletions test/integration/transpiler/constructs/exitTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,11 @@ describe('Transpiler exit(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var exit = core.exit;' +
'exit();' +
'});'
'}'
);
});

Expand All @@ -47,11 +47,11 @@ describe('Transpiler exit(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var createInteger = core.createInteger, exit = core.exit;' +
'exit(createInteger(21));' +
'});'
'}'
);
});

Expand All @@ -70,11 +70,11 @@ describe('Transpiler exit(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var createString = core.createString, exit = core.exit, print = core.print;' +
'(print(createString("My failure message")), exit());' +
'});'
'}'
);
});
});
6 changes: 3 additions & 3 deletions test/integration/transpiler/constructs/heredocTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -37,16 +37,16 @@ describe('Transpiler "heredoc" statement test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getVariable = core.getVariable, interpolate = core.interpolate;' +
'return interpolate([' +
'"Increase ", ' +
'getVariable("firstVar"), ' +
'" with ", ' +
'getVariable("secondVar")' +
']);' +
'});'
'}'
);
});
});
56 changes: 46 additions & 10 deletions test/integration/transpiler/constructs/issetTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,15 +28,15 @@ describe('Transpiler isset(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getVariable = core.getVariable, isSet = core.isSet;' +
'return isSet()([getVariable("a_var")]);' +
'});'
'}'
);
});

it('should correctly transpile a return statement with multiple expressions', function () {
it('should correctly transpile a return statement with multiple benign expressions', function () {
var ast = {
name: 'N_PROGRAM',
statements: [{
Expand All @@ -54,11 +54,47 @@ describe('Transpiler isset(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getVariable = core.getVariable, isSet = core.isSet;' +
'return isSet()([getVariable("a_var"), getVariable("another_var")]);' +
'});'
'}'
);
});

it('should correctly transpile a return statement with multiple expressions, one complex', function () {
var ast = {
name: 'N_PROGRAM',
statements: [{
name: 'N_RETURN_STATEMENT',
expression: {
name: 'N_ISSET',
variables: [{
name: 'N_VARIABLE',
variable: 'a_var'
}, {
name: 'N_VARIABLE_EXPRESSION',
expression: {
name: 'N_VARIABLE',
variable: 'another_var'
}
}]
}
}]
};

expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getVariable = core.getVariable, getVariableVariable = core.getVariableVariable, isSet = core.isSet, snapshot = core.snapshot;' +
'return isSet()([' +
// This operand must be snapshotted as it is followed by an expression that may modify it
// (based on simple heuristics).
'snapshot(getVariable("a_var")), ' +
// Final operand does not need to be snapshotted, as there are no subsequent complex operands
// that may affect its result prior to the actual call executing.
'getVariableVariable(getVariable("another_var"))' +
']);' +
'}'
);
});

Expand All @@ -84,11 +120,11 @@ describe('Transpiler isset(...) construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getElement = core.getElement, getVariable = core.getVariable, isSet = core.isSet;' +
'return isSet()([getElement(getVariable("myArray"), 21)]);' +
'});'
'}'
);
});
});
16 changes: 11 additions & 5 deletions test/integration/transpiler/constructs/listTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ describe('Transpiler list(...) construct test', function () {
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var createArray = core.createArray, createInteger = core.createInteger, createList = core.createList, getVariable = core.getVariable, setValue = core.setValue;' +
'setValue(createList(getVariable("myVar"))())(createArray(createInteger(21))());' +
'setValue(createList(getVariable("myVar")), createArray(createInteger(21)));' +
'}'
);
});
Expand Down Expand Up @@ -82,11 +82,17 @@ describe('Transpiler list(...) construct test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var createArray = core.createArray, createInteger = core.createInteger, createList = core.createList, createVoid = core.createVoid, getVariable = core.getVariable, setValue = core.setValue;' +
'setValue(createList(createVoid())(getVariable("myVar"))())(createArray(createInteger(4))(createInteger(21))());' +
'});'
'setValue(' +
'createList(' +
'createVoid(), ' +
'getVariable("myVar")' +
'), ' +
'createArray(createInteger(4), createInteger(21))' +
');' +
'}'
);
});
});
6 changes: 3 additions & 3 deletions test/integration/transpiler/constructs/nowdocTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,13 +25,13 @@ describe('Transpiler "nowdoc" statement test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var createString = core.createString;' +
'return createString(' +
'"my nowdoc with strings that $look like $interpolated variables"' +
');' +
'});'
'}'
);
});
});
28 changes: 14 additions & 14 deletions test/integration/transpiler/constructs/parentKeywordTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,11 @@ describe('Transpiler parent:: construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getStaticProperty = core.getStaticProperty, getSuperClassNameOrThrow = core.getSuperClassNameOrThrow;' +
'return getStaticProperty(getSuperClassNameOrThrow())("myProp");' +
'});'
'return getStaticProperty(getSuperClassNameOrThrow(), "myProp");' +
'}'
);
});

Expand All @@ -61,8 +61,8 @@ describe('Transpiler parent:: construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var defineClass = core.defineClass, getClassConstant = core.getClassConstant, getSuperClassName = core.getSuperClassName;' +
'defineClass("MyClass", {' +
'superClass: null, ' +
Expand All @@ -72,11 +72,11 @@ describe('Transpiler parent:: construct expression test', function () {
'methods: {}, ' +
'constants: {' +
'"MY_CONST": function (currentClass) { ' +
'return getClassConstant(getSuperClassName(currentClass))("PARENT_CONST"); ' +
'return getClassConstant(getSuperClassName(currentClass), "PARENT_CONST"); ' +
'}' +
'}' +
'});' +
'});'
'}'
);
});

Expand All @@ -101,13 +101,13 @@ describe('Transpiler parent:: construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var callStaticMethod = core.callStaticMethod, getSuperClassNameOrThrow = core.getSuperClassNameOrThrow;' +
'callStaticMethod(getSuperClassNameOrThrow())("myMethod")' +
'(true)' + // Forwarding.
'();' +
'});'
'callStaticMethod(getSuperClassNameOrThrow(), "myMethod", ' +
'true' + // Forwarding.
');' +
'}'
);
});
});
20 changes: 10 additions & 10 deletions test/integration/transpiler/constructs/selfKeywordTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,11 @@ describe('Transpiler self:: construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var getClassNameOrThrow = core.getClassNameOrThrow, getStaticProperty = core.getStaticProperty;' +
'return getStaticProperty(getClassNameOrThrow())("myProp");' +
'});'
'return getStaticProperty(getClassNameOrThrow(), "myProp");' +
'}'
);
});

Expand All @@ -60,13 +60,13 @@ describe('Transpiler self:: construct expression test', function () {
}]
};

expect(phpToJS.transpile(ast)).to.equal(
'require(\'phpruntime\').compile(function (core) {' +
expect(phpToJS.transpile(ast, {bare: true})).to.equal(
'function (core) {' +
'var callStaticMethod = core.callStaticMethod, getClassNameOrThrow = core.getClassNameOrThrow;' +
'callStaticMethod(getClassNameOrThrow())("myMethod")' +
'(true)' + // Forwarding.
'();' +
'});'
'callStaticMethod(getClassNameOrThrow(), "myMethod", ' +
'true' + // Forwarding.
');' +
'}'
);
});

Expand Down
Loading

0 comments on commit 6a01707

Please sign in to comment.