Win32通用控件,加载进程(PE查看器)项目初步(上)

简介: Win32通用控件,加载进程(PE查看器)项目初步

在本专栏上一篇文章中带领大家学习了对话框的创建,并且在项目中创建出了对话框。在这一篇文章中,我将带领大家学习Win32通用控件,了解_WM_NOTIFY消息,并且带领大家初步写出课程中加载Windows所有进程的应用程序的雏形,带领大家详解其中的原理。

一.标准控件与通用控件

Windows中有很多控件,有一些控件是我们不需要加载的,使用频率很高我们称为标准控件,有一些使用频率不是很高,我们在使用的时候需要加载,我们称为通用控件。

标准控件:

Static

Group Box

Button

CHeck Box

Radio Box

Edit

ComboBox

ListBox

Windows通用控件,包含在commctrl32.dll中,使用前需要:

#include <commctrl.h>
#pragma comment(lib,"comctl32.lib")

通用控件包括:

Animation

ComboBoxEx

Drag_List_Box

Flat_Scroll_bar

Header

HotKey

ImageList

IPAddress

List_View

Month_Calendar

Pager

Progress_Bar

Property_Sheets

Rebar

Status Bars

SysLink

Tab

Toolbar

Trackbar

TreeView

Up_and_Down

特别说明:

通过用控件在使用前,需要通过INITCOMMONCONTROLSEX进行初始化。 只要在你的程序中任意地方使用了该函数,就会使得Windows的程序加载器PE Loader加载该库。

INITCOMMONCONTROLSEX icex;
icex.dwSize = sizeof(INITCOMMONCONTROLSEX);
icex.dwICC = ICC_WIN95_CLASSES;
InitCOmmonControlsEx(&icex);

二.WM_INITDIALOG消息

MSDN官方文档;WM_INITDIALOG消息

#define WM_INITDIALOG                   0x0110
• 1

发送时间:在对话框显示之前,发送到对话框回调函数。

参数:

· wParem:用于接收默认键盘焦点的控件的句柄。 仅当对话框过程返回 TRUE 时,系统才分配默认键盘焦点。

lParam:其他初始化数据。

三.WM_NOTIFY消息

1.WM_NOTIFY消息的使用

该消息类型与WM_COMMAND类型相似,都是由子窗口向父窗口发送的消息。

WM_NOTIFY消息可以包含比WM_COMMAND更为丰富的信息。

Windows中有很多通用控件的消息,都是通过WM_NOTIFY来描述的。

2.WM_NOTIFY消息参数

MSDN官方文档:WM_NOTIFY消息

  • 发送时间:当发生事件或控件需要一些信息时,由公共控件发送到父窗口。
  • 参数:
    wParam:发送消息的公用控件的标识符。
    lParam:指向包含通知代码和其他信息的NMHDR的指针。
  • 注意:
    消息的目标必须是控件父级的HWND.

3.NMHDR结构

typedef struct tagNMHDR{
  HWNDhwndFrom;      //发送通知消息的控件窗口句柄
  UINT idFrom;       //发送通知消息的控件ID
  UINT code;         //通知代码
};

这个结构体能满足一般的需求,但能描述的信息任然是有限的。

解决方案:对每一种不同用途的通知消息都定义一种结构体来表示:

四.加载Windows进程应用程序项目初步

这一章开始,带领大家开发一个加载Windows进程的EXE,其中包括:加载Windows当前的所有进程,包括进程名,PID,镜像地址,镜像大小,并且再单击进程的时候,加载该进程所有的模块。

本篇文章将会一步一步带领大家写出基本的代码,在最后给出完整的代码。在项目开发完毕后,我会发布完整代码。

1. 我们首先画出对话框界面:

2. 然后我们来写出应用程序入口函数:

#include "framework.h"
#include "PEProcess.h"
#include <CommCtrl.h>             
#pragma comment(lib,"comctl32.lib")        //需要使用通用控件
HINSTANCE hIns = 0;
//入口函数
int APIENTRY WinMain(
  HINSTANCE hInstance,
  HINSTANCE hPrevInstance,
  LPSTR lpCmdLine,
  int nCmdShow
) {
  hIns = hInstance;
  //使用通用控件的向前声明
  INITCOMMONCONTROLSEX icex;
  icex.dwSize = sizeof(INITCOMMONCONTROLSEX);
  icex.dwICC = ICC_WIN95_CLASSES;
  InitCommonControlsEx(&icex);
  DialogBox(hInstance, MAKEINTRESOURCE(IDD_DIALOG_MAIN), NULL, (DLGPROC)MainDlgProc);     //加载主对话框
  return 0;
}

使用通用控件的向前声明:

1. INITCOMMONTROLSEX结构体:

这里我们使用到了INITCOMMONCONTROLSEX结构体,我们来看看这个结构体:

MSDN官方文档:INITCOMMONTROLSEX结构体

typedef struct tagINITCOMMONCONTROLSEX {
  DWORD dwSize;
  DWORD dwICC;
} INITCOMMONCONTROLSEX, *LPINITCOMMONCONTROLSEX;

