[rust-dev] Handling I/O errors

Greetings Rustaceans! Upon updating your nightly builds tonight some of you may realize that all I/O code will fail to compile. Fear not, this simply means that #11946 has landed! The summary of this change is the same as its title, "remove io::io_error". This is quite a far-reaching change, despite its simple summary. All I/O now returns a value of type `io::IoResult<T>` which is just a typedef to `Result<T, IoError>`. By returning a Result from all function calls, it's not much cleaner to handle errors (condition syntax is quite awkward), less overhead (registering a condition handler was expensive), and clearer what I/O should do now (should you raise? should you return a "0 value"?). Handling errors is always a tricky situation, so the compiler now provides you two tools to assist you in handling errors: 1. The new unused_must_use lint. This lint mode will tell you when you don't use an IoResult<T>. The purpose of this lint is to help you find out where in your program you're silently ignoring errors (often by accident). If you want even more warnings, you can turn on the unused_result lint which will warn about *all* unused results, not just those of type Result/IoResult. 2. The new if_ok!() macro. This macro has a fairly simple definition [0], and the idea is to return-early if an Err is encountered, and otherwise unwrap the Ok value. Some sample usage looks like: fn fun1() -> io::IoResult<int> { ... } fn fun2() -> io::IoResult<uint> { ... } fn fun3() -> io::IoResult<()> { ... } fn foo() -> io::IoResult<uint> { if_ok!(fun3()); let val = if_ok!(fun1()) as uint + if_ok!(fun2()); Ok(val) } These two tools are in place to help you handle errors unobtrusively as well as identify locations where you've forgotten to handle errors. Sorry about the awful rebasings you'll have to do in advance, but it's worth it! [0] - https://github.com/mozilla/rust/blob/master/src/libstd/macros.rs#L202-L204