-
Notifications
You must be signed in to change notification settings - Fork 13k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Basic 'Hello World' Port/Channel example causes abort/memory leak #1155
Comments
This is cute. By default log is turned off, and doesn't evaluate its arguments, so recv isn't even being called. Combine that with the fact that we don't clean up our queues when data gets left in them and the "Hello World" string gets leaked. I bet if you changed 'log' to 'log_err' it would work as expected. I think we should fix the example to be less error prone and properly clean up the port queues when they die. |
Partially for my own edification, I just spent a few minutes poking around in the rt/ folder trying to get a handle on this bug/how ports & channels are structured internally. When the string is sent from the channel, it's buffered by the channel until one if its ports calls recv? And if there are >1 ports bound to one channel, only one port will ever recv "Hello World", or is it broadcast to everyone? If my understanding is correct, this bug would get fixed by modifying the destructor in rt/rust_chan.cpp? |
also how do I enable log, for future reference? My understanding is that its somewhat of a language builtin? |
There's a section in the usage FAQ about enabling logging: https://github.com/graydon/rust/wiki/Usage-FAQ and there is some additional information in the language reference documentation. There is only ever one port associated with a given channel, but there may be any number of channels associated with a port. It looks like messages are queued in individual channels. The fix here is that the rust_chan destructor needs to run the drop glue of the channel's element type on every element in the queue. This presents some problems in that the channel doesn't currently know the type descriptor of the type it contains, and because channels can be sent across tasks, but type descriptors can't. Looks like a bit of a mess - probably we can just pull the drop glue function out of the type descriptor and store it with the channel instead of the entire type descriptor. But now that I think of it, we aren't going to be able to run the drop glue from C++ code once we have split stacks. Maybe instead of drop glue we should just walk the shape of the type, like the cycle collector. As a stopgop, we could just call kernel->free() on every element when we know that they are pointers. That would at least fix this problem with strings, vectors and unique boxes. It would not fix the problem with structural types that contain pointers though. |
Both this and #1038 require tydescs that can move between tasks |
Due to a bug in channel destructors this examples fails when logging is off Issue #1155
This turned out to be easier than expected because all the queuing actually happens on the port side, so it was just a matter of draining the queue (in rust code) when the port dies. |
Reopening. There are still two cases that aren't covered:
|
2 is fixed by 5b9f76e |
Update code of conduct and security policy
I tried to run the example code from the top of lib/comm.rs (here, for your convenience: http://pastebin.com/kwhhMK3Z)
Output of rustc --version:
rustc prerelease (06d14f3 2011-11-07 15:46:00 -0800)
host: i686-unknown-linux-gnu
OS: Ubuntu 11.10, amd64
Error Message:
rust: fatal, 'leaked memory in rust main loop (1 objects)' failed, ./src/rt/memory_region.cpp:131 1 objects
Aborted
FWIW, I tried taking out the argv, that was not the cause. Its my first time using rust, so its possible I did something wrong, but I figured I'd be cautious and open a bug.
The text was updated successfully, but these errors were encountered: