Live data from Hacker News

Four years with Rust

words.steveklabnik.com

101–110 of 199 posts

Re: Four years with Rust

#101
post #84

Earlier quoted context omitted.

> I wasn't sure how much garbage collection rust would do Rust doesn't do magical garbage collection. Rc does reference counting, which is a form of garbage collection, but you get to choose where it gets applied, so it's a linear cost with no magical GC pauses or whatever. Rc isn't unique to Rust, it exists in C++ too. RefCell makes mutation within an Rc safe. It panics if you misuse it. http://manishearth.github.io…

Reference counting is not a form of garbage collection. Both reference counting and garbage collection are types of automatic memory management.

This discussion crops up each time reference counting is brought up.

In academia reference counting generally falls under the umbrella of GC. In the industry "GC" usually means "tracing GC".

The terminology is irrelevant to the point I'm making. I did make a distinction between RC and the "regular magical kind" of GC.

Re: Four years with Rust

#102
post #97

Earlier quoted context omitted.

We tried making copy/move an optimization. The number of useless copies that ended up in the resulting code was absurd. You think compile times are bad now…

You mean there were lots of copies that made it to the back end, only to be converted to non-mutable references late in the compilation process?

How do you convert copies to non-mutable references? That involves proving things about aliasing. Even in Rust that is not that easy…

Re: Four years with Rust

#103
post #94

Earlier quoted context omitted.

No, but I'm pretty new to rust and haven't written enough code to know how often situations that call for unsafe code blocks come up. (My current project I'm using to learn Rust is to port a ray-tracer I wrote in Haskell. I wouldn't expect functional-style code to require a lot of unsafe blocks and I haven't needed any yet, but who knows?)

Cool, just wondering. In general, unsafe code should be encapsulated, to isolate its possible effects, and once you've got it isolated, it's easy to break that bit out in a library.

From poking around in Rust for ~1 year my common ones are uninitialized arrays for scratch buffers(> 1Kb) and FFI(obviously).

Like you said all the other cases are nicely wrapped into a library but I'm not quite sure how you'd abstract the first one above. It's small enough to do the unsafe block inline that it's not annoying but definitely shows up(esp when you hit APIs that are copy of C interfaces).

Re: Four years with Rust

#104

Earlier quoted context omitted.

Cool, just wondering. In general, unsafe code should be encapsulated, to isolate its possible effects, and once you've got it isolated, it's easy to break that bit out in a library.

From poking around in Rust for ~1 year my common ones are uninitialized arrays for scratch buffers(> 1Kb) and FFI(obviously). Like you said all the other cases are nicely wrapped into a library but I'm not quite sure how you'd abstract the first one above. It's small enough to do the unsafe block inline that it's not annoying but definitely shows up(esp when you hit APIs that are copy of C interfaces).

Depends on what you're doing; see https://crates.io/crates/init_with as one example. It's not the exact same thing, and yeah, I would argue that's one area where it's okay to not totally abstract it. Rules are meant to be broken. (I was thinking about removing bounds checks with get_unchecked as well).

Re: Four years with Rust

#105

Getting rid of the syntactic difference between moving and copying seems like a huge step backwards. Ditto with abandoning mailing lists for some wanky "already solved-as-a-service" web app.

> Getting rid of the syntactic difference between moving and copying seems like a huge step backwards. Did you ever use Rust back when you had to write "move"? I did. When you wrote stuff like: let (move x, move y) = (move z.a, (move z.b).append(move z.c)); It got old fast.

Admittedly there's still a syntactic difference between move and copy -- with Swift and C++'s definition of copy. Rust calls that Clone, though. :)

Re: Four years with Rust

#106

Earlier quoted context omitted.

From poking around in Rust for ~1 year my common ones are uninitialized arrays for scratch buffers(> 1Kb) and FFI(obviously). Like you said all the other cases are nicely wrapped into a library but I'm not quite sure how you'd abstract the first one above. It's small enough to do the unsafe block inline that it's not annoying but definitely shows up(esp when you hit APIs that are copy of C interfaces).

Depends on what you're doing; see https://crates.io/crates/init_with as one example. It's not the exact same thing, and yeah, I would argue that's one area where it's okay to not totally abstract it. Rules are meant to be broken. (I was thinking about removing bounds checks with get_unchecked as well).

That's a much more involved use case that I usually have. Looks like a solid abstraction though.

Like I said, not really an issue, just a common pattern that I see.

Re: Four years with Rust

#107

Earlier quoted context omitted.

Depends on what you're doing; see https://crates.io/crates/init_with as one example. It's not the exact same thing, and yeah, I would argue that's one area where it's okay to not totally abstract it. Rules are meant to be broken. (I was thinking about removing bounds checks with get_unchecked as well).

