簡體   English   中英

Windows 上的命名管道文件存儲在哪里?

[英]Where on Windows a named pipe file is stored?

我正在創建一個命名管道文件,如下所示:

 void  SavePipeFile(){


    HANDLE hpipe;
    BOOL bRet;
    DWORD size;

    hpipe =   
        CreateNamedPipe(
        L"\\\\.\\pipe\\mypipe",
        PIPE_ACCESS_OUTBOUND,  
        PIPE_TYPE_BYTE,  
        1, 
        0,  
        0,  
        0,  
        NULL  
        );
    if(hpipe == NULL || hpipe==INVALID_HANDLE_VALUE)
    {
        printf("Error opening handle\n");
    }

    CloseHandle(hpipe);


}

函數存在正常,沒有錯誤。但是我在系統中找不到物理文件“mypipe”。Windows API 是否將其保存到特定位置?在 Windows 7 64 位上運行

引自http://en.wikipedia.org/wiki/Named_pipe

與 Unix 不同,命名管道不能安裝在普通文件系統中。 也不同於它們的 Unix 對應物,命名管道是易變的(在對它們的最后一個引用關閉后被刪除)。 每個管道都放置在命名管道文件系統 (NPFS) 的根目錄中,掛載在特殊路徑 \\.\\pipe\\ 下(即,名為“foo”的管道的完整路徑名稱為 \\.\\pipe\\foo )。 流水線中使用的匿名管道實際上是具有隨機名稱的命名管道。

當您在 ReactOS 上創建命名管道時,kernel32.dll 中的CreateNamedPipe調用 ntdll.dll 中的NtCreateNamedPipeFile ,后者執行系統調用 + SSDT 索引到 ntoskrnl.exe 中的內核模式對應項,后者調用IoCreateFile ,后者調用IopCreateFile ,后者將調用ObOpenObjectByName ,它調用ObpLookupObjectName ,該調用對象的解析例程ParseRoutine = ObjectHeader->Type->TypeInfo.ParseProcedure ,這將是IopParseRoutine ,它發送一個IRP與主代碼IRP_MJ_CREATE_NAMED_PIPE到NPFS驅動器,其獲取由它的名字\\Device\\NamedPipe (它將\\\\.\\pipe解析為\\??\\pipe ,這是到由 NPFS 驅動程序創建的\\Device\\NamedPipe DO 的符號鏈接)。

NPFS的DriverEntry函數賦值DriverObject->MajorFunction[IRP_MJ_CREATE_NAMED_PIPE] = NpFsdCreateNamedPipe; . NpFsdCreateNamedPipe調用NpCreateNewNamedPipe ,它將使用數據隊列設置文件對象和文件對象的 CCB(上下文控制塊)( FileObject->FsContext2 )。

名稱為PipeName的文件對象通過\\\\.\\pipe\\PipeName訪問並轉換為\\Device\\NamedPipe\\PipeName 文件對象指向 Npfs 創建的NamedPipe設備對象, IoGetRelatedDeviceObject將返回該對象,這意味着所有WriteFileReadFile操作都會產生一個 IRP,該 IRP 被發送到此設備對象的設備堆棧的頂部,並傳遞管道名稱\\PipeName 這類似於如何\\??\\C:\\Windows\\Device\\HarddiskVolume1\\Windows文件對象PDEVICE_OBJECT指向Device\\HarddiskVolume1設備對象,文件對象的文件名UNICODE_STRING\\Windows 如果查看文件對象,則可以通過獲取設備對象名稱並將其附加到開頭來獲取完整路徑。 IoCallDriver最終將在設備對象的擁有驅動程序上調用。 根據傳遞的 IRP 中的 IRP 主要代碼, IoCallDriver調用DO->DriverObject->MajorFunction[IRP_MJ_Write] ,即NpFsdWriteDO->DriverObject->MajorFunction[IRP_MJ_Read] ,即NpFsdRead 這些函數將寫入和讀取數據隊列Ccb->DataQueue[FILE_PIPE_OUTBOUND]Ccb->DataQueue[FILE_PIPE_INBOUND] ,其中包含DataEntry標頭的雙向鏈表的頭部,其中DataEntry[0]是標頭和DataEntry[1]是緩沖區。 如果您將命名管道作為服務器打開,則它從入站讀取並寫入出站。 客戶端從出站讀取並寫入入站。

如果使用PIPE_TYPE_MESSAGE ,那么每次寫入管道時,都會將另一個DataEntry添加到鏈表的尾部(因為NpWriteDataQueue將在 IRP 中返回IoStatus STATUS_MORE_PROCESSING_REQUIRED ,調用函數會在調用NpAddDataQueueEntry之前檢查該NpAddDataQueueEntry ),並且每個當你閱讀時,一個DataEntry將從鏈表的頭部移除( NpReadDataQueue只會在!Peek調用NpRemoveDataQueueEntry )。 如果您沒有閱讀所有消息,您將收到錯誤消息。 如果您使用PIPE_TYPE_BYTE ,則僅使用當前的DataEntry並且在您寫入時不會刪除任何DataEntry 簡單地說, DataEntryByteOffset字段隨着讀取的字節數而增加,我真的不確定以字節模式寫入是如何工作的。

DataEntries、CCB 和 FileObjects 分配在非分頁池中。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM