{"action":"created","issue":{"url":"https://api.github.com/repos/rust-lang/rfcs/issues/837","labels_url":"https://api.github.com/repos/rust-lang/rfcs/issues/837/labels{/name}","comments_url":"https://api.github.com/repos/rust-lang/rfcs/issues/837/comments","events_url":"https://api.github.com/repos/rust-lang/rfcs/issues/837/events","html_url":"https://github.com/rust-lang/rfcs/pull/837","id":57663575,"number":837,"title":"RFC: Never allow reads from uninitialized memory in safe Rust","user":{"login":"aturon","id":709807,"avatar_url":"https://avatars.githubusercontent.com/u/709807?v=3","gravatar_id":"","url":"https://api.github.com/users/aturon","html_url":"https://github.com/aturon","followers_url":"https://api.github.com/users/aturon/followers","following_url":"https://api.github.com/users/aturon/following{/other_user}","gists_url":"https://api.github.com/users/aturon/gists{/gist_id}","starred_url":"https://api.github.com/users/aturon/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/aturon/subscriptions","organizations_url":"https://api.github.com/users/aturon/orgs","repos_url":"https://api.github.com/users/aturon/repos","events_url":"https://api.github.com/users/aturon/events{/privacy}","received_events_url":"https://api.github.com/users/aturon/received_events","type":"User","site_admin":false},"labels":[],"state":"closed","locked":false,"assignee":{"login":"aturon","id":709807,"avatar_url":"https://avatars.githubusercontent.com/u/709807?v=3","gravatar_id":"","url":"https://api.github.com/users/aturon","html_url":"https://github.com/aturon","followers_url":"https://api.github.com/users/aturon/followers","following_url":"https://api.github.com/users/aturon/following{/other_user}","gists_url":"https://api.github.com/users/aturon/gists{/gist_id}","starred_url":"https://api.github.com/users/aturon/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/aturon/subscriptions","organizations_url":"https://api.github.com/users/aturon/orgs","repos_url":"https://api.github.com/users/aturon/repos","events_url":"https://api.github.com/users/aturon/events{/privacy}","received_events_url":"https://api.github.com/users/aturon/received_events","type":"User","site_admin":false},"milestone":null,"comments":56,"created_at":"2015-02-13T22:37:27Z","updated_at":"2015-02-25T01:36:19Z","closed_at":"2015-02-24T23:00:28Z","pull_request":{"url":"https://api.github.com/repos/rust-lang/rfcs/pulls/837","html_url":"https://github.com/rust-lang/rfcs/pull/837","diff_url":"https://github.com/rust-lang/rfcs/pull/837.diff","patch_url":"https://github.com/rust-lang/rfcs/pull/837.patch"},"body":"Set an explicit policy that uninitialized memory can never be exposed\r\nin safe Rust, even when it would not lead to undefined behavior.\r\n\r\nSee https://github.com/rust-lang/rust/issues/20314.\r\n\r\n[Rendered](https://github.com/aturon/rfcs/blob/uninit-memory-policy/text/0000-uninit-memory-policy.md)"},"comment":{"url":"https://api.github.com/repos/rust-lang/rfcs/issues/comments/75888981","html_url":"https://github.com/rust-lang/rfcs/pull/837#issuecomment-75888981","issue_url":"https://api.github.com/repos/rust-lang/rfcs/issues/837","id":75888981,"user":{"login":"reem","id":4745181,"avatar_url":"https://avatars.githubusercontent.com/u/4745181?v=3","gravatar_id":"","url":"https://api.github.com/users/reem","html_url":"https://github.com/reem","followers_url":"https://api.github.com/users/reem/followers","following_url":"https://api.github.com/users/reem/following{/other_user}","gists_url":"https://api.github.com/users/reem/gists{/gist_id}","starred_url":"https://api.github.com/users/reem/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/reem/subscriptions","organizations_url":"https://api.github.com/users/reem/orgs","repos_url":"https://api.github.com/users/reem/repos","events_url":"https://api.github.com/users/reem/events{/privacy}","received_events_url":"https://api.github.com/users/reem/received_events","type":"User","site_admin":false},"created_at":"2015-02-25T01:36:19Z","updated_at":"2015-02-25T01:36:19Z","body":"I've thought about this issue a lot when designing traits for async io, and I think I've identified the fundamental issue.\r\n\r\nThe `io::Read` trait attempts to use an out-pointer for efficiency and to avoid double buffering - but this pattern is almost explicitly *not* supported in current Rust. The crux of the issue seems to be how you deal with incorrect implementations which read this out pointer instead of writing to it.\r\n\r\nThe flaw in this design is obvious if you try to generalize Reader and Writer to general types instead of just `u8`. It's obviously incorrect to pass an uninitialized `&mut [T]` to a function, but we sort of paper over this issue for the special case of `T = u8`, leading to this problem.\r\n\r\nI think this special casing is actually incorrect, and just like with the placement new issues, we actually need more advanced language features to properly deal with this, particularly some form of `&uninit` or `&out` pointer. Without it, I don't see how this pattern can be made safe and generalized without implying the same `O(n)` overhead as with double-buffering.\r\n\r\nAn alternative fix/workaround for this specific case is for read to take a `WriteOnly<[u8]>` or similar wrapper which emulates `&out`, which allows only writing to the underlying type, with reading only allowed through  an unsafe API or just forbidden outright."}}