That's a much more involved use case that I usually have. Looks like a solid abstraction though. Like I said, not really an issue, just a common pattern that I see.

Absolutely, understood.

Ironically, this is also a good example of how unsafe is complicated; "hey make an array (not vector) of copies of this thing" has lots of edge cases!

Re: Four years with Rust

#108
post #94

Earlier quoted context omitted.

Is there something today that you're seeing that causes applications to use a lot of unsafe? In general, it should mostly be in library code, not application code.

No, but I'm pretty new to rust and haven't written enough code to know how often situations that call for unsafe code blocks come up. (My current project I'm using to learn Rust is to port a ray-tracer I wrote in Haskell. I wouldn't expect functional-style code to require a lot of unsafe blocks and I haven't needed any yet, but who knows?)

I listed two things Rust doesn't handle well without unsafe code, doubly linked lists and multidimensional arrays. Here are examples of both from popular repositories with high download numbers:

- https://github.com/andelf/rust-adivon/blob/master/src/deque....

- https://github.com/andelf/rust-adivon/blob/master/src/queue....

These are all the doubly-linked list problem:

    struct Node {
        item: T,
        next: Option>>,
        prev: Rawlink>

    }
Since this is templated code, it might be possible to break it by instantiating it on a type with unusual semantics.

- https://github.com/BurntSushi/aho-corasick/blob/master/src/f...

Looks like unsafe code for "performance reasons". But there are no comments near "unsafe", so it's hard to tell.

- https://github.com/SiegeLord/RustAlgebloat/blob/master/algeb...

Matrix math. "Unsafe" all over the place, and unsafeness is exported, allowing the caller to do unsafe things. This is an example of why I occasionally stress the need for multidimensional array support at the language level. If the compiler knew about multidimensional arrays, it could optimize the subscript checks for them, avoiding code such as this.

The unsafe version. The caller can store anywhere in memory.

    fn unsafe_set_idx(&self, $mat: &T, v: f64)
    {
        let $self_ = self;
	let (r, c) = $rc_expr;
	unsafe
	    { $mat.raw_set(r, c, v) }
    }
Safe, but inefficient version. The compiler can't hoist those checks out of loops.

    fn set_idx(&self, $mat: &T, v: f64)
    {    let $self_ = self;
	 let (r, c) = $rc_expr;
	 assert!(r 
This is the sort of thing that leads to exploits in code that reads things like JPEG files. Yet you can't do much better in Rust. That's why doing multidimensional arrays in macros and templates isn't good enough.

Re: Four years with Rust

#109
post #86

Earlier quoted context omitted.

Have you tried VSCode with the Rust(racer,rustfmt) + lldb integration? I've been pretty impressed with it so far. FWIW C# Rust integration is really straightforward. You can actually pass delegates as C fn pointers and then treat them as a closures in Rust. Much less painful that I initially thought.

It is not yet the same as Blend + Visual Studio (C#, F#, C++/CX, C++/CLI). Yes, I do use VSCode, but only for dabbling on Rust during plane/train travels. The language is not yet at a level it just fits on MS stack and is requested by our customers on their Requests For Proposals. Regarding C# Rust interoperability, it is very badly documented. I gave up on searching for it, and just used C# C++/CX Rust instead. Or I…

C# Rust is pretty straightforward. Just follow the C FFI side on Rust and C# has standard marshal mechanisms for calling C code.

extern/dllimport[1] Covers most of it. There's automatic conversion for CString/string and delegates as function pointers. If you need to go deeper than that there's the marshal namespace[2]. Going through C++/CX sounds really painful.

[1] - https://msdn.microsoft.com/en-us/library/e59b22c5.aspx

[2] - https://msdn.microsoft.com/en-us/library/system.runtime.inte...

Re: Four years with Rust

#110
post #86

Earlier quoted context omitted.

Have you tried VSCode with the Rust(racer,rustfmt) + lldb integration? I've been pretty impressed with it so far. FWIW C# Rust integration is really straightforward. You can actually pass delegates as C fn pointers and then treat them as a closures in Rust. Much less painful that I initially thought.

It is not yet the same as Blend + Visual Studio (C#, F#, C++/CX, C++/CLI). Yes, I do use VSCode, but only for dabbling on Rust during plane/train travels. The language is not yet at a level it just fits on MS stack and is requested by our customers on their Requests For Proposals. Regarding C# Rust interoperability, it is very badly documented. I gave up on searching for it, and just used C# C++/CX Rust instead. Or I…

Have you seen the FFI omnibus http://jakegoulding.com/rust-ffi-omnibus/ which includes C# examples?
Post reply on HN