该结构通常用于从动态链接库加载常见控件类信息。

参数说明:

dwSize:结构大小(以字节为单位)

dwICC:指向将从DLL加载哪些常见控件类的位标志集。

2.InitCommonControlsEx函数

MSDN官方文档:InitCOmmonControlsEx函数

BOOL InitCOmmonControlsEx(
  [in] const INITCOMMONCONTROLSEX *pocce
);

函数说明:

函数功能:确保加载公共控件(Comctl32),并从该DLL注册特定的公共控件类

参数说明:

指向INITCOMMONCONTROLSEX结构体,该结构包含指定将注册哪些控件类信息。

返回值:

成功返回TRUE,失败返回FALSE.

在写入了入口函数,并且加载了主对话框之后,我们运行,发现程序页面已经出来了:

3.主对话框的回调函数

我们应该想到:

  1. 在对话框显示之前,需要初始化对话框,需要我们将列名等信息全部初始化
  2. 在对话框显示之前,发送的消息为WM_INITDIALOG,初始化的工作应该在这个消息内完成
  3. 由于初始化的过程比较复杂,我这里对初始化进程窗口和初始化模块窗口分别封装了函数处理
OOL CALLBACK MainDlgProc(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam) {
  BOOL nRet = FALSE;
  switch (uMsg) {
    case WM_CLOSE: {
      EndDialog(hDlg, 0);
      PostQuitMessage(0);
      break;
    }
    case WM_INITDIALOG: {
      InitProcessListView(hDlg);         //设置ProcessListView的风格
      break;
    }
    case WM_COMMAND: {
      switch (LOWORD(wParam)) {
        case IDC_BUTTON_ABOUT: {
          DialogBox(hIns, MAKEINTRESOURCE(IDD_ABOUTBOX), NULL, NULL);
        }
        case IDC_BUTTON_PE: {
          //打开新的对话框,PE查看器
          return 0;
        }
        case IDC_BUTTON_OUT: {
          EndDialog(hDlg, 0);
          return TRUE;
        }
      }
    }
  }
  return nRet;
}


相关文章
|
2月前
|
JavaScript API
使用vue3+vite+electron构建小项目介绍Electron进程间通信
使用vue3+vite+electron构建小项目介绍Electron进程间通信
349 3
|
4月前
|
人工智能 PyTorch 算法框架/工具
Xinference实战指南:全面解析LLM大模型部署流程,携手Dify打造高效AI应用实践案例,加速AI项目落地进程
【8月更文挑战第6天】Xinference实战指南:全面解析LLM大模型部署流程,携手Dify打造高效AI应用实践案例,加速AI项目落地进程
Xinference实战指南:全面解析LLM大模型部署流程,携手Dify打造高效AI应用实践案例,加速AI项目落地进程
后端登录接口使用postman,无法接收返回数据,怎样解决,认真比较与原项目的代码,看看有没有写的不一样的,问题就能解决,不要多少写,根据postman的提示先找到错误的进程,看错误进程出现在那个进程
后端登录接口使用postman,无法接收返回数据,怎样解决,认真比较与原项目的代码,看看有没有写的不一样的,问题就能解决,不要多少写,根据postman的提示先找到错误的进程,看错误进程出现在那个进程
|
7月前
|
Shell Linux
【Linux】进程实践项目(更新中) — 自主shell编写
前几篇文章,我们学习进程的相关知识:进程概念,进程替换,进程控制。熟悉了进程到底是个什么事情,接下来我们来做一个实践,来运用我们所学的相关知识。这个项目就是手搓一个shell模块,模拟实现Xshell中的命令行输入。
68 1
|
测试技术 API
【OS Pintos】Project1 项目要求说明 | 进程中止信息 | 参数传递 | 用户内存访问 | 有关项目实现的建议
【OS Pintos】Project1 项目要求说明 | 进程中止信息 | 参数传递 | 用户内存访问 | 有关项目实现的建议
149 0
|
7月前
|
消息中间件 存储 算法
【C/C++ 泡沫精选面试题04】在实际项目中,多进程和多线程如何选择?
【C/C++ 泡沫精选面试题04】在实际项目中,多进程和多线程如何选择?
223 1
|
7月前
|
消息中间件 并行计算 网络协议
探秘高效Linux C/C++项目架构:让进程、线程和通信方式助力你的代码飞跃
探秘高效Linux C/C++项目架构:让进程、线程和通信方式助力你的代码飞跃
164 0
|
7月前
|
安全 Windows 容器
win32编程 -- 进程
win32编程 -- 进程
36 0
|
7月前
|
监控 Ubuntu 应用服务中间件
强大的进程查看器:htop
强大的进程查看器:htop
217 0
|
开发框架 .NET
解决NET Core发布iis项目覆盖原有的项目时"另一个程序正在使用此文件,进程无法访问"
解决NET Core发布iis项目覆盖原有的项目时"另一个程序正在使用此文件,进程无法访问"