Messages in this thread | | | From | Miguel Ojeda <> | Date | Fri, 16 Apr 2021 20:57:07 +0200 | Subject | Re: [PATCH 04/13] Kbuild: Rust support |
| |
On Fri, Apr 16, 2021 at 8:10 PM Al Viro <viro@zeniv.linux.org.uk> wrote: > > How well would ? operator fit that pattern? _If_ it's just a syntax sugar > along the lines of "if argument matches Err(_), return Err(_)", the types > shouldn't be an issue, but that might need some fun with releasing resources, > etc. If it's something more elaborate... details, please.
Yes, it is just syntax sugar -- it doesn't introduce any power to the language.
It was introduced because it is a very common pattern when using the `Result` and `Option` enums. In fact, before it existed, it was just a simple macro that you could also implement yourself.
For instance, given `Foo` and `Bar` types that need RAII cleanup of some kind (let's say `kill_foo()` and `kill_bar()`):
fn foo() -> KernelResult<Foo> { if black_box() { return Err(EINVAL); }
// something that gets you a `Foo` let foo = ...;
Ok(foo) }
fn bar() -> KernelResult<Bar> { let p = foo()?;
// something that gets you a `Bar`, possibly using the `p` let bar = ...;
Ok(bar) }
This reduces to (full example at https://godbolt.org/z/hjTxd3oP1):
bar: push rbx mov ebx, 1 call qword ptr [rip + black_box@GOTPCREL] test al, al jne .LBB2_2 call qword ptr [rip + kill_foo@GOTPCREL] xor ebx, ebx .LBB2_2: mov eax, ebx mov edx, -1234 pop rbx ret
You can see `bar()` calls `black_box()`. If it failed, it returns the EINVAL. Otherwise, it cleans up the `foo` automatically and returns the successful `bar`.
Cheers, Miguel
| |