为 Windows x86 编写程序集

     2023-02-16     121

关键词:

【中文标题】为 Windows x86 编写程序集【英文标题】:Writing Assembly for Windows x86 【发布时间】:2012-06-03 05:42:18 【问题描述】:

我想使用 x86 程序集为 Windows 编写简单的程序(控制台输入/输出),主要是因为我只是好奇。如果有人能指出我正确的方向,那就太好了。我已经对一些更简单的 x86 指令、寄存器的功能等有了相当好的理解,但对我来说程序如何与操作系统交互以及如何使用标准输入和输出仍然是个谜。我知道这些事情与诸如 advapi32.dll 和 kernel32.dll 之类的库有关,并且有关联的静态库 .lib 文件使编译器能够使用这些动态链接的库,但除此之外,我几乎不知道这是怎么回事发生。我什至对 C 等语言中的头文件如何使用 .lib 文件感到困惑。

【问题讨论】:

先用C写代码,看看编译器生成的程序集。 嘿,这是一个非常时髦的想法。你认为这真的有可能吗? 当然,所有 C 编译器都支持以汇编格式生成代码的选项。调试器还可以显示机器代码,它内置了反汇编器。 我会试一试的。从经验中学习一直是我的强项。我学习的第一种语言是 VB,我通过拖动表单上的元素,双击它们以访问它们的事件处理程序,然后在显示所有命名空间、函数、子例程的小弹出框的帮助下输入有意义的代码,以及可以使用的其他对象。前一年我看过一些 VB 代码,所以我知道如何使用“.”。等等。是的,花了一段时间。最后我用谷歌搜索了一些东西,比如如何在屏幕上画线。我 12 岁的时候编程要简单得多。 哈哈,系统?我四天前刚高中毕业。 【参考方案1】:

也许最简单的方法是为构建一些简单的程序提供指导,并让您从那里进行推断。首先你需要一些源代码:

.386
.MODEL flat, stdcall

; This is what would come from a header -- a declaration of a the Windows function:
MessageBoxA PROTO near32 stdcall, window:dword, text:near32,
        windowtitle:near32, style:dword

.stack 8192

.data
message db "Hello World!", 0
windowtitle   db "Win32 Hello World.", 0

.code
main proc
        invoke MessageBoxA, 0, near32 ptr message, near32 ptr windowtitle, 0
        ret
main endp
        end main

要构建它,我们会调用masm,例如:

ml hello32.asm -link -subsystem:windows user32.lib

这告诉它要组装的文件,当它链接时,告诉它链接它作为 Windows 子系统(主要替代方案是-subsystem:console)并链接到user32.lib。后者为我们提供了MessageBoxA的定义。

写入控制台的类似程序(奇怪的是)稍微复杂一点:

.386
.MODEL flat, stdcall

getstdout = -11

WriteFile PROTO NEAR32 stdcall, \
        handle:dword,           \
        buffer:ptr byte,        \
        bytes:dword,            \
        written: ptr dword,     \
        overlapped: ptr byte

GetStdHandle PROTO NEAR32, device:dword

ExitProcess PROTO NEAR32, exitcode:dword

.data
message db "Hello World!", 13, 10
msg_size dd $ - offset message

.data?
written  dd ?

.code
main proc   
    invoke GetStdHandle, getstdout

    invoke WriteFile,                   \
           eax,                         \
           offset message,              \
           msg_size,                    \
           offset written,              \
           0

    invoke ExitProcess, 0
main endp
        end main

构建几乎相同,只是它使用控制台,因此我们指定控制台子系统,并且我们正在使用的功能在内核中定义:

ml hello_console.asm -link -subsystem:console kernel32.lib

标头将包含我上面为MessageBoxAGetStdHandleWriteFile 等提供的声明的等效项。但每个标头通常会有更多的声明——例如,所有kernel32 中的函数可能位于单个标头中。

就图书馆而言,所涉及的机制有些涉及,但大多无关紧要。要完成这项工作,您可以查看(例如)MSDN,查看要链接的库,然后将其添加到命令行中。

