From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.3 required=5.0 tests=BAYES_00,INVALID_MSGID autolearn=no autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: 109fba,df854b5838c3e14 X-Google-Attributes: gid109fba,public X-Google-Thread: 1014db,df854b5838c3e14 X-Google-Attributes: gid1014db,public X-Google-Thread: 103376,df854b5838c3e14 X-Google-Attributes: gid103376,public From: scs@eskimo.com (Steve Summit) Subject: Re: ANSI C and POSIX Date: 1996/04/14 Message-ID: #1/1 X-Deja-AN: 147479491 sender: news@eskimo.com (News User Id) x-nntp-posting-host: eskimo.com references: <4kbrt5$k3h@mulga.cs.mu.OZ.AU> organization: schmorganization newsgroups: comp.lang.ada,comp.lang.c,comp.lang.c++ Date: 1996-04-14T00:00:00+00:00 List-Id: In article , dewar@cs.nyu.edu (Robert Dewar) writes: > Steve said/asked >> An example was brought up which, I gather, boils down to >> char buf[100]; >> /* exactly 68 characters are known to be available on fd */ >> read(fd, buf, 1000); >> It wasn't clear whether this was being presented as a real-world >> example of a portability problem... > > Of course it is being brought up as an example of a portability problem. > As for > (a) should be written > (b) should be portable in practice > (c) should work > I would say, historically, (b) and (c), I would probably agree, but only if "should" were changed to "happened to". > but not necessarily (a). If the > spec of the POSIX read were defined to say "the buffer must be at least > as long as the data that is read", then certainly (b) and (c) would be > true. But that would be a terrible way for the Posix spec to define it. > As for (a), note that of course *no one* would explicitly write > the dubious code, it occurs in the context of a loop, something like > > while (p < endbuf) {read(fd, p, 8192); p+=8192;) Thank you! Call me lazy, call me stupid, but I was too lazy or stupid to look beyond previous artificial example to see if there might be a real one behind it. (I suspected there might be one, but I was too laz... oh, I'm repeating myself.) > Of course it is possible to modify this code so that > the last read does not have an excessive count, but the resulting code > is a little more complex. Of course. I've written that loop countless times, but always in the slightly "more complex" way which simultaneously decrements a chars-left-to-read count as it increments the pointer. It would honestly never have occurred to me that the code could in some cases be "simplified" to fix read's third argument at a constant. (The simplification is of course only possible if the input size is known and is known not to be growing.) > The issue is not whether this code is defensible or not. Clearly this was > in fact a significant bug, since the code broke on Linux, and this was > intended to be portable, so it was wrong, caused trouble, and had to be > fixed. In that sense it was certainly wrong! > > However, given the vague definition of read, it is easy to see how the > coder here in fact assumed that (b) and (c) were true... Perhaps. My opinion (but I'm speculating, and the thread is getting old, so I probably shouldn't) is that the original coder was probably careless. A more careful programmer would have written the code safely regardless of what the spec for read() said; a careless programmer probably wouldn't have scrutinized the spec for read() at all. > If the spec of read had said: "the buffer must be at least the length > given by the third parameter, even if the actual data is smaller", then > of course the error would not have been made in the first place. Of course? I fear you may be a bit of an optimist. > And that, all along has been my point. Careful specification of > interfaces, and accurate knowledge of these specifications, can > definitely improve portability. In none of the above do I intend to argue against careful specification of interfaces. Steve Summit scs@eskimo.com