Current-Users archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: Problems with packages on a netbsd-6 sparc

>>>> +    memcpy(cp, pw, sizeof(struct passwd));
>>>>      newpw = (struct passwd *) cp;
>>>> -    memcpy(newpw, pw, sizeof(struct passwd));

>>> Why not avoid the non-intuitive memcpy() all together all the time
>>> and just let the compiler do its job????

>>>     *newpw = *pw;

> I think that's kind of irrelevant given that I suggested getting rid
> of the memcpy() entirely, but....

The problem is that cp did not point to a struct passwd.  It pointed
into a mallocked buffer, incremented by the size of some other struct.
"newpw = (struct passwd *) cp" is off in undefined-behaviour weeds
unless cp is suitably aligned ( #7, and note that indirecting
through the result is not necessary to invoke undefined behaviour).
Because of this, the old memcpy (the one copying into newpw) was
justified in assuming newpw was properly aligned for a struct passwd,
which it was on many historical machines, either because of the way the
compiler treated the two structs in question or because the machines
didn't actually have any alignment restrictions.  But in this case that
particular bit of nonportability came back to bite the code.  Struct
assignment such as you suggest would be equally undefined and, in
practice, would almost certainly be at least as big a lose as the
memcpy, in exactly the cases where memcpy failed.

> (So far as I can recall there is no requirement in C, and certainly
> not old C or C89, that a "void *" pointer must be cast back to the
> type it had before it was cast into a "void *" pointer.  [...])

No, there's no requirement that anything be done with it at all.

However, if it is cast to some other type, it has to be correctly
aligned for that type (which is difficult to ensure in general) or "the
behavior is undefined".

/~\ The ASCII                             Mouse
\ / Ribbon Campaign
 X  Against HTML      
/ \ Email!           7D C8 61 52 5D E7 2D 39  4E F1 31 3E E8 B3 27 4B

Home | Main Index | Thread Index | Old Index