摘要:
这里简要描述几个重要的算数运算指令。1. 水平相加指令 SSSE3指令集增加的主要是针对整数进行水平方向上相加的指令,与SSE3的浮点指令类似。 phaddd 寄存器水平方向上按照无符号32位整数进行加法 phaddw 寄存器水平方向上按照无符号16位整数进行加法 phaddsw 寄存器水平方向上按照16位整数进行饱和加法 phsubd 寄存器水平方向上按照无符号32位整数进行减法 phsubw 寄存器水平方向上按照无符号16位整数进行减法 phsubsw 寄存器水平方向上按照16位整数进行饱和减法 示例: phaddw Dest, SRC 源数据和目的数据水平相... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(947)
评论(0)
推荐(0)
摘要:
本文要谈的是这样一条指令:PSADBW这条指令是SSE1引入的用于视频编码绝对差值求和的指令。在视频编码中的运动估计模块,一种常见的SAD代码如下:1 // Get the SAD 16x16 macro block with full pixel2 for (y = 0; y < 16; y++)3 for(x = 0; x < 16; x++)4 sad += abs(current[y][x] - reference[y][x])对于这段代码,我们首先来用MMX指令做优化。1. SAD的MMX优化我们使用带饱和运算的PSUBUSB指令来实现求ABS (B - A)的功能。.. 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(834)
评论(0)
推荐(0)
摘要:
本文要介绍的是SSE4.1指令集中的几条整数指令及其在视频编码中的应用。1.单指令32字节差分绝对值求和指令 MPSADBW 这条指令类似于SSE的PSADBW,但它实现的功能更强大。包括微软官方网站上对这条指令的说明都不是能够让人一目了然。下面这张图也许可以帮助我们理解: 这条指令的灵活之处在于源操作数和目的操作数的位置都是可选的。如何选择关键在于后面那个mask常量。这个常量是一个立即数,但只用到了其中的低三位。 其中,最低2位,用于选择源操作数的连续4个字节的起始位置。由于两位二进制有4中状态,所以源操作数的可选起始位置共有4种,具体见上图。 mask的第三位用于选择目的操... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(1448)
评论(0)
推荐(0)
摘要:
实际上,搞汇编优化的很多时间是在处理如何有效的组织数据,以适应并行计算指令的数据结构。本小结描述的是数据混洗指令,这类指令使用起来相当的灵活。具体如下: 1. shufps XMM,XMM/m128,imm8(0~255) 描述: 从指令后缀来看,这是一条SSE1指令。 该指令把源存储器与目的寄存器按双字32位划分,由立即数imm8八个二进制位(00~11,00^11,00~11,00~11)指定排列, 目的寄存器高64位放源存储器被指定数,目的寄存器低64位放目的寄存器被指定数。内存变量地址必须对齐16字节 imm8的高4位选的是源存储器,低4位选的是目的... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(2294)
评论(0)
推荐(0)
摘要:
本小节描述的是SSE2整数运算指令。5. 数据搬移指令 movdqa XMM,XMM/m128 movdqa XMM/m128,XMM 把源存储器内容值送入目的寄存器,当有m128时,内存地址必须16字节对齐. movdqu XMM,XMM/m128 movdqu XMM/m128,XMM 把源存储器内容值送入目的寄存器,内存地址不必16字节对齐. movq2dq XMM,MM 把源寄存器内容送入目的寄存器的低64位,高64位清零. movdq2q MM,XMM 把源寄存器低64位内容送入目的寄存器.6. 算数运算指令 要点: 1. SSE2的算数运算指... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(1521)
评论(0)
推荐(0)
摘要:
4. 数据重排指令集 unpckhps XMM,XMM/m128 源存储器与目的寄存器高64位按双字交错排列,结果送入目的寄存器,内存变量必须对齐内存16字节. 高64位 | 低64位 目的寄存器: a0 | a1 | a2 | a3 源存储器: b0 | b1 | b2 | b3 目的寄存器结果: b0 | a0 | b1 | a1 例: 当 XMM0 = 0x 0c517e000 44290000 46b6d000 3c4985f0 XMM1 = 0x 045e51000 4240cccd 4a59e540 ... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(2047)
评论(0)
推荐(0)
摘要:
6. SSE整数运算指令 pavgb MM,MM/m64 pavgb XMM,XMM/m128 把源存储器与目的寄存器按字节无符号整数相加,再除以2,结果四舍五入为整数放入目的寄存器。 源存储器为m128时,内存变量地址必须16字节对齐. pavgw MM,MM/m64 pavgw XMM,XMM/m128 把源存储器与目的寄存器按字无符号整数相加,再除以2,结果四舍五入为整数放入目的寄存器, 源存储器为m128时,内存变量必须对齐内存16字节. pextrw r32,MM,imm8 pextrw r32,XMM,imm8 从源寄存器中选第imm8(0~3 或 0~... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(847)
评论(0)
推荐(0)
摘要:
MMX指令有8个64位寄存器(MM0~MM7),不过可惜都是借的FPU的, FPU原来有8个80位寄存器(st(0)~st(7)),现在用在了MMX上,所以用之后要加上一条EMMS指令,用以复位.MMX寄存器有64位,可以同时进行8对字节或4对字或2对双字同时相同操作,还可以进行饱和运算,不会溢出,当然也可以进行普通运算.特别要注意的一点是:在x86上,一个字,WORD的长度是16位,而在ARM上,一个WORD的长度是32位。描述约定: MM表示64位MMX寄存器. r32表示32位通用寄存器或esi,edi m32表示32位内存变量 m64表示64位内存变量 m128表示128位内存变量 i 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(1826)
评论(0)
推荐(0)
摘要:
4. 数据移位指令 4.1 16位并行左移指令 psllw MM,MM/m64 psllw MM,imm8 把目的寄存器按字由源存储器(或imm8 立即数)指定位数逻辑左移,移出的位丢失. 低字移出的位不会移入高字. 例: 当MM0 = 0xffff ffff ffff ffff, 执行psllw MM0,1 则MM0 = 0xfffe fffe fffe fffe 4.2 16位并行逻辑右移指令 psrlw MM,MM/m64 psrlw MM,imm8 把目的寄存器按字由源存储器(或imm8 立即数)指定位数逻辑右移,移出的位丢失. 高字移出的位不会移入低字. 例: 当MM0 = 0xf. 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(791)
评论(0)
推荐(0)
摘要:
6. 数据压缩指令 packuswb MM,MM/m64 把目的寄存器按字有符号数压缩为饱和字节无符号数放入目的寄存器低32位, 把源寄存器字有符号数压缩为饱和字节无符号数放入目的寄存器高32位。 简单的说,就是16位有符号压缩为饱和8位无符号数。 高32位 | 低32位 目的寄存器: a0 | a1 | a2 | a3 源寄存器: b0 | b1 | b2 | b3 目的寄存器压缩结果: b0|b1| b2|b3| a0|a1|a2|a3 例: 当MM0 == 0x 7fff 8000 1234 00ae, ... 阅读全文
posted @ 2013-04-23 12:22
celerychen
阅读(598)
评论(0)
推荐(1)
浙公网安备 33010602011771号