Exit
  • Global community
    • Language:
      • Deutsch
      • English
      • Español
      • Français
      • Português
  • 日本語コミュニティ
  • 한국 커뮤니티
0

Memory leak in an Illustrator script

Guest
Sep 28, 2017 Sep 28, 2017

Hi there,

Open Illustrator, create a path with two points and run the jsx-script:

function test() {

  for(var i=0, x; i<20000; i++)

    x = app.activeDocument.pathItems[0].pathPoints[0].anchor[0];

}

test();

alert($.summary());

You will get "... PathPoint: 20000 ..." and lose 100Mb of memory just for reading of data. The memory will be freed when the jsx-script will be stopped.

When I try to call the function from HTML Extension the memory is never freed. PathPoint: 20000, 40000, 60000 and so on.

Do you have any suggestions how to solve the problem?

Thanks

3.4K
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines

correct answers 1 Correct answer

Guru , Sep 28, 2017 Sep 28, 2017

With Ai you need to use selections

Run through the CSTK (link on main page)

app.executeMenuCommand('deselectall');

(function() {

    function test() {

        var x, i, s, len;

        app.activeDocument.pathItems[0].selected = true;

        s = app.selection[0].pathPoints;

        len = s.length;

        for (i = 0; i < 20000; i++) {

            x = s[i % len].anchor[0];

        }

    }

    test();

})();

$.summary();

No leek 😉

I run extensions on 200,000+ objects and without using selections it takes about one

...
Translate
Valorous Hero ,
Sep 28, 2017 Sep 28, 2017

have you done this with var x; declared prior to your loop?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 28, 2017 Sep 28, 2017

I declared x in the loop - for(var i=0, x; but you can miss it at all like this

function test() {

  for(var i=0; i<20000; i++)

    app.activeDocument.pathItems[0].pathPoints[0].anchor[0];

}

that doesn't matter.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Valorous Hero ,
Sep 28, 2017 Sep 28, 2017

I see. This looks like a good question for the new CEP forum - maybe someone may know the answer over there. Would you like me to move your question to the new CEP forum?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 28, 2017 Sep 28, 2017

Sure, Thanks

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Sep 28, 2017 Sep 28, 2017

Does it make a difference if at the end of the loop you explicitly set i = null;?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 28, 2017 Sep 28, 2017

Are you seriously? I didn't try it but I'll be amazed if it'll help.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Sep 28, 2017 Sep 28, 2017

in my experience with scripting illustrator, sometimes the dumbest things are the right thing. though i don't really know how to test your specific situation (as i've never worked with html extensions).

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 28, 2017 Sep 28, 2017

If the variables bother you, you can try the code without them.

app.activeDocument.pathItems[0].pathPoints[0].anchor[0];

// allocated: pathPoint: 1 - 5kb just to get a data about x-coordinate of the point!

app.activeDocument.pathItems[0].pathPoints[0].anchor[0];

// allocated: pathPoint: 2 - 10kb

...

app.activeDocument.pathItems[0].pathPoints[0].anchor[0];

// allocated: pathPoint: 20000 - !00Mb

I don't see any reasons to allocate the memory for reading a property.

Maybe someone from Adobe staff knows an answer?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guru ,
Sep 28, 2017 Sep 28, 2017

Setting explicitly i = x = p = etc = null and then calling $.gc(); $.gc(); 2 times will sometimes give the garbage collector a hint to do it's job but in this case it won't.

Ai's engine is pretty buggy

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advisor ,
Sep 28, 2017 Sep 28, 2017

The HTML extension will create a separate jsx engine instance, and it will  stays in memory until quitting. So that answers the second part of your question.

However, the jsx should not give you those results from the beginning. My guess is that it's doing some caching of the reads behind the scenes. Try using $.gc() to force the garbage collector to run (maybe call it twice).

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 28, 2017 Sep 28, 2017

Vamitul  wrote

The HTML extension will create a separate jsx engine instance, and it will  stays in memory until quitting.

I read it before in SDK. But I think that's not always true. If it would be true memory should be freed after the jsx-script completed its work.

Vamitul  wrote

Try using $.gc() to force the garbage collector to run (maybe call it twice).

I tried $.gc() but that didn't not help.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guru ,
Sep 28, 2017 Sep 28, 2017

With Ai you need to use selections

Run through the CSTK (link on main page)

app.executeMenuCommand('deselectall');

(function() {

    function test() {

        var x, i, s, len;

        app.activeDocument.pathItems[0].selected = true;

        s = app.selection[0].pathPoints;

        len = s.length;

        for (i = 0; i < 20000; i++) {

            x = s[i % len].anchor[0];

        }

    }

    test();

})();

$.summary();

No leek 😉

I run extensions on 200,000+ objects and without using selections it takes about one hour to populate an array of data, with selection it takes about  3 minutes

You should make sure the app nap if off if using mac otherwise it can add another minute

HTH

Trevor

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 29, 2017 Sep 29, 2017

Thank you Trevor!

It's incredible but It seems "selection" works for simple paths. Maybe you know how to read coordinates of points from compound paths and groups?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guru ,
Sep 29, 2017 Sep 29, 2017

Yep, but I'm off now for the weekend, so mark my answer as correct and ask that on the Ai scripting forum or wait for someone else here.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 29, 2017 Sep 29, 2017

I mean, how to read coordinates of points from compound paths and groups via selections. How to do it in the normal way I know.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guest
Sep 29, 2017 Sep 29, 2017

I'll tell you more. If I change the code:

function test() {

  var p;

  p = app.activeDocument.pathItems[0].pathPoints;

  for(var i=0, x; i<20000; i++)

    x = p[0].anchor[0];

}

test();

alert($.summary());

nothing happens. But if I add two strings:

function test() {

  var p;

  app.activeDocument.pathItems[0].selected = true; 

  p = app.selection[0].pathPoints; 

  p = app.activeDocument.pathItems[0].pathPoints;

  for(var i=0, x; i<20000; i++)

    x = p[0].anchor[0];

}

test();

alert($.summary());

the memory leak disappear. It looks pretty strange

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
New Here ,
Sep 11, 2018 Sep 11, 2018
LATEST

Hi Trevor,

Could you elaborate on how the 'selection' strategy actually works? I'm seeing massive memory-leaks in my scripts, and I don't really see how to replace parts using your approach.

Thanks.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines