Titanium JIRA Archive
Titanium SDK/CLI (TIMOB)

[TIMOB-2616] KrollObject create problems

GitHub Issuen/a
TypeBug
PriorityMedium
StatusClosed
ResolutionFixed
Resolution Date2011-05-16T11:05:39.000+0000
Affected Version/sn/a
Fix Version/sRelease 1.7.0, Sprint 2011-16
ComponentsiOS
Labelscritical, defect, enterprise, ios, klist, kroll, leak, memory, release-1.7.0, reported-1.5.1
ReporterStephen Tramer
AssigneeBlain Hamon
Created2011-04-15T03:24:51.000+0000
Updated2011-05-16T11:05:39.000+0000

Description

KrollObject appears to retain itself twice within its own constructor. This is an issue because quite often these objects are meant to be autoreleased - they never will be, unless this is resolved.

From #2299:

Bumping this down the road, with a note. It's two-pronged: Proxy retention issues (how we handle memory warnings is not smart right now, because it LEADS to memory warnings) and problems in Kroll involving certain objects which should be autoreleased (but never are, because they're retained at very bad points in their lifecycle). Unfortunately at this time there's no good way to handle clearing out stale client responses, simply because there's no good way to tell when they're "stale."
This bug should be a high priority target for a 1.5.1 release due to its critical nature.

