{"action":"created","issue":{"url":"https://api.github.com/repos/corda/corda/issues/989","repository_url":"https://api.github.com/repos/corda/corda","labels_url":"https://api.github.com/repos/corda/corda/issues/989/labels{/name}","comments_url":"https://api.github.com/repos/corda/corda/issues/989/comments","events_url":"https://api.github.com/repos/corda/corda/issues/989/events","html_url":"https://github.com/corda/corda/issues/989","id":240976395,"number":989,"title":"Quasar leaks dead stack frames","user":{"login":"exFalso","id":1042674,"avatar_url":"https://avatars3.githubusercontent.com/u/1042674?v=3","gravatar_id":"","url":"https://api.github.com/users/exFalso","html_url":"https://github.com/exFalso","followers_url":"https://api.github.com/users/exFalso/followers","following_url":"https://api.github.com/users/exFalso/following{/other_user}","gists_url":"https://api.github.com/users/exFalso/gists{/gist_id}","starred_url":"https://api.github.com/users/exFalso/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/exFalso/subscriptions","organizations_url":"https://api.github.com/users/exFalso/orgs","repos_url":"https://api.github.com/users/exFalso/repos","events_url":"https://api.github.com/users/exFalso/events{/privacy}","received_events_url":"https://api.github.com/users/exFalso/received_events","type":"User","site_admin":false},"labels":[{"id":456115737,"url":"https://api.github.com/repos/corda/corda/labels/bug","name":"bug","color":"ee0701","default":true}],"state":"open","locked":false,"assignee":null,"assignees":[],"milestone":null,"comments":1,"created_at":"2017-07-06T14:30:48Z","updated_at":"2017-07-07T08:17:14Z","closed_at":null,"body":"This bug is a bit elaborate and it would take some time to produce a small test case. The gist:\r\n\r\n* Quasar uses two growing arrays to represent the fiber stack, one for metadata and primitive values and one for Objects.\r\n* The arrays grow but never shrink. When a function returns all references in the corresponding dead frame *should* be nulled out in the Objects array.\r\n* However in certain scenarios the nulling out does not happen properly. The stack pointer is set fine though, so this doesn't corrupt the quasar runtime.\r\n* This means that we may end up in a scenario where the fiber holds references to objects in dead frames, which means that we may leak memory, but more importantly those frames will be serialised by Kryo during checkpointing (this is how the bug was found).\r\n\r\nThe precise circumstances under which the buggy nulling out happens are still unclear, but it seems to happen around tricky control flow including try blocks with multiple catches/throws inside the catches.\r\n\r\nWe should dedicate some time to produce a small test case and submit the issue upstream to PU. In the meantime we can write a custom serialiser for quasar stacks that follows through the frame metadata and only serialises live frames."},"comment":{"url":"https://api.github.com/repos/corda/corda/issues/comments/313618467","html_url":"https://github.com/corda/corda/issues/989#issuecomment-313618467","issue_url":"https://api.github.com/repos/corda/corda/issues/989","id":313618467,"user":{"login":"exFalso","id":1042674,"avatar_url":"https://avatars3.githubusercontent.com/u/1042674?v=3","gravatar_id":"","url":"https://api.github.com/users/exFalso","html_url":"https://github.com/exFalso","followers_url":"https://api.github.com/users/exFalso/followers","following_url":"https://api.github.com/users/exFalso/following{/other_user}","gists_url":"https://api.github.com/users/exFalso/gists{/gist_id}","starred_url":"https://api.github.com/users/exFalso/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/exFalso/subscriptions","organizations_url":"https://api.github.com/users/exFalso/orgs","repos_url":"https://api.github.com/users/exFalso/repos","events_url":"https://api.github.com/users/exFalso/events{/privacy}","received_events_url":"https://api.github.com/users/exFalso/received_events","type":"User","site_admin":false},"created_at":"2017-07-07T08:17:14Z","updated_at":"2017-07-07T08:17:14Z","body":"@mikehearn That's a better approach I think. I found another issue with the dead frames, a fresh callchain may create frames that overlap with the dead one. Each frame in quasar has a corresponding unused slot in the object array (at the same index the frame metadata is in the primitive array), which may thus be filled with a dead reference. This means we cannot simply do resizing, we have to follow through the frame metadata and clean up those slots as well.\r\n\r\nOne other thing that comes to mind: I'm actually not sure what happens to uninitialised variables. In the standard java runtime they are initialised to null, but quasar may rely on the assumption that fresh frames always contain nulls, so it may skip the explicit null assignment - this would mean that uninitialised objects may be \"initialised\" with ones from an overlapped dead frame! "}}
{"actor":{"display_login":"exFalso"}}