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.

375 lines
8.7 KiB

  1. #include <windows.h>
  2. #include <winspool.h>
  3. #include <stdio.h>
  4. #include <conio.h>
  5. #include <process.h>
  6. #include <string.h>
  7. #include "psshmem.h"
  8. #include "psprint.h"
  9. // If you use the -m mode for stress, only printers starting with the
  10. // define below will have jobs submitted to them
  11. //
  12. #define NAME_MUST_START_WITH TEXT("STRESS")
  13. #define CHAR_COUNT 100000L
  14. typedef BOOL (CALLBACK* FILEENUMPROC)( LPWIN32_FIND_DATA, LPTSTR , LPVOID);
  15. BOOL bDoEnumPrinters = FALSE;
  16. #define PRINTER_LIST_UPDATE 5000
  17. #define SLEEP_TIME 5000
  18. typedef struct {
  19. DWORD dwUpdateTime;
  20. int iNumPrinters;
  21. int iCurPrinter;
  22. PRINTER_INFO_2 *lpPrinters;
  23. } PRINTERS,*LPPRINTERS;
  24. PRINTERS Printers;
  25. VOID generateprinterlist(VOID){
  26. DWORD dwNeeded;
  27. DWORD dwCount;
  28. int i;
  29. Printers.iNumPrinters = 0;
  30. // Enum all the local printers and build a little list for enuming
  31. // through them
  32. if (!EnumPrinters(PRINTER_ENUM_LOCAL,(LPTSTR)NULL,2,(LPBYTE)NULL,0,&dwNeeded,&dwCount)&&
  33. GetLastError() == ERROR_INSUFFICIENT_BUFFER ) {
  34. // Verify the last error
  35. Printers.lpPrinters = (PRINTER_INFO_2 *) LocalAlloc(LPTR, dwNeeded);
  36. if (Printers.lpPrinters == (PRINTER_INFO_2 *) NULL) {
  37. printf("\nNot enought mem to enum printers?");
  38. exit(1);
  39. }
  40. EnumPrinters( PRINTER_ENUM_LOCAL,
  41. (LPTSTR)NULL,
  42. 2,
  43. (LPBYTE)Printers.lpPrinters,
  44. dwNeeded,
  45. &dwNeeded,
  46. &dwCount );
  47. Printers.iCurPrinter = 0;
  48. Printers.iNumPrinters = dwCount;
  49. printf("\nEnum printers returns %d", dwCount);
  50. for (i=0;i < Printers.iNumPrinters ; i++) {
  51. printf("\nPrinter %ws, %d", Printers.lpPrinters[i].pPrinterName,
  52. Printers.lpPrinters[i].cJobs);
  53. }
  54. Printers.dwUpdateTime = GetTickCount() + PRINTER_LIST_UPDATE;
  55. }else{
  56. printf("\nEnumPrinters returned error of %d", GetLastError());
  57. }
  58. }
  59. BOOL IsPrinterUsable( LPTSTR lpPrinterName )
  60. {
  61. LPTSTR lpKeyName = NAME_MUST_START_WITH;
  62. int i;
  63. while ( *lpKeyName != '\000' ) {
  64. if (*lpPrinterName == '\000' ){
  65. return(FALSE);
  66. }
  67. if (*lpPrinterName != *lpKeyName) {
  68. return(FALSE);
  69. }
  70. lpKeyName++;
  71. lpPrinterName++;
  72. }
  73. return(TRUE);
  74. }
  75. LPTSTR PrnGetNextName(LPTSTR lptNameContains,int iMinJobsOnPrinter)
  76. {
  77. LPTSTR lptRetVal;
  78. int x;
  79. while (TRUE) {
  80. if (GetTickCount() > Printers.dwUpdateTime ) {
  81. LocalFree(Printers.lpPrinters);
  82. generateprinterlist();
  83. }
  84. for (x=0;x < Printers.iNumPrinters;x++ ) {
  85. if (Printers.lpPrinters[Printers.iCurPrinter].cJobs < (WORD) iMinJobsOnPrinter &&
  86. IsPrinterUsable( Printers.lpPrinters[Printers.iCurPrinter].pPrinterName)) {
  87. // This is a candidate...
  88. lptRetVal = Printers.lpPrinters[Printers.iCurPrinter].pPrinterName;
  89. Printers.lpPrinters[Printers.iCurPrinter].cJobs++;
  90. if (++Printers.iCurPrinter >= Printers.iNumPrinters) {
  91. Printers.iCurPrinter =0;
  92. }
  93. return(lptRetVal);
  94. }
  95. if (++Printers.iCurPrinter >= Printers.iNumPrinters) {
  96. Printers.iCurPrinter =0;
  97. }
  98. }
  99. printf("\nStarting sleep...");
  100. Sleep(SLEEP_TIME);
  101. printf("\nDone sleeping");
  102. }
  103. return(lptRetVal);
  104. }
  105. //
  106. // This function will enum the file mask requsted and for each file matching
  107. // call the callback functions
  108. //
  109. DoFileEnumWithCallBack( LPTSTR lptFileMask, FILEENUMPROC pProc, LPVOID lpVoid )
  110. {
  111. HANDLE hFind;
  112. WIN32_FIND_DATA FindData;
  113. LPTSTR lpChar;
  114. LPTSTR lpSepPos;
  115. BOOL bFoundPathSeperator = FALSE;
  116. TCHAR szPathHolder[MAX_PATH];
  117. //
  118. // Get it into local storage
  119. //
  120. lstrcpy( szPathHolder, lptFileMask);
  121. // The trick here is to decide if we need to generate a full path if the
  122. // mask included a path, because the findnextfile code will only return
  123. // file names.
  124. // Now start processing
  125. hFind = FindFirstFile( szPathHolder, &FindData );
  126. if (hFind != (HANDLE)INVALID_HANDLE_VALUE){
  127. lpChar = szPathHolder;
  128. lpSepPos = lpChar;
  129. // Go to the end
  130. while(*lpChar++ ) {
  131. if (*lpChar == '\\' || *lpChar == ':') {
  132. bFoundPathSeperator = TRUE;
  133. lpSepPos = lpChar;
  134. }
  135. }
  136. if (bFoundPathSeperator) {
  137. //Make the char following the last path component a NULL
  138. //So we can prepend the REAL path before calling the callback func
  139. lpSepPos++;
  140. }
  141. do {
  142. //
  143. // Now form a full path name and call the callback
  144. // Break out of the loop if the callback returns FALSE
  145. //
  146. if (!(FindData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) {
  147. lstrcpy( lpSepPos, FindData.cFileName );
  148. if (!pProc( &FindData, szPathHolder, lpVoid )) {
  149. break;
  150. }
  151. }
  152. } while ( FindNextFile(hFind, &FindData ));
  153. // DJC error here??
  154. FindClose(hFind);
  155. }
  156. return(1);
  157. }
  158. //int _cdecl main(int argc, char **argv)
  159. BOOL do_job( LPWIN32_FIND_DATA lpFind, WCHAR *wchOpenName, LPVOID lpVoid)
  160. {
  161. static char wstrData[CHAR_COUNT];
  162. DWORD cbNeeded;
  163. DWORD cReturned;
  164. PRINTER_DEFAULTS Defaults;
  165. HANDLE hPrinter=0;
  166. HANDLE hFile;
  167. HDC hDC;
  168. LPTSTR lpName=TEXT("PSTODIB Local Test Printer");
  169. DOCINFO docInfo;
  170. DOC_INFO_1 doc1;
  171. DWORD dwTotalWrote=0;
  172. static BOOL bIgnore=TRUE;
  173. #ifdef HACK_JOB
  174. //HAck to start where jobs left off...
  175. printf("\nHACK ENABLED to skip jobs........................");
  176. if (lstrcmpi(wchOpenName,L"x:00064.spl") == 0 ) {
  177. bIgnore = FALSE;
  178. }
  179. if (bIgnore) {
  180. return(TRUE);
  181. }
  182. #endif
  183. docInfo.cbSize = sizeof(DOCINFO);
  184. docInfo.lpszDocName = wchOpenName;
  185. docInfo.lpszOutput = NULL;
  186. // 1st convert to wide format
  187. hFile = CreateFile( wchOpenName,
  188. GENERIC_READ,
  189. FILE_SHARE_READ,
  190. (LPSECURITY_ATTRIBUTES) NULL,
  191. OPEN_EXISTING,
  192. FILE_ATTRIBUTE_NORMAL,
  193. (HANDLE) NULL );
  194. if ( hFile == INVALID_HANDLE_VALUE) {
  195. printf("\nSorry cannot open %ws", wchOpenName);
  196. exit(1);
  197. }
  198. //wprintf(TEXT("hello argument is %ts"), argv[0]);
  199. Defaults.pDatatype = PSTODIB_DATATYPE;
  200. Defaults.pDevMode = NULL;
  201. Defaults.DesiredAccess = PRINTER_ACCESS_USE;
  202. if (bDoEnumPrinters) {
  203. // Were enuming printers so get the next one in the list....
  204. lpName = PrnGetNextName(TEXT("PSTODIB"),5);
  205. }
  206. if (!OpenPrinter(lpName, &hPrinter, &Defaults )) {
  207. printf("\nCannot open the printer? %u", GetLastError());
  208. } else {
  209. DWORD dwBytesRead,dwPrintWrote;
  210. doc1.pDocName = wchOpenName;
  211. doc1.pOutputFile = NULL;
  212. doc1.pDatatype = NULL;
  213. StartDocPrinter( hPrinter, 1, (LPBYTE) &doc1 );
  214. printf("\nSubmitting %ws", wchOpenName);
  215. ReadFile( hFile, wstrData, CHAR_COUNT, &dwBytesRead, NULL);
  216. while ( dwBytesRead != 0 ) {
  217. if (wstrData[dwBytesRead - 1 ] == 0x1a) {
  218. dwBytesRead--;
  219. }
  220. WritePrinter( hPrinter, wstrData, dwBytesRead, &dwPrintWrote );
  221. dwTotalWrote += dwBytesRead;
  222. ReadFile( hFile, wstrData, CHAR_COUNT, &dwBytesRead, NULL);
  223. }
  224. EndDocPrinter(hPrinter);
  225. printf("\nDone with job total wrote %d", dwTotalWrote);
  226. // WritePrinter( hPrinter, (LPVOID) wstrData,
  227. ClosePrinter( hPrinter);
  228. }
  229. CloseHandle(hFile);
  230. return(TRUE);
  231. }
  232. #define ONE_FILE
  233. int __cdecl main( int argc, char **argv)
  234. {
  235. HANDLE hEnumFile;
  236. WIN32_FIND_DATA findInfo;
  237. WCHAR wchOpenName[MAX_PATH];
  238. int *xxx;
  239. if (argc < 2 ) {
  240. printf("\nUsage: test [-m] <full path filemask of postscript files to submit>");
  241. printf("\n Without the -m, test will submit to a printer called:");
  242. printf("\n PSTODIB Local Test Printer");
  243. printf("\n If the -m is included, it will roundrobin submit jobs to");
  244. printf("\n any local printers whose names begin with STRESS<foo>");
  245. printf("\n note STRESS must be ALL caps");
  246. printf("\n");
  247. exit(1);
  248. }
  249. OemToChar((LPSTR) argv[1], (LPTSTR) wchOpenName);
  250. if (lstrcmpi(wchOpenName,TEXT("-m")) == 0) {
  251. printf("\nSubmitting jobs to ALL local printers (STRES<fooo>) for stress!");
  252. bDoEnumPrinters=TRUE;
  253. generateprinterlist();
  254. OemToChar((LPSTR) argv[2], (LPTSTR) wchOpenName);
  255. }
  256. DoFileEnumWithCallBack( wchOpenName, do_job, (LPVOID) NULL );
  257. return(1);
  258. }