facebookarchive / prepack

A JavaScript bundle optimizer.
http://prepack.io
Other
14.22k stars 425 forks source link

Unhelpful fatal error with loop in pure mode #2396

Open NTillmann opened 6 years ago

NTillmann commented 6 years ago

Prepacking this...

(function () {
    function f(a) {
        while (a > 10) {
            a--;
        }
    }
    __optimize(f);
    global.f = f;
})();

produces the following. The output looks correct, but what's that FatalError about with no message???

In input file /tmp/test.js(3:20) FatalError PP0001:  (https://github.com/facebook/prepack/wiki/PP0001)
    at f (/tmp/test.js:3:20)
Prepack failed, reporting 1 fatal error.
(function () {
  var _$2 = this;

  var _1 = function (a) {
    var __leaked_0;

    var _4 = function () {
      for (; __leaked_0 > 10;) {
        __leaked_0--;
      }
    };

    __leaked_0 = a;

    var _$1 = _4();

    return void 0;
  };

  _$2.f = _1;
}).call(this);
rahilvora commented 6 years ago

Hey @NTillmann can i work on this issue ?

NTillmann commented 6 years ago

Sure! I don't actually know what's going on here, but it might be easy...

trueadm commented 6 years ago

I thought this was handled with realm.suppressDiagnostics = true;?

NTillmann commented 6 years ago

Maybe that's what should be happening, but isn't?

akidee commented 3 years ago

Same strange results here with v0.2.54:

Input:

class A {
  constructor(a) {
    this.a = a
  }
  add(b){ return this.a + b }
  mult(c, b) { 
    var sum = 0;
    for (var i = 0; i < this.a; i++)
      sum += b;
    return sum
  }
}
__optimize(A.prototype.mult)

Output of prepack --compatibility [ANY] prepacktest.js:

In input file prepacktest.js(8:25) FatalError PP0001:  (https://github.com/facebook/prepack/wiki/PP0001)
    at mult (prepacktest.js:8:25)
Prepack failed, reporting 1 fatal error.
(function () {
  var _$4 = this;

  var _1 = class {
    constructor(a) {
      this.a = a;
    }

    mult(c, b) {
      var __get_scope_binding_0 = function (__selector) {
        var __captured;

        switch (__selector) {
          case 0:
            __captured = [void 0];
            break;
        }

        __scope_0[__selector] = __captured;
        return __captured;
      };

      var __scope_0 = new Array(1);

      var __leaked_0, __leaked_1;

      var _9 = function () {
        var __captured__scope_1 = __scope_0[0] || __get_scope_binding_0(0);

        for (__captured__scope_1[0] = 0; __captured__scope_1[0] < this.a; __captured__scope_1[0]++) __leaked_1 += __leaked_0;
      };

      __leaked_0 = b;
      __leaked_1 = 0;

      var _$2 = _9.call(this);

      var _$3 = __leaked_1;
      return _$3;
    }

    add(b) {
      return this.a + b;
    }

  };

  _$4.A = _1;
}).call(this);

It looks like some parts of the generator code (managing scope) leaked into the output?

However, I have tested prepack with a regular source file of some hundred lines, and the output is promising despite some exaggerated variable declarations (see https://github.com/facebook/prepack/issues/2655).

PS: This is a great library, keep it going!

trueadm commented 3 years ago

@akidee Sorry to say, but Prepack isn't being maintained anymore by Facebook.

akidee commented 3 years ago

@trueadm

However, we'd like to resume work on Prepack again in a few months.

By whom else? You have some more information?

trueadm commented 3 years ago

@akidee Where was that quote from? AFAIK that is not the case.

akidee commented 3 years ago

@trueadm https://github.com/facebook/prepack#status

I see, last commit is two years ago, so this info is not credible any more. A reason to update it.

trueadm commented 3 years ago

@akidee Sorry for the confusion. I've updated the README and removed this part, as it is no longer the case.

akidee commented 3 years ago

@trueadm Thank you. I hope you will nevertheless find someone who takes over responsibility for this project. It's too promising to stay in an experimental state. It's exactly what I wanted to start for myself, but very soon I came to the conclusion that symbolic execution is no trivial task at all.