美好的一天!
我正在使用 Xbyak 在 C++ 中编写 JIT asm 生成。
问题出现在序言和结语中。 我在序言中做的最后一件事是将 Xmms 值写入堆栈。在此之后我不使用堆栈指针直到结语所以我不需要更新堆栈指针。
旧代码是这样的:
# prologue
push( regNumSteps );
push( retTemp );
for( int i = 6; i <= 15; i++ ) {
vmovaps( ptr[rsp - 16 - ( i - 6 ) * 16], Xmm( i ) );
}
# epilogue
for( int i = 15; i >= 6; i-- ) {
vmovaps( Xmm( i ), ptr[rsp - 16 - ( i - 6 ) * 16] );
}
pop( retTemp );
pop( regNumSteps );
leave();
这段代码运行良好。但是在 valgrind 下它会导致
invalid write of size 8
在序言中存储 Xmm14 和 Xmm15 时(为什么是 8?Xmms 是 16)invalid read of size 16
在尾声中加载 Xmm15 和 Xmm14 时我的猜测是可能是 valgrind 不喜欢在不正确移动 rsp 的情况下使用堆栈?.
之后我将序言和结语中的循环重写如下:
// prologue
for( int i = 6; i <= 15; i++ ) {
sub( rsp, 16 ); // keep rsp up-to-date
vmovaps( ptr[rsp], Xmm( i ) );
}
// epilogue
for( int i = 15; i >= 6; i-- ) {
vmovaps( Xmm( i ), ptr[rsp] );
add( rsp, 16 ); // keep rsp up-to-date
}
它通过了valgrind!
问题是为什么?我的猜测是正确的还是巧合?
我查看了 valgrind 的选项,但找不到与此相关的任何内容。谷歌搜索也没有帮助......