4 ms·
> Do whatever your processor does with an 'add' instruction; but don't let anything weird travel backwards in time, or make additional assumptions about executi
by grandempire 2y ago
> Do whatever your processor does with an 'add' instruction; but don't let anything weird travel backwards in time, or make additional assumptions about execution paths not happening.'
That’s exactly what the standard means by undefined. Anything more you are reading into it is an absurd hypothetical. If you find such an implementation - let me know so I can avoid it. Clang and gcc do reasonable things - as you have pointed out there are helpful flags to configure it too.
- formerly_proven 2y agoYeah you definitely wanna review section 3 of the C standard again because it literally doesn't say that lol
- grandempire 2y agoPlease read the context. let me quote myself > A conforming implementation may chose to melt your computer - and you can choose to not use that implementation. But clang and gcc will never melt your Linux. And for the 3rd time, a real world case that might ruin your computer is an embedded device without memory protection.
- jenadine 2y agoYour conception of UB is flawed. This has nothing to do with memory protection. If a process has the ability to do something, then it may do so. It wouldn't be because GCC and clang choose to melt your computer, it is because your program has a bug, and the consequences of that bug can be anything, including jumping into random executable code that happens to ruin the computer.
- grandempire 2y agoWhat are you responding to here? > If a process has the ability to do something, then it may do so You agree with me. Once again, on an embedded device writing over a buffer may do absolutely anything. Thanks to memory protection, what a process can do is more limited. The C spec is written for both cases. No gcc and clang will not insert code to start rm’ing files when you overflow a signed integer.
- jenadine 2y ago> gcc and clang will not insert code to start rm’ing files when you overflow a signed integer. It could. If it detect that a code path cannot be taken without causing overflow, it will assume this code path cannot be taken and will optimise it by removing it. No need even to return from the function. If you reach this code anyway, it can run whatever functions is on the binary after it. If you're unlucky that's a function to remove temporary files which would be ran with bogus arguments.
- eru 2y agoIf you are unlucky, it's going to execute whatever user data a malicious attacker added by carefully crafted input. (Yes, these days that's harder, but you can still do a more complicated version of the same attacks. See return oriented programming.)
- eru 2y ago> Clang and gcc do reasonable things - as you have pointed out there are helpful flags to configure it too. Without these specific flags, they don't do 'reasonable things'. They happily assume that UB can't happen and use that information to declare certain code paths dead and optimise them away. The simplest example is something like this: signed char x = 20; while(x < x+1) { do_something(); x++; } GCC and Clang when told to optimise will happily assume that you have an infinite loop here. (Unless explicitly told otherwise via the compiler flags we mentioned.)
- grandempire 2y agoThat’s a completely reasonable thing to happen - no computer melting here. And as you said you can configure your desired behavior. Did you know you can accidentally write infinite loops in rust?
- dzaima 2y agoThe parent post has a mistake - it should use an "int" type instead of "signed char", otherwise the implicit promotion done by a+b breaks the desired showcase. That fixed, it wouldn't be an infinite loop if taking the "x+1" to do what the hardware would do, i.e. twos complement; "x < x+1" would become false for x==INT_MAX; and yet clang considers it UB, and thus the loop is UB once it hits the wraparound point, and that can result in unintentional computer melting: https://godbolt.org/z/833KzYY5G https://godbolt.org/z/833KzYY5G Of course you still generally need to have whatever harmful code you don't want ran here to still be present in the binary somewhere, and "melt_computer();" is a rather weird thing to have, but a "perform_heavy_work();" or "tolerate_high_temps_for_a_bit();" or "void debug_override_temperature_readings(){...}" are more realistic. (of course you might need special permissions to do those, but, uh, it's possible to get said permissions, especially if the point of the software is to operate those things.. and there are plenty of harmful things one can do without special perms) (edit: actually, even without that char↔int fix, the parent post still shows UB because infinite loops are UB in C (as long as the condition isn't a compile-time constant) (also the x++ is UB on reaching the char limit); copy-pasting it directly into harmless_loop still results in computer melting)