实例介绍
【实例简介】汇编
using static UseAsmCode.Invoker;
namespace DllTest
{
class Program
{
static readonly string _stringCopy =
@"
; $first - pointer to string
; $second - pointer to length
mov ebx, $first
add ebx, 8
mov ecx, $second
mov ecx, [ecx]
inc ecx
mov eax, addr V_String
L_loop:
dec ecx
mov dx, [ebx ecx*2]
mov [eax ecx*2], dx
test ecx, ecx
jnz L_loop
asmret
V_String db 28 dup (0)
";
static readonly string _stringReturn =
@"
; $first - pointer to string
; $second - pointer to length
mov ebx, $first
mov ecx, $second
mov ecx, [ecx]
add ecx, 5
mov eax, addr V_String
L_loop:
dec ecx
mov dx, [ebx ecx*2]
mov [eax ecx*2], dx
test ecx, ecx
jnz L_loop
asmret
V_String db 36 dup (0)
";
static readonly string _getAndReturnObject =
@"
mov eax, $first
asmret
";
static readonly string _fullVonNeumann =
@"
; Constants
STD_OUTPUT_HANDLE equ -0Bh
STD_INPUT_HANDLE equ -0Ah
'Y' equ 59h
'y' equ 79h
'0' equ 30h
'x' equ 78h
; Extern functions
extern GetStdHandle lib kernel32.dll
extern WriteConsoleA lib kernel32.dll
extern WriteConsoleW lib kernel32.dll
extern ReadConsoleA lib kernel32.dll
; Main program
L_prg:
xor eax, eax
db 0Fh, 0C7h, 0F0h, 90h
push eax
invoke P_NumToHexString eax, addr V_HexString
mov edx, addr V_HexString
add edx, 0Ah
mov byte [edx], 0Dh
inc edx
mov byte [edx], 0Ah
invoke GetStdHandle STD_OUTPUT_HANDLE
mov edx, addr V_OutHndl
mov [edx], eax
push eax
invoke WriteConsoleA eax, addr V_HexString, 0Ch, addr V_WriteCount, 0
pop eax
invoke WriteConsoleW eax, addr V_ContinueMsg, 13h, addr V_WriteCount, 0
invoke GetStdHandle STD_INPUT_HANDLE
mov edx, addr V_InHndl
mov [edx], eax
invoke ReadConsoleA eax, addr V_ContinueInput, 3, addr V_ReadCount, 0
mov edx, addr V_ReadCount
cmp [edx], 2
je L_prg
mov edx, addr V_ContinueInput
cmp byte [edx], 'Y'
je L_prg
cmp byte [edx], 'y'
je L_prg
pop eax
asmret
; Procedures
proc P_NumToHexString Number:DWORD, Buffer:DWORD
mov edi, Buffer
mov byte [edi], '0'
mov byte [edi 1], 'x'
mov byte [edi 0Ah], 0
mov eax, Number
mov ebx, 8
L_loop:
dec ebx
mov edx, eax
lea ecx, [ebx * 4]
shl edx, cl
and edx, 0F0000000h
shr edx, 28
cmp edx, 0Ah
jl L_NumToStr
add edx, 7
L_NumToStr:
add edx, 30h
mov byte [ebx edi 2], dl
test ebx, ebx
jnz L_loop
ret 8
endp
; Variables
V_HexString db 0Dh dup (0)
V_ContinueMsg dw 'Продолжить? (Y/n)', 0Dh, 0Ah, 0
V_ContinueInput db 4 dup (0)
V_OutHndl dd 0
V_InHndl dd 0
V_ReadCount dd 0
V_WriteCount dd 0
";
static readonly string _asmInsertionSort =
@"
mov esi, $first
mov edi, $second
mov edi, [edi]
mov ecx, 1
cmp edi, 1
jle L_end
L_loop1:
mov eax, [esi ecx*4]
mov edx, ecx
L_loop2:
mov ebx, [esi edx*4 - 4]
cmp eax, ebx
jg L_loop2end
mov [esi edx*4], ebx
dec edx
jnz L_loop2
L_loop2end:
mov [esi edx*4], eax
inc ecx
cmp ecx, edi
jne L_loop1
L_end:
asmret
";
static string _str = "Hello, World!";
static int[] _arr, _arr1, _arr2;
static void Main(string[] args)
{
unsafe
{
InvokeAsm((void*)0, (void*)0, new SASMCode(
@"
STD_OUTPUT_HANDLE equ -0Bh
extern GetStdHandle lib kernel32.dll
extern WriteConsoleW lib kernel32.dll
invoke GetStdHandle STD_OUTPUT_HANDLE
mov edx, addr V_OutHndl
mov [edx], eax
invoke WriteConsoleW eax, addr V_HelloMsg, 0Eh, addr V_WriteCount, 0
asmret
V_HelloMsg dw 'Hello World!', 0Dh, 0Ah, 0
V_OutHndl dd 0
V_WriteCount dd 0
").Code);
}
Console.WriteLine();
Console.WriteLine($"Исходная строка: {_str}");
int l_len = _str.Length;
SASMCode c1 = new SASMCode(_stringCopy);
SafeInvokeAsm(ref _str, ref l_len, c1.Code);
Console.WriteLine($"Строка в переменной V_String SASM-кода: {c1.GetWStringVariable("V_String")}");
Console.WriteLine();
Console.WriteLine($"Исходная строка: {_str}");
SASMCode c2 = new SASMCode(_stringReturn);
string copy = SafeInvokeAsm<string, int, string>(ref _str, ref l_len, (byte[])c2);
Console.WriteLine($"Строка, указатель на которую вернул ассемблерный код: {copy}");
Console.WriteLine();
Random rnd = new Random();
Console.WriteLine($"Передаём объект типа {rnd.GetType()} с хеш-кодом {rnd.GetHashCode()}.");
Random retRnd = SafeInvokeAsm<Random, Random, Random>(ref rnd, ref rnd, new SASMCode(_getAndReturnObject));
Console.WriteLine($"Получили объект типа {retRnd.GetType()} с хеш-кодом {retRnd.GetHashCode()}.");
Console.WriteLine("Проверка функциональности - 10 случайных целых из интервала [0; 5).");
for (int i = 0; i < 10; i )
{
Console.Write(retRnd.Next(0, 5) " ");
}
Console.WriteLine();
Console.WriteLine();
DateTime n = DateTime.Now;
SASMCode full = new SASMCode(_fullVonNeumann);
Console.WriteLine($"Время трансляции: {DateTime.Now - n}.");
unsafe
{
int selected = (int)InvokeAsm((void*)0, (void*)0, (byte[])full);
Console.WriteLine($"Вы выбрали число {selected} (0x{Convert.ToString(selected, 16)}).");
}
Console.WriteLine();
Console.Write("Введите размер массива для сортировки: ");
int arraySize = Convert.ToInt32(Console.ReadLine());
_arr = new int[arraySize];
_arr1 = new int[arraySize];
_arr2 = new int[arraySize];
Random rand = new Random();
for (int i = 0; i < arraySize; i ) { _arr[i] = rand.Next(); }
Array.Copy(_arr, _arr1, arraySize);
Array.Copy(_arr, _arr2, arraySize);
DateTime start1 = DateTime.Now;
SASMCode sort = new SASMCode(_asmInsertionSort);
DateTime start2 = DateTime.Now;
unsafe
{
fixed (int* arrPtr = _arr1)
{
InvokeAsm(arrPtr, &arraySize, (byte[])sort);
}
}
DateTime finish = DateTime.Now;
Console.WriteLine($"Сортировка вставками на ассемблере заняла (в т.ч. время трансляции): {finish - start1} ({start2 - start1}).");
start1 = DateTime.Now;
for (int i = 1; i < _arr2.Length; i )
{
int tmp = _arr2[i];
int j = i - 1;
for (; j >= 0; j--)
{
if (_arr2[j] > tmp) { _arr2[j 1] = _arr2[j]; }
else
{
break;
}
}
_arr2[j 1] = tmp;
}
finish = DateTime.Now;
Console.WriteLine($"Сортировка вставками на C# заняла: {finish - start2}.");
Array.Sort(_arr);
bool equal = true;
for (int i = 0; i < arraySize; i )
{
if (_arr[i] != _arr1[i] || _arr[i] != _arr2[i])
{
Console.WriteLine($"Разные значения на позиции {i} (ожидаемое - ассемблер - C#): {_arr[i]} - {_arr1[i]} - {_arr2[i]}...");
equal = false;
break;
}
}
if (equal) { Console.WriteLine("Массивы отсортированы корректно!"); }
}
private static void _saveByteCode(SASMCode _c)
{
System.IO.BinaryWriter writer = new System.IO.BinaryWriter(new System.IO.FileStream("bcode.bin", System.IO.FileMode.Create));
writer.Write(_c.Code);
writer.Close();
}
}
}
【实例截图】
【核心代码】
using System;
using UseAsmCode;using static UseAsmCode.Invoker;
namespace DllTest
{
class Program
{
static readonly string _stringCopy =
@"
; $first - pointer to string
; $second - pointer to length
mov ebx, $first
add ebx, 8
mov ecx, $second
mov ecx, [ecx]
inc ecx
mov eax, addr V_String
L_loop:
dec ecx
mov dx, [ebx ecx*2]
mov [eax ecx*2], dx
test ecx, ecx
jnz L_loop
asmret
V_String db 28 dup (0)
";
static readonly string _stringReturn =
@"
; $first - pointer to string
; $second - pointer to length
mov ebx, $first
mov ecx, $second
mov ecx, [ecx]
add ecx, 5
mov eax, addr V_String
L_loop:
dec ecx
mov dx, [ebx ecx*2]
mov [eax ecx*2], dx
test ecx, ecx
jnz L_loop
asmret
V_String db 36 dup (0)
";
static readonly string _getAndReturnObject =
@"
mov eax, $first
asmret
";
static readonly string _fullVonNeumann =
@"
; Constants
STD_OUTPUT_HANDLE equ -0Bh
STD_INPUT_HANDLE equ -0Ah
'Y' equ 59h
'y' equ 79h
'0' equ 30h
'x' equ 78h
; Extern functions
extern GetStdHandle lib kernel32.dll
extern WriteConsoleA lib kernel32.dll
extern WriteConsoleW lib kernel32.dll
extern ReadConsoleA lib kernel32.dll
; Main program
L_prg:
xor eax, eax
db 0Fh, 0C7h, 0F0h, 90h
push eax
invoke P_NumToHexString eax, addr V_HexString
mov edx, addr V_HexString
add edx, 0Ah
mov byte [edx], 0Dh
inc edx
mov byte [edx], 0Ah
invoke GetStdHandle STD_OUTPUT_HANDLE
mov edx, addr V_OutHndl
mov [edx], eax
push eax
invoke WriteConsoleA eax, addr V_HexString, 0Ch, addr V_WriteCount, 0
pop eax
invoke WriteConsoleW eax, addr V_ContinueMsg, 13h, addr V_WriteCount, 0
invoke GetStdHandle STD_INPUT_HANDLE
mov edx, addr V_InHndl
mov [edx], eax
invoke ReadConsoleA eax, addr V_ContinueInput, 3, addr V_ReadCount, 0
mov edx, addr V_ReadCount
cmp [edx], 2
je L_prg
mov edx, addr V_ContinueInput
cmp byte [edx], 'Y'
je L_prg
cmp byte [edx], 'y'
je L_prg
pop eax
asmret
; Procedures
proc P_NumToHexString Number:DWORD, Buffer:DWORD
mov edi, Buffer
mov byte [edi], '0'
mov byte [edi 1], 'x'
mov byte [edi 0Ah], 0
mov eax, Number
mov ebx, 8
L_loop:
dec ebx
mov edx, eax
lea ecx, [ebx * 4]
shl edx, cl
and edx, 0F0000000h
shr edx, 28
cmp edx, 0Ah
jl L_NumToStr
add edx, 7
L_NumToStr:
add edx, 30h
mov byte [ebx edi 2], dl
test ebx, ebx
jnz L_loop
ret 8
endp
; Variables
V_HexString db 0Dh dup (0)
V_ContinueMsg dw 'Продолжить? (Y/n)', 0Dh, 0Ah, 0
V_ContinueInput db 4 dup (0)
V_OutHndl dd 0
V_InHndl dd 0
V_ReadCount dd 0
V_WriteCount dd 0
";
static readonly string _asmInsertionSort =
@"
mov esi, $first
mov edi, $second
mov edi, [edi]
mov ecx, 1
cmp edi, 1
jle L_end
L_loop1:
mov eax, [esi ecx*4]
mov edx, ecx
L_loop2:
mov ebx, [esi edx*4 - 4]
cmp eax, ebx
jg L_loop2end
mov [esi edx*4], ebx
dec edx
jnz L_loop2
L_loop2end:
mov [esi edx*4], eax
inc ecx
cmp ecx, edi
jne L_loop1
L_end:
asmret
";
static string _str = "Hello, World!";
static int[] _arr, _arr1, _arr2;
static void Main(string[] args)
{
unsafe
{
InvokeAsm((void*)0, (void*)0, new SASMCode(
@"
STD_OUTPUT_HANDLE equ -0Bh
extern GetStdHandle lib kernel32.dll
extern WriteConsoleW lib kernel32.dll
invoke GetStdHandle STD_OUTPUT_HANDLE
mov edx, addr V_OutHndl
mov [edx], eax
invoke WriteConsoleW eax, addr V_HelloMsg, 0Eh, addr V_WriteCount, 0
asmret
V_HelloMsg dw 'Hello World!', 0Dh, 0Ah, 0
V_OutHndl dd 0
V_WriteCount dd 0
").Code);
}
Console.WriteLine();
Console.WriteLine($"Исходная строка: {_str}");
int l_len = _str.Length;
SASMCode c1 = new SASMCode(_stringCopy);
SafeInvokeAsm(ref _str, ref l_len, c1.Code);
Console.WriteLine($"Строка в переменной V_String SASM-кода: {c1.GetWStringVariable("V_String")}");
Console.WriteLine();
Console.WriteLine($"Исходная строка: {_str}");
SASMCode c2 = new SASMCode(_stringReturn);
string copy = SafeInvokeAsm<string, int, string>(ref _str, ref l_len, (byte[])c2);
Console.WriteLine($"Строка, указатель на которую вернул ассемблерный код: {copy}");
Console.WriteLine();
Random rnd = new Random();
Console.WriteLine($"Передаём объект типа {rnd.GetType()} с хеш-кодом {rnd.GetHashCode()}.");
Random retRnd = SafeInvokeAsm<Random, Random, Random>(ref rnd, ref rnd, new SASMCode(_getAndReturnObject));
Console.WriteLine($"Получили объект типа {retRnd.GetType()} с хеш-кодом {retRnd.GetHashCode()}.");
Console.WriteLine("Проверка функциональности - 10 случайных целых из интервала [0; 5).");
for (int i = 0; i < 10; i )
{
Console.Write(retRnd.Next(0, 5) " ");
}
Console.WriteLine();
Console.WriteLine();
DateTime n = DateTime.Now;
SASMCode full = new SASMCode(_fullVonNeumann);
Console.WriteLine($"Время трансляции: {DateTime.Now - n}.");
unsafe
{
int selected = (int)InvokeAsm((void*)0, (void*)0, (byte[])full);
Console.WriteLine($"Вы выбрали число {selected} (0x{Convert.ToString(selected, 16)}).");
}
Console.WriteLine();
Console.Write("Введите размер массива для сортировки: ");
int arraySize = Convert.ToInt32(Console.ReadLine());
_arr = new int[arraySize];
_arr1 = new int[arraySize];
_arr2 = new int[arraySize];
Random rand = new Random();
for (int i = 0; i < arraySize; i ) { _arr[i] = rand.Next(); }
Array.Copy(_arr, _arr1, arraySize);
Array.Copy(_arr, _arr2, arraySize);
DateTime start1 = DateTime.Now;
SASMCode sort = new SASMCode(_asmInsertionSort);
DateTime start2 = DateTime.Now;
unsafe
{
fixed (int* arrPtr = _arr1)
{
InvokeAsm(arrPtr, &arraySize, (byte[])sort);
}
}
DateTime finish = DateTime.Now;
Console.WriteLine($"Сортировка вставками на ассемблере заняла (в т.ч. время трансляции): {finish - start1} ({start2 - start1}).");
start1 = DateTime.Now;
for (int i = 1; i < _arr2.Length; i )
{
int tmp = _arr2[i];
int j = i - 1;
for (; j >= 0; j--)
{
if (_arr2[j] > tmp) { _arr2[j 1] = _arr2[j]; }
else
{
break;
}
}
_arr2[j 1] = tmp;
}
finish = DateTime.Now;
Console.WriteLine($"Сортировка вставками на C# заняла: {finish - start2}.");
Array.Sort(_arr);
bool equal = true;
for (int i = 0; i < arraySize; i )
{
if (_arr[i] != _arr1[i] || _arr[i] != _arr2[i])
{
Console.WriteLine($"Разные значения на позиции {i} (ожидаемое - ассемблер - C#): {_arr[i]} - {_arr1[i]} - {_arr2[i]}...");
equal = false;
break;
}
}
if (equal) { Console.WriteLine("Массивы отсортированы корректно!"); }
}
private static void _saveByteCode(SASMCode _c)
{
System.IO.BinaryWriter writer = new System.IO.BinaryWriter(new System.IO.FileStream("bcode.bin", System.IO.FileMode.Create));
writer.Write(_c.Code);
writer.Close();
}
}
}
好例子网口号:伸出你的我的手 — 分享!
小贴士
感谢您为本站写下的评论,您的评论对其它用户来说具有重要的参考价值,所以请认真填写。
- 类似“顶”、“沙发”之类没有营养的文字,对勤劳贡献的楼主来说是令人沮丧的反馈信息。
- 相信您也不想看到一排文字/表情墙,所以请不要反馈意义不大的重复字符,也请尽量不要纯表情的回复。
- 提问之前请再仔细看一遍楼主的说明,或许是您遗漏了。
- 请勿到处挖坑绊人、招贴广告。既占空间让人厌烦,又没人会搭理,于人于己都无利。
关于好例子网
本站旨在为广大IT学习爱好者提供一个非营利性互相学习交流分享平台。本站所有资源都可以被免费获取学习研究。本站资源来自网友分享,对搜索内容的合法性不具有预见性、识别性、控制性,仅供学习研究,请务必在下载后24小时内给予删除,不得用于其他任何用途,否则后果自负。基于互联网的特殊性,平台无法对用户传输的作品、信息、内容的权属或合法性、安全性、合规性、真实性、科学性、完整权、有效性等进行实质审查;无论平台是否已进行审查,用户均应自行承担因其传输的作品、信息、内容而可能或已经产生的侵权或权属纠纷等法律责任。本站所有资源不代表本站的观点或立场,基于网友分享,根据中国法律《信息网络传播权保护条例》第二十二与二十三条之规定,若资源存在侵权或相关问题请联系本站客服人员,点此联系我们。关于更多版权及免责申明参见 版权及免责申明
网友评论
我要评论