您的位置:首页 > 编程语言 > Delphi

一种高速内存校验算法(Delphi MMX优化算法应用之一)

2008-07-06 17:14 295 查看
最近碰到一个项目需要对内存数据进行检测,确定是否和原始值一样,看了现成的算法MD5 CRC 等,感觉速度不太理想,因此动手自己写了用于检测内存数据的高速算法.

该算法利用了CPU的MMX微指令的单指令多数据优点来提高校验速度.对于大数据量校验尤其明显.

1.获取原始内存数据校验值算法:

function GetMemoryValue(aSource: Pointer; aSize: DWORD): PInt64; {获取指定内存MMX运算码和CheckMemory配对用}

asm

mov esi, aSource //开始地址

mov ecx, aSize   //长度

shr ecx,6  //除64

mov eax,0

emms

pxor    mm0,mm0

pxor    mm1,mm1

pxor    mm2,mm2

pxor    mm3,mm3

pxor    mm4,mm4

pxor    mm5,mm5

pxor    mm6,mm6

pxor    mm7,mm7

@XorLoop:

pxor    mm0, qword ptr [esi+eax]

pxor    mm1, qword ptr [esi+eax+$8]

pxor    mm2, qword ptr [esi+eax+$10]

pxor    mm3, qword ptr [esi+eax+$18]

pxor    mm4, qword ptr [esi+eax+$20]

pxor    mm5, qword ptr [esi+eax+$28]

pxor    mm6, qword ptr [esi+eax+$30]

pxor    mm7, qword ptr [esi+eax+$38]

add eax,$40 //64

sub ecx, 1

jnz @XorLoop

pxor    mm0,mm1

pxor    mm0,mm2

pxor    mm0,mm3

pxor    mm0,mm4

pxor    mm0,mm5

pxor    mm0,mm6

pxor    mm0,mm7

lea     eax,[ESP+$8] //MMXValue

movq    qword ptr [eax], mm0  //保存MMX运算值结果

Sfence

Emms

end;

2.检测内存数据校验值算法:

function CheckMemory(aSource: Pointer; aSize: DWORD; MMXValue: PInt64): Boolean;

{内存校验检测,MMXVaule为内存正常值由GetMemoryValue获得,被修改返回True}

asm

mov esi, aSource //开始地址

mov ecx, aSize   //长度

shr ecx,6  //除64

mov eax,0

emms

pxor    mm0,mm0

pxor    mm1,mm1

pxor    mm2,mm2

pxor    mm3,mm3

pxor    mm4,mm4

pxor    mm5,mm5

pxor    mm6,mm6

pxor    mm7,mm7

@XorLoop:

pxor    mm0, qword ptr [esi+eax]

pxor    mm1, qword ptr [esi+eax+$8]

pxor    mm2, qword ptr [esi+eax+$10]

pxor    mm3, qword ptr [esi+eax+$18]

pxor    mm4, qword ptr [esi+eax+$20]

pxor    mm5, qword ptr [esi+eax+$28]

pxor    mm6, qword ptr [esi+eax+$30]

pxor    mm7, qword ptr [esi+eax+$38]

add eax,$40 //64

sub ecx, 1

jnz @XorLoop

pxor    mm0,mm1

pxor    mm0,mm2

pxor    mm0,mm3

pxor    mm0,mm4

pxor    mm0,mm5

pxor    mm0,mm6

pxor    mm0,mm7

mov     eax,[ESP+$8] //MMXValue

movq    mm1, qword ptr [eax] //读值比较

pxor    mm0,mm1

movq    qword ptr [eax], mm0  //保存结果

Sfence

Emms

xor  esi,esi

cmp     dword ptr [eax], esi

Jne @Fal

cmp     dword ptr [eax+4], esi

Jne @Fal

xor eax,eax  //检验成功

jmp @exit

@Fal:  //检验失败

mov eax,1

@Exit:

end;


需要说明的是该算法有个缺陷,就是需要字节按64byte对齐,否则检测将不完整,可能出现对最后1-63byte不检测的情况,当然也可以修改上面算法让他自动适应.上面代码也还有优化余地,比如加入cache高速缓存预读处理prefetchnta预读优化速度.由于时间紧张未能加入.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: