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.

665 lines
21 KiB

  1. /*******************************************************************************
  2. *
  3. * (C) COPYRIGHT MICROSOFT CORP., 2000
  4. *
  5. * TITLE: validate.cpp
  6. *
  7. * VERSION: 1.0
  8. *
  9. * DATE: 17 July, 2000
  10. *
  11. * DESCRIPTION:
  12. *
  13. *******************************************************************************/
  14. #include "pch.h"
  15. extern HINSTANCE g_hInst; // used for WIAS_LOGPROC macro
  16. /**************************************************************************\
  17. * ValidateDataTransferContext
  18. *
  19. * Checks the data transfer context to ensure it's valid.
  20. *
  21. * Arguments:
  22. *
  23. * pDataTransferContext - Pointer the data transfer context.
  24. *
  25. * Return Value:
  26. *
  27. * Status
  28. *
  29. * History:
  30. *
  31. * 7/18/2000 Original Version
  32. *
  33. \**************************************************************************/
  34. HRESULT CWIAScannerDevice::ValidateDataTransferContext(
  35. PMINIDRV_TRANSFER_CONTEXT pDataTransferContext)
  36. {
  37. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  38. WIALOG_NO_RESOURCE_ID,
  39. WIALOG_LEVEL3,
  40. "::ValidateDataTransferContext");
  41. if (pDataTransferContext->lSize != sizeof(MINIDRV_TRANSFER_CONTEXT)) {
  42. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("ValidateDataTransferContext, invalid data transfer context"));
  43. return E_INVALIDARG;;
  44. }
  45. //
  46. // for TYMED file, only WiaImgFmt_BMP is allowed by this driver
  47. //
  48. if (pDataTransferContext->tymed == TYMED_FILE) {
  49. if (pDataTransferContext->guidFormatID != WiaImgFmt_BMP) {
  50. if (pDataTransferContext->guidFormatID != WiaImgFmt_TIFF) {
  51. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("ValidateDataTransferContext, invalid format for TYMED_FILE"));
  52. return E_INVALIDARG;
  53. }
  54. }
  55. }
  56. //
  57. // for TYMED CALLBACK, only WiaImgFmt_MEMORYBMP is allowed by this driver
  58. //
  59. if (pDataTransferContext->tymed == TYMED_CALLBACK) {
  60. if (pDataTransferContext->guidFormatID != WiaImgFmt_MEMORYBMP) {
  61. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("ValidateDataTransferContext, invalid format for TYMED_CALLBACK"));
  62. return E_INVALIDARG;;
  63. }
  64. }
  65. return S_OK;
  66. }
  67. /**************************************************************************\
  68. * UpdateValidDepth
  69. *
  70. * Helper that updates the valid value for depth based on the data type.
  71. *
  72. * Arguments:
  73. *
  74. * pWiasContext - a pointer to the WiaItem context
  75. * lDataType - the value of the DataType property.
  76. * lDepth - the address of the variable where the Depth's new value
  77. * will be returned.
  78. *
  79. * Return Value:
  80. *
  81. * Status - S_OK if successful
  82. * E_INVALIDARG if lDataType is unknown
  83. * Errors are those returned by wiasReadPropLong,
  84. * and wiasWritePropLong.
  85. *
  86. * History:
  87. *
  88. * 7/18/2000 Original Version
  89. *
  90. \**************************************************************************/
  91. HRESULT CWIAScannerDevice::UpdateValidDepth(
  92. BYTE *pWiasContext,
  93. LONG lDataType,
  94. LONG *lDepth)
  95. {
  96. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  97. WIALOG_NO_RESOURCE_ID,
  98. WIALOG_LEVEL3,
  99. "CWIAScannerDevice::UpdateValidDepth");
  100. HRESULT hr = S_OK;
  101. LONG pValidDepth[1];
  102. switch (lDataType) {
  103. case WIA_DATA_THRESHOLD:
  104. pValidDepth[0] = 1;
  105. break;
  106. case WIA_DATA_GRAYSCALE:
  107. pValidDepth[0] = 8;
  108. break;
  109. case WIA_DATA_COLOR:
  110. pValidDepth[0] = 24;
  111. break;
  112. default:
  113. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("UpdateValidDepth, unknown data type"));
  114. return E_INVALIDARG;
  115. }
  116. if (lDepth) {
  117. *lDepth = pValidDepth[0];
  118. }
  119. return hr;
  120. }
  121. /**************************************************************************\
  122. * CheckDataType
  123. *
  124. * This helper method is called to check whether WIA_IPA_DATATYPE
  125. * property is changed. When this property changes, other dependant
  126. * properties and their valid values must also be changed.
  127. *
  128. * Arguments:
  129. *
  130. * pWiasContext - a pointer to the item context whose properties have
  131. * changed.
  132. * pContext - a pointer to the property context (which indicates
  133. * which properties are being written).
  134. *
  135. * Return Value:
  136. *
  137. * Status
  138. *
  139. * History:
  140. *
  141. * 7/18/2000 Original Version
  142. *
  143. \**************************************************************************/
  144. HRESULT CWIAScannerDevice::CheckDataType(
  145. BYTE *pWiasContext,
  146. WIA_PROPERTY_CONTEXT *pContext)
  147. {
  148. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  149. WIALOG_NO_RESOURCE_ID,
  150. WIALOG_LEVEL3,
  151. "CWIAScannerDevice::CheckDataType");
  152. WIAS_CHANGED_VALUE_INFO cviDataType, cviDepth;
  153. HRESULT hr = S_OK;
  154. //
  155. // Call wiasGetChangedValue for DataType. It is checked first since it's
  156. // not dependant on any other property. All properties in this method
  157. // that follow are dependant properties of DataType.
  158. //
  159. // The call to wiasGetChangedValue specifies that validation should not be
  160. // skipped (since valid values for DataType never change). Also,
  161. // the address of a variable for the old value is NULL, since the old
  162. // value is not needed. The address of bDataTypeChanged is passed
  163. // so that dependant properties will know whether the DataType is being
  164. // changed or not. This is important since dependant properties may need
  165. // their valid values updated and may need to be folded to new valid
  166. // values.
  167. //
  168. hr = wiasGetChangedValueLong(pWiasContext,
  169. pContext,
  170. FALSE,
  171. WIA_IPA_DATATYPE,
  172. &cviDataType);
  173. if (FAILED(hr)) {
  174. return hr;
  175. }
  176. //
  177. // Call wiasGetChangedValue for Depth. Depth is a dependant property of
  178. // DataType whose valid value changes according to what the current
  179. // value of DataType is.
  180. //
  181. // The call to wiasGetChangedValue specifies that validation should only
  182. // be skipped if the DataType has changed. This is because the valid
  183. // values for Depth will change according to the new value for
  184. // DataType. The address of a variable for the old value is NULL, since
  185. // the old value is not needed. The address of bDepthChanged is passed
  186. // so that dependant properties will know whether the Depth is being
  187. // changed or not. This is important since dependant properties may need
  188. // their valid values updated and may need to be folded to new valid
  189. // values.
  190. //
  191. hr = wiasGetChangedValueLong(pWiasContext,
  192. pContext,
  193. cviDataType.bChanged,
  194. WIA_IPA_DEPTH,
  195. &cviDepth);
  196. if (FAILED(hr)) {
  197. return hr;
  198. }
  199. if (cviDataType.bChanged) {
  200. //
  201. // DataType changed so update valid value for Depth
  202. //
  203. hr = UpdateValidDepth(pWiasContext, cviDataType.Current.lVal, &cviDepth.Current.lVal);
  204. if (SUCCEEDED(hr)) {
  205. //
  206. // Check whether we must fold. Depth will only be folded if it
  207. // is not one of the properties that the app is changing.
  208. //
  209. if (!cviDepth.bChanged) {
  210. hr = wiasWritePropLong(pWiasContext, WIA_IPA_DEPTH, cviDepth.Current.lVal);
  211. }
  212. }
  213. }
  214. //
  215. // Update properties dependant on DataType and Depth.
  216. // Here, ChannelsPerPixel and BitsPerChannel are updated.
  217. //
  218. if (cviDataType.bChanged || cviDepth.bChanged) {
  219. if (SUCCEEDED(hr)) {
  220. #define NUM_PROPS_TO_SET 2
  221. PROPSPEC ps[NUM_PROPS_TO_SET] = {
  222. {PRSPEC_PROPID, WIA_IPA_CHANNELS_PER_PIXEL},
  223. {PRSPEC_PROPID, WIA_IPA_BITS_PER_CHANNEL}};
  224. PROPVARIANT pv[NUM_PROPS_TO_SET];
  225. for (LONG index = 0; index < NUM_PROPS_TO_SET; index++) {
  226. PropVariantInit(&pv[index]);
  227. pv[index].vt = VT_I4;
  228. }
  229. switch (cviDataType.Current.lVal) {
  230. case WIA_DATA_THRESHOLD:
  231. pv[0].lVal = 1;
  232. pv[1].lVal = 1;
  233. break;
  234. case WIA_DATA_GRAYSCALE:
  235. pv[0].lVal = 1;
  236. pv[1].lVal = 8;
  237. break;
  238. case WIA_DATA_COLOR:
  239. pv[0].lVal = 3;
  240. pv[1].lVal = 8;
  241. break;
  242. default:
  243. pv[0].lVal = 1;
  244. pv[1].lVal = 8;
  245. break;
  246. }
  247. hr = wiasWriteMultiple(pWiasContext, NUM_PROPS_TO_SET, ps, pv);
  248. }
  249. }
  250. return hr;
  251. }
  252. /**************************************************************************\
  253. * CheckIntent
  254. *
  255. * This helper method is called to make the relevant changes if the
  256. * Current Intent property changes.
  257. *
  258. * Arguments:
  259. *
  260. * pWiasContext - a pointer to the item context whose properties have
  261. * changed.
  262. * pContext - a pointer to the property context (which indicates
  263. * which properties are being written).
  264. *
  265. * Return Value:
  266. *
  267. * Status
  268. *
  269. * History:
  270. *
  271. * 7/18/2000 Original Version
  272. *
  273. \**************************************************************************/
  274. HRESULT CWIAScannerDevice::CheckIntent(
  275. BYTE *pWiasContext,
  276. WIA_PROPERTY_CONTEXT *pContext)
  277. {
  278. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  279. WIALOG_NO_RESOURCE_ID,
  280. WIALOG_LEVEL3,
  281. "CWIAScannerDevice::CheckIntent");
  282. HRESULT hr;
  283. WIAS_CHANGED_VALUE_INFO cviIntent;
  284. //
  285. // Call wiasGetChangedValue for CurrentIntent. CurrentIntent is checked first
  286. // since it's not dependant on any other property. All properties in
  287. // this method that follow are dependant properties of CurrentIntent.
  288. //
  289. // The call to wiasGetChangedValue specifies that validation should not be
  290. // skipped (since valid values for CurrentIntent never change). The
  291. // address of the old value is specified as NULL, since it is not used.
  292. // The address of bIntentChanged is passed so that dependant properties
  293. // will know whether the YResolution is being changed or not. This is
  294. // important since dependant properties will need their valid values
  295. // updated and may need to be folded to new valid values.
  296. //
  297. hr = wiasGetChangedValueLong(pWiasContext,
  298. pContext,
  299. FALSE,
  300. WIA_IPS_CUR_INTENT,
  301. &cviIntent);
  302. if (SUCCEEDED(hr)) {
  303. if (cviIntent.bChanged) {
  304. LONG lImageSizeIntent = (cviIntent.Current.lVal & WIA_INTENT_SIZE_MASK);
  305. LONG lImageTypeIntent = (cviIntent.Current.lVal & WIA_INTENT_IMAGE_TYPE_MASK);
  306. switch (lImageTypeIntent) {
  307. case WIA_INTENT_NONE:
  308. break;
  309. case WIA_INTENT_IMAGE_TYPE_GRAYSCALE:
  310. wiasWritePropLong(pWiasContext, WIA_IPA_DATATYPE, WIA_DATA_GRAYSCALE);
  311. UpdateValidDepth (pWiasContext, WIA_DATA_GRAYSCALE, NULL);
  312. wiasWritePropLong(pWiasContext, WIA_IPA_DEPTH, 8);
  313. break;
  314. case WIA_INTENT_IMAGE_TYPE_TEXT:
  315. wiasWritePropLong(pWiasContext, WIA_IPA_DATATYPE, WIA_DATA_THRESHOLD);
  316. UpdateValidDepth (pWiasContext, WIA_DATA_THRESHOLD, NULL);
  317. wiasWritePropLong(pWiasContext, WIA_IPA_DEPTH, 1);
  318. break;
  319. case WIA_INTENT_IMAGE_TYPE_COLOR:
  320. wiasWritePropLong(pWiasContext, WIA_IPA_DATATYPE, WIA_DATA_COLOR);
  321. UpdateValidDepth(pWiasContext, WIA_DATA_COLOR, NULL);
  322. wiasWritePropLong(pWiasContext, WIA_IPA_DEPTH, 24);
  323. break;
  324. default:
  325. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("CheckIntent, unknown intent (TYPE) = %d",lImageTypeIntent));
  326. return E_INVALIDARG;
  327. }
  328. switch (lImageSizeIntent) {
  329. case WIA_INTENT_NONE:
  330. break;
  331. case WIA_INTENT_MINIMIZE_SIZE:
  332. case WIA_INTENT_MAXIMIZE_QUALITY:
  333. {
  334. //
  335. // Set the X and Y Resolutions.
  336. //
  337. wiasWritePropLong(pWiasContext, WIA_IPS_XRES, lImageSizeIntent & WIA_INTENT_MINIMIZE_SIZE ? 150 : 300);
  338. wiasWritePropLong(pWiasContext, WIA_IPS_YRES, lImageSizeIntent & WIA_INTENT_MINIMIZE_SIZE ? 150 : 300);
  339. //
  340. // The Resolutions and DataType were set, so update the property
  341. // context to indicate that they have changed.
  342. //
  343. wiasSetPropChanged(WIA_IPS_XRES, pContext, TRUE);
  344. wiasSetPropChanged(WIA_IPS_YRES, pContext, TRUE);
  345. wiasSetPropChanged(WIA_IPA_DATATYPE, pContext, TRUE);
  346. }
  347. break;
  348. default:
  349. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("CheckIntent, unknown intent (SIZE) = %d",lImageSizeIntent));
  350. return E_INVALIDARG;
  351. }
  352. }
  353. } else {
  354. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("CheckIntent, wiasGetChangedValue (intent) failed"));
  355. }
  356. return hr;
  357. }
  358. /**************************************************************************\
  359. * CheckPreferredFormat
  360. *
  361. * This helper method is called to make the relevant changes if the
  362. * Format property changes.
  363. *
  364. * Arguments:
  365. *
  366. * pWiasContext - a pointer to the item context whose properties have
  367. * changed.
  368. * pContext - a pointer to the property context (which indicates
  369. * which properties are being written).
  370. *
  371. * Return Value:
  372. *
  373. * Status
  374. *
  375. * History:
  376. *
  377. * 7/18/2000 Original Version
  378. *
  379. \**************************************************************************/
  380. HRESULT CWIAScannerDevice::CheckPreferredFormat(
  381. BYTE *pWiasContext,
  382. WIA_PROPERTY_CONTEXT *pContext)
  383. {
  384. HRESULT hr = S_OK;
  385. //
  386. // update WIA_IPA_PREFERRED_FORMAT property
  387. //
  388. GUID FormatGUID;
  389. hr = wiasReadPropGuid(pWiasContext, WIA_IPA_FORMAT, &FormatGUID, NULL, TRUE);
  390. if (SUCCEEDED(hr)) {
  391. hr = wiasWritePropGuid(pWiasContext, WIA_IPA_PREFERRED_FORMAT, FormatGUID);
  392. if (FAILED(hr)) {
  393. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("CheckPreferredFormat, could not write WIA_IPA_PREFERRED_FORMAT"));
  394. return hr;
  395. }
  396. } else {
  397. WIAS_LERROR(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,("CheckIntent, could not read WIA_IPA_FORMAT"));
  398. }
  399. return hr;
  400. }
  401. /**************************************************************************\
  402. * CheckADFStatus
  403. *
  404. *
  405. * Arguments:
  406. *
  407. * pWiasContext - pointer to an Item.
  408. *
  409. * Return Value:
  410. *
  411. * Byte count.
  412. *
  413. * History:
  414. *
  415. * 7/18/2000 Original Version
  416. *
  417. \**************************************************************************/
  418. HRESULT CWIAScannerDevice::CheckADFStatus(BYTE *pWiasContext,
  419. WIA_PROPERTY_CONTEXT *pContext)
  420. {
  421. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  422. WIALOG_NO_RESOURCE_ID,
  423. WIALOG_LEVEL3,
  424. "CWIAScannerDevice::CheckADFStatus");
  425. if(!m_bADFAttached)
  426. return S_OK;
  427. HRESULT hr = S_OK;
  428. BYTE *pRootItemCtx = NULL;
  429. LONG lDocHandlingSelect = 0;
  430. hr = wiasGetRootItem(pWiasContext, &pRootItemCtx);
  431. if (FAILED(hr)) {
  432. return E_FAIL;
  433. }
  434. hr = wiasReadPropLong(pRootItemCtx,
  435. WIA_DPS_DOCUMENT_HANDLING_SELECT,
  436. &lDocHandlingSelect,
  437. NULL,
  438. FALSE);
  439. if(hr == S_FALSE){
  440. lDocHandlingSelect = FEEDER;
  441. }
  442. if (SUCCEEDED(hr)) {
  443. switch (lDocHandlingSelect) {
  444. case FEEDER:
  445. m_bADFEnabled = TRUE;
  446. hr = S_OK;
  447. break;
  448. default:
  449. hr = E_INVALIDARG;
  450. return hr;
  451. break;
  452. }
  453. }
  454. //
  455. // update document handling status
  456. //
  457. if (m_bADFEnabled) {
  458. HRESULT Temphr = m_pScanAPI->FakeScanner_ADFAvailable();
  459. if (S_OK == Temphr) {
  460. hr = wiasWritePropLong(pWiasContext, WIA_DPS_DOCUMENT_HANDLING_STATUS,FEED_READY);
  461. } else {
  462. hr = wiasWritePropLong(pWiasContext, WIA_DPS_DOCUMENT_HANDLING_STATUS,PAPER_JAM);
  463. }
  464. if (FAILED(Temphr))
  465. hr = Temphr;
  466. } else {
  467. hr = wiasWritePropLong(pWiasContext, WIA_DPS_DOCUMENT_HANDLING_STATUS,FLAT_READY);
  468. }
  469. return hr;
  470. }
  471. /**************************************************************************\
  472. * CheckPreview
  473. *
  474. *
  475. * Arguments:
  476. *
  477. * pWiasContext - pointer to an Item.
  478. *
  479. * Return Value:
  480. *
  481. * Byte count.
  482. *
  483. * History:
  484. *
  485. * 8/21/2000 Original Version
  486. *
  487. \**************************************************************************/
  488. HRESULT CWIAScannerDevice::CheckPreview(BYTE *pWiasContext,
  489. WIA_PROPERTY_CONTEXT *pContext)
  490. {
  491. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  492. WIALOG_NO_RESOURCE_ID,
  493. WIALOG_LEVEL3,
  494. "CWIAScannerDevice::CheckPreview");
  495. HRESULT hr = S_OK;
  496. BYTE *pRootItemCtx = NULL;
  497. LONG lPreview = 0;
  498. hr = wiasGetRootItem(pWiasContext, &pRootItemCtx);
  499. if (FAILED(hr)) {
  500. return E_FAIL;
  501. }
  502. hr = wiasReadPropLong(pRootItemCtx,
  503. WIA_DPS_PREVIEW,
  504. &lPreview,
  505. NULL,
  506. FALSE);
  507. if(hr == S_FALSE){
  508. // property does not exist...so return S_OK
  509. return S_OK;
  510. }
  511. if (SUCCEEDED(hr)) {
  512. switch (lPreview) {
  513. case WIA_FINAL_SCAN:
  514. WIAS_LTRACE(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,WIALOG_LEVEL2,("CheckPreview, Set to WIA_FINAL_SCAN"));
  515. hr = S_OK;
  516. break;
  517. default:
  518. WIAS_LTRACE(m_pIWiaLog,WIALOG_NO_RESOURCE_ID,WIALOG_LEVEL2,("CheckPreview, Set to invalid argument (%d)",lPreview));
  519. hr = E_INVALIDARG;
  520. break;
  521. }
  522. }
  523. return hr;
  524. }
  525. /**************************************************************************\
  526. * CheckXExtent
  527. *
  528. *
  529. * Arguments:
  530. *
  531. * pWiasContext - pointer to an Item.
  532. *
  533. * Return Value:
  534. *
  535. * Byte count.
  536. *
  537. * History:
  538. *
  539. * 8/21/2000 Original Version
  540. *
  541. \**************************************************************************/
  542. HRESULT CWIAScannerDevice::CheckXExtent(BYTE *pWiasContext,
  543. WIA_PROPERTY_CONTEXT *pContext,
  544. LONG lWidth)
  545. {
  546. HRESULT hr = S_OK;
  547. CWiaLogProc WIAS_LOGPROC(m_pIWiaLog,
  548. WIALOG_NO_RESOURCE_ID,
  549. WIALOG_LEVEL3,
  550. "CheckXExtent");
  551. LONG lMaxExtent;
  552. LONG lExt;
  553. WIAS_CHANGED_VALUE_INFO cviXRes, cviXExt;
  554. //
  555. // get x resolution changes
  556. //
  557. hr = wiasGetChangedValueLong(pWiasContext,pContext,FALSE,WIA_IPS_XRES,&cviXRes);
  558. if (FAILED(hr)) {
  559. return hr;
  560. }
  561. //
  562. // get x extent changes
  563. //
  564. hr = wiasGetChangedValueLong(pWiasContext,pContext,cviXRes.bChanged,WIA_IPS_XEXTENT,&cviXExt);
  565. if (FAILED(hr)) {
  566. return hr;
  567. }
  568. //
  569. // update extent
  570. //
  571. lMaxExtent = ((cviXRes.Current.lVal * lWidth) / 1000);
  572. //
  573. // Update read-only property : PIXELS_PER_LINE. The width in pixels
  574. // of the scanned image is the same size as the XExtent.
  575. //
  576. if (SUCCEEDED(hr)) {
  577. hr = wiasWritePropLong(pWiasContext, WIA_IPS_XEXTENT, lMaxExtent);
  578. hr = wiasWritePropLong(pWiasContext, WIA_IPA_PIXELS_PER_LINE, lMaxExtent);
  579. }
  580. return hr;
  581. }