基于AFD驱动的进程流量控制

本文介绍了基于AFD驱动的进程流量控制方案,通过HOOK AFDSend和AFDReceive等IO控制码,限制进程发送和接收数据的速度,以减少带宽占用。文章详细阐述了AFD驱动的工作原理、控制方法以及实现过程,包括数据结构和内核层的HOOK技术。
摘要由CSDN通过智能技术生成

基于AFD驱动的进程流量控制

摘要:目前有些软件可以监控进程流量,功能实现的都很多错的。对于进程流量的控制很很多种方案,每一种方案也都有其缺点。比如有应用层基于LSP来做的,也有通过TDINDIS中间层来做的。其实现的效果和复杂度也各不相同。而我们要讨论的是一种基于AFD驱动来做的一种进程流量控制方案。

    关键词:AFD 进程流量  控制驱动

1.   总述

目前有些软件可以监控进程流量,功能实现的都很多错的。对于进程流量的控制很很多种方案,每一种方案也都有其缺点。比如有应用层基于LSP来做的,也有通过TDINDIS中间层来做的。其实现的效果和复杂度也各不相同。而我们要讨论的是一种基于AFD驱动来做的一种进程流量控制方案。当然这里说的流量控制和传统意义上的流量控制不一样,这里讨论的进程流量控制是按照用户的设置来放慢进程发送和接收数据的速度从而减少带宽的占用。

2.   AFD驱动

首先来介绍一下AFD驱动。大家可能对NDISTDI了解的比较多,AFD驱动相对会少一些。NDISTDI是微软提供的内核网络驱动模型中的编程接口规范,而AFD驱动是微软Windows操作一个驱动部件。它是上层SOCKET在内核心中的实现。我这里画了一个图例来说明它们之间的关系:

 

简来说AFD驱动向上与SOCKET应用接口约定了接口来实现SOCKETAFD驱动实际上是一个TDI客户端,它通过TDI接口调用微软件的另一个网络部件TCPIP驱动来完成功能。AFD并没有官方的资料说明它的接口,但是在网上还是可以找到很关于AFD驱动的资料的。这里笔者参考了ReactOS-0.3.4-REL-src源代码中的AFD的内容,它于官方的AFD驱动实现还是有一些驱动别的,比如未实现FASTIO接口等。

AFD中它主要处理如下IO控制码,上层的应用也主要是通过它们来完成SOCKET各种操作。

/* IOCTL Generation */

#define FSCTL_AFD_BASE                  FILE_DEVICE_NETWORK

#define _AFD_CONTROL_CODE(Operation,Method) /

  ((FSCTL_AFD_BASE)<<12 | (Operation<<2) | Method)

 

/* AFD Commands */

#define AFD_BIND            0

#define AFD_CONNECT              1

#define AFD_START_LISTEN         2

#define AFD_WAIT_FOR_LISTEN      3

#define AFD_ACCEPT          4

#define AFD_RECV            5

#define AFD_RECV_DATAGRAM        6

#define AFD_SEND            7

#define AFD_SEND_DATAGRAM        8

#define AFD_SELECT          9

#define AFD_DISCONNECT           10

#define AFD_GET_SOCK_NAME        11

#define AFD_GET_PEER_NAME               12

#define AFD_GET_TDI_HANDLES      13

#define AFD_SET_INFO             14

#define AFD_GET_CONTEXT          16

#define AFD_SET_CONTEXT          17

#define AFD_SET_CONNECT_DATA         18

#define AFD_SET_CONNECT_OPTIONS      19

#define AFD_SET_DISCONNECT_DATA      20

#define AFD_SET_DISCONNECT_OPTIONS   21

#define AFD_GET_CONNECT_DATA         22

#define AFD_GET_CONNECT_OPTIONS      23

#define AFD_GET_DISCONNECT_DATA      24

#define AFD_GET_DISCONNECT_OPTIONS   25

#define AFD_SET_CONNECT_DATA_SIZE       26

#define AFD_SET_CONNECT_OPTIONS_SIZE    27

#define AFD_SET_DISCONNECT_DATA_SIZE    28

#define AFD_SET_DISCONNECT_OPTIONS_SIZE 29

#define AFD_GET_INFO             30

#define AFD_EVENT_SELECT         33

#define AFD_ENUM_NETWORK_EVENTS         34

#define AFD_DEFER_ACCEPT         35

#define AFD_GET_PENDING_CONNECT_DATA 41

 

/* AFD IOCTLs */

 

#define IOCTL_AFD_BIND /

  _AFD_CONTROL_CODE(AFD_BIND, METHOD_NEITHER)

#define IOCTL_AFD_CONNECT /

  _AFD_CONTROL_CODE(AFD_CONNECT, METHOD_NEITHER)

#define IOCTL_AFD_START_LISTEN /

  _AFD_CONTROL_CODE(AFD_START_LISTEN, METHOD_NEITHER)

#define IOCTL_AFD_WAIT_FOR_LISTEN /

  _AFD_CONTROL_CODE(AFD_WAIT_FOR_LISTEN, METHOD_BUFFERED )

#define IOCTL_AFD_ACCEPT /

  _AFD_CONTROL_CODE(AFD_ACCEPT, METHOD_BUFFERED )

