Support
 

    MMX Shift Instructions

    The logical shift left, logical shift right and arithmetic shift right instructions shift each element by a specified number of bits. The logical left and right shifts also enable a 64-bit quantity (quadword) to be shifted as one block, assisting in data type conversions and alignment operations.

     

    PSLLW mm, mm/m64
    PSLLW mm, imm8
    PSLLD mm, mm/m64
    PSLLD mm, imm8
    PSLLQ mm, mm/m64
    PSLLQ mm, imm8

    The PSLL (Packed Shift Left Logical) instructions shift the bits of the first operand to the left by the amount of bits specified in the source operand. The empty low-order bits are set to zero. If the value specified by the second operand is greater than 15 (for words), 31 (for doublewords), or 63 (for quadwords), then the destination is set to all zeros. The destination operand is an MMX register, while the source operand can be either an MMX register, a 64-bit memory operand or 
    an immediate 8-bit operand. PSLL supports packed word (PSLLW), packed doubleword (PSLLD) and quadword (PSLLQ) data types.

    PSLLW instruction with 64-bit operand:
    IF (COUNT > 15)
    THEN DEST[64..0] ← 0000000000000000H
    ELSE DEST[15..0] ← ZeroExtend(DEST[15..0] << COUNT);
    * repeat shift operation for 2nd and 3rd words *;
    DEST[63..48] ← ZeroExtend(DEST[63..48] << COUNT);

    PSLLD instruction with 64-bit operand:
    IF (COUNT > 31)
    THEN DEST[64..0] ← 0000000000000000H
    ELSE DEST[31..0] ← ZeroExtend(DEST[31..0] << COUNT);
    DEST[63..32] ← ZeroExtend(DEST[63..32] << COUNT);

    PSLLQ instruction with 64-bit operand:
    IF (COUNT > 63)
    THEN DEST[64..0] ← 0000000000000000H
    ELSE DEST ← ZeroExtend(DEST << COUNT);

    PSLLW __m64 _mm_slli_pi16 (__m64 m, int count)
    PSLLW __m64 _mm_sll_pi16(__m64 m, __m64 count)

    PSLLD __m64 _mm_slli_pi32(__m64 m, int count)
    PSLLD __m64 _mm_sll_pi32(__m64 m, __m64 count)

    PSLLQ __m64 _mm_slli_si64(__m64 m, int count)
    PSLLQ __m64 _mm_sll_si64(__m64 m, __m64 count)


     

    PSRLW mm, mm/m64
    PSRLW mm, imm8
    PSRLD mm, mm/m64
    PSRLD mm, imm8
    PSRLQ mm, mm/m64
    PSRLQ mm, imm8

    The PSRL (Packed Shift Right Logical) instructions shift the bits of the first operand to the right by the amount of bits specified in the count operand. The result of the shift operation is written to the destination register. The empty high-order bits are set to zero. If the value specified by the second operand is greater than 15 (for words), or 31 (for doublewords), or 63 (for quadwords), then the destination is set to all zeros. The destination operand is an MMX register, while the count operand (source operand) can be either an MMX register, a 64-bit memory operand, or an immediate 8-bit operand. PSRL supports packed word (PSRLW), packed doubleword (PSRLD) and quadword (PSRLQ) data types.

    PSRLW instruction with 64-bit operand:
    IF (COUNT > 15)
    THEN DEST[64..0] ← 0000000000000000H
    ELSE DEST[15..0] ← ZeroExtend(DEST[15..0] >> COUNT);
    * repeat shift operation for 2nd and 3rd words *;
    DEST[63..48] ← ZeroExtend(DEST[63..48] >> COUNT);

    PSRLD instruction with 64-bit operand:
    IF (COUNT > 31)
    THEN DEST[64..0] ← 0000000000000000H
    ELSE DEST[31..0] ← ZeroExtend(DEST[31..0] >> COUNT);
    DEST[63..32] ← ZeroExtend(DEST[63..32] >> COUNT);

    PSRLQ instruction with 64-bit operand:
    IF (COUNT > 63)
    THEN DEST[64..0] ← 0000000000000000H
    ELSE DEST ← ZeroExtend(DEST >> COUNT);

    PSRLW __m64 _mm_srli_pi16(__m64 m, int count)
    PSRLW __m64 _mm_srl_pi16 (__m64 m, __m64 count)

    PSRLD __m64 _mm_srli_pi32 (__m64 m, int count)
    PSRLD __m64 _mm_srl_pi32 (__m64 m, __m64 count)

    PSRLQ __m64 _mm_srli_si64 (__m64 m, int count)
    PSRLQ __m64 _mm_srl_si64 (__m64 m, __m64 count)


     

    PSRAW mm, mm/m64
    PSRAW mm, imm8
    PSRAD mm, mm/m64
    PSRAD mm, imm8

    The PSRA (Packed Shift Right Arithmetic) instructions shift the bits of the first operand to the right by the amount of bits specified in the source operand. The empty high-order bits of each element are filled with the initial value of the sign bit of the data element. If the value specified by the second operand is greater than 15 (for words), or 31 (for doublewords), each destination element is filled with the initial value of the sign bit of the element. The destination operand is an MMX register, while the source operand can be either an MMX register, a 64-bit memory operand, or an immediate 8-bit operand. This instruction supports packed word (PSRAW) and packed doubleword (PSRAD) data types. 

    PSRAW instruction with 64-bit operand:
    IF (COUNT > 15)
    THEN COUNT ← 16;
    DEST[15..0] ← SignExtend(DEST[15..0] >> COUNT);
    * repeat shift operation for 2nd and 3rd words *;
    DEST[63..48] ← SignExtend(DEST[63..48] >> COUNT);

    PSRAD instruction with 64-bit operand:
    IF (COUNT > 31)
    THEN COUNT ← 32;
    DEST[31..0] ← SignExtend(DEST[31..0] >> COUNT);
    DEST[63..32] ← SignExtend(DEST[63..32] >> COUNT);

    PSRAW __m64 _mm_srai_pi16 (__m64 m, int count)

    PSRAW __m64 _mm_sraw_pi16 (__m64 m, __m64 count)

    PSRAD __m64 _mm_srai_pi32 (__m64 m, int count)

    PSRAD __m64 _mm_sra_pi32 (__m64 m, __m64 count)

    An example of arithmetic shift usage is the absolute value of a vector of signed words. The following code fragment assumes that the MMX register MM0 holds the signed source operand, while MM1 returns the absolute value of each component of MM0.

    MOVQ MM1, MM0 make a copy of source data
    PSRAW MM0,15 replicate sign bit
    PXOR MM0, MM1 take 1's complement of just the negative fields
    PSUBS MM1,MM0 add 1 to just the negative fields
     
     
     

    << Back to MMX Primer Home Next: MMX Data Transfer >>
Copyright Stefano Tommesani 2000/03 - All trademarks belong to their respective holders