Leaked source code of windows server 2003
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.

2296 lines
57 KiB

  1. #include "brian.h"
  2. //
  3. // Local constants and procedure declarations.
  4. //
  5. #define CHAR_POSITION 51
  6. #define COPY_BUFF_SRC_DEFAULT 0
  7. #define COPY_BUFF_DST_DEFAULT 0
  8. #define COPY_BUFF_SRC_OFF_DEFAULT 0
  9. #define COPY_BUFF_DST_OFF_DEFAULT 0
  10. #define COPY_BUFF_LENGTH_DEFAULT 0
  11. #define DISPLAY_INDEX_DEFAULT 0
  12. #define DISPLAY_OFFSET_DEFAULT 0
  13. #define DISPLAY_LENGTH_DEFAULT 0x100
  14. #define ALLOC_ZERO_BITS_DEFAULT 0
  15. #define ALLOC_REGION_SIZE_DEFAULT 0x100
  16. #define ALLOC_VERBOSE_DEFAULT TRUE
  17. #define ALLOC_DISPLAY_PARMS_DEFAULT FALSE
  18. ULONG
  19. PrintDwords (
  20. IN PULONG BufferAddress,
  21. IN ULONG CountWords
  22. );
  23. ULONG
  24. PrintWords (
  25. IN PUSHORT BufferAddress,
  26. IN ULONG CountWords
  27. );
  28. ULONG
  29. PrintBytes (
  30. IN PCHAR BufferAddress,
  31. IN ULONG CountChars
  32. );
  33. VOID
  34. PrintChars(
  35. IN PCHAR BufferAddress,
  36. IN ULONG CountChars
  37. );
  38. VOID
  39. ClearBuffer(
  40. IN ULONG Index
  41. );
  42. VOID
  43. DisplayBuffer (
  44. IN ULONG Index,
  45. IN ULONG StartOffset,
  46. IN ULONG DisplayLength,
  47. IN ULONG DisplaySize
  48. );
  49. VOID
  50. CopyBuffer(
  51. IN ULONG SrcIndex,
  52. IN ULONG DstIndex,
  53. IN ULONG Length,
  54. IN ULONG SrcOffset,
  55. IN ULONG DstOffset
  56. );
  57. VOID
  58. FillBuffer (
  59. IN ULONG Index,
  60. IN PVOID Structure,
  61. IN ULONG Length
  62. );
  63. NTSTATUS
  64. FullAllocMem(
  65. IN ULONG ZeroBits,
  66. IN OUT PSIZE_T RegionSize,
  67. OUT PULONG BufferIndex,
  68. IN BOOLEAN VerboseResults,
  69. IN BOOLEAN DisplayParms
  70. );
  71. NTSTATUS
  72. FullDeallocMem(
  73. IN ULONG Index,
  74. IN BOOLEAN VerboseResults,
  75. IN BOOLEAN DisplayParms
  76. );
  77. VOID
  78. InitBuffers (
  79. )
  80. {
  81. NtCreateEvent( &BufferEvent, SYNCHRONIZE | GENERIC_READ | GENERIC_WRITE | GENERIC_EXECUTE,
  82. NULL, SynchronizationEvent, TRUE );
  83. RtlZeroMemory( Buffers, sizeof( Buffers ));
  84. }
  85. VOID
  86. UninitBuffers (
  87. )
  88. {
  89. USHORT Index;
  90. //
  91. // Deallocate any buffers remaining.
  92. //
  93. for (Index = 0; Index < MAX_BUFFERS; Index++) {
  94. DeallocateBuffer( Index );
  95. }
  96. }
  97. NTSTATUS
  98. AllocateBuffer (
  99. IN ULONG ZeroBits,
  100. IN OUT PSIZE_T RegionSize,
  101. OUT PULONG BufferIndex
  102. )
  103. {
  104. NTSTATUS Status;
  105. PVOID BufferAddress;
  106. ULONG Index;
  107. BufferAddress = NULL;
  108. //
  109. // Wait for the buffer event.
  110. //
  111. if ((Status = NtWaitForSingleObject( BufferEvent,
  112. FALSE,
  113. NULL )) != STATUS_SUCCESS) {
  114. return Status;
  115. }
  116. try {
  117. //
  118. // Find an available index. Return STATUS_INSUFFICIENT_RESOURCES
  119. // if not found.
  120. //
  121. for (Index = 0; Index < MAX_BUFFERS; Index++) {
  122. if (!Buffers[Index].Used) {
  123. break;
  124. }
  125. }
  126. if (Index >= MAX_BUFFERS) {
  127. Status = STATUS_INSUFFICIENT_RESOURCES;
  128. //
  129. // Otherwise allocate the virtual memory. If no error occurs, then
  130. // store the data in the buffer array.
  131. //
  132. } else if ((Status = NtAllocateVirtualMemory( NtCurrentProcess(),
  133. &BufferAddress,
  134. ZeroBits,
  135. RegionSize,
  136. MEM_COMMIT,
  137. PAGE_READWRITE )) == STATUS_SUCCESS) {
  138. Buffers[Index].Buffer = BufferAddress;
  139. Buffers[Index].Length = (ULONG) *RegionSize;
  140. Buffers[Index].Used = TRUE;
  141. }
  142. //
  143. // Set the buffer event back to the signalled state.
  144. //
  145. *BufferIndex = Index;
  146. try_return( NOTHING );
  147. try_exit: NOTHING;
  148. } finally {
  149. if (AbnormalTermination()) {
  150. printf( "\nAllocate Buffer: Abnormal termination\n" );
  151. }
  152. NtSetEvent( BufferEvent, NULL );
  153. }
  154. return Status;
  155. }
  156. NTSTATUS
  157. DeallocateBuffer (
  158. IN ULONG Index
  159. )
  160. {
  161. NTSTATUS Status;
  162. //
  163. // Wait for the buffer event.
  164. //
  165. if ((Status = NtWaitForSingleObject( BufferEvent,
  166. FALSE,
  167. NULL )) != STATUS_SUCCESS) {
  168. return Status;
  169. }
  170. try {
  171. if (Index <= MAX_BUFFERS
  172. && Buffers[Index].Used) {
  173. SIZE_T RegionSize = Buffers[Index].Length;
  174. Status = NtFreeVirtualMemory( NtCurrentProcess(),
  175. (PVOID *) &Buffers[Index].Buffer,
  176. &RegionSize,
  177. MEM_RELEASE );
  178. Buffers[Index].Used = FALSE;
  179. }
  180. try_return( NOTHING );
  181. try_exit: NOTHING;
  182. } finally {
  183. if (AbnormalTermination()) {
  184. printf( "\nDeallocate Buffer: Abnormal termination\n" );
  185. }
  186. NtSetEvent( BufferEvent, NULL );
  187. }
  188. return Status;
  189. }
  190. BOOLEAN
  191. BufferInfo (
  192. IN ULONG Index,
  193. OUT PVOID *BufferAddress,
  194. OUT PULONG RegionSize
  195. )
  196. {
  197. if (Index >= MAX_BUFFERS || !Buffers[Index].Used) {
  198. return FALSE;
  199. }
  200. *BufferAddress = Buffers[Index].Buffer;
  201. *RegionSize = Buffers[Index].Length;
  202. return TRUE;
  203. }
  204. VOID
  205. InputClearBuffer(
  206. IN PCHAR ParamBuffer
  207. )
  208. {
  209. ULONG Index;
  210. BOOLEAN LastInput;
  211. BOOLEAN ParmSpecified;
  212. Index = 0;
  213. ParmSpecified = FALSE;
  214. LastInput = TRUE;
  215. //
  216. // While there is more input, analyze the parameter and update the
  217. // query flags.
  218. //
  219. while (TRUE) {
  220. ULONG DummyCount;
  221. //
  222. // Swallow leading white spaces.
  223. //
  224. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  225. if (*ParamBuffer) {
  226. //
  227. // If the next parameter is legal then check the paramter value.
  228. // Update the parameter value.
  229. //
  230. if ((*ParamBuffer == '-'
  231. || *ParamBuffer == '/')
  232. && (ParamBuffer++, *ParamBuffer != '\0')) {
  233. //
  234. // Switch on the next character.
  235. //
  236. switch( *ParamBuffer ) {
  237. //
  238. // Check buffer index.
  239. //
  240. case 'b' :
  241. case 'B' :
  242. //
  243. // Move to the next character, as long as there
  244. // are no white spaces continue analyzing letters.
  245. // On the first bad letter, skip to the next
  246. // parameter.
  247. //
  248. ParamBuffer++;
  249. Index = AsciiToInteger( ParamBuffer );
  250. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  251. ParmSpecified = TRUE;
  252. break;
  253. default :
  254. //
  255. // Swallow to the next white space and continue the
  256. // loop.
  257. //
  258. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  259. }
  260. }
  261. //
  262. // Else the text is invalid, skip the entire block.
  263. //
  264. //
  265. //
  266. // Else if there is no input then exit.
  267. //
  268. } else if ( LastInput ) {
  269. break;
  270. //
  271. // Else try to read another line for open parameters.
  272. //
  273. } else {
  274. }
  275. }
  276. //
  277. // If no parameters were received then display the syntax message.
  278. //
  279. if (!ParmSpecified) {
  280. printf( "\n Usage: clb -b<digits> \n" );
  281. printf( "\n -b<digits> Buffer index" );
  282. printf( "\n\n" );
  283. //
  284. // Else call our copy buffer routine.
  285. //
  286. } else {
  287. ClearBuffer( Index );
  288. }
  289. return;
  290. }
  291. VOID
  292. ClearBuffer(
  293. IN ULONG Index
  294. )
  295. {
  296. //
  297. // Check for an invalid index.
  298. //
  299. if (!Buffers[Index].Used) {
  300. printf( "\nClearBuffer: Invalid buffer" );
  301. } else {
  302. RtlZeroMemory( Buffers[Index].Buffer, Buffers[Index].Length );
  303. }
  304. return;
  305. }
  306. VOID
  307. DisplayBuffer (
  308. IN ULONG Index,
  309. IN ULONG StartOffset,
  310. IN ULONG DisplayLength,
  311. IN ULONG DisplaySize
  312. )
  313. {
  314. //
  315. // If the index is unused, display message but take no action.
  316. //
  317. if (!Buffers[Index].Used) {
  318. printf( "\nDisplayBuffer: Index refers to invalid buffer" );
  319. //
  320. // Else if the start offset is invalid, then display error
  321. // message.
  322. //
  323. } else if (StartOffset >= Buffers[Index].Length) {
  324. printf( "\nDisplayBuffer: Start offset is invalid" );
  325. //
  326. // Else compute the legal display length and output to the screen.
  327. //
  328. } else {
  329. ULONG LegalLength;
  330. ULONG FullLines;
  331. PCHAR BufferAddress;
  332. ULONG SpacesFilled;
  333. //
  334. // The legal display length is the minimum of the remaining
  335. // bytes in the buffer and the desired display length.
  336. //
  337. LegalLength = Buffers[Index].Length - StartOffset;
  338. LegalLength = min( LegalLength, DisplayLength );
  339. BufferAddress = Buffers[Index].Buffer;
  340. //
  341. // Display the display information.
  342. //
  343. printf( "\nIndex -> %u, Buffer Base -> %p, ", Index, BufferAddress );
  344. printf( "Buffer Offset -> %08lx, Bytes -> %u", StartOffset, LegalLength );
  345. printf( "\n" );
  346. BufferAddress += StartOffset;
  347. //
  348. // Compute the number and display the full lines.
  349. //
  350. FullLines = LegalLength / 16;
  351. while (FullLines--) {
  352. if (DisplaySize == sizeof( UCHAR )) {
  353. PrintBytes( BufferAddress, 16 );
  354. } else if (DisplaySize == sizeof( WCHAR )) {
  355. PrintWords( (PVOID) BufferAddress, 8 );
  356. } else {
  357. PrintDwords( (PVOID) BufferAddress, 4 );
  358. }
  359. printf( " " );
  360. PrintChars( BufferAddress, 16 );
  361. BufferAddress += 16;
  362. }
  363. //
  364. // Display the remaining bytes.
  365. //
  366. if (DisplaySize == sizeof( UCHAR )) {
  367. SpacesFilled = PrintBytes( BufferAddress, LegalLength % 16 );
  368. } else if (DisplaySize == sizeof( WCHAR )) {
  369. SpacesFilled = PrintWords( (PVOID) BufferAddress, LegalLength % 8 );
  370. } else {
  371. SpacesFilled = PrintDwords( (PVOID) BufferAddress, LegalLength % 4 );
  372. }
  373. if (SpacesFilled) {
  374. SpacesFilled = CHAR_POSITION - SpacesFilled;
  375. while ( SpacesFilled-- ) {
  376. printf( " " );
  377. }
  378. }
  379. PrintChars( BufferAddress, LegalLength % 16 );
  380. printf( "\n\n" );
  381. }
  382. return;
  383. }
  384. ULONG
  385. PrintBytes (
  386. IN PCHAR BufferAddress,
  387. IN ULONG CountChars
  388. )
  389. {
  390. ULONG CountSpaces;
  391. ULONG RemainingChars;
  392. //
  393. // Initialize the local variables.
  394. //
  395. CountSpaces = CountChars * 3 + (CountChars ? 1 : 0);
  396. RemainingChars = CountChars - min( CountChars, 8 );
  397. CountChars = min( CountChars, 8 );
  398. //
  399. // Print the first 8 bytes (if possible).
  400. //
  401. if (CountChars) {
  402. printf( "\n" );
  403. while (CountChars--) {
  404. printf( "%02x ", *((PUCHAR) BufferAddress++) );
  405. }
  406. //
  407. // If more bytes, then add a blank space and print the rest of the
  408. // bytes.
  409. //
  410. printf( " " );
  411. while (RemainingChars--) {
  412. printf( "%02x ", *((PUCHAR) BufferAddress++) );
  413. }
  414. }
  415. //
  416. // Return the number of spaces used.
  417. //
  418. return CountSpaces;
  419. }
  420. ULONG
  421. PrintWords (
  422. IN PWCHAR BufferAddress,
  423. IN ULONG CountWords
  424. )
  425. {
  426. ULONG CountSpaces;
  427. ULONG RemainingWords;
  428. //
  429. // Initialize the local variables.
  430. //
  431. CountSpaces = CountWords * 5 + (CountWords ? 1 : 0);
  432. RemainingWords = CountWords - min( CountWords, 4 );
  433. CountWords = min( CountWords, 4 );
  434. //
  435. // Print the first 4 words (if possible).
  436. //
  437. if (CountWords) {
  438. printf( "\n" );
  439. while (CountWords--) {
  440. printf( "%04x ", *((PWCHAR) BufferAddress++) );
  441. }
  442. //
  443. // If more bytes, then add a blank space and print the rest of the
  444. // bytes.
  445. //
  446. printf( " " );
  447. while (RemainingWords--) {
  448. printf( "%04x ", *((PWCHAR) BufferAddress++) );
  449. }
  450. }
  451. //
  452. // Return the number of spaces used.
  453. //
  454. return CountSpaces;
  455. }
  456. ULONG
  457. PrintDwords (
  458. IN PULONG BufferAddress,
  459. IN ULONG CountDwords
  460. )
  461. {
  462. ULONG CountSpaces;
  463. ULONG RemainingDwords;
  464. //
  465. // Initialize the local variables.
  466. //
  467. CountSpaces = CountDwords * 7 + (CountDwords ? 1 : 0);
  468. RemainingDwords = CountDwords - min( CountDwords, 8 );
  469. CountDwords = min( CountDwords, 8 );
  470. //
  471. // Print the first 2 Dwords (if possible).
  472. //
  473. if (CountDwords) {
  474. printf( "\n" );
  475. while (CountDwords--) {
  476. printf( "%08x ", *((PULONG) BufferAddress++) );
  477. }
  478. //
  479. // If more bytes, then add a blank space and print the rest of the
  480. // bytes.
  481. //
  482. printf( " " );
  483. while (RemainingDwords--) {
  484. printf( "%08x ", *((PULONG) BufferAddress++) );
  485. }
  486. }
  487. //
  488. // Return the number of spaces used.
  489. //
  490. return CountSpaces;
  491. }
  492. VOID
  493. PrintChars(
  494. IN PCHAR BufferAddress,
  495. IN ULONG CountChars
  496. )
  497. {
  498. ULONG RemainingChars;
  499. //
  500. // Initialize the local variables.
  501. //
  502. RemainingChars = CountChars - min( CountChars, 8 );
  503. CountChars = min( CountChars, 8 );
  504. //
  505. // Print the first 8 bytes (if possible).
  506. //
  507. if (CountChars) {
  508. while (CountChars--) {
  509. if (*BufferAddress > 31
  510. && *BufferAddress != 127) {
  511. printf( "%c", *BufferAddress );
  512. } else {
  513. printf( "." );
  514. }
  515. BufferAddress++;
  516. }
  517. //
  518. // If more bytes, then add a blank space and print the rest of the
  519. // bytes.
  520. //
  521. printf( " " );
  522. while (RemainingChars--) {
  523. if (*BufferAddress > 31
  524. && *BufferAddress != 127) {
  525. printf( "%c", *BufferAddress );
  526. } else {
  527. printf( "." );
  528. }
  529. BufferAddress++;
  530. }
  531. }
  532. return;
  533. }
  534. VOID
  535. InputDisplayBuffer(
  536. IN PCHAR ParamBuffer,
  537. IN ULONG DisplaySize
  538. )
  539. {
  540. ULONG DisplayLength;
  541. ULONG DisplayOffset;
  542. ULONG BufferIndex;
  543. BOOLEAN ParamReceived;
  544. BOOLEAN LastInput;
  545. //
  546. // Set the defaults.
  547. //
  548. ParamReceived = FALSE;
  549. LastInput = TRUE;
  550. BufferIndex = DISPLAY_INDEX_DEFAULT;
  551. BufferIndex = DISPLAY_INDEX_DEFAULT;
  552. DisplayOffset = DISPLAY_OFFSET_DEFAULT;
  553. DisplayLength = DISPLAY_LENGTH_DEFAULT;
  554. //
  555. // While there is more input, analyze the parameter and update the
  556. // query flags.
  557. //
  558. while (TRUE) {
  559. ULONG DummyCount;
  560. //
  561. // Swallow leading white spaces.
  562. //
  563. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  564. if (*ParamBuffer) {
  565. //
  566. // If the next parameter is legal then check the paramter value.
  567. // Update the parameter value.
  568. //
  569. if ((*ParamBuffer == '-'
  570. || *ParamBuffer == '/')
  571. && (ParamBuffer++, *ParamBuffer != '\0')) {
  572. //
  573. // Switch on the next character.
  574. //
  575. switch( *ParamBuffer ) {
  576. //
  577. // Check the buffer index.
  578. //
  579. case 'b' :
  580. case 'B' :
  581. //
  582. // Move to the next character, as long as there
  583. // are no white spaces continue analyzing letters.
  584. // On the first bad letter, skip to the next
  585. // parameter.
  586. //
  587. ParamBuffer++;
  588. BufferIndex = AsciiToInteger( ParamBuffer );
  589. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  590. ParamReceived = TRUE;
  591. break;
  592. //
  593. // Check the display length.
  594. //
  595. case 'l' :
  596. case 'L' :
  597. //
  598. // Move to the next character, as long as there
  599. // are no white spaces continue analyzing letters.
  600. // On the first bad letter, skip to the next
  601. // parameter.
  602. //
  603. ParamBuffer++;
  604. DisplayLength = AsciiToInteger( ParamBuffer );
  605. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  606. break;
  607. //
  608. // Check the display offset.
  609. //
  610. case 'o' :
  611. case 'O' :
  612. //
  613. // Move to the next character, as long as there
  614. // are no white spaces continue analyzing letters.
  615. // On the first bad letter, skip to the next
  616. // parameter.
  617. //
  618. ParamBuffer++;
  619. DisplayOffset = AsciiToInteger( ParamBuffer );
  620. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  621. break;
  622. default :
  623. //
  624. // Swallow to the next white space and continue the
  625. // loop.
  626. //
  627. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  628. }
  629. }
  630. //
  631. // Else the text is invalid, skip the entire block.
  632. //
  633. //
  634. //
  635. // Else if there is no input then exit.
  636. //
  637. } else if ( LastInput ) {
  638. break;
  639. //
  640. // Else try to read another line for open parameters.
  641. //
  642. } else {
  643. }
  644. }
  645. //
  646. // If no parameters were received then display the syntax message.
  647. //
  648. if (!ParamReceived) {
  649. printf( "\n Usage: db [options]* -i<digits> [options]*\n" );
  650. printf( "\n Options:" );
  651. printf( "\n -b<digits> Buffer index" );
  652. printf( "\n -l<digits> Display length" );
  653. printf( "\n -o<digits> Display starting offset" );
  654. printf( "\n\n" );
  655. //
  656. // Else call our display buffer routine.
  657. //
  658. } else {
  659. DisplayBuffer( BufferIndex, DisplayOffset, DisplayLength, DisplaySize );
  660. }
  661. }
  662. VOID
  663. InputCopyBuffer(
  664. IN PCHAR ParamBuffer
  665. )
  666. {
  667. ULONG SrcIndex;
  668. ULONG DstIndex;
  669. ULONG Length;
  670. ULONG SrcOffset;
  671. ULONG DstOffset;
  672. BOOLEAN DstSpecified;
  673. BOOLEAN SrcSpecified;
  674. BOOLEAN LastInput;
  675. //
  676. // Set the defaults.
  677. //
  678. SrcIndex = COPY_BUFF_SRC_DEFAULT;
  679. DstIndex = COPY_BUFF_DST_DEFAULT;
  680. Length = COPY_BUFF_SRC_OFF_DEFAULT;
  681. SrcOffset = COPY_BUFF_DST_OFF_DEFAULT;
  682. DstOffset = COPY_BUFF_LENGTH_DEFAULT;
  683. DstSpecified = FALSE;
  684. SrcSpecified = FALSE;
  685. LastInput = TRUE;
  686. //
  687. // While there is more input, analyze the parameter and update the
  688. // query flags.
  689. //
  690. while(TRUE) {
  691. ULONG DummyCount;
  692. //
  693. // Swallow leading white spaces.
  694. //
  695. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  696. if ( *ParamBuffer ) {
  697. //
  698. // If the next parameter is legal then check the paramter value.
  699. // Update the parameter value.
  700. //
  701. if ((*ParamBuffer == '-'
  702. || *ParamBuffer == '/')
  703. && (ParamBuffer++, *ParamBuffer != '\0')) {
  704. //
  705. // Switch on the next character.
  706. //
  707. switch( *ParamBuffer ) {
  708. //
  709. // Check the destination index.
  710. //
  711. case 'd' :
  712. case 'D' :
  713. //
  714. // Move to the next character, as long as there
  715. // are no white spaces continue analyzing letters.
  716. // On the first bad letter, skip to the next
  717. // parameter.
  718. //
  719. ParamBuffer++;
  720. DstIndex = AsciiToInteger( ParamBuffer );
  721. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  722. DstSpecified = TRUE;
  723. break;
  724. //
  725. // Check source starting offset.
  726. //
  727. case 'f' :
  728. case 'F' :
  729. //
  730. // Move to the next character, as long as there
  731. // are no white spaces continue analyzing letters.
  732. // On the first bad letter, skip to the next
  733. // parameter.
  734. //
  735. ParamBuffer++;
  736. SrcOffset = AsciiToInteger( ParamBuffer );
  737. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  738. break;
  739. //
  740. // Check copy length.
  741. //
  742. case 'l' :
  743. case 'L' :
  744. //
  745. // Move to the next character, as long as there
  746. // are no white spaces continue analyzing letters.
  747. // On the first bad letter, skip to the next
  748. // parameter.
  749. //
  750. ParamBuffer++;
  751. Length = AsciiToInteger( ParamBuffer );
  752. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  753. break;
  754. //
  755. // Check the source index.
  756. //
  757. case 's' :
  758. case 'S' :
  759. //
  760. // Move to the next character, as long as there
  761. // are no white spaces continue analyzing letters.
  762. // On the first bad letter, skip to the next
  763. // parameter.
  764. //
  765. ParamBuffer++;
  766. SrcIndex = AsciiToInteger( ParamBuffer );
  767. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  768. SrcSpecified = TRUE;
  769. break;
  770. //
  771. // Check destination offset.
  772. //
  773. case 't' :
  774. case 'T' :
  775. //
  776. // Move to the next character, as long as there
  777. // are no white spaces continue analyzing letters.
  778. // On the first bad letter, skip to the next
  779. // parameter.
  780. //
  781. ParamBuffer++;
  782. DstOffset = AsciiToInteger( ParamBuffer );
  783. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  784. break;
  785. default :
  786. //
  787. // Swallow to the next white space and continue the
  788. // loop.
  789. //
  790. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  791. }
  792. }
  793. //
  794. // Else the text is invalid, skip the entire block.
  795. //
  796. //
  797. //
  798. // Else if there is no input then exit.
  799. //
  800. } else if ( LastInput ) {
  801. break;
  802. //
  803. // Else try to read another line for open parameters.
  804. //
  805. } else {
  806. }
  807. }
  808. //
  809. // If no parameters were received then display the syntax message.
  810. //
  811. if (!SrcSpecified || !DstSpecified) {
  812. printf( "\n Usage: cb [options]* -d<digits> [options]* -s<digits> [options]*\n" );
  813. printf( "\n Options:" );
  814. printf( "\n -d<digits> Destination index" );
  815. printf( "\n -f<digits> Source offset" );
  816. printf( "\n -l<digits> Transfer length" );
  817. printf( "\n -s<digits> Source index" );
  818. printf( "\n -t<digits> Destination offset" );
  819. printf( "\n\n" );
  820. //
  821. // Else call our copy buffer routine.
  822. //
  823. } else {
  824. CopyBuffer( SrcIndex,
  825. DstIndex,
  826. Length,
  827. SrcOffset,
  828. DstOffset );
  829. }
  830. }
  831. VOID
  832. CopyBuffer(
  833. IN ULONG SrcIndex,
  834. IN ULONG DstIndex,
  835. IN ULONG Length,
  836. IN ULONG SrcOffset,
  837. IN ULONG DstOffset
  838. )
  839. {
  840. //
  841. // Check for an invalid source index.
  842. //
  843. if (!Buffers[SrcIndex].Used) {
  844. printf( "\nCopyBuffer: Invalid source buffer" );
  845. //
  846. // Otherwise check for an invalid destination index.
  847. //
  848. } else if (!Buffers[DstIndex].Used) {
  849. printf( "\nCopyBuffer: Invalid destination buffer" );
  850. //
  851. // Test for an invalid source offset.
  852. //
  853. } else if (SrcOffset >= Buffers[SrcIndex].Length) {
  854. printf( "\nCopyBuffer: Source offset is invalid" );
  855. //
  856. // Test for an invalid destination offset.
  857. //
  858. } else if (DstOffset >= Buffers[DstIndex].Length) {
  859. printf( "\nCopyBuffer: Destination offset is invalid" );
  860. //
  861. // This statement handles the case of two correct indexes and offsets.
  862. //
  863. } else {
  864. ULONG LegalLength;
  865. PCHAR SrcAddress;
  866. PCHAR DstAddress;
  867. //
  868. // Adjust the length according to the source buffer size.
  869. //
  870. LegalLength = Buffers[SrcIndex].Length - SrcOffset;
  871. LegalLength = min( LegalLength, Length );
  872. Length = Buffers[DstIndex].Length - DstOffset;
  873. LegalLength = min( LegalLength, Length );
  874. SrcAddress = Buffers[SrcIndex].Buffer + SrcOffset;
  875. DstAddress = Buffers[DstIndex].Buffer + DstOffset;
  876. //
  877. // Display the header information.
  878. //
  879. printf( "\nSource index -> %2u, Source base -> %p, Source offset -> %08lx, ",
  880. SrcIndex,
  881. Buffers[SrcIndex].Buffer,
  882. SrcOffset );
  883. printf( "\n Dest index -> %2u, Dest base -> %p, Dest offset -> %08lx, ",
  884. DstIndex,
  885. Buffers[DstIndex].Buffer,
  886. DstOffset );
  887. printf( "\nLength -> %u", Length );
  888. //
  889. // Perform the transfer for non-zero lengths only.
  890. //
  891. if (Length) {
  892. RtlMoveMemory( DstAddress, SrcAddress, Length );
  893. }
  894. }
  895. return;
  896. }
  897. VOID
  898. InputAllocMem(
  899. IN PCHAR ParamBuffer
  900. )
  901. {
  902. ULONG ZeroBits;
  903. SIZE_T RegionSize;
  904. ULONG BufferIndex;
  905. BOOLEAN VerboseResults;
  906. BOOLEAN DisplayParms;
  907. BOOLEAN ParamReceived;
  908. BOOLEAN LastInput;
  909. //
  910. // Set the defaults.
  911. //
  912. ZeroBits = ALLOC_ZERO_BITS_DEFAULT;
  913. RegionSize = ALLOC_REGION_SIZE_DEFAULT;
  914. VerboseResults = ALLOC_VERBOSE_DEFAULT;
  915. DisplayParms = ALLOC_DISPLAY_PARMS_DEFAULT;
  916. ParamReceived = FALSE;
  917. LastInput = TRUE;
  918. //
  919. // While there is more input, analyze the parameter and update the
  920. // query flags.
  921. //
  922. while (TRUE) {
  923. ULONG DummyCount;
  924. //
  925. // Swallow leading white spaces.
  926. //
  927. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  928. if ( *ParamBuffer ) {
  929. //
  930. // If the next parameter is legal then check the paramter value.
  931. // Update the parameter value.
  932. //
  933. if ((*ParamBuffer == '-'
  934. || *ParamBuffer == '/')
  935. && (ParamBuffer++, *ParamBuffer != '\0')) {
  936. //
  937. // Switch on the next character.
  938. //
  939. switch (*ParamBuffer) {
  940. //
  941. // Update zero bits.
  942. //
  943. case 'b' :
  944. case 'B' :
  945. //
  946. // Move to the next character, as long as there
  947. // are no white spaces continue analyzing letters.
  948. // On the first bad letter, skip to the next
  949. // parameter.
  950. //
  951. ParamBuffer++;
  952. ZeroBits = AsciiToInteger( ParamBuffer );
  953. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  954. ParamReceived = TRUE;
  955. break;
  956. //
  957. // Update the region size.
  958. //
  959. case 'r' :
  960. case 'R' :
  961. //
  962. // Move to the next character, as long as there
  963. // are no white spaces continue analyzing letters.
  964. // On the first bad letter, skip to the next
  965. // parameter.
  966. //
  967. ParamBuffer++;
  968. RegionSize = AsciiToInteger( ParamBuffer );
  969. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  970. ParamReceived = TRUE;
  971. break;
  972. case 'v' :
  973. case 'V' :
  974. //
  975. // Legal values for params are T/t or F/f.
  976. //
  977. ParamBuffer++;
  978. if (*ParamBuffer == 'T'
  979. || *ParamBuffer == 't') {
  980. VerboseResults = TRUE;
  981. ParamBuffer++;
  982. } else if (*ParamBuffer == 'F'
  983. || *ParamBuffer == 'f') {
  984. VerboseResults = FALSE;
  985. ParamBuffer++;
  986. }
  987. ParamReceived = TRUE;
  988. break;
  989. case 'y' :
  990. case 'Y' :
  991. //
  992. // Set the display parms flag and jump over this
  993. // character.
  994. //
  995. DisplayParms = TRUE;
  996. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  997. ParamReceived = TRUE;
  998. break;
  999. default :
  1000. //
  1001. // Swallow to the next white space and continue the
  1002. // loop.
  1003. //
  1004. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1005. }
  1006. }
  1007. //
  1008. // Else the text is invalid, skip the entire block.
  1009. //
  1010. //
  1011. //
  1012. // Else if there is no input then exit.
  1013. //
  1014. } else if ( LastInput ) {
  1015. break;
  1016. //
  1017. // Else try to read another line for open parameters.
  1018. //
  1019. } else {
  1020. }
  1021. }
  1022. //
  1023. // If no parameters were received then display the syntax message.
  1024. //
  1025. if (!ParamReceived) {
  1026. printf( "\n Usage: am [options]*\n" );
  1027. printf( "\n Options:" );
  1028. printf( "\n -b<digits> Zero bits" );
  1029. printf( "\n -r<digits> Region size" );
  1030. printf( "\n -v[t|f] Verbose results" );
  1031. printf( "\n -y Display parameters to query" );
  1032. printf( "\n\n" );
  1033. //
  1034. // Else call our allocation routine.
  1035. //
  1036. } else {
  1037. FullAllocMem(
  1038. ZeroBits,
  1039. &RegionSize,
  1040. &BufferIndex,
  1041. VerboseResults,
  1042. DisplayParms
  1043. );
  1044. }
  1045. }
  1046. NTSTATUS
  1047. FullAllocMem(
  1048. IN ULONG ZeroBits,
  1049. IN OUT PSIZE_T RegionSize,
  1050. OUT PULONG BufferIndex,
  1051. IN BOOLEAN VerboseResults,
  1052. IN BOOLEAN DisplayParms
  1053. )
  1054. {
  1055. NTSTATUS Status;
  1056. Status = STATUS_SUCCESS;
  1057. if (DisplayParms) {
  1058. printf( "\nAlloc Memory Parameters" );
  1059. printf( "\n Zero Bits -> %ld", ZeroBits );
  1060. printf( "\n Region Size -> %ld", *RegionSize );
  1061. printf( "\n\n" );
  1062. }
  1063. //
  1064. // Try to get the next buffer.
  1065. //
  1066. Status = AllocateBuffer( ZeroBits, RegionSize, BufferIndex );
  1067. //
  1068. // Print the results if verbose.
  1069. //
  1070. if (VerboseResults) {
  1071. printf( "\nAllocMem: Status -> %08lx", Status );
  1072. printf( "\n RegionSize -> %08lx", *RegionSize );
  1073. printf( "\n BufferIndex -> %ld", *BufferIndex );
  1074. printf( "\n\n" );
  1075. }
  1076. return Status;
  1077. }
  1078. VOID
  1079. InputDeallocMem(
  1080. IN PCHAR ParamBuffer
  1081. )
  1082. {
  1083. ULONG BufferIndex;
  1084. BOOLEAN ParamReceived;
  1085. BOOLEAN LastInput;
  1086. BOOLEAN VerboseResults;
  1087. BOOLEAN DisplayParms;
  1088. //
  1089. // Set the defaults.
  1090. //
  1091. VerboseResults = ALLOC_VERBOSE_DEFAULT;
  1092. DisplayParms = ALLOC_DISPLAY_PARMS_DEFAULT;
  1093. ParamReceived = FALSE;
  1094. LastInput = TRUE;
  1095. //
  1096. // While there is more input, analyze the parameter and update the
  1097. // query flags.
  1098. //
  1099. while (TRUE) {
  1100. ULONG DummyCount;
  1101. //
  1102. // Swallow leading white spaces.
  1103. //
  1104. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  1105. if (*ParamBuffer) {
  1106. //
  1107. // If the next parameter is legal then check the paramter value.
  1108. // Update the parameter value.
  1109. //
  1110. if ((*ParamBuffer == '-'
  1111. || *ParamBuffer == '/')
  1112. && (ParamBuffer++, *ParamBuffer != '\0')) {
  1113. //
  1114. // Switch on the next character.
  1115. //
  1116. switch (*ParamBuffer) {
  1117. //
  1118. // Find the Index value.
  1119. //
  1120. case 'b' :
  1121. case 'B' :
  1122. //
  1123. // Move to the next character, as long as there
  1124. // are no white spaces continue analyzing letters.
  1125. // On the first bad letter, skip to the next
  1126. // parameter.
  1127. //
  1128. ParamBuffer++;
  1129. BufferIndex = AsciiToInteger( ParamBuffer );
  1130. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1131. ParamReceived = TRUE;
  1132. break;
  1133. case 'v' :
  1134. case 'V' :
  1135. //
  1136. // Legal values for params are T/t or F/f.
  1137. //
  1138. ParamBuffer++;
  1139. if (*ParamBuffer == 'T'
  1140. || *ParamBuffer == 't') {
  1141. VerboseResults = TRUE;
  1142. ParamBuffer++;
  1143. } else if (*ParamBuffer == 'F'
  1144. || *ParamBuffer == 'f') {
  1145. VerboseResults = FALSE;
  1146. ParamBuffer++;
  1147. }
  1148. ParamReceived = TRUE;
  1149. break;
  1150. case 'y' :
  1151. case 'Y' :
  1152. //
  1153. // Set the display parms flag and jump over this
  1154. // character.
  1155. //
  1156. DisplayParms = TRUE;
  1157. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1158. ParamReceived = TRUE;
  1159. break;
  1160. default :
  1161. //
  1162. // Swallow to the next white space and continue the
  1163. // loop.
  1164. //
  1165. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1166. }
  1167. }
  1168. //
  1169. // Else the text is invalid, skip the entire block.
  1170. //
  1171. //
  1172. //
  1173. // Else if there is no input then exit.
  1174. //
  1175. } else if ( LastInput ) {
  1176. break;
  1177. //
  1178. // Else try to read another line for open parameters.
  1179. //
  1180. } else {
  1181. }
  1182. }
  1183. //
  1184. // If no parameters were received then display the syntax message.
  1185. //
  1186. if (!ParamReceived) {
  1187. printf( "\n Usage: dm [options]*\n" );
  1188. printf( "\n Options:" );
  1189. printf( "\n -b<digits> Buffer Index number" );
  1190. printf( "\n -v[t|f] Verbose results" );
  1191. printf( "\n -y Display parameters to query" );
  1192. printf( "\n\n" );
  1193. //
  1194. // Else call our allocation routine.
  1195. //
  1196. } else {
  1197. FullDeallocMem(
  1198. BufferIndex,
  1199. VerboseResults,
  1200. DisplayParms );
  1201. }
  1202. }
  1203. NTSTATUS
  1204. FullDeallocMem(
  1205. IN ULONG Index,
  1206. IN BOOLEAN VerboseResults,
  1207. IN BOOLEAN DisplayParms
  1208. )
  1209. {
  1210. NTSTATUS Status;
  1211. Status = STATUS_SUCCESS;
  1212. if (DisplayParms) {
  1213. printf( "\nDealloc Memory Parameters" );
  1214. printf( "\n Buffer Index -> %ld", Index );
  1215. printf( "\n\n" );
  1216. }
  1217. //
  1218. // Try to free the desired buffer.
  1219. //
  1220. Status = DeallocateBuffer( Index );
  1221. //
  1222. // Print the results if verbose.
  1223. //
  1224. if (VerboseResults) {
  1225. printf( "\nDeallocMem: Status -> %08lx", Status );
  1226. printf( "\n\n" );
  1227. }
  1228. return Status;
  1229. }
  1230. VOID InputFillBuffer(
  1231. IN PCHAR ParamBuffer
  1232. )
  1233. {
  1234. ULONG BufferIndex;
  1235. BOOLEAN ParamReceived;
  1236. BOOLEAN LastInput;
  1237. BOOLEAN HaveStructure = FALSE;
  1238. MFT_ENUM_DATA EnumUsnData;
  1239. READ_USN_JOURNAL_DATA ReadUsnJournal;
  1240. CREATE_USN_JOURNAL_DATA CreateUsnJournal;
  1241. LARGE_INTEGER LargeIntegerInput;
  1242. FILE_ALLOCATED_RANGE_BUFFER AllocatedRangeBuffer;
  1243. PVOID StructurePointer;
  1244. ULONG StructureSize;
  1245. ParamReceived = FALSE;
  1246. LastInput = TRUE;
  1247. BufferIndex = DISPLAY_INDEX_DEFAULT;
  1248. RtlZeroMemory( &EnumUsnData, sizeof( MFT_ENUM_DATA ));
  1249. RtlZeroMemory( &ReadUsnJournal, sizeof( READ_USN_JOURNAL_DATA ));
  1250. RtlZeroMemory( &CreateUsnJournal, sizeof( CREATE_USN_JOURNAL_DATA ));
  1251. RtlZeroMemory( &LargeIntegerInput, sizeof( LARGE_INTEGER ));
  1252. RtlZeroMemory( &AllocatedRangeBuffer, sizeof( FILE_ALLOCATED_RANGE_BUFFER ));
  1253. //
  1254. // While there is more input, analyze the parameter and update the
  1255. // query flags.
  1256. //
  1257. while (TRUE) {
  1258. ULONG DummyCount;
  1259. //
  1260. // Swallow leading white spaces.
  1261. //
  1262. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  1263. if (*ParamBuffer) {
  1264. //
  1265. // If the next parameter is legal then check the paramter value.
  1266. // Update the parameter value.
  1267. //
  1268. if ((*ParamBuffer == '-'
  1269. || *ParamBuffer == '/')
  1270. && (ParamBuffer++, *ParamBuffer != '\0')) {
  1271. //
  1272. // Switch on the next character.
  1273. //
  1274. switch( *ParamBuffer ) {
  1275. BOOLEAN SwitchBool;
  1276. //
  1277. // Check the buffer index.
  1278. //
  1279. case 'b' :
  1280. case 'B' :
  1281. //
  1282. // Move to the next character, as long as there
  1283. // are no white spaces continue analyzing letters.
  1284. // On the first bad letter, skip to the next
  1285. // parameter.
  1286. //
  1287. ParamBuffer++;
  1288. BufferIndex = AsciiToInteger( ParamBuffer );
  1289. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1290. ParamReceived = TRUE;
  1291. break;
  1292. //
  1293. // Check the structure to fill.
  1294. //
  1295. case 's' :
  1296. case 'S' :
  1297. SwitchBool = TRUE;
  1298. ParamBuffer++;
  1299. if (*ParamBuffer
  1300. && *ParamBuffer != ' '
  1301. && *ParamBuffer != '\t') {
  1302. //
  1303. // Perform switch on character.
  1304. //
  1305. switch (*ParamBuffer) {
  1306. case 'a' :
  1307. case 'A' :
  1308. case 'b' :
  1309. case 'B' :
  1310. HaveStructure = TRUE;
  1311. StructurePointer = &LargeIntegerInput;
  1312. StructureSize = sizeof( LARGE_INTEGER );
  1313. ParamBuffer++;
  1314. if (*ParamBuffer
  1315. && *ParamBuffer != ' '
  1316. && *ParamBuffer != '\t') {
  1317. switch (*ParamBuffer) {
  1318. case 'a' :
  1319. case 'A' :
  1320. ParamBuffer++;
  1321. LargeIntegerInput.QuadPart = AsciiToLargeInteger( ParamBuffer );
  1322. break;
  1323. default :
  1324. NOTHING;
  1325. }
  1326. }
  1327. break;
  1328. case 'c' :
  1329. case 'C' :
  1330. HaveStructure = TRUE;
  1331. StructurePointer = &AllocatedRangeBuffer;
  1332. StructureSize = sizeof( FILE_ALLOCATED_RANGE_BUFFER );
  1333. ParamBuffer++;
  1334. if (*ParamBuffer
  1335. && *ParamBuffer != ' '
  1336. && *ParamBuffer != '\t') {
  1337. switch (*ParamBuffer) {
  1338. case 'a' :
  1339. case 'A' :
  1340. ParamBuffer++;
  1341. AllocatedRangeBuffer.FileOffset.QuadPart = AsciiToLargeInteger( ParamBuffer );
  1342. break;
  1343. case 'b' :
  1344. case 'B' :
  1345. ParamBuffer++;
  1346. AllocatedRangeBuffer.Length.QuadPart = AsciiToLargeInteger( ParamBuffer );
  1347. break;
  1348. default :
  1349. NOTHING;
  1350. }
  1351. }
  1352. break;
  1353. default :
  1354. NOTHING;
  1355. }
  1356. }
  1357. break;
  1358. default :
  1359. NOTHING;
  1360. }
  1361. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1362. }
  1363. //
  1364. // Else the text is invalid, skip the entire block.
  1365. //
  1366. //
  1367. //
  1368. // Else if there is no input then exit.
  1369. //
  1370. } else if ( LastInput ) {
  1371. break;
  1372. //
  1373. // Else try to read another line for open parameters.
  1374. //
  1375. } else {
  1376. }
  1377. }
  1378. //
  1379. // If no parameters were received then display the syntax message.
  1380. //
  1381. if (!ParamReceived) {
  1382. printf( "\n Usage: fb -b<digits> -s<struct>[options]* \n" );
  1383. printf( "\n -sa[options] Get Volume Bitmap" );
  1384. printf( "\n a<digits> Starting lcn" );
  1385. printf( "\n -sb[options] Query Retrieval Pointers" );
  1386. printf( "\n a<digits> Starting vcn" );
  1387. printf( "\n -sc[options] Query Allocated Ranges" );
  1388. printf( "\n a<digits> FileOffset" );
  1389. printf( "\n b<digits> Length" );
  1390. printf( "\n\n" );
  1391. //
  1392. // Else fill the buffer.
  1393. //
  1394. } else if (HaveStructure) {
  1395. FillBuffer( BufferIndex, StructurePointer, StructureSize );
  1396. }
  1397. }
  1398. VOID InputFillBufferUsn(
  1399. IN PCHAR ParamBuffer
  1400. )
  1401. {
  1402. ULONG BufferIndex;
  1403. BOOLEAN ParamReceived;
  1404. BOOLEAN LastInput;
  1405. BOOLEAN HaveStructure = FALSE;
  1406. MFT_ENUM_DATA EnumUsnData;
  1407. READ_USN_JOURNAL_DATA ReadUsnJournal;
  1408. CREATE_USN_JOURNAL_DATA CreateUsnJournal;
  1409. DELETE_USN_JOURNAL_DATA DeleteUsnJournal;
  1410. PVOID StructurePointer;
  1411. ULONG StructureSize;
  1412. ParamReceived = FALSE;
  1413. LastInput = TRUE;
  1414. BufferIndex = DISPLAY_INDEX_DEFAULT;
  1415. RtlZeroMemory( &EnumUsnData, sizeof( MFT_ENUM_DATA ));
  1416. RtlZeroMemory( &ReadUsnJournal, sizeof( READ_USN_JOURNAL_DATA ));
  1417. RtlZeroMemory( &CreateUsnJournal, sizeof( CREATE_USN_JOURNAL_DATA ));
  1418. RtlZeroMemory( &DeleteUsnJournal, sizeof( DELETE_USN_JOURNAL_DATA ));
  1419. //
  1420. // While there is more input, analyze the parameter and update the
  1421. // query flags.
  1422. //
  1423. while (TRUE) {
  1424. ULONG DummyCount;
  1425. //
  1426. // Swallow leading white spaces.
  1427. //
  1428. ParamBuffer = SwallowWhite( ParamBuffer, &DummyCount );
  1429. if (*ParamBuffer) {
  1430. //
  1431. // If the next parameter is legal then check the paramter value.
  1432. // Update the parameter value.
  1433. //
  1434. if ((*ParamBuffer == '-'
  1435. || *ParamBuffer == '/')
  1436. && (ParamBuffer++, *ParamBuffer != '\0')) {
  1437. //
  1438. // Switch on the next character.
  1439. //
  1440. switch( *ParamBuffer ) {
  1441. BOOLEAN SwitchBool;
  1442. //
  1443. // Check the buffer index.
  1444. //
  1445. case 'b' :
  1446. case 'B' :
  1447. //
  1448. // Move to the next character, as long as there
  1449. // are no white spaces continue analyzing letters.
  1450. // On the first bad letter, skip to the next
  1451. // parameter.
  1452. //
  1453. ParamBuffer++;
  1454. BufferIndex = AsciiToInteger( ParamBuffer );
  1455. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1456. ParamReceived = TRUE;
  1457. break;
  1458. //
  1459. // Check the structure to fill.
  1460. //
  1461. case 's' :
  1462. case 'S' :
  1463. SwitchBool = TRUE;
  1464. ParamBuffer++;
  1465. if (*ParamBuffer
  1466. && *ParamBuffer != ' '
  1467. && *ParamBuffer != '\t') {
  1468. //
  1469. // Perform switch on character.
  1470. //
  1471. switch (*ParamBuffer) {
  1472. //
  1473. // ENUM_USN_DATA
  1474. //
  1475. case 'a' :
  1476. case 'A' :
  1477. HaveStructure = TRUE;
  1478. StructurePointer = &EnumUsnData;
  1479. StructureSize = sizeof( MFT_ENUM_DATA );
  1480. ParamBuffer++;
  1481. if (*ParamBuffer
  1482. && *ParamBuffer != ' '
  1483. && *ParamBuffer != '\t') {
  1484. switch (*ParamBuffer) {
  1485. case 'a' :
  1486. case 'A' :
  1487. ParamBuffer++;
  1488. EnumUsnData.LowUsn = AsciiToLargeInteger( ParamBuffer );
  1489. break;
  1490. case 'b' :
  1491. case 'B' :
  1492. ParamBuffer++;
  1493. EnumUsnData.HighUsn = AsciiToLargeInteger( ParamBuffer );
  1494. break;
  1495. case 'c' :
  1496. case 'C' :
  1497. ParamBuffer++;
  1498. EnumUsnData.StartFileReferenceNumber = AsciiToLargeInteger( ParamBuffer );
  1499. break;
  1500. default :
  1501. NOTHING;
  1502. }
  1503. }
  1504. break;
  1505. case 'b' :
  1506. case 'B' :
  1507. HaveStructure = TRUE;
  1508. StructurePointer = &ReadUsnJournal;
  1509. StructureSize = sizeof( READ_USN_JOURNAL_DATA );
  1510. ParamBuffer++;
  1511. if (*ParamBuffer
  1512. && *ParamBuffer != ' '
  1513. && *ParamBuffer != '\t') {
  1514. switch (*ParamBuffer) {
  1515. case 'a' :
  1516. case 'A' :
  1517. ParamBuffer++;
  1518. ReadUsnJournal.StartUsn = AsciiToLargeInteger( ParamBuffer );
  1519. break;
  1520. case 'b' :
  1521. case 'B' :
  1522. ParamBuffer++;
  1523. ReadUsnJournal.ReasonMask = AsciiToInteger( ParamBuffer );
  1524. break;
  1525. case 'c' :
  1526. case 'C' :
  1527. ParamBuffer++;
  1528. ReadUsnJournal.ReturnOnlyOnClose = AsciiToInteger( ParamBuffer );
  1529. break;
  1530. case 'd' :
  1531. case 'D' :
  1532. ParamBuffer++;
  1533. ReadUsnJournal.Timeout = AsciiToLargeInteger( ParamBuffer );
  1534. break;
  1535. case 'e' :
  1536. case 'E' :
  1537. ParamBuffer++;
  1538. ReadUsnJournal.BytesToWaitFor = AsciiToLargeInteger( ParamBuffer );
  1539. break;
  1540. case 'f' :
  1541. case 'F' :
  1542. ParamBuffer++;
  1543. ReadUsnJournal.UsnJournalID = AsciiToLargeInteger( ParamBuffer );
  1544. break;
  1545. default :
  1546. NOTHING;
  1547. }
  1548. }
  1549. break;
  1550. case 'c' :
  1551. case 'C' :
  1552. HaveStructure = TRUE;
  1553. StructurePointer = &CreateUsnJournal;
  1554. StructureSize = sizeof( CREATE_USN_JOURNAL_DATA );
  1555. ParamBuffer++;
  1556. if (*ParamBuffer
  1557. && *ParamBuffer != ' '
  1558. && *ParamBuffer != '\t') {
  1559. switch (*ParamBuffer) {
  1560. case 'a' :
  1561. case 'A' :
  1562. ParamBuffer++;
  1563. CreateUsnJournal.MaximumSize = AsciiToLargeInteger( ParamBuffer );
  1564. break;
  1565. case 'b' :
  1566. case 'B' :
  1567. ParamBuffer++;
  1568. CreateUsnJournal.AllocationDelta = AsciiToLargeInteger( ParamBuffer );
  1569. break;
  1570. default :
  1571. NOTHING;
  1572. }
  1573. }
  1574. break;
  1575. case 'd' :
  1576. case 'D' :
  1577. HaveStructure = TRUE;
  1578. StructurePointer = &DeleteUsnJournal;
  1579. StructureSize = sizeof( DELETE_USN_JOURNAL_DATA );
  1580. ParamBuffer++;
  1581. if (*ParamBuffer
  1582. && *ParamBuffer != ' '
  1583. && *ParamBuffer != '\t') {
  1584. switch (*ParamBuffer) {
  1585. case 'a' :
  1586. case 'A' :
  1587. ParamBuffer++;
  1588. DeleteUsnJournal.UsnJournalID = AsciiToLargeInteger( ParamBuffer );
  1589. break;
  1590. default :
  1591. NOTHING;
  1592. }
  1593. }
  1594. break;
  1595. default :
  1596. NOTHING;
  1597. }
  1598. }
  1599. break;
  1600. default :
  1601. NOTHING;
  1602. }
  1603. ParamBuffer = SwallowNonWhite( ParamBuffer, &DummyCount );
  1604. }
  1605. //
  1606. // Else the text is invalid, skip the entire block.
  1607. //
  1608. //
  1609. //
  1610. // Else if there is no input then exit.
  1611. //
  1612. } else if ( LastInput ) {
  1613. break;
  1614. //
  1615. // Else try to read another line for open parameters.
  1616. //
  1617. } else {
  1618. }
  1619. }
  1620. //
  1621. // If no parameters were received then display the syntax message.
  1622. //
  1623. if (!ParamReceived) {
  1624. printf( "\n Usage: fbusn -b<digits> -s<struct>[options]* \n" );
  1625. printf( "\n -sa[options] Enum Usn Data" );
  1626. printf( "\n a<digits> Low usn" );
  1627. printf( "\n b<digits> High usn" );
  1628. printf( "\n c<digits> File ref" );
  1629. printf( "\n -sb[options] Read Usn Data" );
  1630. printf( "\n a<digits> Start usn" );
  1631. printf( "\n b<digits> Reason mask" );
  1632. printf( "\n c<digits> Return only on close" );
  1633. printf( "\n d<digits> Timeout" );
  1634. printf( "\n e<digits> Bytes to wait for" );
  1635. printf( "\n f<digits> Journal id" );
  1636. printf( "\n -sc[options] Create Usn Data" );
  1637. printf( "\n a<digits> Maximum size" );
  1638. printf( "\n b<digits> Allocation delta" );
  1639. printf( "\n -sd[options] Delete Usn Journal Data" );
  1640. printf( "\n a<digits> Usn journal id" );
  1641. printf( "\n\n" );
  1642. //
  1643. // Else fill the buffer.
  1644. //
  1645. } else if (HaveStructure) {
  1646. FillBuffer( BufferIndex, StructurePointer, StructureSize );
  1647. }
  1648. }
  1649. VOID
  1650. FillBuffer (
  1651. IN ULONG Index,
  1652. IN PVOID Structure,
  1653. IN ULONG Length
  1654. )
  1655. {
  1656. //
  1657. // If the index is unused, display message but take no action.
  1658. //
  1659. if (!Buffers[Index].Used) {
  1660. printf( "\nFillBuffer: Index refers to invalid buffer" );
  1661. //
  1662. // Else copy as much of the data as will fit into the buffer.
  1663. //
  1664. } else {
  1665. if (Length > Buffers[Index].Length) {
  1666. Length = Buffers[Index].Length;
  1667. }
  1668. RtlCopyMemory( Buffers[Index].Buffer, Structure, Length );
  1669. }
  1670. return;
  1671. }