4 ms·
Ways C compilers break for objects larger than PTRDIFF_MAX bytes
- zamalek 10y agoResults from VC++ (VS2015 Update 2): - 32-bit, demo 1: -268435456 - 32-bit, demo 2: 0 - 64-bit, demo 3: warning C4034: sizeof returns 0 error C2036: 'arrayptr': unknown size
- jwilk 10y agoIf the site showed anything beyond red bouncing balls, I'd so happy. And no, I'm not going to enable JS in my browser.
- userbinator 10y agoI can see the article fine without JS, it's not dynamically generated and you can see the text there in the page if you view the source.
- marcoperaza 10y agoNo HackerNews thread is complete without someone complaining about JS on the website.
- derefr 10y agoI always figured this (or an equivalent problem with mmap(3)) was what was behind Erlang's DETS filesize limit.
- userbinator 10y agoStrange results are acceptable because the overflow in pointer subtractions is undefined behavior The first example, with -2130706432, is not strange at all and there doesn't appear to be any exploiting of UB, since that is just 0x81000000 interpreted as a signed number; it's the following examples that really show the oddness caused by the signedness of the type. That 64-bit example, however, is IMHO a bug --- I doubt the system he ran it on has anywhere near the 14 exabytes of RAM he asked for, so malloc() succeeding in that case is ridiculous.
- unwind 10y agoIn C, 0x81000000 is always a signed number, since that's a regular "int"-type literal (like "17"). Whether it's negative or not is of course implementation-dependent, on a 32-bit system with 32-bit "int" it will be since bit 31 is set. To make it unsigned you'd have to append an 'u'. I'm sure you know this, but people somehow sometimes seem to magically expect "certain" literals to be unsigned just because they're hex, and that's not how it works.' EDIT: It seems I forgot about the complexities pointed out by replies to this comment. Thanks. Now the only think I'm certain about is that I'm confused.
- userbinator 10y agobut people somehow sometimes seem to magically expect "certain" literals to be unsigned just because they're hex, and that's not how it works Indeed, and in the most general sense, the signed/unsigned is really nothing more than how those 32 bits are interpreted by whatever operates on them. C attaches a particular type to literals which is used by the built-in operators, but things like printf() to a certain extent will do their own interpretation, as this shows: printf("%d %u %x", 0x81000000, 0x81000000, 0x81000000); This is definitely a concept that seems quite unfamiliar to those used to higher-level languages.
- cremno 10y agoThat's not true. Hexadecimals integer constants without suffix may have a signed type but they also may have an unsigned one. For example, 0x81000000 usually has type unsigned int. http://port70.net/~nsz/c/c11/n1570.html#6.4.4.1p5 http://port70.net/~nsz/c/c11/n1570.html#6.4.4.1p5
- ryao 10y agoPassing %d to printf says to print an int. 0x81000000 is a negative number when processed as a 32-bit signed integer. The output is the two's complement interpretation of the value. To print an unsigned int, you should pass %u. This would be more obviously correct if %x were used to print the hexadecimal representation, which is 0x81000000.
- 10y ago