News for hackers. Stuff that matters.
Re:Modern C by skohan on Friday September 04, 2020 @09:53AM (#24374919)
I see them as filling fundamentally different (if occasionally overlapping) use-cases. Rust is a language for high-performance programs which require strong safety guarantees. C is a language to make the computer do what you tell it to.

So for instance, if what I need to do is just manipulate memory with the least overhead possible, C is a really good tool for the job where Rust adds unnecessary ceremony. For instance, if I'm just walking arena-allocated memory, the borrow checker does nothing for me.

Also I think C plays an important pedagogical role. When writing C you learn a lot about what a computer actually does, whereas with Rust you're working with an abstract system.

I think a lot of the reason C gets a bad rap is because it has been used historically in a lot of use-cases where a language with better safety guarantees would have been a better fit, but that alternative didn't exist until maybe quite recently.

Re:Modern C by masklinn on Friday September 04, 2020 @10:40AM (#24375306)
> Also I think C plays an important pedagogical role. When writing C you learn a lot about what a computer actually does, whereas with Rust you're working with an abstract system.

That has not been true in decades, if ever. C is very much defined in terms of an abstract machine, and the behaviour of C is not that of the underlying assembly, which itself is an abstraction over the µops which actually tell the hardware how to work.

Re:Modern C by flohofwoe on Friday September 04, 2020 @10:46AM (#24375365)
That's nitpicky though. If you put C and the resulting assembly code side by side on godbolt.org you can see which lines of C code translate to which lines of assembly code, and you can see how this changes when enabling the various optimization levels. Higher level languages which rely more on "zero cost abstractions" are much further removed from CPU and memory.

Sure if you dive down into memory-model and CPU-internal details like micro-ops and pipelining then this model quickly falls apart, but on the surface, the "C abstract machine" still maps pretty well to what's happening under the hood.

Re:Modern C by SubjectToChange on Saturday September 05, 2020 @12:13AM (#24381361)
Higher level languages which rely more on "zero cost abstractions" are much further removed from CPU and memory.

Higher level languages are much further removed from C's model of the CPU and memory. And despite that "distance" there is virtually no difference between C's and C++'s (and often Rust's) performance. And at the end of the day, it doesn't matter how low level your language is if it isn't getting you any performance uplift.

Sure if you dive down into memory-model and CPU-internal details like micro-ops and pipelining then this model quickly falls apart, but on the surface, the "C abstract machine" still maps pretty well to what's happening under the hood.

A core part of the "C abstract machine" is sequential execution. Instruction-level parallelism is par for the course in modern processors, many of which have hundreds of instructions executing at any given time. So C hasn't been reflective of typical desktop/server CPUs for the last 30 years at least.

Hardware vendors spend a lot of money to make C code execute quickly, but we're now seeing the absolute limits of that.

Re:Modern C by verall on Saturday September 05, 2020 @01:53PM (#24385464)
This is silly. ILP doesn't matter because the HW has kept the same basic ISA with the same memory guarantees since forever. A lot of stuff goes on under the hood to make C code execute quickly (also to make Java code execute quickly, etc). Hundreds of in-flight instructions does not matter when they all commit in order.
Re:Modern C by flohofwoe on Saturday September 05, 2020 @08:47AM (#24383144)
> And despite that "distance" there is virtually no difference between C's and C++'s (and often Rust's) performance.

I'm not seeing that in real-world projects though, and it's not only about performance. These are just two random examples from my own experience of where high-level language features get in the way (I guess the TL;DR is: yes, it's possible to write high-performance software in high-level languages, but it's often more effort, and may require to write unreadble and "non-idiomatic" code, because you need to "appease" the compiler much more than in a lower level language):

https://floooh.github.io/2018/05/01/cpp-to-c-size-reduction....

https://floooh.github.io/2016/01/14/metal-arc.html

Also let's not forget about build times.

Re:Modern C by richardwhiuk on Friday September 04, 2020 @01:06PM (#24376768)
You can do this with Rust on godbolt as well.
Re:Modern C by saagarjha on Friday September 04, 2020 @02:07PM (#24377413)
Generally with Rust you're going to get significantly more "junk" in the output.
Re:Modern C by SubjectToChange on Friday September 04, 2020 @10:31PM (#24380943)
Most of the noise in Rust's emitted assembly is just panic code. Without that Rust's assembly looks a lot like C++'s and more like C's.
Re:Modern C by nwmcsween on Saturday September 05, 2020 @02:29AM (#24381742)
Compile both with -o0 see which one is more readable
Re:Modern C by skohan on Friday September 04, 2020 @10:44AM (#24375348)
Yes I mean this will always be true unless you work with raw machine code. The point is the C abstraction is lower level: give me memory, write to memory etc. where with Rust you’re moreso interacting with the compiler in a declarative way
Re:Modern C by SubjectToChange on Friday September 04, 2020 @11:47PM (#24381266)
> For instance, if I'm just walking arena-allocated memory, the borrow checker does nothing for me.

The borrow checker is most useful when you are using it in a team or just using external Rust code. By forcing code to be explicit the borrow checker ensures that most, if not all, implicit restrictions are propagated through the codebase. Naturally this makes Rust far easier to compose than C.

> Also I think C plays an important pedagogical role. When writing C you learn a lot about what a computer actually does, whereas with Rust you're working with an abstract system.

C is to modern hardware like the Intel 8086 is to an Intel Xeon Platinum. The mere fact that ISO C runs on some many different types of architectures and platforms proves that C is far removed from any particular computer's mode of operation (which isn't a bad thing). Even programming in machine code wouldn't reflect a CPU's true mode of operation because of things like Macro-op Fusion, Register Renaming, TLBs, etc. Processors nowadays are probably the most dynamic and complex "programs" seen in the industry.

If C and Rust were graded on "similarity" to hardware, then C would be neighbours with Rust and hardware would be located ten timezones ahead.

> I think a lot of the reason C gets a bad rap is because it has been used historically in a lot of use-cases where a language with better safety guarantees would have been a better fit, but that alternative didn't exist until maybe quite recently.

Ada is only eight years younger than C, Pascal pre-dates C, etc. There were alternatives but people used what they knew and what their systems were written in. But to be fair, it is far easier to find new languages and tools today than it was pre-internet. However, the problem with C being used in inappropriate places hasn't gone away. People still push to write new applications and software in C despite the safety problems and developer ergonomics.