Windows在调用Main()之前做了什么?
Windows必须做一些事情来解析PE头,在内存中加载可执行文件,并将命令行参数传递给main().
使用OllyDbg我已将调试器设置为在main()上中断,因此我可以查看调用堆栈: 好像符号缺失所以我们无法获得函数名称,只能看到它的内存地址.但是我们可以看到main的调用者是kernel32.767262C4,它是ntdll.77A90FD9的被调用者.在堆栈的底部,我们看到RETURN到ntdll.77A90FA4,我认为它是第一个被调用来运行可执行文件的函数.看起来传递给该函数的值得注意的参数是Windows的结构化异常处理程序地址和可执行文件的入口点. 那么这些函数究竟是如何最终将程序加载到内存中并为入口点执行做好准备呢?调试器是否在main()之前显示操作系统执行的整个过程?
如果你在内部调用
CreateProcess 系统调用
ZwCreateThread[Ex] 来创建进程中的第一个线程
当你创建线程时 – 你(如果直接调用 此例程的名称取决于Windows版本. 早期这是来自kernel32.dll的BaseThreadStartThunk或BaseProcessStartThunk(如果来自CreateProcess,则调用). 但现在系统从ntdll.dll指定RtlUserThreadStart. RtlUserThreadStart通常从kernel32.dll调用BaseThreadInitThunk(本机(启动执行)应用程序除外,例如smss.exe和chkdsk.exe,它们在自己的地址空间中根本没有kernel32.dll). BaseThreadInitThunk已经调用了原始的线程入口点,并在(if)之后返回 – 调用了
但无论线程入口点 – 用户空间中的线程 – 从这一点开始执行! 用户模式线程开始执行时的早期 – 系统将APC连接到带有LdrInitializeThunk的线程作为Apc例程 – 这是通过将(保存)线程CONTEXT复制到用户堆栈然后调用调用LdrInitializeThunk的KiUserApcDispatcher来完成的.当LdrInitializeThunk完成时 – 我们返回KiUserApcDispatcher,它使用保存的线程CONTEXT调用NtContinue – 只有在此线程入口点开始执行之后. 但是现在系统在这个过程中做了一些优化 – 它将线程CONTEXT复制(保存)到用户堆栈并直接调用LdrInitializeThunk.在这个函数的末尾,NtContinue调用了 – 并且正在执行线程入口点. 所以每个线程都从LdrInitializeThunk开始在用户模式下执行. (具有确切名称的此函数存在并在从nt4到win10的所有Windows版本中调用)
>初始化不同的流程结构
(编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
- windows-server-2008 – MSDN许可?
- windows-8 – Windows 8 Live Tile多久更新一次?
- 部署 – 如何阻止Windows 10安装修改BIOS启动设置?
- Windows系统命令行net user命令 新增 删除更新 用户
- windows-server-2008 – 增加Kerberos票证的MaxTokenSize的
- windows – Add-AzureAccount:unknown_user_type:天蓝色自
- .net – 为Windows窗体应用程序选择字体
- 许可 – 获取Microsoft Office降级的密钥
- windows-store-apps – 查看Windows开发人员中心的应用程序
- Visual Studio 关闭鼠标悬停时自动出现快速文档浮层的方法
- grails清理Windows bat文件上的run-app
- ActiveX Edge在Microsoft Edge中有替代品吗?
- WMI Win32_BaseBoard SerialNumber
- Windows 2008从不以“管理员”身份运行程序
- windbg – 为什么sosex!dlk在Windows 7上永远运
- 在Windows环境下搭建Nginx文件服务器(简单实用版
- 命令行界面 – 命令行 – 切换到管理员模式
- windows-8 – 如何更改我的Windows 8发布者显示名
- .net – 在IIS 7.5中托管WCF与Windows服务的性能
- FreeRadius+Cisco交换机+Windows AD实现802.1X认