You can, but shouldn't, abuse case labels in a switch far worse than that — and far worse than Duff's Device. Duff's Device has the dubious privilege of being almost plausibly useful and yet can be regarded as abusing switch.
Not all abuses of switch can claim to be plausibly useful. For instance, this compiles as C or C++, even with stringent warnings set:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main(int argc, char **argv)
{
unsigned seed;
if (argc == 2)
seed = atoi(argv[1]);
else
seed = time(0);
printf("seed: %u\n", seed);
srand(seed);
int i = rand() % 10;
int j = 21;
int k = 37;
printf("i: %d\n", i);
switch (i)
{
case 1:
for (j = 10; j > i; j--)
{
case 2:
printf("case 2:\n");
for (k = j - 1; k > 0; k--)
{
case 6:
printf("case 6:\n");
default:
printf("%d-%d-%d\n", i, j, k);
}
case 5:
printf("case 5:\n");
printf("%d-%d\n", i, j);
break;
}
break;
case 3:
printf("case 3:\n");
break;
}
return 0;
}
The argument handling allows you set the seed, so you can reproduce results if you want to. I'd make no claim that it is useful; indeed, it is not useful. Note that break inside the loops breaks the loop, not the switch.
Basically, case labels (and default) must be within the scope of a switch, and are associated with the innermost enclosing switch. There are few other constraints on them. You have to be careful not to jump over variable initializations, etc (that's why j and k are defined outside the switch()). But otherwise, they're just labels, and control will flow to them when 'appropriate'.