更复杂的解释是,至少当您链接到静态库时,它会简单地找到您调用的任何函数,并将每个函数的副本放入您的可执行文件/DLL 中。如果(如上)您使用的是 DLL 中的代码,它基本上只是将一条记录放入可执行文件中,该记录告诉它所依赖的 DLL 中的哪个函数。然后,当您加载/运行程序时,加载程序会查找您的程序所依赖的所有 DLL,并加载它们(当然,也递归加载它们所依赖的任何内容)。然后加载程序修复这些引用,因此对 DLL 中函数的引用将填充为该 DLL 中已分配给该函数的任何地址。

【讨论】:

这就是装配体的样子? mov、add、jne、call、ret、pop 和其他类似的简单指令发生了什么?我认为“调用”调用过程是否正确?它似乎执行了大量指令,将几个值推送到堆栈然后执行调用。这根本不是我认为的组装...... @BigEndian:是的,invoke 是一个宏,它先进行一些推送然后调用。如果您不想使用,则不必使用,但也没有太多理由避免使用它。至于其他说明,是的,它们仍然存在,如果你要做很多事情,你可以使用它们。我们不在这里,而且比我们使用 DOS “hello world” 加载偏移量到 BX 并调用 DOS 函数 09h 的情况更多。 我认为 09h 是执行标准输出的函数的地址? @BigEndian:哎呀,对不起。不,这是函数的编号。在 DOS 下,每个函数都有一个数字,您将其加载到 AH 中,然后执行 int 21h 来调用该函数。

从给定的 x86 程序集编写 C 函数

】从给定的x86程序集编写C函数【英文标题】:WritingaCfunctionfromgivenx86assembly【发布时间】:2018-08-2706:58:15【问题描述】:我正在尝试对这个神秘功能进行逆向工程。该函数返回一个整数,并以一个结构节点作为参数#include"mystery.h"... 查看详情

x86 程序集 - 如何使用 Windows API _WriteConsole@4 - masm32 语法

】x86程序集-如何使用WindowsAPI_WriteConsole@4-masm32语法【英文标题】:x86assembly-howtouseWindowsAPI_WriteConsole@4-masm32syntax【发布时间】:2012-05-1712:34:36【问题描述】:在我的帖子中我可以在windowsxp上使用int21h来打印东西吗?,我看到了一... 查看详情

为 x86 系统编译 Readline(静态模式)

...50【问题描述】:我正在使用Debian9x86为x86架构在QTCreator中编写程序。该程序将使用GNUReadline库[8.0]。另外,我的程序必须是静态构建的(QT已经是静态构建的)。为此,我从here.下载了Readline然后进行静态程序集 查看详情

VB.NET 为 x86 平台编译的应用程序设置不会在 Windows XP/Vista 32 位上运行

】VB.NET为x86平台编译的应用程序设置不会在WindowsXP/Vista32位上运行【英文标题】:VB.NETcompiledappsetupforx86platformwon\'trunonWindowsXP/Vista32-bit【发布时间】:2014-04-1312:13:35【问题描述】:在我的Windows764位机器上使用VS2010Ultimate,我用Visua... 查看详情

无法为 x64 和 x86 加载文件或程序集 'CefSharp.Wpf;只有一个作品

】无法为x64和x86加载文件或程序集\\\'CefSharp.Wpf;只有一个作品【英文标题】:Couldnotloadfileorassembly\'CefSharp.Wpfforbothx64andx86;onlyoneworks无法为x64和x86加载文件或程序集\'CefSharp.Wpf;只有一个作品【发布时间】:2015-09-1905:50:37【问题描... 查看详情

x86 指令集的声明式表示

...布时间】:2013-10-1315:41:39【问题描述】:我正在为编译器编写一个x86后端,发现为我需要的每条汇编指令编码机器代码真的很乏味,而且我显然是在重新发明***。是否在任何地方都有该指令集的声明性表示,例如一个XML文件将指... 查看详情

为 Windows 7 安装 MSSQL 并运行使用 MSSQL2016 为 X86 系统制作的应用程序

