Live data from Hacker News

There is no 'printf'

netmeister.org

21–30 of 158 posts

Re: There is no 'printf'

#21

> puts(3) only returns "a nonnegative integer on success and EOF on error" How does it decide which nonnegative integer to return?

It's arbitrary. The article shows an implementation that returns 10 (ASCII '\n'). But the spec says it doesn't matter, so you should only be using it to test >0 for success.

Re: There is no 'printf'

#22

> puts(3) only returns "a nonnegative integer on success and EOF on error" How does it decide which nonnegative integer to return?

That's answered below:

> On success, puts(3) appears to return '\n', the newline or line feed (LF) character, which has ASCII value... 10.

But note that that isn't standard behavior. The language in POSIX[1] is identical to that in the blog post. `puts` is free to return whatever positive number it wants on return.

[1]: https://pubs.opengroup.org/onlinepubs/9699919799/functions/p...

Re: There is no 'printf'

#24

> puts(3) only returns "a nonnegative integer on success and EOF on error" How does it decide which nonnegative integer to return?

It's arbitrary. The article shows an implementation that returns 10 (ASCII '\n'). But the spec says it doesn't matter, so you should only be using it to test >0 for success.

The correct implementation is obviously to return 1 on success !

Re: There is no 'printf'

#25
Compiler optimization can sometimes cause unpredictable or even incorrect behavior. Below is a blob of C code for the TI MSP430 compiler that exemplifies at least one of TI's optimization bugs:

// Define Common Communications Frame

typedef volatile union commFrameType

{

  struct

  {

    unsigned SyncHeader:16;

    unsigned MessageID:8;

    unsigned short MessageData[msgDataSize];  // ID-unique data

    unsigned CRC:8;             // LSB of CCITT-16 for above data

  } __attribute__ ((packed)) Frame;

  unsigned char  b[16];         // Accessible as raw bytes as well

  unsigned short w[8];          // Accessible as raw words as well

  unsigned long  l[4];          // Accessible as raw long words as well
} __attribute__ ((packed)) CommFrame;

static CommFrame IpcMessage = { FRAME_SYNC_R, IpcBlankMessage };

    // If frame was accepted into TX queue, prepare next frame for transmission
// IpcMessage.Frame.MessageID++; // Bump up to next message type

// IpcMessage.Frame.MessageID += 1;

// The above two lines that are commented out cause a bizzare linker error if either are used instead of the line below.

    IpcMessage.Frame.MessageID = IpcMessage.Frame.MessageID + 1; // Bump up to next message type
The MSP-430 is a 16-bit microcontroller and the packed CommFrame structure has Frame.MessageID on an odd-byte boundary. Some processors might raise a SIGBUS, but TI says that it's okay to access a byte on an odd address boundary.

It's pretty silly that i++; and i+=1; don't work, but i=i+1; is just fine.

Re: There is no 'printf'

#26

So, why does puts do "return r ? EOF : '\n';"? Some backwards compatibility? Or is there a logical reason for that?

It's what historic Unix did: https://github.com/v7unix/v7unix/blob/master/v7/usr/src/libc...

Why it did that? I'm not sure, but at the time C did not have 'void' functions: every function returned a value. They probably wanted to make the behavior of the stdlib functions deterministic, even if the return value was useless and undocumented.

Re: There is no 'printf'

#27
post #14

This is a bit like saying there is no '+'; Because if you put in return 1+2+3; And look at the assembly code, you will see that the compiler generated something like return 6; The compiler is allowed to take advantage of the standard to substitute in more efficient code that does the same thing. IIRC, for C++, it would actually be ok if std::vector was implemented completely as a compiler intrinsic with no actual hea…

Code that does #include must compile, so that header must exist (whether it is stored in a file is the implementer’s choice. AFAIK, the standard carefully avoids the use of the term ‘header file’) Also, I think code that doesn’t do that include must fail to compile when it tries to use std::vector . So, logically, that header must exist.

Well not really. The preprocessor is part of the compiler, so it only needs set a flag to tell the compiler proper to enable std::vector.

Re: There is no 'printf'

#29

Compiler optimization can sometimes cause unpredictable or even incorrect behavior. Below is a blob of C code for the TI MSP430 compiler that exemplifies at least one of TI's optimization bugs: // Define Common Communications Frame typedef volatile union commFrameType { struct { unsigned SyncHeader:16; unsigned MessageID:8; unsigned short MessageData[msgDataSize]; // ID-unique data unsigned CRC:8; // LSB of CCITT-16…

'unsigned MessageID:8;' isn't the same as 'unsigned char MessageId'
Post reply on HN