win系统中ReadFile和内核层ZwReadFile到底有什么联系呢?

liutingting2020 2014-07-18 04:42:47
win系统中ReadFile和内核层ZwReadFile到底有什么联系呢?
...全文
287 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
赵4老师 2014-07-23
  • 打赏
  • 举报
回复
参考File: C:\windows_2000_source_code\win2k\private\windows\base\client\filehops.c
    192: BOOL
    193: WINAPI
    194: ReadFile(
    195:     HANDLE hFile,
    196:     LPVOID lpBuffer,
    197:     DWORD nNumberOfBytesToRead,
    198:     LPDWORD lpNumberOfBytesRead,
    199:     LPOVERLAPPED lpOverlapped
    200:     )
    201: 
    202: /*++
    203: 
    204: Routine Description:
    205: 
    206:     Data can be read from a file using ReadFile.
    207: 
    208:     This API is used to read data from a file.  Data is read from the
    209:     file from the position indicated by the file pointer.  After the
    210:     read completes, the file pointer is adjusted by the number of bytes
    211:     actually read.  A return value of TRUE coupled with a bytes read of
    212:     0 indicates that the file pointer was beyond the current end of the
    213:     file at the time of the read.
    214: 
    215: Arguments:
    216: 
    217:     hFile - Supplies an open handle to a file that is to be read.  The
    218:         file handle must have been created with GENERIC_READ access to
    219:         the file.
    220: 
    221:     lpBuffer - Supplies the address of a buffer to receive the data read
    222:         from the file.
    223: 
    224:     nNumberOfBytesToRead - Supplies the number of bytes to read from the
    225:         file.
    226: 
    227:     lpNumberOfBytesRead - Returns the number of bytes read by this call.
    228:         This parameter is always set to 0 before doing any IO or error
    229:         checking.
    230: 
    231:     lpOverlapped - Optionally points to an OVERLAPPED structure to be used with the
    232:     request. If NULL then the transfer starts at the current file position
    233:     and ReadFile will not return until the operation completes.
    234: 
    235:     If the handle hFile was created without specifying FILE_FLAG_OVERLAPPED
    236:     the file pointer is moved to the specified offset plus
    237:     lpNumberOfBytesRead before ReadFile returns. ReadFile will wait for the
    238:     request to complete before returning (it will not return
    239:     ERROR_IO_PENDING).
    240: 
    241:     When FILE_FLAG_OVERLAPPED is specified, ReadFile may return
    242:     ERROR_IO_PENDING to allow the calling function to continue processing
    243:     while the operation completes. The event (or hFile if hEvent is NULL) will
    244:     be set to the signalled state upon completion of the request.
    245: 
    246:     When the handle is created with FILE_FLAG_OVERLAPPED and lpOverlapped
    247:     is set to NULL, ReadFile will return ERROR_INVALID_PARAMTER because
    248:     the file offset is required.
    249: 
    250: 
    251: Return Value:
    252: 
    253:     TRUE - The operation was successul.
    254: 
    255:     FALSE - The operation failed.  Extended error status is available
    256:         using GetLastError.
    257: 
    258: --*/
    259: 
    260: {
    261:     NTSTATUS Status;
    262:     IO_STATUS_BLOCK IoStatusBlock;
    263:     PPEB Peb;
    264:     DWORD InputMode;
    265: 
    266:     if ( ARGUMENT_PRESENT(lpNumberOfBytesRead) ) {
    267:         *lpNumberOfBytesRead = 0;
    268:         }
    269: 
    270:     Peb = NtCurrentPeb();
    271: 
    272:     switch( HandleToUlong(hFile) ) {
    273:         case STD_INPUT_HANDLE:  hFile = Peb->ProcessParameters->StandardInput;
    274:                                 break;
    275:         case STD_OUTPUT_HANDLE: hFile = Peb->ProcessParameters->StandardOutput;
    276:                                 break;
    277:         case STD_ERROR_HANDLE:  hFile = Peb->ProcessParameters->StandardError;
    278:                                 break;
    279:         }
    280: 
    281:     if (CONSOLE_HANDLE(hFile)) {
    282:         if (ReadConsoleA(hFile,
    283:                         lpBuffer,
    284:                         nNumberOfBytesToRead,
    285:                         lpNumberOfBytesRead,
    286:                         lpOverlapped
    287:                        )
    288:            ) {
    289:             Status = STATUS_SUCCESS;
    290:             if (!GetConsoleMode( hFile, &InputMode )) {
    291:                 InputMode = 0;
    292:                 }
    293: 
    294:             if (InputMode & ENABLE_PROCESSED_INPUT) {
    295:                 try {
    296:                     if (*(PCHAR)lpBuffer == 0x1A) {
    297:                         *lpNumberOfBytesRead = 0;
    298:                         }
    299:                     }
    300:                 except( EXCEPTION_EXECUTE_HANDLER ) {
    301:                     Status = GetExceptionCode();
    302:                     }
    303:                 }
    304: 
    305:             if (NT_SUCCESS(Status)) {
    306:                 return TRUE;
    307:                 }
    308:             else {
    309:                 BaseSetLastNTError(Status);
    310:                 return FALSE;
    311:                 }
    312:             }
    313:         else {
    314:             return FALSE;
    315:             }
    316:         }
    317: 
    318:     if ( ARGUMENT_PRESENT( lpOverlapped ) ) {
    319:         LARGE_INTEGER Li;
    320: 
    321:         lpOverlapped->Internal = (DWORD)STATUS_PENDING;
    322:         Li.LowPart = lpOverlapped->Offset;
    323:         Li.HighPart = lpOverlapped->OffsetHigh;
    324:         Status = NtReadFile(
    325:                 hFile,
    326:                 lpOverlapped->hEvent,
    327:                 NULL,
    328:                 (ULONG_PTR)lpOverlapped->hEvent & 1 ? NULL : lpOverlapped,
    329:                 (PIO_STATUS_BLOCK)&lpOverlapped->Internal,
    330:                 lpBuffer,
    331:                 nNumberOfBytesToRead,
    332:                 &Li,
    333:                 NULL
    334:                 );
    335: 
    336: 
    337:         if ( NT_SUCCESS(Status) && Status != STATUS_PENDING) {
    338:             if ( ARGUMENT_PRESENT(lpNumberOfBytesRead) ) {
    339:                 try {
    340:                     *lpNumberOfBytesRead = (DWORD)lpOverlapped->InternalHigh;
    341:                     }
    342:                 except(EXCEPTION_EXECUTE_HANDLER) {
    343:                     *lpNumberOfBytesRead = 0;
    344:                     }
    345:                 }
    346:             return TRUE;
    347:             }
    348:         else
    349:         if (Status == STATUS_END_OF_FILE) {
    350:             if ( ARGUMENT_PRESENT(lpNumberOfBytesRead) ) {
    351:                 *lpNumberOfBytesRead = 0;
    352:                 }
    353:             BaseSetLastNTError(Status);
    354:             return FALSE;
    355:             }
    356:         else {
    357:             BaseSetLastNTError(Status);
    358:             return FALSE;
    359:             }
    360:         }
    361:     else
    362:         {
    363:         Status = NtReadFile(
    364:                 hFile,
    365:                 NULL,
    366:                 NULL,
    367:                 NULL,
    368:                 &IoStatusBlock,
    369:                 lpBuffer,
    370:                 nNumberOfBytesToRead,
    371:                 NULL,
    372:                 NULL
    373:                 );
    374: 
    375:         if ( Status == STATUS_PENDING) {
    376:             // Operation must complete before return & IoStatusBlock destroyed
    377:             Status = NtWaitForSingleObject( hFile, FALSE, NULL );
    378:             if ( NT_SUCCESS(Status)) {
    379:                 Status = IoStatusBlock.Status;
    380:                 }
    381:             }
    382: 
    383:         if ( NT_SUCCESS(Status) ) {
    384:             *lpNumberOfBytesRead = (DWORD)IoStatusBlock.Information;
    385:             return TRUE;
    386:             }
    387:         else
    388:         if (Status == STATUS_END_OF_FILE) {
    389:             *lpNumberOfBytesRead = 0;
    390:             return TRUE;
    391:             }
    392:         else {
    393:             if ( NT_WARNING(Status) ) {
    394:                 *lpNumberOfBytesRead = (DWORD)IoStatusBlock.Information;
    395:                 }
    396:             BaseSetLastNTError(Status);
    397:             return FALSE;
    398:             }
    399:         }
    400: }
liutingting2020 2014-07-23
  • 打赏
  • 举报
回复
引用 1 楼 zhao4zhong1 的回复:
用WinDbg单步调试ReadFile进去一探究竟。
你能不能再说的具体详细一些。如何对ReadFile单步调试,是调试应用层中的吗? 需要动反汇编吗?
赵4老师 2014-07-18
  • 打赏
  • 举报
回复
用WinDbg单步调试ReadFile进去一探究竟。

33,311

社区成员

发帖
与我相关
我的任务
社区描述
C/C++ 新手乐园
社区管理员
  • 新手乐园社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