】为Windows7安装MSSQL并运行使用MSSQL2016为X86系统制作的应用程序【英文标题】:InstallingMSSQLforWindows7andrunningapplicationmadewithMSSQL2016forX86systems【发布时间】:2018-07-3115:52:38【问题描述】:我正在通过Windows窗体应用程序使用(C#和SQL)... 查看详情

程序集 x86:如何计算 32 位长整数中的设置位数

...2016-09-2021:31:52【问题描述】:我是一个新手,我正在尝试编写代码来计算32位整数中设置的位数。我写了这个,但我得到了很多错误:.586.modelflat,stdcall.stack4096;Windowslibrariesinclu 查看详情

cmp 不工作 - Intel x86 (IA32) 程序集

...间】:2017-04-2920:47:45【问题描述】:我正在尝试在汇编中编写一个简单的代码,但在使用cmp比较两个值时遇到了麻烦。如果我的值不在65到90之间,我想跳转到某个点。cmp$65,(%ebx)jlloopingcmp$90,(%ebx)jgcheck_minusculas运行gdb 查看详情

x86 程序集 - 4 个给定数字中的 2 个最大值

...时间】:2016-10-2423:36:36【问题描述】:我正在用汇编程序编写一个C子例程,它需要从传入的4个值中找出2个最大值并将它们相乘。我正在寻找最大值,但我有点卡住了。我有这个找到最大值,但我似乎无法推理如何获得第二高。... 查看详情

如何用vs2012编写能在windows2000运行的程序

现在只有工具vs2012,有什么办法在windows2000运行吗,MFC也试过,提示“不是有效的win32程序”,大家有什么好的方法吗?项目属性里面,找到:链接器>高级>所需的最低版本,输入5.0(即win2000的版本号)5.1表示winXP,6.0表示vis... 查看详情

具有线性插值的 x86 程序集衰落 bmp

】具有线性插值的x86程序集衰落bmp【英文标题】:x86assemblyfadingbmpwithlinearinterpolation【发布时间】:2015-08-2309:37:33【问题描述】:任务是:将24bpp.BMP图像的顶部淡化为白色,以便对每个像素的颜色进行线性插值根据其与顶部边缘... 查看详情

我可以将 x86 程序集的 Intel 语法与 GCC 一起使用吗?

...某些部分,我需要使用汇编语言,但其余代码将使用C/C++编写。那么,如果我将使用GCC将C/C++与汇编代码混合使用,我需要使用AT&T语法还是可以我使用英特尔语法?或者你如何以其他方 查看详情

未能加载的文件或程序集.怎么解决

...更改目录至"<system_drive>:\\ProgramFiles(x86)\\MicrosoftSDKs\\Windows\\v<x.xx& 查看详情

x86 程序集分段错误

】x86程序集分段错误【英文标题】:x86Assemblysegmentationfault【发布时间】:2015-11-0316:28:12【问题描述】:我可以编译它,但是当我运行它时,我得到“分段错误”。如果有人解释原因会很高兴。.section.datadigitformatstr:.string"%d\\n".sect... 查看详情

Windows NT 本机应用程序是不是可以访问 x86 软件中断(如 int 19)?

】WindowsNT本机应用程序是不是可以访问x86软件中断(如int19)?【英文标题】:DoWindowsNTNativeApplicationshaveaccesstox86softwareinterrupts(likeint19)?WindowsNT本机应用程序是否可以访问x86软件中断(如int19)?【发布时间】:2013-11-0504:10:58【问... 查看详情

跨平台程序集 ((x64 || x86) && (Microsoft x64 || SystemV))

...【发布时间】:2019-02-2517:53:24【问题描述】:我正在尝试编写一些代码,以了解更多关于汇编和JIT编译器之类的知识。到目前为止,我已经能够提出一个XOR函数,理论上它应该可 查看详情

在“任何 CPU”.NET 程序集上强制 x86 CLR

】在“任何CPU”.NET程序集上强制x86CLR【英文标题】:Forcex86CLRonan\'AnyCPU\'.NETassembly【发布时间】:2010-12-0304:44:35【问题描述】:在.NET中,“平台目标:任何CPU”编译器选项允许.NET程序集在x64机器上以64位运行,在x86机器上以32位... 查看详情