According to the description of llSetPrimitiveParams on lslwiki.net, if it's applied to a child prim in a linked set, PRIM_ROTATION sets the local rotation and position relative to the root prim.
However, I find that llSetPrimitiveParams([PRIM_ROTATION,ZERO_ROTATION]) sets the local rotation equal to the global rotation of the root prim (i.e. the child's global rotation becomes the square of the global rotation of the root). In general, if I want to set the local rotation to r, I have to write this instead:
llSetPrimitiveParams([PRIM_ROTATION,r/llGetRootRotation()])
Surely it isn't meant to work this way?
If I use llSetLocalRot it works as I expect.
The reason I'm using llSetPrimitiveParams is that I want to set the position and rotation together, and separate calls to llSetLocalRot and llSetPos are animated separately.