Comments

  1. Stephen Tramer 2011-04-15

    Pushing to 1.7 Kroll work. No milestone yet so tagging.

  2. Don Thorp 2011-04-15

    removing release- tag as it's for committed code. Using tbs-1.7.0 to find items we know need to go in the next release.

  3. Blain Hamon 2011-04-15

    A bunch of issues fixed along these lines.

  4. Reggie Seagraves 2011-04-15

    There will be further changes to eliminate other memory leaks and we must insure that we do not regress on this issue.

  5. Fred Spencer 2011-04-15

    This does not appear to be resolved. Though static proxies (absent of listeners) appear to be releasing, proxies that do have listeners will not.

    Specific test cases can be provided once this issue is clarified.

  6. Rick Blalock 2011-04-15

    Experiencing the same thing with a project as well. Allocations continue to build over time until the app inevitably crashes. This is even true with windows in separate javascript contexts (i.e. if you're patient enough, going back and forth in a nav group in Kitchen Sink will merit the same results). Another symptom seems to be in a large tableview. If you scroll through 300-400 rows allocations will build up, then scroll back up, they will continue to build up, scroll back down, will continue to build up but never get released.

  7. Fred Spencer 2011-04-15

    Test for recent changes:

    ATTEMPT 1: Memory is released, but event listeners do not work consistently.

    ATTEMPT 2: Memory is released, but event listeners do not work consistently.

    ATTEMPT 3: Event listeners work, but memory is not released.

       
       var TestApp = (function() {
           var API = {
               App: {
                   run: null
               },
               SectionManager: null,
               UI: null
           };
           
           API.UI = {
               win: Ti.UI.createWindow(),
               button: Ti.UI.createButton({ left:10, top:10, right:10, height:30, title:'Reload Section' }),
               items: []
           };
           
           // used for @ATTEMPT 3
           API.Controllers = {
               addEventListener: function(params) {
                   params.obj.addEventListener(params.type, params.func);
               }
           };
           
           API.SectionManager = {
               view: null,
               generateSection: function(params) {
                   var sectionView = API.SectionManager.view = Ti.UI.createScrollView({ top:50, bottom:0, right:0, left:0, contentHeight:'auto', backgroundColor:'#ccc', layout:'horizontal', zIndex:0 });
                   var item = null;
                   
                   // EVENT HANDLER
                   function showAlert(e) {
                       alert('Tapped ' + e.source);
                   }
                   
                   API.UI.items = []; // clear this out
                   
                   for (var i = 0; i < 500; i++) {
                       item = Ti.UI.createImageView({ width:100, height:80, image:'image.png', left:10, right:10, top:10, bottom:10 });
                       API.UI.items.push(item); // used for @ATTEMPT 2
                       
                       // @ATTEPT 1 - ADDING EVENT LISTENER
                       // inconsistent
                       // item.addEventListener('click', showAlert);
                       
                       API.SectionManager.view.add(item);
                   }
                   
                   API.UI.win.add(API.SectionManager.view);
       
                   // @ATTEPT 2 - ADDING EVENT LISTENER
                   // inconsistent
                   // for (var o = 0, p = API.UI.items.length; o < p; o++) {
                   //  API.UI.items[o].addEventListener('click', showAlert);
                   // }
                   
                   // @ATTEPT 3 - ADDING EVENT LISTENER
                   // causes memory retain
                   for (var o = 0, p = API.UI.items.length; o < p; o++) {
                       API.Controllers.addEventListener({ obj:API.UI.items[o], type:'click', func:showAlert });
                   }
               },
               destroySection: function(params) {
                   API.UI.win.remove(API.SectionManager.view);
                   API.SectionManager.generateSection();
               }
           };
           
           API.App.run = function(params) {        
               API.UI.button.addEventListener('click', function(e) {
                   API.SectionManager.destroySection();
               });
       
               API.UI.win.add(API.UI.button);
               API.SectionManager.generateSection();
               API.UI.win.open();
           };
           
           return API;
       })();
       
       // run app
       TestApp.App.run();
       
  8. Rick Blalock 2011-04-15

    I'm noticing the same with a customer's app. Event listeners do not work in the ios_proxy_registration branch.

  9. Fred Spencer 2011-04-15

    This test is successful (based on attempt 2, above). Memory is being released and event listeners/handlers are working.

    Hoorah! :-)

    Adding event listeners using method attempt 1 remains inconsistent. Attempt 3 method retains. Awkward method, regardless.

    https://github.com/appcelerator/titanium_mobile/tree/ios_proxy_registration"> https://github.com/appcelerator/titanium_mobile/tree/ios_proxy_regi...
    commit: ee514a640ab1150f962f

    Performing additional tests on enterprise client projects.

       var TestApp = (function() {
           var API = {
               App: {
                   run: null
               },
               SectionManager: null,
               UI: null
           };
           
           API.UI = {
               win: Ti.UI.createWindow(),
               button: Ti.UI.createButton({ left:10, top:10, right:10, height:30, title:'Reload Section' }),
               items: [] // @SUCCESS - hold items
           };
               
           API.SectionManager = {
               view: null,
               generateSection: function(params) {
                   var sectionView = API.SectionManager.view = Ti.UI.createScrollView({ top:50, bottom:0, right:0, left:0, contentHeight:'auto', backgroundColor:'#ccc', layout:'horizontal', zIndex:0 });
                   var item = null;
                   
                   // EVENT HANDLER
                   function showAlert(e) {
                       alert('Tapped ' + e.source);
                   }
                   
                   API.UI.items = []; // @SUCCESS - empty the array on rebuild
                   
                   for (var i = 0; i < 500; i++) {
                       item = Ti.UI.createImageView({ width:100, height:80, image:'image.png', left:10, right:10, top:10, bottom:10 });
                       API.UI.items.push(item); // @SUCCESS - push item to array
                                       
                       API.SectionManager.view.add(item);
                   }
                   
                   API.UI.win.add(API.SectionManager.view);
       
                   // @SUCCESS - ADDING EVENT LISTENER - cycle through array
                   for (var o = 0, p = API.UI.items.length; o < p; o++) {
                       API.UI.items[o].addEventListener('click', showAlert);
                   }
               },
               destroySection: function(params) {
                   API.UI.win.remove(API.SectionManager.view);
                   API.SectionManager.generateSection();
               }
           };
           
           API.App.run = function(params) {        
               API.UI.button.addEventListener('click', function(e) {
                   API.SectionManager.destroySection();
               });
       
               API.UI.win.add(API.UI.button);
               API.SectionManager.generateSection();
               API.UI.win.open();
           };
           
           return API;
       })();
       
       // run app
       TestApp.App.run();
       
  10. Reggie Seagraves 2011-04-15

    Blain, we have reports that this is still having problems. Please fix and regress.

JSON Source