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.

713 lines
16 KiB

  1. /*++
  2. Copyright (c) 1990-2003 Microsoft Corporation
  3. Module Name:
  4. readgpc.c
  5. Abstract:
  6. This module contain functions to read the PLOTGPC data file
  7. Development History:
  8. 15-Nov-1993 Mon 10:00:01 created
  9. [Environment:]
  10. GDI Device Driver - Plotter.
  11. --*/
  12. #include "precomp.h"
  13. #pragma hdrstop
  14. extern DEVHTINFO DefDevHTInfo;
  15. BOOL
  16. ValidateFormSrc(
  17. PGPCVARSIZE pFormGPC,
  18. SIZEL DeviceSize,
  19. BOOL DevRollFeed
  20. )
  21. /*++
  22. Routine Description:
  23. This function validate if FORMSRC has valid filed in it
  24. Arguments:
  25. pFormGPC - pointer to the GPCVARSIZE for the form data.
  26. DeviceSize - Device size to check against,
  27. DevRollFeed - TRUE if device can do roll feed
  28. Return Value:
  29. BOOL return value, the fields already verified and corrected.
  30. Development History:
  31. 15-Nov-1993 Mon 10:34:29 created
  32. --*/
  33. {
  34. PFORMSRC pFS;
  35. LONG cy;
  36. UINT Count;
  37. BOOL InvalidFS;
  38. BOOL Ok = TRUE;
  39. pFS = (PFORMSRC)pFormGPC->pData;
  40. Count = (UINT)pFormGPC->Count;
  41. while (Count--) {
  42. InvalidFS = FALSE;
  43. //
  44. // Make sure that imageable area is less or eqaul to the size
  45. //
  46. if (pFS->Size.cy) {
  47. if (pFS->Size.cy < MIN_PLOTGPC_FORM_CY) {
  48. //
  49. // Make it as variable length paper
  50. //
  51. PLOTERR(("Invalid Form CY, make it as variable length (%ld)",
  52. pFS->Size.cy));
  53. pFS->Size.cy = 0;
  54. }
  55. }
  56. if (!(cy = pFS->Size.cy)) {
  57. cy = DeviceSize.cy;
  58. }
  59. if (((pFS->Size.cx <= DeviceSize.cx) &&
  60. (pFS->Size.cy <= cy)) ||
  61. ((pFS->Size.cy <= DeviceSize.cx) &&
  62. (pFS->Size.cx <= cy))) {
  63. NULL;
  64. } else {
  65. PLOTERR(("Invalid Form Size, too big for device to handle"));
  66. InvalidFS = TRUE;
  67. }
  68. if ((pFS->Size.cy) &&
  69. ((pFS->Size.cy - pFS->Margin.top - pFS->Margin.bottom) <
  70. MIN_PLOTGPC_FORM_CY)) {
  71. PLOTERR(("Invalid Form CY or top/bottom margins"));
  72. InvalidFS = TRUE;
  73. }
  74. if ((pFS->Size.cx < MIN_PLOTGPC_FORM_CX) ||
  75. ((pFS->Size.cx - pFS->Margin.left - pFS->Margin.right) <
  76. MIN_PLOTGPC_FORM_CX)) {
  77. PLOTERR(("Invalid Form CX or left/right margins"));
  78. InvalidFS = TRUE;
  79. }
  80. if ((!DevRollFeed) && (pFS->Size.cy == 0)) {
  81. InvalidFS = TRUE;
  82. PLOTERR(("The device cannot handle roll paper %hs", pFS->Name));
  83. }
  84. if (InvalidFS) {
  85. PLOTERR(("ValidateFormSrc: invalid form data, (removed it)"));
  86. Ok = FALSE;
  87. if (Count) {
  88. CopyMemory(pFS, pFS + 1, sizeof(FORMSRC));
  89. }
  90. pFormGPC->Count -= 1;
  91. } else {
  92. //
  93. // Make sure ansi ascii end with a NULL
  94. //
  95. pFS->Name[sizeof(pFS->Name) - 1] = '\0';
  96. ++pFS;
  97. }
  98. }
  99. if (!pFormGPC->Count) {
  100. PLOTERR(("ValidateFormSrc: NO form are valid, count = 0"));
  101. ZeroMemory(pFormGPC, sizeof(GPCVARSIZE));
  102. }
  103. return(Ok);
  104. }
  105. DWORD
  106. PickDefaultHTPatSize(
  107. WORD xDPI,
  108. WORD yDPI,
  109. BOOL HTFormat8BPP
  110. )
  111. /*++
  112. Routine Description:
  113. This function return default halftone pattern size used for a particular
  114. device resolution
  115. Arguments:
  116. xDPI - Device LOGPIXELS X
  117. yDPI - Device LOGPIXELS Y
  118. 8BitHalftone - If a 8-bit halftone will be used
  119. Return Value:
  120. DWORD HT_PATSIZE_xxxx
  121. Development History:
  122. 29-Jun-1993 Tue 14:46:49 created
  123. --*/
  124. {
  125. DWORD HTPatSize;
  126. //
  127. // use the smaller resolution as the pattern guide
  128. //
  129. if (xDPI > yDPI) {
  130. xDPI = yDPI;
  131. }
  132. if (xDPI >= 2400) {
  133. HTPatSize = HT_PATSIZE_16x16_M;
  134. } else if (xDPI >= 1800) {
  135. HTPatSize = HT_PATSIZE_14x14_M;
  136. } else if (xDPI >= 1200) {
  137. HTPatSize = HT_PATSIZE_12x12_M;
  138. } else if (xDPI >= 900) {
  139. HTPatSize = HT_PATSIZE_10x10_M;
  140. } else if (xDPI >= 400) {
  141. HTPatSize = HT_PATSIZE_8x8_M;
  142. } else if (xDPI >= 180) {
  143. HTPatSize = HT_PATSIZE_6x6_M;
  144. } else {
  145. HTPatSize = HT_PATSIZE_4x4_M;
  146. }
  147. if (HTFormat8BPP) {
  148. HTPatSize -= 2;
  149. }
  150. return(HTPatSize);
  151. }
  152. BOOL
  153. ValidatePlotGPC(
  154. PPLOTGPC pPlotGPC
  155. )
  156. /*++
  157. Routine Description:
  158. This function validate a PLOTGPC data structure
  159. Arguments:
  160. pPlotGPC
  161. Return Value:
  162. BOOL
  163. Development History:
  164. 15-Feb-1994 Tue 22:49:40 updated
  165. Update the pen plotter validation for the bitmap font and color
  166. 15-Nov-1993 Mon 10:11:58 created
  167. Revision History:
  168. 02-Apr-1995 Sun 11:23:46 updated
  169. Update the COLORINFO checking so it will make to NT3.51's default
  170. and not compute the devpels on the spot.
  171. --*/
  172. {
  173. if ((pPlotGPC->ID != PLOTGPC_ID) ||
  174. (pPlotGPC->cjThis != sizeof(PLOTGPC))) {
  175. PLOTERR(("ValidatePlotGPC: invalid PLOTGPC data (ID/Size)"));
  176. return(FALSE);
  177. }
  178. pPlotGPC->DeviceName[sizeof(pPlotGPC->DeviceName) - 1] = '\0';
  179. pPlotGPC->Flags &= PLOTF_ALL_FLAGS;
  180. //
  181. // Validate device size and its margin
  182. //
  183. if (pPlotGPC->DeviceSize.cx - (pPlotGPC->DeviceMargin.left +
  184. pPlotGPC->DeviceMargin.right) < MIN_PLOTGPC_FORM_CX) {
  185. PLOTERR(("Invalid Device CX (%ld) set to default",
  186. pPlotGPC->DeviceSize.cx));
  187. pPlotGPC->DeviceSize.cx = pPlotGPC->DeviceMargin.left +
  188. pPlotGPC->DeviceMargin.right +
  189. MIN_PLOTGPC_FORM_CX;
  190. }
  191. if (pPlotGPC->DeviceSize.cy < MIN_PLOTGPC_FORM_CY) {
  192. PLOTERR(("Invalid Device CY (%ld) default to 50' long",
  193. pPlotGPC->DeviceSize.cx));
  194. pPlotGPC->DeviceSize.cy = 15240000;
  195. }
  196. if (pPlotGPC->DeviceSize.cy - (pPlotGPC->DeviceMargin.top +
  197. pPlotGPC->DeviceMargin.bottom) < MIN_PLOTGPC_FORM_CY) {
  198. PLOTERR(("Invalid Device CY (%ld) set to default",
  199. pPlotGPC->DeviceSize.cy));
  200. pPlotGPC->DeviceSize.cx = pPlotGPC->DeviceMargin.top +
  201. pPlotGPC->DeviceMargin.bottom +
  202. MIN_PLOTGPC_FORM_CY;
  203. }
  204. //
  205. // For now we must have 1:1 ratio
  206. //
  207. if (pPlotGPC->PlotXDPI != pPlotGPC->PlotYDPI) {
  208. pPlotGPC->PlotYDPI = pPlotGPC->PlotXDPI;
  209. }
  210. if (pPlotGPC->RasterXDPI != pPlotGPC->RasterYDPI) {
  211. pPlotGPC->RasterYDPI = pPlotGPC->RasterXDPI;
  212. }
  213. if (pPlotGPC->ROPLevel > ROP_LEVEL_MAX) {
  214. pPlotGPC->ROPLevel = ROP_LEVEL_MAX;
  215. }
  216. if (pPlotGPC->MaxScale > MAX_SCALE_MAX) {
  217. pPlotGPC->MaxScale = MAX_SCALE_MAX;
  218. }
  219. if ((!(pPlotGPC->Flags & PLOTF_RASTER)) &&
  220. (pPlotGPC->MaxPens > MAX_PENPLOTTER_PENS)) {
  221. pPlotGPC->MaxPens = MAX_PENPLOTTER_PENS;
  222. }
  223. if (pPlotGPC->MaxPolygonPts < 3) { // minimum 3 points to make up a
  224. // region
  225. pPlotGPC->MaxPolygonPts = 0;
  226. }
  227. if (pPlotGPC->MaxQuality > MAX_QUALITY_MAX) {
  228. pPlotGPC->MaxQuality = MAX_QUALITY_MAX;
  229. }
  230. if (pPlotGPC->Flags & PLOTF_PAPERTRAY) {
  231. if ((pPlotGPC->PaperTraySize.cx != pPlotGPC->DeviceSize.cx) &&
  232. (pPlotGPC->PaperTraySize.cy != pPlotGPC->DeviceSize.cx)) {
  233. PLOTERR(("Invalid PaperTraySize (%ld x %ld), Make it as DeviceSize",
  234. pPlotGPC->PaperTraySize.cx,
  235. pPlotGPC->PaperTraySize.cy));
  236. pPlotGPC->PaperTraySize.cx = pPlotGPC->DeviceSize.cx;
  237. pPlotGPC->PaperTraySize.cy = pPlotGPC->DeviceSize.cy;
  238. }
  239. } else {
  240. pPlotGPC->PaperTraySize.cx =
  241. pPlotGPC->PaperTraySize.cy = 0;
  242. }
  243. if (!pPlotGPC->ci.Cyan.Y) {
  244. //
  245. // This is NT3.51 default
  246. //
  247. pPlotGPC->ci = DefDevHTInfo.ColorInfo;
  248. pPlotGPC->DevicePelsDPI = 0;
  249. } else if ((pPlotGPC->DevicePelsDPI < 30) ||
  250. (pPlotGPC->DevicePelsDPI > pPlotGPC->RasterXDPI)) {
  251. pPlotGPC->DevicePelsDPI = 0;
  252. }
  253. if (pPlotGPC->HTPatternSize > HT_PATSIZE_16x16_M) {
  254. pPlotGPC->HTPatternSize = PickDefaultHTPatSize(pPlotGPC->RasterXDPI,
  255. pPlotGPC->RasterYDPI,
  256. FALSE);
  257. }
  258. if ((pPlotGPC->InitString.Count != 1) ||
  259. (!pPlotGPC->InitString.SizeEach) ||
  260. (!pPlotGPC->InitString.pData)) {
  261. ZeroMemory(&(pPlotGPC->InitString), sizeof(GPCVARSIZE));
  262. }
  263. if ((pPlotGPC->Forms.Count) &&
  264. (pPlotGPC->Forms.SizeEach == sizeof(FORMSRC)) &&
  265. (pPlotGPC->Forms.pData)) {
  266. ValidateFormSrc(&(pPlotGPC->Forms),
  267. pPlotGPC->DeviceSize,
  268. (pPlotGPC->Flags & PLOTF_ROLLFEED));
  269. } else {
  270. ZeroMemory(&(pPlotGPC->Forms), sizeof(GPCVARSIZE));
  271. }
  272. if (!(pPlotGPC->Flags & PLOTF_RASTER)) {
  273. //
  274. // PEN PLOTTER MUST COLOR and NO_BMP_FONT
  275. //
  276. pPlotGPC->Flags |= (PLOTF_NO_BMP_FONT | PLOTF_COLOR);
  277. }
  278. if ((!(pPlotGPC->Flags & PLOTF_RASTER)) &&
  279. (pPlotGPC->Pens.Count) &&
  280. (pPlotGPC->Pens.SizeEach == sizeof(PENDATA)) &&
  281. (pPlotGPC->Pens.pData)) {
  282. UINT i;
  283. PPENDATA pPD;
  284. pPD = (PPENDATA)pPlotGPC->Pens.pData;
  285. for (i = 0; i < (UINT)pPlotGPC->MaxPens; i++, pPD++) {
  286. if (pPD->ColorIdx > PC_IDX_LAST) {
  287. PLOTERR(("Invalid ColorIndex (%ld), set to default",
  288. pPD->ColorIdx));
  289. pPD->ColorIdx = PC_IDX_FIRST;
  290. }
  291. }
  292. } else {
  293. ZeroMemory(&(pPlotGPC->Pens), sizeof(GPCVARSIZE));
  294. }
  295. return(TRUE);
  296. }
  297. VOID
  298. CopyPlotGPCFromPCD(
  299. PPLOTGPC pPlotGPC,
  300. PPLOTGPC_PCD pPlotGPC_PCD
  301. )
  302. /*++
  303. Routine Description:
  304. This function copies a PLOTGPC_PCD structure into a PLOTGPC structure.
  305. Arguments:
  306. pPlotGPC - destination
  307. pPlotGPC_PCD - source
  308. Return Value:
  309. None
  310. Development History:
  311. 1 Feb 2000
  312. Revision History:
  313. --*/
  314. {
  315. // All the datatypes upto InitString are the same in both the structures.
  316. CopyMemory(pPlotGPC,
  317. pPlotGPC_PCD,
  318. (LPBYTE)&(pPlotGPC_PCD->InitString) - (LPBYTE)pPlotGPC_PCD);
  319. // We replace sizeof(PLOTGPC_PCD) with sizeof(PLOTGPC)
  320. pPlotGPC->cjThis = sizeof(PLOTGPC);
  321. pPlotGPC->InitString.Count = pPlotGPC_PCD->InitString.Count;
  322. pPlotGPC->InitString.SizeEach = pPlotGPC_PCD->InitString.SizeEach;
  323. if (pPlotGPC_PCD->InitString.pData) {
  324. pPlotGPC->InitString.pData = (LPVOID)(pPlotGPC_PCD->InitString.pData
  325. + (sizeof(PLOTGPC) - sizeof(PLOTGPC_PCD)));
  326. } else {
  327. pPlotGPC->InitString.pData = NULL;
  328. }
  329. pPlotGPC->Forms.Count = pPlotGPC_PCD->Forms.Count;
  330. pPlotGPC->Forms.SizeEach = pPlotGPC_PCD->Forms.SizeEach;
  331. if (pPlotGPC_PCD->Forms.pData) {
  332. pPlotGPC->Forms.pData = (LPVOID)(pPlotGPC_PCD->Forms.pData
  333. + (sizeof(PLOTGPC) - sizeof(PLOTGPC_PCD)));
  334. } else {
  335. pPlotGPC->Forms.pData = NULL;
  336. }
  337. pPlotGPC->Pens.Count = pPlotGPC_PCD->Pens.Count;
  338. pPlotGPC->Pens.SizeEach = pPlotGPC_PCD->Pens.SizeEach;
  339. if (pPlotGPC_PCD->Pens.pData) {
  340. pPlotGPC->Pens.pData = (LPVOID)(pPlotGPC_PCD->Pens.pData
  341. + (sizeof(PLOTGPC) - sizeof(PLOTGPC_PCD)));
  342. } else {
  343. pPlotGPC->Pens.pData = NULL;
  344. }
  345. }
  346. PPLOTGPC
  347. ReadPlotGPCFromFile(
  348. PWSTR pwsDataFile
  349. )
  350. /*++
  351. Routine Description:
  352. This function open/read the PlotGPC data file and validate them also
  353. Arguments:
  354. pwsDataFile - a pointer to full qualify path for the data file name
  355. Return Value:
  356. BOOL - to indicate state
  357. Development History:
  358. 15-Nov-1993 Mon 10:01:17 created
  359. Revision History:
  360. --*/
  361. {
  362. HANDLE hFile;
  363. DWORD dwSize;
  364. PLOTGPC_PCD PlotGPC_PCD;
  365. BOOL bSuccess = TRUE;
  366. PPLOTGPC pPlotGPC = NULL;
  367. if ((hFile = OpenPlotFile(pwsDataFile)) == (HANDLE)INVALID_HANDLE_VALUE) {
  368. PLOTERR(("ReadPlotGPCFromFile: Open data file failed"));
  369. return(NULL);
  370. }
  371. if ((ReadPlotFile(hFile, &PlotGPC_PCD, sizeof(PLOTGPC_PCD), &dwSize)) &&
  372. (dwSize == sizeof(PLOTGPC_PCD))) {
  373. if ((PlotGPC_PCD.ID != PLOTGPC_ID) ||
  374. (PlotGPC_PCD.cjThis != sizeof(PLOTGPC_PCD))) {
  375. bSuccess = FALSE;
  376. PLOTERR(("ReadPlotGPCFromFile: invalid data file"));
  377. }
  378. } else {
  379. bSuccess = FALSE;
  380. PLOTERR(("ReadPlotGPCFromFile: Read data file failed"));
  381. }
  382. //
  383. // if we have pPlotGPC_PCD == NULL then an error ocurred
  384. //
  385. if (bSuccess) {
  386. dwSize = PlotGPC_PCD.SizeExtra + sizeof(PLOTGPC);
  387. if (pPlotGPC = (PPLOTGPC)LocalAlloc(LPTR, dwSize)) {
  388. CopyPlotGPCFromPCD(pPlotGPC, &PlotGPC_PCD);
  389. if ((PlotGPC_PCD.SizeExtra) &&
  390. (ReadPlotFile(hFile,
  391. (LPBYTE)pPlotGPC + sizeof(PLOTGPC),
  392. PlotGPC_PCD.SizeExtra,
  393. &dwSize)) &&
  394. (dwSize == PlotGPC_PCD.SizeExtra)) {
  395. if ((pPlotGPC->InitString.Count == 1) &&
  396. (pPlotGPC->InitString.SizeEach) &&
  397. (pPlotGPC->InitString.pData)) {
  398. (LPBYTE)pPlotGPC->InitString.pData += (ULONG_PTR)pPlotGPC;
  399. } else {
  400. ZeroMemory(&(pPlotGPC->InitString), sizeof(GPCVARSIZE));
  401. }
  402. if ((pPlotGPC->Forms.Count) &&
  403. (pPlotGPC->Forms.SizeEach == sizeof(FORMSRC)) &&
  404. (pPlotGPC->Forms.pData)) {
  405. (LPBYTE)pPlotGPC->Forms.pData += (ULONG_PTR)pPlotGPC;
  406. } else {
  407. ZeroMemory(&(pPlotGPC->Forms), sizeof(GPCVARSIZE));
  408. }
  409. if ((pPlotGPC->Pens.Count) &&
  410. (pPlotGPC->Pens.SizeEach == sizeof(PENDATA)) &&
  411. (pPlotGPC->Pens.pData)) {
  412. (LPBYTE)pPlotGPC->Pens.pData += (ULONG_PTR)pPlotGPC;
  413. } else {
  414. ZeroMemory(&(pPlotGPC->Pens), sizeof(GPCVARSIZE));
  415. }
  416. } else {
  417. //
  418. // Failed to read, free the memory and return NULL
  419. //
  420. LocalFree((HLOCAL)pPlotGPC);
  421. pPlotGPC = NULL;
  422. PLOTERR(("ReadPlotGPCFromFile: read variable size data failed"));
  423. }
  424. } else {
  425. PLOTERR(("ReadPlotGPCFromFile: allocate memory (%lu bytes) failed",
  426. dwSize));
  427. }
  428. }
  429. ClosePlotFile(hFile);
  430. if (pPlotGPC) {
  431. ValidatePlotGPC(pPlotGPC);
  432. }
  433. return(pPlotGPC);
  434. }