Tricky way to unroll string copy loops

Mark Brader msb at lsuc.UUCP
Sun Apr 7 14:25:22 AEST 1985


All think talk about string copies made me figure it was time to
repost Duff's Device.  This was invented by Tom Duff when he was
at Lucasfilm, and he posted it about last May with the comment that
"I feel a combination of pride and revulsion at this discovery".

It was originally written in a slightly different form; I'll transform
it slightly so that it copies n bytes from "from" to "to", like strncpy
except that it won't treat nulls specially.

The tricky part is the way the last loop is handled.  Watch carefully:

	tdsdcopy (to, from, count)
	register char *to, *from;
	register int count;
	{
		register n;
		if (count > 0) {
			n = (count+7) / 8;
			switch (count % 8) {

			case 0: do {	*to++ = *from++;
			case 7:		*to++ = *from++;
			case 6:		*to++ = *from++;
			case 5:		*to++ = *from++;
			case 4:		*to++ = *from++;
			case 3:		*to++ = *from++;
			case 2:		*to++ = *from++;
			case 1:		*to++ = *from++;
				} while (--n > 0);
			}
		}
	}

Duff also remarked as follows:

	Dennis Ritchie has endorsed it as legal C.
	...
	Many people (even Brian Kernighan?) have said that the worst feature
	of C is that switches don't break automatically before each case label.
	This code forms some sort of argument in that debate, but I'm not sure
	whether it's for or against.

Mark Brader



More information about the Comp.lang.c mailing list