Source code of Windows XP (NT5)
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.

284 lines
7.4 KiB

  1. /*--
  2. Copyright (c) 1999 Microsoft Corporation
  3. Module Name:
  4. dumpsdb.c
  5. Abstract:
  6. code for a dump tool for shim db files
  7. Author:
  8. dmunsil 02/02/2000
  9. Revision History:
  10. Notes:
  11. This program dumps a text representation of all of the data in a shim db file.
  12. --*/
  13. #define _UNICODE
  14. #define WIN
  15. #define FLAT_32
  16. #define TRUE_IF_WIN32 1
  17. #include <nt.h>
  18. #include <ntrtl.h>
  19. #include <nturtl.h>
  20. #define _WINDOWS
  21. #include <windows.h>
  22. #include <stdio.h>
  23. extern "C" {
  24. #include "shimdb.h"
  25. }
  26. BOOL bDumpDB(PDB pdb, TAGID tiParent, WCHAR *szIndent, BOOL bWithTagIDs);
  27. BOOL bGetTypeName(TAG tWhich, WCHAR *szName);
  28. extern "C" int __cdecl wmain(int argc, wchar_t *argv[])
  29. {
  30. PDB pdb;
  31. int nReturn = 0;
  32. LPWSTR szDB = NULL;
  33. BOOL bSuccess;
  34. BOOL bWithTagIDs = TRUE;
  35. WCHAR szIndent[500];
  36. WCHAR szArg[500];
  37. WCHAR szDbID[128];
  38. PSDBDATABASEINFO psdbInfo = NULL;
  39. if (argc < 2 || (argv[1][1] == '?')) {
  40. wprintf(L" Usage: dumpsdb foo.sdb > foo.txt\n");
  41. return 1;
  42. }
  43. if ((argv[1][0] == '/' || argv[1][0] == '-') &&
  44. (argv[1][1] == 'd' || argv[1][1] == 'D')) {
  45. bWithTagIDs = FALSE;
  46. szDB = argv[2];
  47. } else {
  48. szDB = argv[1];
  49. }
  50. // Open the DB.
  51. pdb = SdbOpenDatabase(szDB, DOS_PATH);
  52. if (pdb == NULL) {
  53. nReturn = 1;
  54. wprintf(L"Error: can't open DB \"%s\"\n", szDB);
  55. return 0;
  56. }
  57. SdbGetDatabaseInformationByName(szDB, &psdbInfo);
  58. SdbGUIDToString(&psdbInfo->guidDB, szDbID);
  59. wprintf(L"Dumping DB \"%s %s. Version %d.%d.\"\n",
  60. szDB,
  61. szDbID,
  62. psdbInfo->dwVersionMajor,
  63. psdbInfo->dwVersionMinor);
  64. wcscpy(szIndent, L"");
  65. SdbFreeDatabaseInformation(psdbInfo);
  66. bSuccess = bDumpDB(pdb, TAGID_ROOT, szIndent, bWithTagIDs);
  67. wprintf(L"Closing DB.\n");
  68. SdbCloseDatabase(pdb);
  69. return nReturn;
  70. }
  71. BOOL bGetTypeName(TAG tWhich, WCHAR *szName)
  72. {
  73. DWORD i;
  74. LPCWSTR pName = SdbTagToString(tWhich);
  75. if (NULL != pName) {
  76. wcscpy(szName, pName);
  77. return TRUE;
  78. }
  79. swprintf(szName, L"!unknown_tag!");
  80. return TRUE;
  81. }
  82. BOOL bDumpDB(PDB pdb, TAGID tiParent, WCHAR *szIndent, BOOL bWithTagIDs)
  83. {
  84. TAGID tiTemp;
  85. WCHAR szTemp[200];
  86. WCHAR szNewIndent[200];
  87. tiTemp = SdbGetFirstChild(pdb, tiParent);
  88. while (tiTemp) {
  89. TAG tWhich;
  90. TAG_TYPE ttType;
  91. DWORD dwData;
  92. LARGE_INTEGER liData;
  93. WCHAR szData[1000];
  94. tWhich = SdbGetTagFromTagID(pdb, tiTemp);
  95. ttType = GETTAGTYPE(tWhich);
  96. if (!bGetTypeName(tWhich, szTemp)) {
  97. wprintf(L"Error getting Tag name. Tag: 0x%4.4X\n", (DWORD)tWhich);
  98. return FALSE;
  99. }
  100. if (bWithTagIDs) {
  101. wprintf(L"%s0x%8.8X | 0x%4.4X | %-13s ", szIndent, tiTemp, tWhich, szTemp);
  102. } else {
  103. wprintf(L"%s%-13s ", szIndent, szTemp);
  104. if (wcsstr(szTemp, L"_TAGID")) {
  105. tiTemp = SdbGetNextChild(pdb, tiParent, tiTemp);
  106. continue;
  107. }
  108. }
  109. switch (ttType) {
  110. case TAG_TYPE_NULL:
  111. wprintf(L" | NULL |\n");
  112. break;
  113. case TAG_TYPE_BYTE:
  114. dwData = SdbReadBYTETag(pdb, tiTemp, 0);
  115. wprintf(L" | BYTE | 0x%2.2X\n", dwData);
  116. break;
  117. case TAG_TYPE_WORD:
  118. dwData = SdbReadWORDTag(pdb, tiTemp, 0);
  119. if (tWhich == TAG_INDEX_KEY || tWhich == TAG_INDEX_TAG) {
  120. // for index tags and keys, we'd like to see what the names are
  121. if (!bGetTypeName((TAG)dwData, szTemp)) {
  122. wprintf(L"Error getting Tag name. Tag: 0x%4.4X\n", dwData);
  123. return FALSE;
  124. }
  125. wprintf(L" | WORD | 0x%4.4X (%s)\n", dwData, szTemp);
  126. } else {
  127. wprintf(L" | WORD | 0x%4.4X\n", dwData);
  128. }
  129. break;
  130. case TAG_TYPE_DWORD:
  131. dwData = SdbReadDWORDTag(pdb, tiTemp, 0);
  132. wprintf(L" | DWORD | 0x%8.8X\n", dwData);
  133. break;
  134. case TAG_TYPE_QWORD:
  135. liData.QuadPart = SdbReadQWORDTag(pdb, tiTemp, 0);
  136. wprintf(L" | QWORD | 0x%8.8X%8.8X\n", liData.HighPart, liData.LowPart);
  137. break;
  138. case TAG_TYPE_STRINGREF:
  139. if (!SdbReadStringTag(pdb, tiTemp, szData, 1000 * sizeof(WCHAR))) {
  140. wcscpy(szData, L"(error)");
  141. }
  142. wprintf(L" | STRINGREF | %s\n", szData);
  143. break;
  144. case TAG_TYPE_STRING:
  145. dwData = SdbGetTagDataSize(pdb, tiTemp);
  146. if (!SdbReadStringTag(pdb, tiTemp, szData, 1000)) {
  147. wcscpy(szData, L"(error)");
  148. }
  149. wprintf(L" | STRING | Size 0x%8.8X | %s\n", dwData, szData);
  150. break;
  151. case TAG_TYPE_BINARY:
  152. dwData = SdbGetTagDataSize(pdb, tiTemp);
  153. wprintf(L" | BINARY | Size 0x%8.8X", dwData);
  154. switch(tWhich) {
  155. case TAG_INDEX_BITS:
  156. {
  157. char szKey[9];
  158. DWORD dwRecords;
  159. INDEX_RECORD *pRecords;
  160. DWORD i;
  161. wprintf(L"\n");
  162. ZeroMemory(szKey, 9);
  163. dwRecords = dwData / sizeof(INDEX_RECORD);
  164. pRecords = (INDEX_RECORD *)SdbGetBinaryTagData(pdb, tiTemp);
  165. for (i = 0; i < dwRecords; ++i) {
  166. char *szRevKey;
  167. int j;
  168. szRevKey = (char *)&pRecords[i].ullKey;
  169. for (j = 0; j < 8; ++j) {
  170. szKey[j] = isprint(szRevKey[7-j]) ? szRevKey[7-j] : '.';
  171. }
  172. if (bWithTagIDs) {
  173. wprintf(L"%s Key: 0x%I64X (\"%-8S\"), TAGID: 0x%08X\n",
  174. szIndent, pRecords[i].ullKey, szKey, pRecords[i].tiRef);
  175. } else {
  176. wprintf(L"%s Key: 0x%I64X (\"%-8S\")\n",
  177. szIndent, pRecords[i].ullKey, szKey);
  178. }
  179. }
  180. }
  181. break;
  182. case TAG_EXE_ID:
  183. case TAG_MSI_PACKAGE_ID:
  184. case TAG_DATABASE_ID:
  185. // this is exe id -- which happens to be GUID which we do understand
  186. {
  187. GUID *pGuid;
  188. UNICODE_STRING sGuid;
  189. pGuid = (GUID*)SdbGetBinaryTagData(pdb, tiTemp);
  190. // convert this thing to string
  191. if (pGuid && NT_SUCCESS(RtlStringFromGUID(*pGuid, &sGuid))) {
  192. wprintf(L" | %s", sGuid.Buffer);
  193. RtlFreeUnicodeString(&sGuid);
  194. }
  195. wprintf(L"\n");
  196. }
  197. break;
  198. default:
  199. wprintf(L"\n");
  200. break;
  201. }
  202. break;
  203. case TAG_TYPE_LIST:
  204. dwData = SdbGetTagDataSize(pdb, tiTemp);
  205. wprintf(L" | LIST | Size 0x%8.8X\n", dwData);
  206. wcscpy(szNewIndent, szIndent);
  207. wcscat(szNewIndent, L" ");
  208. bDumpDB(pdb, tiTemp, szNewIndent, bWithTagIDs);
  209. wprintf(L"%s-end- %s\n", szIndent, szTemp);
  210. break;
  211. default:
  212. dwData = SdbGetTagDataSize(pdb, tiTemp);
  213. wprintf(L" | UNKNOWN | Size 0x%8.8X\n", dwData);
  214. break;
  215. }
  216. tiTemp = SdbGetNextChild(pdb, tiParent, tiTemp);
  217. }
  218. return TRUE;
  219. }