如何解决需要一种方法来处理 C# 汇编程序中的 2/3 字节 VEX
你好,我已经将 x86 汇编器(和自动汇编器)从作弊引擎完全移植到 C#。
大多数情况下一切正常,但“VEX”前缀指令目前已损坏。
有 2 段代码我还无法转换,所以我想知道是否有人可以提供解决方案。
注释掉的部分是我不确定如何处理的部分。
2 字节 vex
//2byte vex
bytes.SetLength(bytes.Length + 2);
for (i = bytes.Length - 1; i >= RexPrefixLocation + 2; i--)
bytes[i] = bytes[i - 2];
bytes[RexPrefixLocation] = 0xc5; //2 byte VEX
//pvex2byte(&bytes[RexPrefixLocation + 1])->pp = (int) (Assembler.OpCodes[j].VexLeadingOpCode);
//pvex2byte(&bytes[RexPrefixLocation + 1])->l = Assembler.OpCodes[j].VexL;
//pvex2byte(&bytes[RexPrefixLocation + 1])->vvvv = vexvvvv;
//pvex2byte(&bytes[RexPrefixLocation + 1])->r = RexR ? 0 : 1;
if (RelativeAddressLocation != -1)
RelativeAddressLocation += 2;
3 字节 vex
//3byte vex
bytes.SetLength(bytes.Length + 3);
for (i = bytes.Length - 1; i >= RexPrefixLocation + 3; i--)
bytes[i] = bytes[i - 3];
bytes[RexPrefixLocation] = 0xc4; //3 byte VEX
//pvex3byte(&bytes[RexPrefixLocation + 1])->mmmmm = (int)(Assembler.OpCodes[j].VexLeadingOpCode);
//pvex3byte(&bytes[RexPrefixLocation + 1])->b = RexB ? 0 : 1;
//pvex3byte(&bytes[RexPrefixLocation + 1])->x = RexX ? 0 : 1;
//pvex3byte(&bytes[RexPrefixLocation + 1])->r = RexR ? 0 : 1;
//pvex3byte(&bytes[RexPrefixLocation + 1])->pp = (int)(Assembler.OpCodes[j].VexLeadingOpCode);
//pvex3byte(&bytes[RexPrefixLocation + 1])->l = Assembler.OpCodes[j].VexL;
//pvex3byte(&bytes[RexPrefixLocation + 1])->vvvv = vexvvvv;
//pvex3byte(&bytes[RexPrefixLocation + 1])->w = RexW ? 1 : 0; //not inverted
if (RelativeAddressLocation != -1)
RelativeAddressLocation += 3;
原始汇编/自动汇编器是用 pascal (lazarus) 编写的,这里是 pvex3byte 的定义
TVEX3Byte=bitpacked record
mmmmm: 0..31;
B: 0..1;
X: 0..1;
R: 0..1;
pp: 0..3;
L: 0..1;
vvvv: 0..15;
W: 0..1;
end;
PVEX3Byte=^TVEX3Byte;
TVEX2Byte=bitpacked record
pp: 0..3;
L: 0..1;
vvvv: 0..15;
R: 0..1;
end;
PVex2Byte=^TVex2Byte;
有人可以解决如何填写这部分吗?如果可能的话,为“字节”(字节 [])数组提供一个完整的类或扩展,以允许正确编辑/读取 vexs?
我认为它与位有关,不幸的是,c# 中没有位结构(没有以这种方式工作的)。
解决方法
在github上找到这个
/* VEX 2 byte form */
/* 7 0 */
/* +---+---+---+---+---+---+---+---+ */
/* |~R | ~vvvv | L | pp | */
/* +---+---+---+---+---+---+---+---+ */
/* VEX 3 byte form */
/* 7 0 7 0 */
/* +---+---+---+---+---+---+---+---+ +---+---+---+---+---+---+---+---+*/
/* |~R |~X |~B | map_select | |W/E| ~vvvv | L | pp |*/
/* +---+---+---+---+---+---+---+---+ +---+---+---+---+---+---+---+---+*/
在朋友的帮助下,我的自定义 vec() 类很快就解决了问题。
最终结果是一个新的 multiByte 类,它使用简单的属性处理 vex2/3。
public class AVex3Byte : AMultiByte
{
#region Constants
private const int SIZE = 2;
#endregion
#region R
public Byte R
{
get => (Byte)Get(7,1,true);
set
{
Set(7,true,value);
Apply();
}
}
#endregion
#region X
public Byte X
{
get => (Byte)Get(6,true);
set
{
Set(6,value);
Apply();
}
}
#endregion
#region B
public Byte B
{
get => (Byte)Get(5,true);
set
{
Set(5,value);
Apply();
}
}
#endregion
#region Mmmmm
public Byte Mmmmm
{
get => (Byte)Get(0,5,true);
set
{
Set(0,value);
Apply();
}
}
#endregion
#region W
public Byte W
{
get => (Byte)Get(15,true);
set
{
Set(15,value);
Apply();
}
}
#endregion
#region Vvvv
public Byte Vvvv
{
get => (Byte)Get(11,4,true);
set
{
Set(11,value);
Apply();
}
}
#endregion
#region L
public Byte L
{
get => (Byte)Get(10,true);
set
{
Set(10,value);
Apply();
}
}
#endregion
#region Pp
public Byte Pp
{
get => (Byte)Get(8,2,true);
set
{
Set(8,value);
Apply();
}
}
#endregion
#region Constructor
public AVex3Byte()
: base(SIZE)
{
}
public AVex3Byte(AByteArray bytes,int index)
: base(SIZE,bytes,index)
{
}
public AVex3Byte(IntPtr bytesPointer)
: base(SIZE,bytesPointer,0)
{
}
public AVex3Byte(IntPtr bytesPointer,index)
{
}
#endregion
}
这里是原始问题代码在修复时的样子
//2byte vex
bytes.SetLength(bytes.Length + 2);
for (i = bytes.Length - 1; i >= RexPrefixLocation + 2; i--)
bytes[i] = bytes[i - 2];
bytes[RexPrefixLocation] = 0xc5; //2 byte VEX
var vex2 = new AVex2Byte(bytes,RexPrefixLocation + 1);
vex2.Pp = (Byte)Assembler.OpCodes[j].VexLeadingOpCode;
vex2.L = Assembler.OpCodes[j].VexL;
vex2.Vvvv = (Byte)vexvvvv;
vex2.R = (Byte)(RexR ? 0 : 1);
if (RelativeAddressLocation != -1)
RelativeAddressLocation += 2;
//3byte vex
bytes.SetLength(bytes.Length + 3);
for (i = bytes.Length - 1; i >= RexPrefixLocation + 3; i--)
bytes[i] = bytes[i - 3];
bytes[RexPrefixLocation] = 0xc4; //3 byte VEX
var vex3 = new AVex3Byte(bytes,RexPrefixLocation + 1);
vex3.Mmmmm = (Byte)(Assembler.OpCodes[j].VexLeadingOpCode);
vex3.B = (Byte)(RexB ? 0 : 1);
vex3.X = (Byte)(RexX ? 0 : 1);
vex3.R = (Byte)(RexR ? 0 : 1);
vex3.Pp = (Byte)(Assembler.OpCodes[j].VexLeadingOpCode);
vex3.L = Assembler.OpCodes[j].VexL;
vex3.Vvvv = (Byte)vexvvvv;
vex3.W = (Byte)(RexW ? 1 : 0); //not inverted
if (RelativeAddressLocation != -1)
RelativeAddressLocation += 3;
我需要的是关于哪些位、它们在哪里、它们有多大以及如何读取/写入/从中读取的正确信息。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。