Path: utzoo!utgpu!jarvis.csri.toronto.edu!clyde.concordia.ca!uunet!samsung!think!mintaka!bloom-beacon!eru!luth!sunic!dkuug!freja!skinfaxe!thorinn From: thorinn@skinfaxe.diku.dk (Lars Henrik Mathiesen) Newsgroups: comp.lang.c Subject: Re: strncpy Keywords: strncpy null termination Message-ID: <5079@freja.diku.dk> Date: 26 Dec 89 23:16:53 GMT References: <1231@srhqla.SR.COM> <11510@csli.Stanford.EDU> <2287@cs-spool.calgary.UUCP> Sender: news@freja.diku.dk Lines: 53 brucet@cpsc.ucalgary.ca (Bruce Thompson) writes: >I must be naive, and may be repeating things others have put in, but it seems >to me that if null termination is not needed/wanted, why not use bcopy? strncpy() seems to be intended for a fixed-length, null-padded string representation. bcopy() can, indeed, be used to copy such a string to another (of the same length), but strncpy is necessary to convert null-terminated strings to null-padded strings. In applications where the null-padded strings are full-word aligned, they have the further advantage that they can be moved and compared (for equality) with full-word operations. (On big-endian machines with unsigned char's, even ordered comparisons can be done that way.) Here's how you convert between the formats: #define LENGTH 14 /* Today's magical number */ char padded[LENGTH]; char terminated[LENGTH + 1]; /* Move terminated to padded */ strncpy(padded, terminated, LENGTH); /* Move padded to terminated */ strncpy(terminated, padded, LENGTH); terminated[LENGTH] = '\0'; Actually the last move could just as well use bcopy(). If you need to guarantee that the move only modifies the destination up to the terminating null, no single library routine seems to fill the ticket. A buffer with a permanent extra null, maybe: /* Move padded to terminated, no extra nulls */ static __move_buffer[LENGTH + 1]; bcopy(padded, __move_buffer, LENGTH); strcpy(terminated, __move_buffer); Given the general lack of support for null-padded strings in the standard library, you will either have to do something like that before accessing one at all (even getting its length), or you will have to write a set of support routines yourself. Come to think of it, strnlen() would be really useful sometimes --- or even, safe_strlen(const char *str, size_t max): Returns the length of the string pointed to by _str_ if _str_ points to valid memory and the string is not longer than _max_, otherwise it returns -1. But this is more a question of safe programming than of string representation. -- Lars Mathiesen, DIKU, U of Copenhagen, Denmark [uunet!]mcvax!diku!thorinn Institute of Datalogy -- we're scientists, not engineers. thorinn@diku.dk