Live data from Hacker News

Problems of C, and how Zig addresses them

avestura.dev

81–90 of 290 posts

Re: Problems of C, and how Zig addresses them

#81
post #71
post #33

Earlier quoted context omitted.

Could you specify the main ways it isn't? I have limited experience in both but I haven't seen much that suggests otherwise

Many features of C do not directly correspond with most modern assembly languages. You cannot predict the exact assembly it will generate without knowing a lot of details about your compiler and platform, and even then it's often iffy. It seems like a bit of a leap to call something "a minimal abstraction" if you can't even correctly describe how an operation in the abstraction corresponds to operations in the lower…

That's mainly the result of optimizer passes, C itself doesn't have much to do with it.

Assembly languages actually haven't changed all that much since the 70's, but compilers have improved a lot. The output of early C compilers did indeed match the source code quite closely (and not just on the PDP-11), but even today that's true if you disable optimizations (and even with optimizations is usually pretty straightforward to map the C source to the assembly listing - if you're somewhat aware what optimizer passes in modern compilers are doing).

Of course CPU ISAs are already human-friendly abstractions over what's actually happening down in the hardware.

Re: Problems of C, and how Zig addresses them

#82

Earlier quoted context omitted.

> The operations C gives you map 1-to-1 with assembly int test(int x, int y) { return x % y; } test: // @test sdiv w8, w0, w1 msub w0, w8, w1, w0 ret Surprisingly, assembly doesn't have the remainder instruction, but instead it has a multiply-then-subtract instruction which is not corresponding 1-to-1 to anything in C.

x86 doesn't have remainder. Other instruction sets do. But yeah I agree with your point. Some targets might not even have multiply.

x86 has remainder: IDIV calculates both the quotient and the remainder at the same time and places them in different registers just like many other ISAs before it did. In fact, DIV instruction of PDP-11 worked that way too:

    Description:    The 32-bit two's complement integer in R and Rv1 is divided
                    by the source operand. The quotient is left in R; the remain-
                    der in Rv1. Division will be performed so that the remainder
                    is of the same sign as the dividend. R must be even.

    Example:        CLR RO
                    MOV #20001,R1
                    DIV #2, RO

                       Before          After
                    (RO) = 000000   (RO) = 010000   Quotient
                    (R1) = 020001   (R1) = 000001   Remainder
PDP-11 also had ADC and SBC (add/subtract with carry) instructions which weren't (and still aren't) exposed in C either.

Re: Problems of C, and how Zig addresses them

#83
I'm super sold on Zig except that it doesn't make graphics/vector coding with operator overloading possible :( I've heard what Andrew Kelley has to say about it ("that ONE little feature from C++...") but it's just a very sad situation for what otherwise looks like a lovely basis for graphics coding.

Actually, I don't even want operator overloading in general (leading to stuff like the C++ stream API), it's JUST for vector stuff (ideally with swizzles); same for all the shading languages.

Perhaps it's doable to make a little domain-specific language (DSL) in Zig for this purpose?

With vector extensions (and as floh [hi!] points out, also matrices please) I'm 100% ready to seriously consider transitioning from C++, given the smooth C integration.

Re: Problems of C, and how Zig addresses them

#84
post #68

Earlier quoted context omitted.

Can't they add a new header file?

What if a library API needs to include this new header because it wants to use the new typedefs in its API declarations but your own code (which needs to include the library header) also has its own 'u8' typedefs? (PS: it's probably ok because C compilers seem to accept redundant typedefs)

It sounds like you got some refactoring to use since you didn't namespace your own core types?

Re: Problems of C, and how Zig addresses them

#85
post #60
post #29

Earlier quoted context omitted.

The problem I believe is being discussed is that dereferencing a pointer after the memory it references is freed does not throw a warning at compile time. This means the programmer has to manually keep track of pointers, making sure not to free the relevant memory until there are no more references to it lingering about. While there are programming techniques which to lesser or greater extent prevent problems from oc…

So, Zig set out to solve all but the biggest issue with C?

The biggest issue with C is arguably buffer overflows, not use-after-free (Zig offers spatial but not temporal runtime memory safety).

If you want both, but don't want a Rust-style borrow checker (with all the restrictions this entails), use 'tagged-index-handles', those work just fine across all languages (and even make sense in Rust):

https://floooh.github.io/2018/06/17/handles-vs-pointers.html

Re: Problems of C, and how Zig addresses them

#86

I'm super sold on Zig except that it doesn't make graphics/vector coding with operator overloading possible :( I've heard what Andrew Kelley has to say about it ("that ONE little feature from C++...") but it's just a very sad situation for what otherwise looks like a lovely basis for graphics coding. Actually, I don't even want operator overloading in general (leading to stuff like the C++ stream API), it's JUST for…

+1 (don't want general operator overloading, but a more powerful @Vector builtin type, basically Clang's ext_vector_type: https://clang.llvm.org/docs/LanguageExtensions.html#vectors-...), plus maybe a similar @Matrix builtin up to 4x4.

Re: Problems of C, and how Zig addresses them

#87

Earlier quoted context omitted.

What if a library API needs to include this new header because it wants to use the new typedefs in its API declarations but your own code (which needs to include the library header) also has its own 'u8' typedefs? (PS: it's probably ok because C compilers seem to accept redundant typedefs)

It sounds like you got some refactoring to use since you didn't namespace your own core types?

C doesn't have namespaces.

The only sane way to deal with name collisions is either to use C stdlib types in library APIs (e.g. uint8_t), or use a library specific prefix (e.g. mylib_u8) - which is of course even more awkward than just using the standard uint8_t.

Re: Problems of C, and how Zig addresses them

#88

Technically there is no "compile time" in C. Any part of the program can be computed at compile time or at runtime. Its entirely up the the implementation. The AS-IF rule in the C standard lets implementations do whatever they want as long as the program outputs the same things. The pre-processor, const expressions, constexpr (a for this reason compliably broken feature in my opinion), even text parsing and tokenizat…

C23 includes constexpr for some constructs, by the way.

I know, and its very broken.

Re: Problems of C, and how Zig addresses them

#89

Earlier quoted context omitted.

Zig and Python/Java are completely different beasts. One is a low-level systems language on the order of Rust or C. The other two are much higher level, easier to work with languages more attuned to desktop, mobile applications and enterprise work. I don't think anyone is seriously "jumping ship" from Zig to those.

Low-level programming isn't the holy grail. If a person gets fed up with limitations of C, they might as well move to a higher-level domain area as well. Especially, given the higher pay there. Those who haven't will have a much lower tolerance for changes. Survivor bias of a kind.

It's not really a choice of low-level or high-level. Neither is better than the other.

It's about choosing the right language for the task at hand. Some work will really be suited (or only be feasible) with a low-level language and vice-versa.

If I'm writing a command-line tool on the order of ripgrep or working on a microcontroller embedded in a dishwasher, I'm not going to go to Java. That would be weird and awkward. And if I'm writing a new 3D AAA-level game, I'm going to jump to something maybe even higher level like UE5 - trying to do all that in Rust would be a PITA.

Re: Problems of C, and how Zig addresses them

#90

Earlier quoted context omitted.

What if a library API needs to include this new header because it wants to use the new typedefs in its API declarations but your own code (which needs to include the library header) also has its own 'u8' typedefs? (PS: it's probably ok because C compilers seem to accept redundant typedefs)

It sounds like you got some refactoring to use since you didn't namespace your own core types?

I think that "namespacing" basic types such as u32 is completely unecessary.

In what world would an u32_MYLIB would be different than an u32_SOMELIB?

Basic types are common enough.

Post reply on HN