1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145
| #include <Windows.h> #include <cstdio> typedef NTSTATUS(NTAPI* pfnRtlGetCompressionWorkSpaceSize)( _In_ USHORT CompressionFormatAndEngine, _Out_ PULONG CompressBufferWorkSpaceSize, _Out_ PULONG CompressFragmentWorkSpaceSize ); typedef NTSTATUS(NTAPI* pfnRtlCompressBuffer)( _In_ USHORT CompressionFormatAndEngine, _In_ PUCHAR UncompressedBuffer, _In_ ULONG UncompressedBufferSize, _Out_ PUCHAR CompressedBuffer, _In_ ULONG CompressedBufferSize, _In_ ULONG UnCompressedChunkSize, _Out_ PULONG FinalCompressedSize, _In_ PVOID WorkSpace ); typedef NTSTATUS(NTAPI* pfnRtlDecompressBuffer)( _In_ USHORT CompressionFormat, _Out_ PUCHAR UncompressedBuffer, _In_ ULONG UncompressedBufferSize, _In_ PUCHAR CompressedBuffer, _In_ ULONG CompressedBufferSize, _Out_ PULONG FinalUncompressedSize ); BOOL CompressData(BYTE* pUncompressData, DWORD dwUncompressDataLength, BYTE** ppCompressData, DWORD* pdwCompressDataLength) { BOOL bRet = FALSE; HMODULE hModule=NULL; pfnRtlGetCompressionWorkSpaceSize RtlGetCompressionWorkSpaceSize = NULL; pfnRtlCompressBuffer RtlCompressBuffer=NULL; NTSTATUS status=0; DWORD dwWorkSpaceSize=0, dwFragmentWorkSpaceSize=0; PUCHAR pWorkSpace,pCompressData; DWORD dwCompressDataLength=4096; DWORD dwFinalCompressSize=0; do { hModule = ::LoadLibrary(L"ntdll.dll"); if (NULL == hModule) break; RtlGetCompressionWorkSpaceSize = (pfnRtlGetCompressionWorkSpaceSize)::GetProcAddress(hModule, "RtlGetCompressionWorkSpaceSize"); if (RtlGetCompressionWorkSpaceSize == NULL) break; RtlCompressBuffer = (pfnRtlCompressBuffer)::GetProcAddress(hModule, "RtlCompressBuffer"); if (NULL == RtlCompressBuffer) break; status = RtlGetCompressionWorkSpaceSize(COMPRESSION_FORMAT_LZNT1|COMPRESSION_ENGINE_STANDARD,&dwWorkSpaceSize,&dwFragmentWorkSpaceSize); if (0 != status) break; pWorkSpace = new BYTE[dwWorkSpaceSize]; if (NULL == pWorkSpace) break; ::RtlZeroMemory(pWorkSpace, dwWorkSpaceSize); while (TRUE) { pCompressData = new BYTE[dwCompressDataLength]; if (NULL == pCompressData) break; ::RtlZeroMemory(pCompressData, dwCompressDataLength); RtlCompressBuffer(COMPRESSION_FORMAT_LZNT1, pUncompressData, dwUncompressDataLength, pCompressData, dwCompressDataLength, 4096, &dwFinalCompressSize, (PVOID)pWorkSpace); if (dwCompressDataLength < dwFinalCompressSize) { if (pCompressData) { delete[]pCompressData; pCompressData = NULL; }; dwCompressDataLength = dwFinalCompressSize; } else break; }; *ppCompressData = pCompressData; *pdwCompressDataLength = dwFinalCompressSize; bRet = TRUE; }while(FALSE); if (pWorkSpace) { delete[]pWorkSpace; pWorkSpace = NULL; }; if (hModule) ::FreeLibrary(hModule); return bRet; }; BOOL UncompressData(BYTE* pCompressData, DWORD dwCompressDataLength, BYTE** ppUncompressData, DWORD* pdwUncompressDataLength) { BOOL bRet = FALSE; HMODULE hModule = NULL; pfnRtlDecompressBuffer RtlDecompressBuffer = NULL; BYTE* pUncompressData = NULL; DWORD dwUncompressDataLength = 4096; DWORD dwFinalUncompressSize = 0; do { hModule = ::LoadLibrary(L"ntdll.dll"); if (NULL == hModule) break; RtlDecompressBuffer = (pfnRtlDecompressBuffer)::GetProcAddress(hModule, "RtlDecompressBuffer"); if (NULL == RtlDecompressBuffer) break; while (TRUE) { pUncompressData = new BYTE[dwUncompressDataLength]; if (NULL == pUncompressData) break; ::RtlZeroMemory(pUncompressData, dwUncompressDataLength); RtlDecompressBuffer(COMPRESSION_FORMAT_LZNT1, pUncompressData, dwUncompressDataLength, pCompressData, dwCompressDataLength, &dwFinalUncompressSize); if (dwUncompressDataLength < dwFinalUncompressSize) { if (pUncompressData) { delete[]pUncompressData; pUncompressData = NULL; }; dwUncompressDataLength = dwFinalUncompressSize; } else break; }; *ppUncompressData = pUncompressData; *pdwUncompressDataLength = dwFinalUncompressSize; bRet = TRUE; }while(FALSE); if (hModule) ::FreeLibrary(hModule); return bRet; } int main(int argc,char* argv[]) { BOOL bRet = FALSE; char szBuffer[] = "xxx"; DWORD dwBufferLength = ::lstrlen((LPCWSTR)szBuffer); BYTE* pCompressData = NULL; DWORD dwCompressDataLength = 0; BYTE* pUncompressData = NULL; DWORD dwUncompressDataLength = 0; CompressData((BYTE*)szBuffer, dwBufferLength, &pCompressData, &dwCompressDataLength); UncompressData(pCompressData, dwCompressDataLength, &pUncompressData, &dwUncompressDataLength); for (DWORD i = 0; i < dwBufferLength; i++) printf("%X", szBuffer[i]); for (DWORD i = 0; i < dwCompressDataLength; i++) printf("%X", pCompressData[i]); for (DWORD i = 0; i < dwUncompressDataLength; i++) printf("%X", pUncompressData[i]); if (pUncompressData) { delete[]pUncompressData; pUncompressData = NULL; }; if (pCompressData) { delete[]pCompressData; pCompressData = NULL; }; system("pause"); return 0; };
|