You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
340 lines
8.4 KiB
340 lines
8.4 KiB
|
|
//***************************************************************************
|
|
//
|
|
// (c) 2001 by Microsoft Corp. All Rights Reserved.
|
|
//
|
|
// PAGEMGR.H
|
|
//
|
|
// Declarations for CPageFile, CPageSource for WMI repository for
|
|
// Windows XP.
|
|
//
|
|
// 21-Feb-01 raymcc
|
|
//
|
|
//***************************************************************************
|
|
|
|
#ifndef _PAGEMGR_H_
|
|
#define _PAGEMGR_H_
|
|
|
|
#define WMIREP_PAGE_SIZE (8192)
|
|
|
|
#define WMIREP_INVALID_PAGE 0xFFFFFFFF
|
|
#define WMIREP_RESERVED_PAGE 0xFFFFFFFE
|
|
|
|
#define WMIREP_OBJECT_DATA L"OBJECTS.DATA"
|
|
#define WMIREP_BTREE_DATA L"INDEX.BTR"
|
|
|
|
#define WMIREP_MAP_1 L"MAPPING1.MAP"
|
|
#define WMIREP_MAP_2 L"MAPPING2.MAP"
|
|
#define WMIREP_MAP_VER L"MAPPING.VER"
|
|
|
|
//Old files for upgrade purpose only
|
|
#define WMIREP_OBJECT_MAP L"OBJECTS.MAP"
|
|
#define WMIREP_OBJECT_MAP_NEW L"OBJECTS.MAP.NEW"
|
|
#define WMIREP_BTREE_MAP L"INDEX.MAP"
|
|
#define WMIREP_BTREE_MAP_NEW L"INDEX.MAP.NEW"
|
|
#define WMIREP_ROLL_FORWARD L"ROLL_FORWARD"
|
|
|
|
#include <vector>
|
|
#include <wstlallc.h>
|
|
#include <wstring.h>
|
|
#include <sync.h>
|
|
|
|
typedef LONG NTSTATUS;
|
|
|
|
struct SCachePage
|
|
{
|
|
BOOL m_bDirty;
|
|
DWORD m_dwPhysId;
|
|
LPBYTE m_pPage;
|
|
|
|
SCachePage() { m_bDirty = 0; m_dwPhysId = 0; m_pPage = 0; }
|
|
~SCachePage() { if (m_pPage) delete [] m_pPage; }
|
|
};
|
|
|
|
class AutoClose
|
|
{
|
|
HANDLE m_hHandle;
|
|
public:
|
|
AutoClose(HANDLE h) { m_hHandle = h; }
|
|
~AutoClose() { CloseHandle(m_hHandle); }
|
|
};
|
|
|
|
class CPageCache
|
|
{
|
|
private:
|
|
const wchar_t *m_wszStoreName;
|
|
|
|
DWORD m_dwPageSize;
|
|
DWORD m_dwCacheSize;
|
|
|
|
DWORD m_dwCachePromoteThreshold;
|
|
DWORD m_dwCacheSpillRatio;
|
|
|
|
DWORD m_dwLastFlushTime;
|
|
DWORD m_dwWritesSinceFlush;
|
|
DWORD m_dwLastCacheAccess;
|
|
DWORD m_dwReadHits;
|
|
DWORD m_dwReadMisses;
|
|
DWORD m_dwWriteHits;
|
|
DWORD m_dwWriteMisses;
|
|
|
|
HANDLE m_hFile;
|
|
|
|
// Page r/w cache
|
|
std::vector <SCachePage *, wbem_allocator<SCachePage *> > m_aCache;
|
|
public:
|
|
DWORD ReadPhysPage( // Does a real disk access
|
|
IN DWORD dwPage, // Always physical ID
|
|
OUT LPBYTE *pPageMem // Returns read-only pointer (copy of ptr in SCachePage struct)
|
|
);
|
|
|
|
DWORD WritePhysPage( // Does a real disk access
|
|
DWORD dwPageId, // Always physical ID
|
|
LPBYTE pPageMem // Read-only; doesn't acquire pointer
|
|
);
|
|
|
|
DWORD Spill();
|
|
DWORD Empty();
|
|
|
|
// Private methods
|
|
public:
|
|
CPageCache(const wchar_t *wszStoreName);
|
|
~CPageCache();
|
|
|
|
DWORD Init(
|
|
LPCWSTR pszFilename, // File
|
|
DWORD dwPageSize, // In bytes
|
|
DWORD dwCacheSize = 64, // Pages in cache
|
|
DWORD dwCachePromoteThreshold = 16, // When to ignore promote-to-front
|
|
DWORD dwCacheSpillRatio = 4 // How many additional pages to write on cache write-through
|
|
);
|
|
|
|
DWORD DeInit();
|
|
|
|
// Cache operations
|
|
|
|
DWORD Write( // Only usable from within a transaction
|
|
DWORD dwPhysId,
|
|
LPBYTE pPageMem // Acquires memory (operator new required)
|
|
);
|
|
|
|
DWORD Read(
|
|
IN DWORD dwPhysId,
|
|
OUT LPBYTE *pMem // Use operator delete
|
|
);
|
|
|
|
DWORD Flush();
|
|
|
|
DWORD GetFileSize(LARGE_INTEGER *pFileSize);
|
|
|
|
DWORD EmptyCache() { DWORD dwRet = Flush(); if (dwRet == ERROR_SUCCESS) Empty(); return dwRet; }
|
|
void Dump(FILE *f);
|
|
|
|
DWORD GetReadHits() { return m_dwReadHits; }
|
|
DWORD GetReadMisses() { return m_dwReadMisses; }
|
|
DWORD GetWriteHits() { return m_dwWriteHits; }
|
|
DWORD GetWriteMisses() { return m_dwWriteMisses; }
|
|
SIZE_T GetCacheSize(){ return m_aCache.size(); };
|
|
};
|
|
|
|
class CPageFile
|
|
{
|
|
private:
|
|
friend class CPageSource;
|
|
|
|
const wchar_t *m_wszStoreName;
|
|
|
|
LONG m_lRef;
|
|
DWORD m_dwPageSize;
|
|
DWORD m_dwCacheSpillRatio;
|
|
|
|
CRITICAL_SECTION m_cs;
|
|
bool m_bCsInit;
|
|
|
|
CPageCache m_Cache;
|
|
BOOL m_bInTransaction;
|
|
DWORD m_dwLastCheckpoint;
|
|
DWORD m_dwTransVersion;
|
|
|
|
// Generation A Mapping
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aPageMapA;
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aPhysFreeListA;
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aLogicalFreeListA;
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aReplacedPagesA;
|
|
DWORD m_dwPhysPagesA;
|
|
|
|
// Generation B Mapping
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aPageMapB;
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aPhysFreeListB;
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aLogicalFreeListB;
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aReplacedPagesB;
|
|
DWORD m_dwPhysPagesB;
|
|
|
|
std::vector <DWORD, wbem_allocator<DWORD> > m_aDeferredFreeList;
|
|
|
|
public: // temp for testing
|
|
// Internal methods
|
|
DWORD Trans_Begin();
|
|
DWORD Trans_Rollback();
|
|
DWORD Trans_Commit();
|
|
|
|
DWORD Trans_Checkpoint(HANDLE hFile);
|
|
|
|
DWORD InitFreeList();
|
|
DWORD ResyncMaps();
|
|
DWORD ReadMap(HANDLE hFile);
|
|
DWORD WriteMap(HANDLE hFile);
|
|
|
|
DWORD ValidateMapFile();
|
|
|
|
DWORD AllocPhysPage(DWORD *pdwId);
|
|
|
|
DWORD ReclaimLogicalPages(
|
|
DWORD dwCount,
|
|
DWORD *pdwId
|
|
);
|
|
|
|
DWORD GetTransVersion() { return m_dwTransVersion; }
|
|
void IncrementTransVersion(){ m_dwTransVersion++; }
|
|
void DumpFreeListInfo();
|
|
|
|
public:
|
|
|
|
CPageFile(const wchar_t *wszStoreName);
|
|
|
|
~CPageFile();
|
|
|
|
//First-time initializatoin of structure
|
|
DWORD Init(
|
|
WString &sMainFile,
|
|
DWORD dwRepPageSize,
|
|
DWORD dwCacheSize,
|
|
DWORD dwCacheSpillRatio
|
|
);
|
|
|
|
//Clear all caches and structures out
|
|
DWORD DeInit();
|
|
|
|
|
|
static DWORD RollForwardV1Maps(WString& sDirectory);
|
|
|
|
ULONG AddRef();
|
|
ULONG Release();
|
|
|
|
DWORD GetPage(
|
|
DWORD dwId, // page zero is admin page; doesn't require NewPage() call
|
|
DWORD dwFlags,
|
|
LPVOID pPage
|
|
);
|
|
|
|
DWORD PutPage(
|
|
DWORD dwId,
|
|
DWORD dwFlags,
|
|
LPVOID pPage
|
|
);
|
|
|
|
DWORD NewPage(
|
|
DWORD dwFlags,
|
|
DWORD dwCount,
|
|
DWORD *pdwFirstId
|
|
);
|
|
|
|
DWORD FreePage(
|
|
DWORD dwFlags,
|
|
DWORD dwId
|
|
);
|
|
|
|
DWORD GetPageSize() { return m_dwPageSize; }
|
|
DWORD GetNumPages() { return m_aPageMapB.size(); }
|
|
DWORD GetPhysPage(DWORD dwLogical) { return m_aPageMapB[dwLogical]; }
|
|
|
|
DWORD EmptyCache()
|
|
{
|
|
return m_Cache.EmptyCache();
|
|
}
|
|
|
|
#ifdef WMI_PRIVATE_DBG
|
|
DWORD CPageFile::DumpFileInformation(HANDLE hFile);
|
|
#endif
|
|
|
|
void Dump(FILE *f);
|
|
|
|
DWORD CompactPages(DWORD dwNumPages);
|
|
};
|
|
|
|
class CPageSource
|
|
{
|
|
private:
|
|
DWORD m_dwStatus;
|
|
DWORD m_dwPageSize;
|
|
|
|
DWORD m_dwCacheSize;
|
|
DWORD m_dwCacheSpillRatio;
|
|
|
|
DWORD m_dwLastCheckpoint;
|
|
|
|
WString m_sDirectory;
|
|
|
|
CPageFile m_BTreePF;
|
|
CPageFile m_ObjPF;
|
|
|
|
WString m_FileMainData;
|
|
WString m_FileMainBtr;
|
|
WString m_FileMap1;
|
|
WString m_FileMap2;
|
|
WString m_FileMapVer;
|
|
|
|
HANDLE m_hFileMap1;
|
|
HANDLE m_hFileMap2;
|
|
HANDLE m_hFileMapVer;
|
|
|
|
DWORD m_dwFileMapVer;
|
|
DWORD Startup();
|
|
|
|
DWORD OpenMapFiles();
|
|
DWORD CloseMapFiles();
|
|
|
|
DWORD V1ReposititoryExists(bool *pbV1RepositoryExists);
|
|
DWORD V2ReposititoryExists(bool *pbV2RepositoryExists);
|
|
DWORD UpgradeV1Maps();
|
|
|
|
DWORD DeleteRepository();
|
|
|
|
public:
|
|
CPageSource();
|
|
~CPageSource();
|
|
|
|
DWORD Init( );
|
|
|
|
DWORD Shutdown(DWORD dwFlags);
|
|
|
|
DWORD GetBTreePageFile(OUT CPageFile **pPF); // Use Release() when done
|
|
DWORD GetObjectHeapPageFile(OUT CPageFile **pPF); // Use Release() when done
|
|
|
|
// Transactions
|
|
|
|
DWORD BeginTrans();
|
|
DWORD CommitTrans();
|
|
DWORD RollbackTrans();
|
|
|
|
// Checkpoint
|
|
|
|
DWORD Checkpoint(bool bCompactPages);
|
|
|
|
// Cache discard
|
|
|
|
DWORD EmptyCaches();
|
|
|
|
void Dump(FILE *f);
|
|
|
|
//Compacts the last n physical pages of the files to the start of the file.
|
|
//It does this for the BTree and ObjHeap.
|
|
HRESULT CompactPages(DWORD dwNumPages);
|
|
|
|
static BOOL FileExists(LPCWSTR pFile, NTSTATUS& lastStatus);
|
|
|
|
};
|
|
|
|
|
|
#endif
|
|
|