In CSiBE I've seen code that goes like this ... left shift: mov.b @(...),r0 extu.b r0,r1 ... shld r1,r2 right shift: mov.b @(...),r0 extu.b r0,r1 neg r1,r1 ... shld r1,r2 In both cases the zero extension can be omitted. The shld/shad shift count is truncated to a 5 bit and as per C/C++ standard shift counts > 31 or negative shift counts are undefined behavior for int32_t/uint32_t. If a shift count value is loaded from memory and is not explicitly AND'ed with 31, it can be assumed that the value is in the range 0..31. For example value in mem signed ext. unsigned ext. 0...31 0...31 0...31 OK 33 33 33 NG 255 255 -1 NG I can't think of a case where keeping the zero extension would avoid undefined behavior.