#define IOCTL_AFD_RECV /

  _AFD_CONTROL_CODE(AFD_RECV, METHOD_NEITHER)

#define IOCTL_AFD_RECV_DATAGRAM /

  _AFD_CONTROL_CODE(AFD_RECV_DATAGRAM, METHOD_NEITHER)

#define IOCTL_AFD_SEND /

  _AFD_CONTROL_CODE(AFD_SEND, METHOD_NEITHER)

#define IOCTL_AFD_SEND_DATAGRAM /

  _AFD_CONTROL_CODE(AFD_SEND_DATAGRAM, METHOD_NEITHER)

#define IOCTL_AFD_SELECT /

  _AFD_CONTROL_CODE(AFD_SELECT, METHOD_BUFFERED )

#define IOCTL_AFD_DISCONNECT /

  _AFD_CONTROL_CODE(AFD_DISCONNECT, METHOD_NEITHER)

#define IOCTL_AFD_GET_SOCK_NAME /

  _AFD_CONTROL_CODE(AFD_GET_SOCK_NAME, METHOD_NEITHER)

#define IOCTL_AFD_GET_PEER_NAME /

  _AFD_CONTROL_CODE(AFD_GET_PEER_NAME, METHOD_NEITHER)

#define IOCTL_AFD_GET_TDI_HANDLES /

  _AFD_CONTROL_CODE(AFD_GET_TDI_HANDLES, METHOD_NEITHER)

#define IOCTL_AFD_SET_INFO /

  _AFD_CONTROL_CODE(AFD_SET_INFO, METHOD_NEITHER)

#define IOCTL_AFD_GET_CONTEXT /

  _AFD_CONTROL_CODE(AFD_GET_CONTEXT, METHOD_NEITHER)

#define IOCTL_AFD_SET_CONTEXT /

  _AFD_CONTROL_CODE(AFD_SET_CONTEXT, METHOD_NEITHER)

#define IOCTL_AFD_SET_CONNECT_DATA /

  _AFD_CONTROL_CODE(AFD_SET_CONNECT_DATA, METHOD_NEITHER)

#define IOCTL_AFD_SET_CONNECT_OPTIONS /

  _AFD_CONTROL_CODE(AFD_SET_CONNECT_OPTIONS, METHOD_NEITHER)

#define IOCTL_AFD_SET_DISCONNECT_DATA /

  _AFD_CONTROL_CODE(AFD_SET_DISCONNECT_DATA, METHOD_NEITHER)

#define IOCTL_AFD_SET_DISCONNECT_OPTIONS /

  _AFD_CONTROL_CODE(AFD_SET_DISCONNECT_OPTIONS, METHOD_NEITHER)

#define IOCTL_AFD_GET_CONNECT_DATA /

  _AFD_CONTROL_CODE(AFD_GET_CONNECT_DATA, METHOD_NEITHER)

#define IOCTL_AFD_GET_CONNECT_OPTIONS /

  _AFD_CONTROL_CODE(AFD_GET_CONNECT_OPTIONS, METHOD_NEITHER)

#define IOCTL_AFD_GET_DISCONNECT_DATA /

  _AFD_CONTROL_CODE(AFD_GET_DISCONNECT_DATA, METHOD_NEITHER)

#define IOCTL_AFD_GET_DISCONNECT_OPTIONS /

  _AFD_CONTROL_CODE(AFD_GET_DISCONNECT_OPTIONS, METHOD_NEITHER)

#define IOCTL_AFD_SET_CONNECT_DATA_SIZE /

  _AFD_CONTROL_CODE(AFD_SET_CONNECT_DATA_SIZE, METHOD_NEITHER)

#define IOCTL_AFD_SET_CONNECT_OPTIONS_SIZE /

  _AFD_CONTROL_CODE(AFD_SET_CONNECT_OPTIONS_SIZE, METHOD_NEITHER)

#define IOCTL_AFD_SET_DISCONNECT_DATA_SIZE /

  _AFD_CONTROL_CODE(AFD_SET_DISCONNECT_DATA_SIZE, METHOD_NEITHER)

#define IOCTL_AFD_SET_DISCONNECT_OPTIONS_SIZE /

  _AFD_CONTROL_CODE(AFD_SET_DISCONNECT_OPTIONS_SIZE, METHOD_NEITHER)

#define IOCTL_AFD_GET_INFO /

  _AFD_CONTROL_CODE(AFD_GET_INFO, METHOD_NEITHER)

#define IOCTL_AFD_EVENT_SELECT /

  _AFD_CONTROL_CODE(AFD_EVENT_SELECT, METHOD_NEITHER)

#define IOCTL_AFD_DEFER_ACCEPT /

  _AFD_CONTROL_CODE(AFD_DEFER_ACCEPT, METHOD_NEITHER)

#define IOCTL_AFD_GET_PENDING_CONNECT_DATA /

  _AFD_CONTROL_CODE(AFD_GET_PENDING_CONNECT_DATA, METHOD_NEITHER)

#define IOCTL_AFD_ENUM_NETWORK_EVENTS /

  _AFD_CONTROL_CODE(AFD_ENUM_NETWORK_EVENTS, METHOD_NEITHER)

可以通过名称看出这些IO控制码,对应了我们常用的SOCKET API

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值