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.

240 lines
5.2 KiB

  1. /*++
  2. Copyright (c) 1998 Microsoft Corporation
  3. Module Name:
  4. batch.c
  5. Abstract:
  6. This module implements batch command processing.
  7. Author:
  8. Wesley Witt (wesw) 21-Oct-1998
  9. Revision History:
  10. --*/
  11. #include "cmdcons.h"
  12. #pragma hdrstop
  13. ULONG InBatchMode;
  14. HANDLE OutputFileHandle;
  15. LARGE_INTEGER OutputFileOffset;
  16. BOOLEAN RedirectToNULL;
  17. #ifdef DBG
  18. VOID
  19. RcDumpTokenizedLine(
  20. PTOKENIZED_LINE Line
  21. )
  22. {
  23. if (Line) {
  24. PLINE_TOKEN Token = Line->Tokens;
  25. ULONG Index ;
  26. for(Index=0; ((Index < Line->TokenCount) && Token); Index++) {
  27. KdPrint(("%ws, ", Token->String));
  28. Token = Token->Next;
  29. }
  30. KdPrint(("\n"));
  31. } else {
  32. KdPrint(("Line is null!!!\n"));
  33. }
  34. }
  35. #endif
  36. ULONG
  37. pRcExecuteBatchFile(
  38. IN PWSTR BatchFileName,
  39. IN PWSTR OutputFileName,
  40. IN BOOLEAN Quiet
  41. )
  42. {
  43. NTSTATUS Status = 0;
  44. LPCWSTR Arg;
  45. HANDLE FileHandle = NULL;
  46. HANDLE SectionHandle;
  47. PVOID ViewBase;
  48. ULONG FileSize;
  49. ULONG rc;
  50. WCHAR *s;
  51. WCHAR *p;
  52. ULONG sz;
  53. WCHAR *pText;
  54. ULONG rVal = 1; // continue with RC
  55. BOOLEAN b = FALSE;
  56. UNICODE_STRING UnicodeString;
  57. IO_STATUS_BLOCK IoStatusBlock;
  58. OBJECT_ATTRIBUTES Obja;
  59. PTOKENIZED_LINE TokenizedLine;
  60. BOOLEAN bCloseOutputFile = FALSE;
  61. if (!RcFormFullPath(BatchFileName,_CmdConsBlock->TemporaryBuffer,TRUE)) {
  62. RcMessageOut(MSG_INVALID_PATH);
  63. goto exit;
  64. }
  65. Status = SpOpenAndMapFile(
  66. _CmdConsBlock->TemporaryBuffer,
  67. &FileHandle,
  68. &SectionHandle,
  69. &ViewBase,
  70. &FileSize,
  71. FALSE
  72. );
  73. if( !NT_SUCCESS(Status) ) {
  74. if (!Quiet) {
  75. RcNtError(Status,MSG_CANT_OPEN_FILE);
  76. }
  77. goto exit;
  78. }
  79. pText = SpMemAlloc((FileSize+16)*sizeof(WCHAR));
  80. RtlZeroMemory(pText,(FileSize+16)*sizeof(WCHAR));
  81. Status = RtlMultiByteToUnicodeN(
  82. pText,
  83. FileSize * sizeof(WCHAR),
  84. &FileSize,
  85. ViewBase,
  86. FileSize
  87. );
  88. s = pText;
  89. sz = FileSize / sizeof(WCHAR);
  90. SpUnmapFile(SectionHandle,ViewBase);
  91. ZwClose(FileHandle);
  92. if (OutputFileName != NULL) {
  93. if (OutputFileHandle == NULL) {
  94. if (!RcFormFullPath(OutputFileName,_CmdConsBlock->TemporaryBuffer, TRUE)) {
  95. RcMessageOut(MSG_INVALID_PATH);
  96. if (pText)
  97. SpMemFree(pText);
  98. goto exit;
  99. }
  100. INIT_OBJA(&Obja,&UnicodeString,_CmdConsBlock->TemporaryBuffer);
  101. Status = ZwCreateFile(
  102. &OutputFileHandle,
  103. FILE_GENERIC_WRITE | SYNCHRONIZE,
  104. &Obja,
  105. &IoStatusBlock,
  106. NULL,
  107. FILE_ATTRIBUTE_NORMAL,
  108. 0,
  109. FILE_OVERWRITE_IF,
  110. FILE_NON_DIRECTORY_FILE | FILE_SYNCHRONOUS_IO_NONALERT | FILE_SEQUENTIAL_ONLY,
  111. NULL,
  112. 0
  113. );
  114. if (!NT_SUCCESS(Status)) {
  115. OutputFileHandle = NULL;
  116. RcMessageOut(Status);
  117. } else {
  118. bCloseOutputFile = TRUE;
  119. }
  120. OutputFileOffset.QuadPart = 0;
  121. }
  122. }
  123. InBatchMode += 1;
  124. //
  125. // get each line and invoke dispatch command
  126. // on that line after tokenizing the arguments
  127. //
  128. while (sz) {
  129. p = s;
  130. while (sz && (*p != L'\r')) {
  131. p += 1;
  132. sz--;
  133. }
  134. if (sz && (*p == L'\r')) {
  135. *p = 0;
  136. TokenizedLine = RcTokenizeLine(s);
  137. if (TokenizedLine->TokenCount) {
  138. rVal = RcDispatchCommand( TokenizedLine );
  139. if (rVal == 0 || rVal == 2) {
  140. b = FALSE;
  141. } else {
  142. b = TRUE;
  143. }
  144. RcTextOut(L"\r\n");
  145. } else {
  146. b = TRUE;
  147. }
  148. RcFreeTokenizedLine(&TokenizedLine);
  149. if (b == FALSE) {
  150. goto exit;
  151. }
  152. s = p + 1;
  153. sz--;
  154. if (sz && (*s == L'\n')) {
  155. s += 1;
  156. sz--;
  157. }
  158. }
  159. }
  160. SpMemFree(pText);
  161. InBatchMode -= 1;
  162. if (bCloseOutputFile) {
  163. ASSERT(OutputFileHandle != NULL);
  164. ZwClose(OutputFileHandle);
  165. OutputFileHandle = NULL;
  166. }
  167. exit:
  168. return rVal;
  169. }
  170. ULONG
  171. RcCmdBatch(
  172. IN PTOKENIZED_LINE TokenizedLine
  173. )
  174. {
  175. if (RcCmdParseHelp( TokenizedLine, MSG_BATCH_HELP )) {
  176. return 1;
  177. }
  178. if (TokenizedLine->TokenCount < 2 || (InBatchMode != 0 && 3 == TokenizedLine->TokenCount)) {
  179. RcMessageOut( MSG_SYNTAX_ERROR );
  180. return 1;
  181. }
  182. return pRcExecuteBatchFile(
  183. TokenizedLine->Tokens->Next->String,
  184. (TokenizedLine->TokenCount == 3) ? TokenizedLine->Tokens->Next->Next->String : NULL,
  185. FALSE
  186. );
  187. }