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.

486 lines
13 KiB

  1. //+---------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. // Copyright (C) Microsoft Corporation, 1992 - 1998.
  5. //
  6. // File: Main.cxx
  7. //
  8. // Contents: Main file for CI security dump utility
  9. //
  10. // History: 29-Jul-1998 KyleP Created
  11. //
  12. //----------------------------------------------------------------------------
  13. #include <stdio.h>
  14. #include <windows.h>
  15. #include <aclapi.h>
  16. typedef ULONG SDID;
  17. //
  18. // Copied from SecCache.hxx (NtCiUtil directory)
  19. //
  20. const USHORT SECSTORE_REC_SIZE = 64;
  21. const ULONG SECSTORE_HASH_SIZE = 199;
  22. struct SSdHeaderRecord
  23. {
  24. ULONG cbSD; // size in bytes of the security descriptor
  25. ULONG ulHash; // the hash of the security descriptor
  26. SDID iHashChain; // index to previous entry for hash bucket
  27. };
  28. //
  29. // Used for mapping bitmasks to text.
  30. //
  31. struct SPermDisplay
  32. {
  33. DWORD Perm;
  34. char * Display;
  35. };
  36. //
  37. // Local constants and function prototypes
  38. //
  39. unsigned const SixtyFourK = 1024 * 64;
  40. void DisplayTrustee( TRUSTEE const & Trustee );
  41. void DisplayACE( char const * pszPreface, unsigned cACE, EXPLICIT_ACCESS * pACE );
  42. void DisplayMode( DWORD mode );
  43. void DisplayInheritance( DWORD Inherit );
  44. void DisplayPerms( DWORD grfAccess );
  45. void Display( DWORD grfAccess, SPermDisplay aPerm[], unsigned cPerm, unsigned cDisplay = 0 );
  46. void Usage();
  47. //+---------------------------------------------------------------------------
  48. //
  49. // Function: wmain, public
  50. //
  51. // Synopsis: Program entry point. Iterates and displays SDID mapping.
  52. //
  53. // Arguments: [argc] -- Argument count
  54. // [argv] -- Program arguments
  55. //
  56. // History: 29-Jul-1998 KyleP Created
  57. //
  58. //----------------------------------------------------------------------------
  59. extern "C" int __cdecl wmain( int argc, WCHAR * argv[] )
  60. {
  61. if ( argc != 2 )
  62. {
  63. Usage();
  64. return 1;
  65. }
  66. //
  67. // Open handle
  68. //
  69. WCHAR wszSecFile[MAX_PATH];
  70. wcscpy( wszSecFile, argv[1] );
  71. wcscat( wszSecFile, L"\\CiST0000.001" );
  72. HANDLE h = CreateFile( wszSecFile,
  73. GENERIC_READ,
  74. FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
  75. 0,
  76. OPEN_EXISTING,
  77. 0,
  78. 0 );
  79. if ( INVALID_HANDLE_VALUE == h )
  80. {
  81. printf( "Can't open file %ws. Error %u\n", wszSecFile, GetLastError() );
  82. return GetLastError();
  83. }
  84. //
  85. // Read until done.
  86. //
  87. BYTE abTemp[SixtyFourK];
  88. DWORD cbRead;
  89. int i = 0;
  90. SSdHeaderRecord Header;
  91. while ( ReadFile( h,
  92. &Header,
  93. sizeof(Header),
  94. &cbRead,
  95. 0 ) )
  96. {
  97. if ( 0 == Header.cbSD )
  98. break;
  99. i++;
  100. printf( "SDID %u / 0x%x (cbSD = %u bytes)\n", i, i, Header.cbSD );
  101. //
  102. // Read rest of first record.
  103. //
  104. if ( !ReadFile( h,
  105. abTemp,
  106. SECSTORE_REC_SIZE - sizeof(Header) + 4,
  107. &cbRead,
  108. 0 ) )
  109. {
  110. printf( "Error %u reading file\n", GetLastError() );
  111. return 1;
  112. }
  113. //
  114. // Read additional records, which together create one security descriptor
  115. //
  116. if ( Header.cbSD > (SECSTORE_REC_SIZE - sizeof(Header)) )
  117. {
  118. unsigned iCurrent = SECSTORE_REC_SIZE - sizeof(Header);
  119. for ( unsigned cLeft = (Header.cbSD - SECSTORE_REC_SIZE + sizeof(Header) - 1) / SECSTORE_REC_SIZE + 1;
  120. cLeft > 0;
  121. cLeft-- )
  122. {
  123. if ( !ReadFile( h,
  124. abTemp + iCurrent,
  125. SECSTORE_REC_SIZE + 4,
  126. &cbRead,
  127. 0 ) )
  128. {
  129. printf( "Error %u reading file\n", GetLastError() );
  130. return 1;
  131. }
  132. i++;
  133. iCurrent += SECSTORE_REC_SIZE;
  134. }
  135. }
  136. SECURITY_DESCRIPTOR * pSD = (SECURITY_DESCRIPTOR *)abTemp;
  137. //
  138. // Create a human-readable descriptor
  139. //
  140. TRUSTEE * pOwner;
  141. TRUSTEE * pGroup;
  142. DWORD cACE;
  143. EXPLICIT_ACCESS * pACE;
  144. DWORD dwError = LookupSecurityDescriptorParts( &pOwner,
  145. &pGroup,
  146. &cACE,
  147. &pACE,
  148. 0,
  149. 0,
  150. pSD );
  151. //
  152. // And display it.
  153. //
  154. if ( ERROR_SUCCESS == dwError )
  155. {
  156. if ( 0 != pOwner )
  157. {
  158. printf( "Owner: " );
  159. DisplayTrustee( *pOwner );
  160. LocalFree( pOwner );
  161. }
  162. if ( 0 != pGroup )
  163. {
  164. printf( "Group: " );
  165. DisplayTrustee( *pGroup );
  166. LocalFree( pGroup );
  167. }
  168. if ( cACE > 0 )
  169. {
  170. printf( "Access: " );
  171. DisplayACE( " ", cACE, pACE );
  172. LocalFree( pACE );
  173. }
  174. }
  175. else
  176. printf( "LookupSecurityDescriptorParts returned %u\n", dwError );
  177. printf( "\n\n" );
  178. }
  179. CloseHandle( h );
  180. return 0;
  181. }
  182. //+---------------------------------------------------------------------------
  183. //
  184. // Function: DisplayTrustee
  185. //
  186. // Synopsis: Prints out trustee (user, group, etc.)
  187. //
  188. // Arguments: [Trustee] -- Trustee description
  189. //
  190. // History: 29-Jul-1998 KyleP Created
  191. //
  192. //----------------------------------------------------------------------------
  193. char * aszTrusteeType[] = { "Unknown", // TRUSTEE_IS_UNKNOWN
  194. "User", // TRUSTEE_IS_USER,
  195. "Group", // TRUSTEE_IS_GROUP,
  196. "Domain", // TRUSTEE_IS_DOMAIN,
  197. "Alias", // TRUSTEE_IS_ALIAS,
  198. "Group", // TRUSTEE_IS_WELL_KNOWN_GROUP,
  199. "Deleted", // TRUSTEE_IS_DELETED,
  200. "Invalid" }; // TRUSTEE_IS_INVALID
  201. void DisplayTrustee( TRUSTEE const & Trustee )
  202. {
  203. if ( TRUSTEE_IS_NAME == Trustee.TrusteeForm )
  204. {
  205. printf( "%ws (%s)", Trustee.ptstrName, aszTrusteeType[Trustee.TrusteeType] );
  206. }
  207. else if ( TRUSTEE_IS_SID == Trustee.TrusteeForm )
  208. {
  209. }
  210. else
  211. printf( "Invalid Trustee form\n" );
  212. }
  213. //+---------------------------------------------------------------------------
  214. //
  215. // Function: DisplayACE
  216. //
  217. // Synopsis: Prints out Access Control Entry(ies)
  218. //
  219. // Arguments: [pszPreface] -- String to append at beginning of each line.
  220. // [cACE] -- Count of entries
  221. // [pACE] -- Array of entries
  222. //
  223. // History: 29-Jul-1998 KyleP Created
  224. //
  225. //----------------------------------------------------------------------------
  226. void DisplayACE( char const * pszPreface, unsigned cACE, EXPLICIT_ACCESS * pACE )
  227. {
  228. for ( unsigned i = 0; i < cACE; i++ )
  229. {
  230. if ( 0 != i )
  231. printf( "%s", pszPreface );
  232. DisplayTrustee( pACE[i].Trustee );
  233. printf( " : " );
  234. DisplayMode( pACE[i].grfAccessMode );
  235. printf( " /" );
  236. DisplayInheritance( pACE[i].grfInheritance );
  237. printf( " /" );
  238. DisplayPerms( pACE[i].grfAccessPermissions );
  239. printf( "\n" );
  240. }
  241. //ACCESS_MODE grfAccessMode; DWORD grfInheritance;
  242. }
  243. //+---------------------------------------------------------------------------
  244. //
  245. // Function: DisplayMode, private
  246. //
  247. // Synopsis: Prints out access mode (Set or Deny access)
  248. //
  249. // Arguments: [mode] -- Access mode
  250. //
  251. // History: 29-Jul-1998 KyleP Created
  252. //
  253. //----------------------------------------------------------------------------
  254. char * aszAccessDisplay[] = { "NOT_USED",
  255. "GRANT_ACCESS",
  256. "SET_ACCESS",
  257. "DENY_ACCESS",
  258. "REVOKE_ACCESS",
  259. "SET_AUDIT_SUCCESS",
  260. "SET_AUDIT_FAILURE" };
  261. void DisplayMode( DWORD mode )
  262. {
  263. printf( "%s", aszAccessDisplay[mode] );
  264. }
  265. //+---------------------------------------------------------------------------
  266. //
  267. // Function: DisplayInheritance, private
  268. //
  269. // Synopsis: Prints out inheritance, both up (to parent) and down (to children)
  270. //
  271. // Arguments: [Inherit] -- Inheritance bitmask
  272. //
  273. // History: 29-Jul-1998 KyleP Created
  274. //
  275. //----------------------------------------------------------------------------
  276. SPermDisplay aInheritDisplay[] = {
  277. //{ INHERITED_ACCESS_ENTRY, "(inherited)" },
  278. { INHERITED_PARENT, "(inherited from parent)" },
  279. { INHERITED_GRANDPARENT, "(inherited from grandparent)" },
  280. { SUB_OBJECTS_ONLY_INHERIT, "SUB_OBJECTS_ONLY" },
  281. { SUB_CONTAINERS_ONLY_INHERIT, "SUB_CONTAINERS_ONLY" },
  282. { SUB_CONTAINERS_AND_OBJECTS_INHERIT, "SUB_CONTAINERS_AND_OBJECTS" },
  283. { INHERIT_NO_PROPAGATE, "INHERIT_NO_PROPAGATE" },
  284. { INHERIT_ONLY, "INHERIT_ONLY" } };
  285. void DisplayInheritance( DWORD Inherit )
  286. {
  287. if ( NO_INHERITANCE == Inherit )
  288. printf( "\n\t\t(not inherited)" );
  289. else
  290. Display( Inherit, aInheritDisplay, sizeof(aInheritDisplay)/sizeof(aInheritDisplay[0]) );
  291. }
  292. //+---------------------------------------------------------------------------
  293. //
  294. // Function: DisplayPerms
  295. //
  296. // Synopsis: Displays file permissions
  297. //
  298. // Arguments: [grfAccess] -- Access permission bitmask
  299. //
  300. // History: 29-Jul-1998 KyleP Created
  301. //
  302. //----------------------------------------------------------------------------
  303. SPermDisplay aPermDisplay[] = {
  304. { FILE_READ_DATA, "READ_DATA" },
  305. { FILE_WRITE_DATA, "WRITE_DATA" },
  306. { FILE_ADD_FILE, "ADD_FILE" },
  307. { FILE_APPEND_DATA, "APPEND_DATA" },
  308. { FILE_ADD_SUBDIRECTORY, "ADD_SUBDIRECTORY" },
  309. { FILE_CREATE_PIPE_INSTANCE, "CREATE_PIPE_INSTANCE" },
  310. { FILE_READ_EA, "READ_EA" },
  311. { FILE_WRITE_EA, "WRITE_EA" },
  312. { FILE_EXECUTE, "EXECUTE" },
  313. { FILE_TRAVERSE, "TRAVERSE" },
  314. { FILE_DELETE_CHILD, "DELETE_CHILD" },
  315. { FILE_READ_ATTRIBUTES, "READ_ATTRIBUTES" },
  316. { FILE_WRITE_ATTRIBUTES, "WRITE_ATTRIBUTES" },
  317. { DELETE, "DELETE" },
  318. { READ_CONTROL, "READ_CONTROL" },
  319. { WRITE_DAC, "WRITE_DAC" },
  320. { WRITE_OWNER, "WRITE_OWNER" },
  321. { SYNCHRONIZE, "SYNCHRONIZE" },
  322. { GENERIC_READ, "GENERIC_READ" },
  323. { GENERIC_WRITE, "GENERIC_WRITE" },
  324. { GENERIC_EXECUTE, "GENERIC_EXECUTE" } };
  325. void DisplayPerms( DWORD grfAccess )
  326. {
  327. BOOL cDisplay = 0;
  328. DWORD grfRemove = 0;
  329. printf( "\n\t\t" );
  330. //
  331. // First, get rid of the basics...
  332. //
  333. if ( (grfAccess & FILE_GENERIC_READ) == FILE_GENERIC_READ )
  334. {
  335. printf( "GENERIC_READ" );
  336. grfRemove = FILE_GENERIC_READ;
  337. cDisplay++;
  338. }
  339. if ( (grfAccess & FILE_GENERIC_WRITE) == FILE_GENERIC_WRITE )
  340. {
  341. if ( 0 != cDisplay )
  342. printf( " | " );
  343. printf( "GENERIC_WRITE" );
  344. grfRemove = grfRemove | FILE_GENERIC_WRITE;
  345. cDisplay++;
  346. }
  347. if ( (grfAccess & FILE_GENERIC_EXECUTE) == FILE_GENERIC_EXECUTE )
  348. {
  349. if ( 0 != cDisplay )
  350. printf( " | " );
  351. if ( 0 == (cDisplay % 2) )
  352. printf( " \n\t\t" );
  353. printf( "GENERIC_EXECUTE" );
  354. grfRemove = grfRemove | FILE_GENERIC_EXECUTE;
  355. cDisplay++;
  356. }
  357. //
  358. // Now, individual permissions.
  359. //
  360. DWORD grfRemainder = grfAccess & ~grfRemove;
  361. Display( grfRemainder, aPermDisplay, sizeof(aPermDisplay)/sizeof(aPermDisplay[0]), cDisplay );
  362. printf( " (0x%x)", grfAccess );
  363. }
  364. //+---------------------------------------------------------------------------
  365. //
  366. // Function: Display, private
  367. //
  368. // Synopsis: Print bit masks
  369. //
  370. // Arguments: [grfAccess] -- Bit mask
  371. // [aPerm] -- Description of bits
  372. // [cPerm] -- Count of entries in [aPerm]
  373. // [cDisplay] -- Number of entries already displayed on
  374. // current line by caller.
  375. //
  376. // History: 29-Jul-1998 KyleP Created
  377. //
  378. //----------------------------------------------------------------------------
  379. void Display( DWORD grfAccess, SPermDisplay aPerm[], unsigned cPerm, unsigned cDisplay )
  380. {
  381. for ( unsigned i = 0; i < cPerm ; i++ )
  382. {
  383. if ( grfAccess & aPerm[i].Perm )
  384. {
  385. if ( 0 != cDisplay )
  386. printf( " | " );
  387. if ( 0 == (cDisplay % 2) )
  388. printf( " \n\t\t" );
  389. printf( "%s", aPerm[i].Display );
  390. cDisplay++;
  391. }
  392. }
  393. }
  394. //+---------------------------------------------------------------------------
  395. //
  396. // Function: Usage
  397. //
  398. // Synopsis: Displays program usage
  399. //
  400. // History: 29-Jul-1998 KyleP Created
  401. //
  402. //----------------------------------------------------------------------------
  403. void Usage()
  404. {
  405. printf( "Usage: DumpSec <Path to catalog>\n" );
  406. }