boywhp
驱动中牛
驱动中牛
  • 注册日期2007-08-09
  • 最后登录2015-04-24
  • 粉丝2
  • 关注0
  • 积分1105分
  • 威望515点
  • 贡献值0点
  • 好评度254点
  • 原创分1分
  • 专家分0分
阅读:1972回复:5

获取进程完整路径-2000DDK+VM6[2K Sp4]

楼主#
更多 发布于:2008-07-25 16:27
驱动网要源码是可耻的
驱动网发源码是光荣的
NTSTATUS
SfNtNameToDosName(
    IN PUNICODE_STRING NtName,
    OUT PUNICODE_STRING DosName)
{
    OBJECT_ATTRIBUTES attributes;
    UNICODE_STRING driveLetterName, linkTarget;
    HANDLE linkHandle;
    WCHAR c;
    
    linkTarget.Length = 0;
    linkTarget.MaximumLength = 256;
    linkTarget.Buffer = ExAllocatePool(PagedPool, linkTarget.MaximumLength);
    
    RtlInitUnicodeString(&driveLetterName, L"\\??\\C:");
    for (c = L'A'; c <= L'Z'; c++)
    {
        driveLetterName.Buffer[4] = c;
        InitializeObjectAttributes(&attributes, &driveLetterName, OBJ_CASE_INSENSITIVE, 0, NULL);
        
        if (!NT_SUCCESS(ZwOpenSymbolicLinkObject(&linkHandle, GENERIC_READ, &attributes))) continue;
        if (!NT_SUCCESS(ZwQuerySymbolicLinkObject(linkHandle, &linkTarget, NULL))) continue;
        
        //KdPrint(("%wZ->%wZ\n", &driveLetterName, &linkTarget));
        
        if (_wcsnicmp(NtName->Buffer, linkTarget.Buffer, linkTarget.Length>>1) == 0)
        {
            DosName->Length = 4 + NtName->Length - linkTarget.Length;
            DosName->MaximumLength = DosName->Length + 2;
            DosName->Buffer = ExAllocatePool(PagedPool, DosName->MaximumLength);
            if (!DosName->Buffer) return STATUS_INSUFFICIENT_RESOURCES;

            memcpy((PBYTE)DosName->Buffer + 4, (PBYTE)NtName->Buffer + linkTarget.Length, NtName->Length - linkTarget.Length);

            DosName->Buffer[0] = c;
            DosName->Buffer[1] = L':';
            DosName->Buffer[DosName->Length>>1] = 0;

            RtlFreeUnicodeString(&linkTarget);
            return STATUS_SUCCESS;
        }
    }
    
    RtlFreeUnicodeString(&linkTarget);
    return STATUS_NOT_FOUND;
}

ULONG
GetProcessDosPath(
    IN PEPROCESS Process,
    IN OUT PUNICODE_STRING DosPath
    )
{
    //获取指定进程的完整文件路径
    ULONG Ret;
    PVOID SectionObject;

    ASSERT(Process);
    
    SectionObject = (PVOID)(*(PULONG)((PBYTE)Process + g_EProcessOffset.wOffsetSection));

    if (4 == (ULONG)SectionObject)
    {
        //Win2K里面对应的是句柄
        KeAttachProcess(Process);
        if (!NT_SUCCESS(ObReferenceObjectByHandle(SectionObject, 0, NULL, KernelMode, &SectionObject, NULL)))
        {
            KeDetachProcess();
            return 0;
        }
        Ret = GetSectionObjectDosPath(SectionObject, DosPath);
        ObfDereferenceObject(SectionObject);
        KeDetachProcess();
    }
    else
    {
        Ret = GetSectionObjectDosPath(SectionObject, DosPath);
    }
    
    //KdPrint(("SectionObject:%08x\n", SectionObject));
    return Ret;
}

ULONG
GetSectionObjectDosPath(
    IN HANDLE SectionObject,
    IN OUT PUNICODE_STRING DosPath
    )
{
    HANDLE Segment, ControlArea;
    PFILE_OBJECT FilePointer;

    if (!SectionObject) return 0;

    Segment = (PVOID)(*(PULONG)((ULONG)SectionObject + 0x14));
    ControlArea = (PVOID)(*(PULONG)Segment);
    FilePointer = (PFILE_OBJECT) *(PULONG)((ULONG) ControlArea + 0x24);

    //KdPrint(("Segment %08x ControlArea %08x: FilePointer At %08x\n", Segment, ControlArea, FilePointer));

    if (FilePointer && MmIsAddressValid(FilePointer))
    {
        BYTE nameInfo[512];
        ULONG ret;
        POBJECT_NAME_INFORMATION objInfo = (POBJECT_NAME_INFORMATION)nameInfo;

        if (!NT_SUCCESS(ObQueryNameString(FilePointer, (POBJECT_NAME_INFORMATION)nameInfo, sizeof(nameInfo), &ret)))
        {
            KdPrint(("ObQueryNameString Fail %08x!\n", FilePointer));
            return 0;
        }
        if (!NT_SUCCESS(SfNtNameToDosName(&objInfo->Name, DosPath)))
        {
            KdPrint(("SfNtNameToDosName Fail %wZ!\n", &objInfo->Name));
            return 0;
        }
        /*
        if (!NT_SUCCESS(RtlVolumeDeviceToDosName(FilePointer->DeviceObject, &dosName)))
        {
            //映射网络驱动器会有问题
            KdPrint(("RtlVolumeDeviceToDosName Failed DeviceObject:%08x\n", FilePointer->DeviceObject));
            return 0;
        }
        */        
        return DosPath->Length;
    }
    return 0;
}
boywhp
驱动中牛
驱动中牛
  • 注册日期2007-08-09
  • 最后登录2015-04-24
  • 粉丝2
  • 关注0
  • 积分1105分
  • 威望515点
  • 贡献值0点
  • 好评度254点
  • 原创分1分
  • 专家分0分
沙发#
发布于:2008-07-28 20:44
貌似大家都知道比较好的方法了?也不发个代码,害我到处找,有怕问了让人耻笑
boywhp
驱动中牛
驱动中牛
  • 注册日期2007-08-09
  • 最后登录2015-04-24
  • 粉丝2
  • 关注0
  • 积分1105分
  • 威望515点
  • 贡献值0点
  • 好评度254点
  • 原创分1分
  • 专家分0分
板凳#
发布于:2008-07-29 11:00
wowowowowocock 有没有好的方法 啊?比较保险的方法是调用API,但是API不熟啊
游客

返回顶部