I/O 控制代碼的緩衝區描述
I/O 控制代碼包含在 IRP_MJ_DEVICE_CONTROL 和 IRP_MJ_INTERNAL_DEVICE_CONTROL 要求中。 I/O 管理員會建立這些要求,因為呼叫 DeviceIoControl 和 IoBuildDeviceIoControlRequest。
由於 DeviceIoControl 和 IoBuildDeviceIoControlRequest 接受輸入緩衝區和輸出緩衝區作為引數,因此所有 IRP_MJ_DEVICE_CONTROL 和 IRP_MJ_INTERNAL_DEVICE_CONTROL 要求都會同時提供輸入緩衝區和輸出緩衝區。 系統描述這些緩衝區的方式取決於資料傳輸類型。 傳輸類型是由建立 IOCTL 程式碼值的CTL_CODE宏中的TransferType值所指定。
系統會描述每個 TransferType 值的緩衝區,如下所示。
METHOD_BUFFERED
針對此傳輸類型,IRP 會在 Irp-AssociatedIrp.SystemBuffer >提供緩衝區的指標。 此緩衝區代表呼叫 DeviceIoControl 和IoBuildDeviceIoControlRequest中指定的輸入緩衝區和輸出緩衝區。 驅動程式會將資料移出,然後移入這個緩衝區。
針對輸入資料,緩衝區大小是由驅動程式IO_STACK_LOCATION結構中的Parameters.DeviceIoControl.InputBufferLength所指定。 針對輸出資料,緩衝區大小是由驅動程式IO_STACK_LOCATION結構中的Parameters.DeviceIoControl.OutputBufferLength所指定。
系統為單一輸入/輸出緩衝區配置的空間大小,是兩個長度值中較大的空間。
METHOD_IN_DIRECT或METHOD_OUT_DIRECT
針對這些傳輸類型,IRP 會在 Irp-AssociatedIrp.SystemBuffer >提供緩衝區的指標。 這代表呼叫 DeviceIoControl 和 IoBuildDeviceIoControlRequest中指定的第一個緩衝區。 緩衝區大小是由驅動程式IO_STACK_LOCATION結構中的Parameters.DeviceIoControl.InputBufferLength所指定。
針對這些傳輸類型,IRP 也會在 Irp-MdlAddress >提供 MDL 的指標。 這代表呼叫 DeviceIoControl 和 IoBuildDeviceIoControlRequest中指定的第二個緩衝區。 此緩衝區可作為輸入緩衝區或輸出緩衝區,如下所示:
如果處理 IRP 的驅動程式在呼叫緩衝區時收到資料,就會指定METHOD_IN_DIRECT。 MDL 描述輸入緩衝區,並指定METHOD_IN_DIRECT可確保執行中的執行緒具有緩衝區的讀取權限。
如果處理 IRP 的驅動程式會在完成 IRP 之前將資料寫入緩衝區,就會指定METHOD_OUT_DIRECT。 MDL 描述輸出緩衝區,並指定METHOD_OUT_DIRECT可確保執行中的執行緒具有緩衝區的寫入權限。
針對這兩種傳輸類型, Parameters.DeviceIoControl.OutputBufferLength 會指定 MDL 所描述的緩衝區大小。
METHOD_NEITHER
I/O 管理員不提供任何系統緩衝區或 MDL。 IRP 會提供 指定給 DeviceIoControl 或 IoBuildDeviceIoControlRequest之輸入和輸出緩衝區的使用者模式虛擬位址,而不需驗證或對應它們。
輸入緩衝區的位址是由驅動程式IO_STACK_LOCATION結構中的Parameters.DeviceIoControl.Type3InputBuffer提供,而輸出緩衝區的位址是由Irp-UserBuffer >指定。
緩衝區大小是由驅動程式IO_STACK_LOCATION結構中的Parameters.DeviceIoControl.InputBufferLength和Parameters.DeviceIoControl.OutputBufferLength提供。
如需 CTL_CODE宏和 上面所列傳輸類型的詳細資訊,請參閱 定義 I/O 控制代碼。