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.

2507 lines
86 KiB

  1. //==========================================================================;
  2. //
  3. // ATIConfg.CPP
  4. // WDM MiniDrivers development.
  5. // ATIHwConfiguration class implementation.
  6. // Copyright (c) 1996 - 1997 ATI Technologies Inc. All Rights Reserved.
  7. //
  8. // $Date: 10 Jun 1999 09:54:42 $
  9. // $Revision: 1.21 $
  10. // $Author: KLEBANOV $
  11. //
  12. //==========================================================================;
  13. extern"C"
  14. {
  15. #include "conio.h"
  16. #include "strmini.h"
  17. #include "wdmdebug.h"
  18. #include "ksmedia.h" //Paul
  19. }
  20. #include "aticonfg.h"
  21. #include "wdmdrv.h"
  22. #include "atigpio.h"
  23. #include "mmconfig.h"
  24. /*^^*
  25. * CATIHwConfiguration()
  26. * Purpose : CATIHwConfiguration Class constructor
  27. * Determines I2CExpander address and all possible hardware IDs and addresses
  28. *
  29. * Inputs : PDEVICE_OBJECT pDeviceObject : pointer to the creator DeviceObject
  30. * CI2CScript * pCScript : pointer to the I2CScript class object
  31. * PUINT puiError : pointer to return Error code
  32. *
  33. * Outputs : none
  34. * Author : IKLEBANOV
  35. *^^*/
  36. CATIHwConfiguration::CATIHwConfiguration( PPORT_CONFIGURATION_INFORMATION pConfigInfo, CI2CScript * pCScript, PUINT puiError)
  37. {
  38. ENSURE
  39. {
  40. m_VideoInStandardsSupported = 0;
  41. m_CrystalIDInMMTable = 0xF; // invalid entry, needs to be set when set with the value from MMTable
  42. m_gpioProviderInterface.gpioOpen = NULL;
  43. m_gpioProviderInterface.gpioAccess = NULL;
  44. m_pdoDriver = NULL;
  45. m_usE2PROMValidation = ( USHORT)-1;
  46. if( InitializeAttachGPIOProvider( &m_gpioProviderInterface, pConfigInfo->PhysicalDeviceObject))
  47. // there was no error to get GPIOInterface from the MiniVDD
  48. m_pdoDriver = pConfigInfo->RealPhysicalDeviceObject;
  49. else
  50. {
  51. * puiError = WDMMINI_ERROR_NOGPIOPROVIDER;
  52. FAIL;
  53. }
  54. if( !FindI2CExpanderAddress( pCScript))
  55. {
  56. * puiError = WDMMINI_NOHARDWARE;
  57. FAIL;
  58. }
  59. if( !FindHardwareProperties( pConfigInfo->RealPhysicalDeviceObject, pCScript))
  60. {
  61. * puiError = WDMMINI_NOHARDWARE;
  62. FAIL;
  63. }
  64. * puiError = WDMMINI_NOERROR;
  65. OutputDebugTrace(( "CATIHwConfig:CATIHwConfiguration() exit\n"));
  66. } END_ENSURE;
  67. if( * puiError != WDMMINI_NOERROR)
  68. OutputDebugError(( "CATIHwConfig:CATIHwConfiguration() uiError=%x\n", * puiError));
  69. }
  70. /*^^*
  71. * FindHardwareProperties()
  72. * Purpose : Determines hardware properties : I2C address and the type
  73. *
  74. * Inputs : PDEVICEOBJECT pDeviceObject: pointer to device object
  75. * CI2CScript * pCScript : pointer to the I2CScript object
  76. *
  77. * Outputs : BOOL, TRUE if a valid ATI hardware Configuration was found
  78. * Author : IKLEBANOV
  79. *^^*/
  80. BOOL CATIHwConfiguration::FindHardwareProperties( PDEVICE_OBJECT pDeviceObject, CI2CScript * pCScript)
  81. {
  82. UCHAR uchI2CValue;
  83. UCHAR uchORMask = 0x00;
  84. UCHAR uchANDMask = 0xFF;
  85. BOOL bResult = TRUE;
  86. I2CPacket i2cPacket;
  87. m_VideoInStandardsSupported = 0; //Paul
  88. m_uchTunerAddress = 0;
  89. m_usTunerId = 0;
  90. m_usTunerPowerConfiguration = ATI_TUNER_POWER_CONFIG_0;
  91. m_uchDecoderAddress = 0;
  92. m_usDecoderId = VIDEODECODER_TYPE_NOTINSTALLED;
  93. m_usDecoderConfiguration = 0;
  94. m_uchAudioAddress = 0;
  95. m_uiAudioConfiguration = 0;
  96. switch( m_uchI2CExpanderAddress)
  97. {
  98. case 0x70: // a standard external tuner board
  99. m_uchTunerAddress = 0xC0;
  100. m_uchDecoderAddress = 0x88;
  101. // we need to determine actual Decoder ID, implement later
  102. m_usDecoderId = VIDEODECODER_TYPE_BT829;
  103. if( GetI2CExpanderConfiguration( pCScript, &uchI2CValue))
  104. {
  105. m_usTunerId = uchI2CValue & 0x0F;
  106. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_1;
  107. if( uchI2CValue & 0x10)
  108. {
  109. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_4;
  110. m_uchAudioAddress = 0x82;
  111. }
  112. else
  113. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_3;
  114. }
  115. m_VideoInStandardsSupported = SetVidStdBasedOnI2CExpander( uchI2CValue ); //Paul
  116. break;
  117. case 0x78: // FM tuner
  118. m_uchTunerAddress = 0xC0;
  119. m_uchDecoderAddress = 0x88;
  120. // we need to determine actual Decoder ID, implement later
  121. m_usDecoderId = VIDEODECODER_TYPE_BT829;
  122. if( GetI2CExpanderConfiguration( pCScript, &uchI2CValue))
  123. {
  124. m_usTunerId = uchI2CValue & 0x0F;
  125. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_1;
  126. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_5;
  127. }
  128. m_VideoInStandardsSupported = SetVidStdBasedOnI2CExpander( uchI2CValue ); //Paul
  129. break;
  130. case 0x76: // AllInWonder, configuration is in the BIOS
  131. {
  132. CATIMultimediaTable CMultimediaInfo( pDeviceObject, &m_gpioProviderInterface, &bResult);
  133. if( bResult)
  134. {
  135. // tuner and decoder Info is included
  136. m_uchTunerAddress = 0xC6;
  137. m_uchDecoderAddress = 0x8A;
  138. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_1;
  139. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_1;
  140. if( !CMultimediaInfo.GetTVTunerId( &m_usTunerId) ||
  141. !CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  142. bResult = FALSE;
  143. else
  144. m_VideoInStandardsSupported = SetVidStdBasedOnMMTable( &CMultimediaInfo ); //Paul
  145. }
  146. break;
  147. }
  148. case 0x7C:
  149. ENSURE
  150. {
  151. i2cPacket.uchChipAddress = m_uchI2CExpanderAddress;
  152. i2cPacket.cbReadCount = 1;
  153. i2cPacket.cbWriteCount = 0;
  154. i2cPacket.puchReadBuffer = &uchI2CValue;
  155. i2cPacket.puchWriteBuffer = NULL;
  156. i2cPacket.usFlags = 0;
  157. pCScript->ExecuteI2CPacket( &i2cPacket);
  158. if( i2cPacket.uchI2CResult != I2C_STATUS_NOERROR)
  159. {
  160. bResult = FALSE;
  161. FAIL;
  162. }
  163. uchI2CValue |= 0x0F;
  164. i2cPacket.uchChipAddress = m_uchI2CExpanderAddress;
  165. i2cPacket.cbReadCount = 0;
  166. i2cPacket.cbWriteCount = 1;
  167. i2cPacket.puchReadBuffer = NULL;
  168. i2cPacket.puchWriteBuffer = &uchI2CValue;
  169. i2cPacket.usFlags = 0;
  170. pCScript->ExecuteI2CPacket( &i2cPacket);
  171. if (i2cPacket.uchI2CResult != I2C_STATUS_NOERROR)
  172. {
  173. bResult = FALSE;
  174. FAIL;
  175. }
  176. // information should be correct now
  177. if( GetI2CExpanderConfiguration( pCScript, &uchI2CValue))
  178. {
  179. m_usTunerId = uchI2CValue & 0x0F;
  180. }
  181. m_VideoInStandardsSupported = SetVidStdBasedOnI2CExpander( uchI2CValue ); //Paul
  182. } END_ENSURE;
  183. if (!bResult)
  184. break;
  185. // For IO Expander address == 0x7c there might be more information in the BIOS Table sto do not return
  186. // or break at this point
  187. case 0xFF: // AllInWonder PRO, configuration is in the BIOS
  188. ENSURE
  189. {
  190. CATIMultimediaTable CMultimediaInfo( pDeviceObject, &m_gpioProviderInterface, &bResult);
  191. USHORT nOEMId, nOEMRevision, nATIProductType;
  192. BOOL bATIProduct;
  193. if( !bResult)
  194. FAIL;
  195. // OEM Id information is included
  196. if( !CMultimediaInfo.IsATIProduct( &bATIProduct))
  197. {
  198. bResult = FALSE;
  199. FAIL;
  200. }
  201. m_uchDecoderAddress = 0x8A;
  202. m_uchTunerAddress = 0xC6;
  203. if( bATIProduct)
  204. {
  205. if( !CMultimediaInfo.GetATIProductId( &nATIProductType))
  206. {
  207. bResult = FALSE;
  208. FAIL;
  209. }
  210. if( CMultimediaInfo.GetTVTunerId( &m_usTunerId) &&
  211. CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  212. {
  213. switch( nATIProductType)
  214. {
  215. case ATI_PRODUCT_TYPE_AIW_PRO_NODVD:
  216. case ATI_PRODUCT_TYPE_AIW_PRO_DVD:
  217. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  218. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_2;
  219. m_usTunerPowerConfiguration = ATI_TUNER_POWER_CONFIG_1;
  220. m_uchAudioAddress = 0xB4;
  221. break;
  222. case ATI_PRODUCT_TYPE_AIW_PLUS:
  223. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_6;
  224. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  225. m_uchAudioAddress = 0xB6;
  226. break;
  227. case ATI_PRODUCT_TYPE_AIW_PRO_R128_KITCHENER:
  228. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_7;
  229. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  230. m_uchAudioAddress = 0xB4;
  231. break;
  232. case ATI_PRODUCT_TYPE_AIW_PRO_R128_TORONTO:
  233. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_8;
  234. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_UNDEFINED;
  235. m_uchAudioAddress = 0x80;
  236. break;
  237. default:
  238. bResult = FALSE;
  239. break;
  240. }
  241. }
  242. else
  243. bResult = FALSE;
  244. }
  245. else
  246. {
  247. // non ATI Product
  248. if( !CMultimediaInfo.GetOEMId( &nOEMId) ||
  249. !CMultimediaInfo.GetOEMRevisionId( &nOEMRevision))
  250. {
  251. bResult = FALSE;
  252. FAIL;
  253. }
  254. m_uchDecoderAddress = 0x8A;
  255. m_uchTunerAddress = 0xC6;
  256. switch( nOEMId)
  257. {
  258. case OEM_ID_INTEL:
  259. switch( nOEMRevision)
  260. {
  261. case INTEL_ANCHORAGE:
  262. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId) &&
  263. CMultimediaInfo.GetTVTunerId( &m_usTunerId))
  264. {
  265. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_1;
  266. switch( m_usDecoderId)
  267. {
  268. case VIDEODECODER_TYPE_BT829:
  269. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_3;
  270. break;
  271. case VIDEODECODER_TYPE_BT829A:
  272. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  273. break;
  274. default:
  275. bResult = FALSE;
  276. break;
  277. }
  278. }
  279. else
  280. bResult = FALSE;
  281. break;
  282. default:
  283. bResult = FALSE;
  284. break;
  285. }
  286. break;
  287. case OEM_ID_APRICOT:
  288. switch( nOEMRevision)
  289. {
  290. case REVISION1:
  291. case REVISION2:
  292. if( CMultimediaInfo.GetTVTunerId( &m_usTunerId))
  293. {
  294. switch( m_usDecoderId)
  295. {
  296. case VIDEODECODER_TYPE_BT829:
  297. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_4;
  298. break;
  299. case VIDEODECODER_TYPE_BT829A:
  300. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  301. break;
  302. }
  303. }
  304. else
  305. bResult = FALSE;
  306. break;
  307. default:
  308. bResult = FALSE;
  309. break;
  310. }
  311. break;
  312. case OEM_ID_FUJITSU:
  313. m_uchDecoderAddress = 0x88;
  314. switch( nOEMRevision)
  315. {
  316. case REVISION1:
  317. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  318. {
  319. switch( m_usDecoderId)
  320. {
  321. case VIDEODECODER_TYPE_BT829A:
  322. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  323. break;
  324. default:
  325. bResult = FALSE;
  326. break;
  327. }
  328. }
  329. else
  330. bResult = FALSE;
  331. break;
  332. default:
  333. bResult = FALSE;
  334. break;
  335. }
  336. break;
  337. case OEM_ID_COMPAQ:
  338. switch( nOEMRevision)
  339. {
  340. case REVISION1:
  341. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  342. {
  343. switch( m_usDecoderId)
  344. {
  345. case VIDEODECODER_TYPE_BT829:
  346. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_3;
  347. break;
  348. case VIDEODECODER_TYPE_BT829A:
  349. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  350. break;
  351. default:
  352. bResult = FALSE;
  353. break;
  354. }
  355. }
  356. else
  357. bResult = FALSE;
  358. break;
  359. default:
  360. bResult = FALSE;
  361. break;
  362. }
  363. break;
  364. case OEM_ID_BCM:
  365. case OEM_ID_SAMSUNG:
  366. switch( nOEMRevision)
  367. {
  368. case REVISION0:
  369. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  370. {
  371. switch( m_usDecoderId)
  372. {
  373. case VIDEODECODER_TYPE_BT829A:
  374. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  375. break;
  376. default:
  377. bResult = FALSE;
  378. }
  379. }
  380. else
  381. bResult = FALSE;
  382. break;
  383. default:
  384. bResult = FALSE;
  385. break;
  386. }
  387. break;
  388. case OEM_ID_SAMREX:
  389. switch( nOEMRevision)
  390. {
  391. case REVISION0:
  392. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  393. {
  394. switch( m_usDecoderId)
  395. {
  396. case VIDEODECODER_TYPE_BT829A:
  397. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  398. break;
  399. default:
  400. bResult = FALSE;
  401. break;
  402. }
  403. }
  404. else
  405. bResult = FALSE;
  406. break;
  407. default:
  408. bResult = FALSE;
  409. break;
  410. }
  411. break;
  412. case OEM_ID_NEC:
  413. switch( nOEMRevision)
  414. {
  415. case REVISION0:
  416. case REVISION1:
  417. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  418. {
  419. switch( m_usDecoderId)
  420. {
  421. case VIDEODECODER_TYPE_BT829A:
  422. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  423. break;
  424. default:
  425. bResult = FALSE;
  426. break;
  427. }
  428. }
  429. else
  430. bResult = FALSE;
  431. break;
  432. default:
  433. bResult = FALSE;
  434. break;
  435. }
  436. break;
  437. default:
  438. if( CMultimediaInfo.GetVideoDecoderId( &m_usDecoderId))
  439. {
  440. if( m_usDecoderId == VIDEODECODER_TYPE_RTHEATER)
  441. {
  442. // default the configuration to Toronto board
  443. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_8;
  444. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_UNDEFINED;
  445. m_uchAudioAddress = 0x80;
  446. }
  447. else
  448. {
  449. // default the configuration to Kitchener board
  450. m_uiAudioConfiguration = ATI_AUDIO_CONFIG_7;
  451. m_usDecoderConfiguration = ATI_VIDEODECODER_CONFIG_2;
  452. m_uchAudioAddress = 0xB4;
  453. }
  454. bResult = TRUE;
  455. }
  456. else
  457. bResult = FALSE;
  458. break;
  459. }
  460. }
  461. m_VideoInStandardsSupported = SetVidStdBasedOnMMTable( &CMultimediaInfo ); //Paul
  462. } END_ENSURE;
  463. break;
  464. }
  465. OutputDebugInfo(( "CATIHwConfig:FindHardwareConfiguration() found:\n"));
  466. OutputDebugInfo(( "Tuner: Id = %d, I2CAddress = 0x%x\n",
  467. m_usTunerId, m_uchTunerAddress));
  468. OutputDebugInfo(( "Decoder: Id = %d, I2CAddress = 0x%x, Configuration = %d\n",
  469. m_usDecoderId, m_uchDecoderAddress, m_usDecoderConfiguration));
  470. OutputDebugInfo(( "Audio: I2CAddress = 0x%x, Configuration = %d\n",
  471. m_uchAudioAddress, m_uiAudioConfiguration));
  472. return( bResult);
  473. }
  474. /*^^*
  475. * GetTunerConfiguration()
  476. * Purpose : Gets tuner Id and i2C address
  477. * Inputs : PUINT puiTunerId : pointer to return tuner Id
  478. * PUCHAR puchTunerAddress : pointer to return tuner I2C address
  479. *
  480. * Outputs : BOOL : returns TRUE
  481. * also sets the requested values into the input pointers
  482. * Author : IKLEBANOV
  483. *^^*/
  484. BOOL CATIHwConfiguration::GetTunerConfiguration( PUINT puiTunerId, PUCHAR puchTunerAddress)
  485. {
  486. if(( puiTunerId != NULL) && ( puchTunerAddress != NULL))
  487. {
  488. * puiTunerId = ( UINT)m_usTunerId;
  489. * puchTunerAddress = m_uchTunerAddress;
  490. return( TRUE);
  491. }
  492. else
  493. return( FALSE);
  494. }
  495. /*^^*
  496. * GetDecoderConfiguration()
  497. * Purpose : Gets decoder Id and i2C address
  498. *
  499. * Inputs : puiDecoderId : pointer to return Decoder Id
  500. *
  501. * Outputs : BOOL : returns TRUE
  502. * also sets the requested values into the input pointer
  503. * Author : IKLEBANOV
  504. *^^*/
  505. BOOL CATIHwConfiguration::GetDecoderConfiguration( PUINT puiDecoderId, PUCHAR puchDecoderAddress)
  506. {
  507. if(( puiDecoderId != NULL) && ( puchDecoderAddress != NULL))
  508. {
  509. * puiDecoderId = ( UINT)m_usDecoderId;
  510. * puchDecoderAddress = m_uchDecoderAddress;
  511. return( TRUE);
  512. }
  513. else
  514. return( FALSE);
  515. }
  516. /*^^*
  517. * GetAudioConfiguration()
  518. * Purpose : Gets Audio solution Id and i2C address
  519. *
  520. * Inputs : PUINT puiAudioConfiguration : pointer to return Audio configuration Id
  521. * PUCHAR puchAudioAddress : pointer to return audio hardware
  522. * I2C address
  523. *
  524. * Outputs : BOOL : returns TRUE
  525. * also sets the requested values into the input pointer
  526. * Author : IKLEBANOV
  527. *^^*/
  528. BOOL CATIHwConfiguration::GetAudioConfiguration( PUINT puiAudioConfiguration, PUCHAR puchAudioAddress)
  529. {
  530. if(( puiAudioConfiguration != NULL) && ( puchAudioAddress != NULL))
  531. {
  532. * puiAudioConfiguration = ( UINT)m_uiAudioConfiguration;
  533. * puchAudioAddress = m_uchAudioAddress;
  534. return( TRUE);
  535. }
  536. else
  537. return( FALSE);
  538. }
  539. /*^^*
  540. * InitializeAudioConfiguration()
  541. * Purpose : Initializes Audio Chip with default / power up values. This function will
  542. * be called at Low priority with i2CProvider locked
  543. *
  544. * Inputs : CI2CScript * pCScript : pointer to the I2CScript object
  545. * UINT uiAudioConfigurationId : detected Audio configuration
  546. * UCHAR uchAudioChipAddress : detected Audio chip I2C address
  547. * Outputs : none
  548. * Author : IKLEBANOV
  549. *^^*/
  550. BOOL CATIHwConfiguration::InitializeAudioConfiguration( CI2CScript * pCScript, UINT uiAudioConfigurationId, UCHAR uchAudioChipAddress)
  551. {
  552. I2CPacket i2cPacket;
  553. UCHAR uchWrite16Value[5];
  554. #ifdef I2S_CAPTURE
  555. UCHAR uchRead16Value[5];
  556. #endif // I2S_CAPTURE
  557. BOOL bResult;
  558. switch( uiAudioConfigurationId)
  559. {
  560. case ATI_AUDIO_CONFIG_2:
  561. case ATI_AUDIO_CONFIG_7:
  562. // TDA9850 has to be initialized with the values from I2C EEPROM, if
  563. // those answers the CheckSum. If not, take hardcoded default values
  564. {
  565. UINT nIndex, nNumberOfRegs;
  566. PUCHAR puchInitializationBuffer = NULL;
  567. UCHAR uchWriteBuffer[2];
  568. bResult = FALSE;
  569. nNumberOfRegs = AUDIO_TDA9850_Reg_Align3 - AUDIO_TDA9850_Reg_Control1 + 1;
  570. puchInitializationBuffer = ( PUCHAR) \
  571. ::ExAllocatePool( NonPagedPool, nNumberOfRegs * sizeof( PUCHAR));
  572. if( puchInitializationBuffer == NULL)
  573. return( bResult);
  574. // fill in the Initialization buffer with the defaults values
  575. puchInitializationBuffer[0] = AUDIO_TDA9850_Control1_DefaultValue;
  576. puchInitializationBuffer[1] = AUDIO_TDA9850_Control2_DefaultValue;
  577. puchInitializationBuffer[2] = AUDIO_TDA9850_Control3_DefaultValue;
  578. puchInitializationBuffer[3] = AUDIO_TDA9850_Control4_DefaultValue;
  579. puchInitializationBuffer[4] = AUDIO_TDA9850_Align1_DefaultValue;
  580. puchInitializationBuffer[5] = AUDIO_TDA9850_Align2_DefaultValue;
  581. puchInitializationBuffer[6] = AUDIO_TDA9850_Align3_DefaultValue;
  582. // we have to see if anything in I2C EEPROM is waiting for us to
  583. // overwrite the default values
  584. if( ValidateConfigurationE2PROM( pCScript))
  585. {
  586. // The configuration E2PROM kept its integrity. Let's read the
  587. // initialization values from the device
  588. ReadConfigurationE2PROM( pCScript, 3, &puchInitializationBuffer[4]);
  589. ReadConfigurationE2PROM( pCScript, 4, &puchInitializationBuffer[5]);
  590. }
  591. // write the power-up defaults values into the chip
  592. i2cPacket.uchChipAddress = uchAudioChipAddress;
  593. i2cPacket.cbReadCount = 0;
  594. i2cPacket.cbWriteCount = 2;
  595. i2cPacket.puchReadBuffer = NULL;
  596. i2cPacket.puchWriteBuffer = uchWriteBuffer;
  597. i2cPacket.usFlags = I2COPERATION_WRITE;
  598. for( nIndex = 0; nIndex < nNumberOfRegs; nIndex ++)
  599. {
  600. uchWriteBuffer[0] = AUDIO_TDA9850_Reg_Control1 + nIndex;
  601. uchWriteBuffer[1] = puchInitializationBuffer[nIndex];
  602. if( !( bResult = pCScript->ExecuteI2CPacket( &i2cPacket)))
  603. break;
  604. }
  605. if( puchInitializationBuffer != NULL)
  606. ::ExFreePool( puchInitializationBuffer);
  607. return( bResult);
  608. }
  609. break;
  610. case ATI_AUDIO_CONFIG_4:
  611. // TDA8425 volume control should be initialized
  612. return( SetDefaultVolumeControl( pCScript));
  613. break;
  614. case ATI_AUDIO_CONFIG_6:
  615. {
  616. UCHAR uchWriteBuffer;
  617. // write the power-up defaults values into the chip
  618. i2cPacket.uchChipAddress = uchAudioChipAddress;
  619. i2cPacket.cbReadCount = 0;
  620. i2cPacket.cbWriteCount = 1;
  621. i2cPacket.puchReadBuffer = NULL;
  622. i2cPacket.puchWriteBuffer = &uchWriteBuffer;
  623. i2cPacket.usFlags = I2COPERATION_WRITE;
  624. uchWriteBuffer = AUDIO_TDA9851_DefaultValue;
  625. return( pCScript->ExecuteI2CPacket( &i2cPacket));
  626. }
  627. break;
  628. case ATI_AUDIO_CONFIG_8:
  629. //Reset MSP3430
  630. i2cPacket.uchChipAddress = m_uchAudioAddress;
  631. i2cPacket.cbReadCount = 0;
  632. i2cPacket.usFlags = I2COPERATION_WRITE;
  633. i2cPacket.puchWriteBuffer = uchWrite16Value;
  634. //Write 0x80 - 00 to Subaddr 0x00
  635. i2cPacket.cbWriteCount = 3;
  636. uchWrite16Value[0] = 0x00;
  637. uchWrite16Value[1] = 0x80;
  638. uchWrite16Value[2] = 0x00;
  639. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  640. if(bResult)
  641. {
  642. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  643. return(FALSE);
  644. }
  645. else
  646. return(FALSE);
  647. //Write 0x00 - 00 to Subaddr 0x00
  648. i2cPacket.cbWriteCount = 3;
  649. uchWrite16Value[0] = 0x00;
  650. uchWrite16Value[1] = 0x00;
  651. uchWrite16Value[2] = 0x00;
  652. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  653. if(bResult)
  654. {
  655. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  656. return(FALSE);
  657. }
  658. else
  659. return(FALSE);
  660. //SubAddr 0x12 Reg 0x13 Val 0x3f60
  661. i2cPacket.cbWriteCount = 5;
  662. uchWrite16Value[0] = 0x12;
  663. uchWrite16Value[1] = 0x00;
  664. uchWrite16Value[2] = 0x13;
  665. uchWrite16Value[3] = 0x3f;
  666. uchWrite16Value[4] = 0x60;
  667. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  668. if(bResult)
  669. {
  670. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  671. return(FALSE);
  672. }
  673. else
  674. return(FALSE);
  675. //SubAddr 0x12 Reg 0x00 Val 0x0000
  676. i2cPacket.cbWriteCount = 5;
  677. uchWrite16Value[0] = 0x12;
  678. uchWrite16Value[1] = 0x00;
  679. uchWrite16Value[2] = 0x00;
  680. uchWrite16Value[3] = 0x00;
  681. uchWrite16Value[4] = 0x00;
  682. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  683. if(bResult)
  684. {
  685. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  686. return(FALSE);
  687. }
  688. else
  689. return(FALSE);
  690. #ifdef I2S_CAPTURE
  691. #pragma message ("\n!!! PAY ATTENTION: Driver has been build with ITT CHIP I2S CAPTURE CONFIGURED !!!\n")
  692. i2cPacket.uchChipAddress = m_uchAudioAddress;
  693. i2cPacket.usFlags = I2COPERATION_WRITE;
  694. i2cPacket.puchWriteBuffer = uchWrite16Value;
  695. i2cPacket.puchReadBuffer = uchRead16Value;
  696. //Setup I2S Source Select and Output Channel Matrix
  697. //SubAddr 0x12 Reg 0x0b Val 0x0320
  698. i2cPacket.cbWriteCount = 5;
  699. i2cPacket.cbReadCount = 0;
  700. uchWrite16Value[0] = 0x12;
  701. uchWrite16Value[1] = 0x00;
  702. uchWrite16Value[2] = 0x0b;
  703. uchWrite16Value[3] = 0x03;
  704. uchWrite16Value[4] = 0x20;
  705. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  706. if(bResult)
  707. {
  708. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  709. return(FALSE);
  710. }
  711. else
  712. return(FALSE);
  713. //Setup MODUS
  714. i2cPacket.cbWriteCount = 5;
  715. i2cPacket.cbReadCount = 0;
  716. uchWrite16Value[0] = 0x10;
  717. uchWrite16Value[1] = 0x00;
  718. uchWrite16Value[2] = 0x30;
  719. uchWrite16Value[3] = 0x20;
  720. uchWrite16Value[4] = 0xe3;
  721. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  722. if(bResult)
  723. {
  724. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  725. return(FALSE);
  726. }
  727. else
  728. return(FALSE);
  729. #endif // I2S_CAPTURE
  730. break;
  731. default:
  732. break;
  733. }
  734. return( TRUE);
  735. }
  736. /*^^*
  737. * GetTVAudioSignalProperties()
  738. * Purpose : Gets Audio signal properties readable from ATI dependand hardware,
  739. * like I2C expander. This call is always synchronous.
  740. *
  741. * Inputs : CI2CScript * pCScript : pointer to the I2CScript object
  742. * PBOOL pbStereo : pointer to the Stereo Indicator
  743. * PBOOL pbSAP : pointer to the SAP Indicator
  744. *
  745. * Outputs : BOOL, returns TRUE, if successful
  746. * Author : IKLEBANOV
  747. *^^*/
  748. BOOL CATIHwConfiguration::GetTVAudioSignalProperties( CI2CScript * pCScript, PBOOL pbStereo, PBOOL pbSAP)
  749. {
  750. I2CPacket i2cPacket;
  751. UCHAR uchReadValue, uchWriteValue;
  752. BOOL bResult;
  753. switch( m_uiAudioConfiguration)
  754. {
  755. case ATI_AUDIO_CONFIG_1:
  756. case ATI_AUDIO_CONFIG_5:
  757. // Stereo property is read back from I2C expander
  758. i2cPacket.uchChipAddress = m_uchI2CExpanderAddress;
  759. i2cPacket.cbReadCount = 1;
  760. i2cPacket.cbWriteCount = 1;
  761. i2cPacket.puchReadBuffer = &uchReadValue;
  762. i2cPacket.puchWriteBuffer = &uchWriteValue;
  763. i2cPacket.usFlags = I2COPERATION_READWRITE;
  764. i2cPacket.uchORValue = 0x40;
  765. i2cPacket.uchANDValue = 0xFF;
  766. bResult = FALSE;
  767. ENSURE
  768. {
  769. if( !pCScript->LockI2CProviderEx())
  770. FAIL;
  771. pCScript->ExecuteI2CPacket( &i2cPacket);
  772. if( !( bResult = ( i2cPacket.uchI2CResult == I2C_STATUS_NOERROR)))
  773. FAIL;
  774. i2cPacket.puchWriteBuffer = NULL;
  775. i2cPacket.usFlags = I2COPERATION_READ;
  776. pCScript->ExecuteI2CPacket( &i2cPacket);
  777. if( !( bResult = ( i2cPacket.uchI2CResult == I2C_STATUS_NOERROR)))
  778. FAIL;
  779. * pbStereo = uchReadValue & 0x40;
  780. bResult = TRUE;
  781. } END_ENSURE;
  782. pCScript->ReleaseI2CProvider();
  783. break;
  784. default:
  785. bResult = FALSE;
  786. break;
  787. }
  788. if( bResult)
  789. // no case, where SAP property is read back from ATI's hardware
  790. * pbSAP = FALSE;
  791. return( bResult);
  792. }
  793. /*^^*
  794. * GetDecoderOutputEnableLevel()
  795. * Purpose : Retrieves ATI dependent hardware configuration property of the logical level
  796. * should be applied on OUTEN field of Bt829x decoder in order to enable
  797. * output stream
  798. *
  799. * Inputs : none
  800. *
  801. * Outputs : UINT,
  802. * UINT( -1) value is returned if an error occures
  803. * Author : IKLEBANOV
  804. *^^*/
  805. UINT CATIHwConfiguration::GetDecoderOutputEnableLevel( void)
  806. {
  807. UINT uiEnableLevel;
  808. switch( m_usDecoderConfiguration)
  809. {
  810. case ATI_VIDEODECODER_CONFIG_1:
  811. case ATI_VIDEODECODER_CONFIG_3:
  812. case ATI_VIDEODECODER_CONFIG_4:
  813. uiEnableLevel = 0;
  814. break;
  815. case ATI_VIDEODECODER_CONFIG_2:
  816. uiEnableLevel = 1;
  817. break;
  818. default:
  819. uiEnableLevel = UINT( -1);
  820. break;
  821. }
  822. return( uiEnableLevel);
  823. }
  824. /*^^*
  825. * EnableDecoderI2CAccess()
  826. * Purpose : Enables/disables I2C access to the decoder chip
  827. *
  828. * Inputs : CI2CScript * pCScript : pointer to the I2CScript object
  829. * BOOL bEnable : defines what to do - enable/disable the decoder's outputs
  830. *
  831. * Outputs : none
  832. * Author : IKLEBANOV
  833. *^^*/
  834. void CATIHwConfiguration::EnableDecoderI2CAccess( CI2CScript * pCScript, BOOL bEnable)
  835. {
  836. UCHAR uchORMask = 0;
  837. UCHAR uchANDMask = 0xFF;
  838. UCHAR uchReadValue, uchWriteValue;
  839. I2CPacket i2cPacket;
  840. switch( m_usDecoderConfiguration)
  841. {
  842. case ATI_VIDEODECODER_CONFIG_1: // Add-On TV Tuner board - ATI TV requires certain actions to be taken
  843. i2cPacket.uchChipAddress = m_uchI2CExpanderAddress;
  844. i2cPacket.cbReadCount = 1;
  845. i2cPacket.cbWriteCount = 1;
  846. if( bEnable)
  847. uchANDMask &= 0x7F;
  848. else
  849. uchORMask |= 0x80;
  850. i2cPacket.puchReadBuffer = &uchReadValue;
  851. i2cPacket.puchWriteBuffer = &uchWriteValue;
  852. i2cPacket.usFlags = I2COPERATION_READWRITE;
  853. i2cPacket.uchORValue = uchORMask;
  854. i2cPacket.uchANDValue = uchANDMask;
  855. pCScript->PerformI2CPacketOperation( &i2cPacket);
  856. break;
  857. #ifdef _X86_
  858. case ATI_VIDEODECODER_CONFIG_3:
  859. _outp( 0x7D, ( _inp( 0x7D) | 0x80));
  860. if( bEnable)
  861. _outp( 0x7C, ( _inp( 0x7C) & 0x7F));
  862. else
  863. _outp( 0x7C, ( _inp( 0x7C) | 0x80));
  864. return;
  865. case ATI_VIDEODECODER_CONFIG_4:
  866. if( bEnable)
  867. _outp( 0x78, ( _inp( 0x78) & 0xF7));
  868. else
  869. _outp( 0x78, ( _inp( 0x78) | 0x08));
  870. return;
  871. #endif
  872. default:
  873. break;
  874. }
  875. }
  876. /*^^*
  877. * GetI2CExpanderConfiguration()
  878. * Purpose : Gets board configuration via I2C expander
  879. * Reads the configuration registers back
  880. * Inputs : CI2CScript * pCScript : pointer to CI2CScript object
  881. * PUCHAR puchI2CValue : pointer to read the I2C value into
  882. *
  883. * Outputs : BOOL : returns TRUE
  884. * also sets the requested values into the input pointers
  885. * Author : IKLEBANOV
  886. *^^*/
  887. BOOL CATIHwConfiguration::GetI2CExpanderConfiguration( CI2CScript * pCScript, PUCHAR puchI2CValue)
  888. {
  889. I2CPacket i2cPacket;
  890. if( puchI2CValue == NULL)
  891. return( FALSE);
  892. i2cPacket.uchChipAddress = m_uchI2CExpanderAddress;
  893. i2cPacket.cbReadCount = 1;
  894. i2cPacket.cbWriteCount = 0;
  895. i2cPacket.puchReadBuffer = puchI2CValue;
  896. i2cPacket.puchWriteBuffer = NULL;
  897. i2cPacket.usFlags = 0;
  898. pCScript->ExecuteI2CPacket( &i2cPacket);
  899. return(( i2cPacket.uchI2CResult == I2C_STATUS_NOERROR) ? TRUE : FALSE);
  900. }
  901. /*^^*
  902. * FindI2CExpanderAddress()
  903. * Purpose : Determines I2C expander address.
  904. *
  905. * Inputs : CI2CScript * pCScript : pointer to the I2CScript class object
  906. *
  907. * Outputs : BOOL : returns TRUE, if no I2C access error;
  908. * also sets m_uchI2CExpanderAddress class member. If any was not found, set it as 0xFF
  909. * Author : IKLEBANOV
  910. *^^*/
  911. BOOL CATIHwConfiguration::FindI2CExpanderAddress( CI2CScript * pCScript)
  912. {
  913. USHORT nIndex;
  914. UCHAR uchI2CValue;
  915. I2CPacket i2cPacket;
  916. // table of the possible I2C expender addresses
  917. UCHAR auchI2CExpenderAddress[] = { 0x70, 0x78, 0x7c, 0x76};
  918. // unknown I2C expender address
  919. m_uchI2CExpanderAddress = 0xFF;
  920. for( nIndex = 0; nIndex < sizeof( auchI2CExpenderAddress); nIndex ++)
  921. {
  922. i2cPacket.uchChipAddress = auchI2CExpenderAddress[nIndex];
  923. i2cPacket.cbReadCount = 1;
  924. i2cPacket.cbWriteCount = 0;
  925. i2cPacket.puchReadBuffer = &uchI2CValue;
  926. i2cPacket.puchWriteBuffer = NULL;
  927. i2cPacket.usFlags = 0;
  928. pCScript->ExecuteI2CPacket( &i2cPacket);
  929. if( i2cPacket.uchI2CResult == I2C_STATUS_NOERROR)
  930. {
  931. m_uchI2CExpanderAddress = auchI2CExpenderAddress[nIndex];
  932. break;
  933. }
  934. }
  935. OutputDebugInfo(( "CATIHwConfig:FindI2CExpanderAddress() exit address = %x\n", m_uchI2CExpanderAddress));
  936. return( TRUE);
  937. }
  938. /*^^*
  939. * GetAudioProperties()
  940. * Purpose : Gets numbers of Audio inputs and outputs
  941. * Inputs : PULONG pulNumberOfInputs : pointer to return number of Audio inputs
  942. * PULONG pulNumberOfOutputs : pointer to return number of Audio outputs
  943. *
  944. * Outputs : BOOL : returns TRUE
  945. * also sets the requested values into the input pointers
  946. * Author : IKLEBANOV
  947. *^^*/
  948. BOOL CATIHwConfiguration::GetAudioProperties( PULONG pulNumberOfInputs, PULONG pulNumberOfOutputs)
  949. {
  950. if(( pulNumberOfInputs != NULL) && ( pulNumberOfOutputs != NULL))
  951. {
  952. // Hardcoded for AIW with no FM support - FM stuff has not been defined by Microsoft yet
  953. * pulNumberOfInputs = 2;
  954. * pulNumberOfOutputs = 1;
  955. return( TRUE);
  956. }
  957. else
  958. return( FALSE);
  959. }
  960. /*^^*
  961. * CanConnectAudioSource()
  962. * Purpose : Determines possibility to connect the specified Audio source to the audio output.
  963. *
  964. * Inputs : int nAudioSource : the audio source the function is asked about
  965. *
  966. * Outputs : BOOL : returns TRUE, the connection is possible;
  967. * Author : IKLEBANOV
  968. *^^*/
  969. BOOL CATIHwConfiguration::CanConnectAudioSource( int nAudioSource)
  970. {
  971. BOOL bResult;
  972. if( nAudioSource != AUDIOSOURCE_MUTE)
  973. bResult = nAudioSource < AUDIOSOURCE_LASTSUPPORTED;
  974. else
  975. switch( m_uiAudioConfiguration)
  976. {
  977. case ATI_AUDIO_CONFIG_1:
  978. case ATI_AUDIO_CONFIG_2:
  979. case ATI_AUDIO_CONFIG_4:
  980. case ATI_AUDIO_CONFIG_5:
  981. case ATI_AUDIO_CONFIG_6:
  982. case ATI_AUDIO_CONFIG_7:
  983. case ATI_AUDIO_CONFIG_8:
  984. bResult = TRUE;
  985. break;
  986. case ATI_AUDIO_CONFIG_3:
  987. default:
  988. bResult = FALSE;
  989. break;
  990. }
  991. return( bResult);
  992. }
  993. /*^^*
  994. * SetDefaultVolumeControl()
  995. * Purpose : Set the default volume level, if the hardware support volume control
  996. *
  997. * Inputs : CI2CScript * pCScript : pointer to I2CScript class object
  998. *
  999. * Outputs : BOOL : returns FALSE, if either unknown audio source or I2C access error;
  1000. * Author : IKLEBANOV
  1001. *^^*/
  1002. BOOL CATIHwConfiguration::SetDefaultVolumeControl( CI2CScript * pCScript)
  1003. {
  1004. BOOL bResult;
  1005. I2CPacket i2cPacket;
  1006. UCHAR uchWriteBuffer[3];
  1007. switch( m_uiAudioConfiguration)
  1008. {
  1009. case ATI_AUDIO_CONFIG_4:
  1010. ENSURE
  1011. {
  1012. i2cPacket.uchChipAddress = m_uchAudioAddress;
  1013. i2cPacket.cbReadCount = 0;
  1014. i2cPacket.cbWriteCount = 3;
  1015. i2cPacket.puchReadBuffer = NULL;
  1016. i2cPacket.puchWriteBuffer = uchWriteBuffer;
  1017. i2cPacket.usFlags = I2COPERATION_WRITE;
  1018. uchWriteBuffer[0] = 0x00; // volume left + right
  1019. uchWriteBuffer[1] = 0xFA;
  1020. uchWriteBuffer[2] = 0xFA;
  1021. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1022. } END_ENSURE;
  1023. break;
  1024. default:
  1025. bResult = TRUE;
  1026. break;
  1027. }
  1028. return( bResult);
  1029. }
  1030. /*^^*
  1031. * ConnectAudioSource()
  1032. * Purpose : Connects the specified Audio input to the Audio output.
  1033. *
  1034. * Inputs : CI2CScript * pCScript : pointer to I2CScript class object
  1035. * int nAudioSource : the audio source to be connected to the audio output
  1036. *
  1037. * Outputs : BOOL : returns FALSE, if either unknown audio source or I2C access error;
  1038. * Author : IKLEBANOV
  1039. *^^*/
  1040. BOOL CATIHwConfiguration::ConnectAudioSource( CI2CScript * pCScript,
  1041. int nAudioSource)
  1042. {
  1043. UCHAR uchORMask = 0;
  1044. UCHAR uchANDMask = 0xFF;
  1045. UCHAR uchReadValue, uchWriteValue[2];
  1046. UCHAR uchWrite16Value[5];
  1047. I2CPacket i2cPacket;
  1048. BOOL bI2CAccess, bResult;
  1049. GPIOControl gpioAccessBlock;
  1050. UCHAR uchI2CAddr;
  1051. USHORT cbWRCount;
  1052. USHORT cbRDCount;
  1053. USHORT usI2CMode;
  1054. switch( m_uiAudioConfiguration)
  1055. {
  1056. case ATI_AUDIO_CONFIG_1:
  1057. bI2CAccess = TRUE;
  1058. uchI2CAddr = m_uchI2CExpanderAddress;
  1059. cbWRCount = 1;
  1060. cbRDCount = 1;
  1061. usI2CMode = I2COPERATION_READWRITE;
  1062. uchANDMask &= 0xAF;
  1063. switch( nAudioSource)
  1064. {
  1065. case AUDIOSOURCE_MUTE:
  1066. uchORMask |= 0x00;
  1067. break;
  1068. case AUDIOSOURCE_TVAUDIO:
  1069. uchORMask |= 0x10;
  1070. break;
  1071. case AUDIOSOURCE_LINEIN:
  1072. uchORMask |= 0x50;
  1073. break;
  1074. case AUDIOSOURCE_FMAUDIO:
  1075. // no FM is supported
  1076. default:
  1077. return( FALSE);
  1078. }
  1079. break;
  1080. case ATI_AUDIO_CONFIG_2:
  1081. bI2CAccess = FALSE;
  1082. uchANDMask &= 0xFC;
  1083. switch( nAudioSource)
  1084. {
  1085. case AUDIOSOURCE_MUTE:
  1086. uchORMask |= 0x02;
  1087. break;
  1088. case AUDIOSOURCE_TVAUDIO:
  1089. uchORMask |= 0x01;
  1090. break;
  1091. case AUDIOSOURCE_LINEIN:
  1092. uchORMask |= 0x00;
  1093. break;
  1094. case AUDIOSOURCE_FMAUDIO:
  1095. uchORMask |= 0x03;
  1096. default:
  1097. return( FALSE);
  1098. }
  1099. break;
  1100. case ATI_AUDIO_CONFIG_3:
  1101. bI2CAccess = TRUE;
  1102. uchI2CAddr = m_uchI2CExpanderAddress;
  1103. cbWRCount = 1;
  1104. cbRDCount = 1;
  1105. usI2CMode = I2COPERATION_READWRITE;
  1106. uchANDMask &= 0xDF;
  1107. switch( nAudioSource)
  1108. {
  1109. case AUDIOSOURCE_TVAUDIO:
  1110. uchORMask |= 0x00;
  1111. break;
  1112. case AUDIOSOURCE_LINEIN:
  1113. uchORMask |= 0x40;
  1114. break;
  1115. case AUDIOSOURCE_FMAUDIO:
  1116. // no FM is supported
  1117. case AUDIOSOURCE_MUTE:
  1118. // no mute is supported
  1119. default:
  1120. return( FALSE);
  1121. }
  1122. break;
  1123. case ATI_AUDIO_CONFIG_4:
  1124. bI2CAccess = TRUE;
  1125. uchI2CAddr = m_uchAudioAddress;
  1126. cbWRCount = 2;
  1127. cbRDCount = 0;
  1128. usI2CMode = I2COPERATION_WRITE;
  1129. uchWriteValue[0] = 0x08;
  1130. switch( nAudioSource)
  1131. {
  1132. case AUDIOSOURCE_MUTE:
  1133. uchWriteValue[1] = 0xF7;
  1134. break;
  1135. case AUDIOSOURCE_TVAUDIO:
  1136. SetDefaultVolumeControl( pCScript);
  1137. uchWriteValue[1] = 0xD7;
  1138. break;
  1139. case AUDIOSOURCE_LINEIN:
  1140. SetDefaultVolumeControl( pCScript);
  1141. uchWriteValue[1] = 0xCE;
  1142. break;
  1143. case AUDIOSOURCE_FMAUDIO:
  1144. // no FM is supported
  1145. default:
  1146. return( FALSE);
  1147. }
  1148. break;
  1149. case ATI_AUDIO_CONFIG_5:
  1150. bI2CAccess = TRUE;
  1151. uchI2CAddr = m_uchI2CExpanderAddress;
  1152. cbWRCount = 1;
  1153. cbRDCount = 1;
  1154. usI2CMode = I2COPERATION_READWRITE;
  1155. uchANDMask &= 0xAF;
  1156. switch( nAudioSource)
  1157. {
  1158. case AUDIOSOURCE_MUTE:
  1159. uchORMask |= 0x50;
  1160. break;
  1161. case AUDIOSOURCE_TVAUDIO:
  1162. uchORMask |= 0x00;
  1163. break;
  1164. case AUDIOSOURCE_LINEIN:
  1165. uchORMask |= 0x40;
  1166. break;
  1167. case AUDIOSOURCE_FMAUDIO:
  1168. uchORMask |= 0x10;
  1169. default:
  1170. return( FALSE);
  1171. }
  1172. break;
  1173. case ATI_AUDIO_CONFIG_6:
  1174. case ATI_AUDIO_CONFIG_7:
  1175. bI2CAccess = TRUE;
  1176. uchI2CAddr = m_uchDecoderAddress;
  1177. cbWRCount = 2;
  1178. cbRDCount = 1;
  1179. usI2CMode = I2COPERATION_READWRITE;
  1180. uchWriteValue[0] = 0x3F;
  1181. uchANDMask &= 0xFC;
  1182. switch( nAudioSource)
  1183. {
  1184. case AUDIOSOURCE_MUTE:
  1185. uchORMask |= 0x02;
  1186. break;
  1187. case AUDIOSOURCE_TVAUDIO:
  1188. uchORMask |= 0x01;
  1189. break;
  1190. case AUDIOSOURCE_LINEIN:
  1191. uchORMask |= 0x00;
  1192. break;
  1193. case AUDIOSOURCE_FMAUDIO:
  1194. uchORMask |= 0x03;
  1195. default:
  1196. return( FALSE);
  1197. }
  1198. break;
  1199. case ATI_AUDIO_CONFIG_8:
  1200. switch( nAudioSource)
  1201. {
  1202. case AUDIOSOURCE_MUTE:
  1203. i2cPacket.uchChipAddress = m_uchAudioAddress;
  1204. i2cPacket.cbReadCount = 0;
  1205. i2cPacket.cbWriteCount = 5;
  1206. i2cPacket.usFlags = I2COPERATION_WRITE;
  1207. i2cPacket.puchWriteBuffer = uchWrite16Value;
  1208. //SubAddr 0x12 Reg 0x13 Val 0x3f60
  1209. uchWrite16Value[0] = 0x12;
  1210. uchWrite16Value[1] = 0x00;
  1211. uchWrite16Value[2] = 0x13;
  1212. uchWrite16Value[3] = 0x3f;
  1213. uchWrite16Value[4] = 0x60;
  1214. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1215. if(bResult)
  1216. {
  1217. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1218. return(FALSE);
  1219. }
  1220. else
  1221. return(FALSE);
  1222. //SubAddr 0x12 Reg 0xD Val 0x0000
  1223. uchWrite16Value[0] = 0x12;
  1224. uchWrite16Value[1] = 0x00;
  1225. uchWrite16Value[2] = 0x0d;
  1226. uchWrite16Value[3] = 0x00;
  1227. uchWrite16Value[4] = 0x00;
  1228. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1229. if(bResult)
  1230. {
  1231. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1232. return(FALSE);
  1233. }
  1234. else
  1235. return(FALSE);
  1236. //SubAddr 0x12 Reg 0x8 Val 0x0220
  1237. uchWrite16Value[0] = 0x12;
  1238. uchWrite16Value[1] = 0x00;
  1239. uchWrite16Value[2] = 0x08;
  1240. uchWrite16Value[3] = 0x02;
  1241. uchWrite16Value[4] = 0x20;
  1242. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1243. if(bResult)
  1244. {
  1245. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1246. return(FALSE);
  1247. }
  1248. else
  1249. return(FALSE);
  1250. //SubAddr 0x12 Reg 0x00 Val 0x0000
  1251. uchWrite16Value[0] = 0x12;
  1252. uchWrite16Value[1] = 0x00;
  1253. uchWrite16Value[2] = 0x00;
  1254. uchWrite16Value[3] = 0x00;
  1255. uchWrite16Value[4] = 0x00;
  1256. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1257. if(bResult)
  1258. {
  1259. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1260. return(FALSE);
  1261. }
  1262. else
  1263. return(FALSE);
  1264. break;
  1265. case AUDIOSOURCE_LINEIN:
  1266. i2cPacket.uchChipAddress = m_uchAudioAddress;
  1267. i2cPacket.cbReadCount = 0;
  1268. i2cPacket.cbWriteCount = 5;
  1269. i2cPacket.usFlags = I2COPERATION_WRITE;
  1270. i2cPacket.puchWriteBuffer = uchWrite16Value;
  1271. //SubAddr 0x10 Reg 0x30 Val 0x0000
  1272. uchWrite16Value[0] = 0x10;
  1273. uchWrite16Value[1] = 0x00;
  1274. uchWrite16Value[2] = 0x30;
  1275. uchWrite16Value[3] = 0x00;
  1276. #ifdef I2S_CAPTURE
  1277. #pragma message ("\n!!! PAY ATTENTION: Driver has been build with ITT CHIP I2S CAPTURE CONFIGURED !!!\n")
  1278. uchWrite16Value[4] = 0xe0;
  1279. #else
  1280. uchWrite16Value[4] = 0x00;
  1281. #endif
  1282. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1283. if(bResult)
  1284. {
  1285. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1286. return(FALSE);
  1287. }
  1288. else
  1289. return(FALSE);
  1290. //SubAddr 0x10 Reg 0x20 Val 0x0000
  1291. uchWrite16Value[0] = 0x10;
  1292. uchWrite16Value[1] = 0x00;
  1293. uchWrite16Value[2] = 0x20;
  1294. uchWrite16Value[3] = 0x00;
  1295. uchWrite16Value[4] = 0x00;
  1296. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1297. if(bResult)
  1298. {
  1299. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1300. return(FALSE);
  1301. }
  1302. else
  1303. return(FALSE);
  1304. //SubAddr 0x12 Reg 0xe Val 0x0000
  1305. uchWrite16Value[0] = 0x12;
  1306. uchWrite16Value[1] = 0x00;
  1307. uchWrite16Value[2] = 0x0e;
  1308. uchWrite16Value[3] = 0x00;
  1309. uchWrite16Value[4] = 0x00;
  1310. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1311. if(bResult)
  1312. {
  1313. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1314. return(FALSE);
  1315. }
  1316. else
  1317. return(FALSE);
  1318. //SubAddr 0x12 Reg 0x13 Val 0x3c40
  1319. uchWrite16Value[0] = 0x12;
  1320. uchWrite16Value[1] = 0x00;
  1321. uchWrite16Value[2] = 0x13;
  1322. uchWrite16Value[3] = 0x3c;
  1323. uchWrite16Value[4] = 0x40;
  1324. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1325. if(bResult)
  1326. {
  1327. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1328. return(FALSE);
  1329. }
  1330. else
  1331. return(FALSE);
  1332. //SubAddr 0x12 Reg 0x8 Val 0x3c40
  1333. uchWrite16Value[0] = 0x12;
  1334. uchWrite16Value[1] = 0x00;
  1335. uchWrite16Value[2] = 0x08;
  1336. uchWrite16Value[3] = 0x02;
  1337. uchWrite16Value[4] = 0x20;
  1338. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1339. if(bResult)
  1340. {
  1341. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1342. return(FALSE);
  1343. }
  1344. else
  1345. return(FALSE);
  1346. //SubAddr 0x12 Reg 0xd Val 0x1900
  1347. uchWrite16Value[0] = 0x12;
  1348. uchWrite16Value[1] = 0x00;
  1349. uchWrite16Value[2] = 0x0d;
  1350. uchWrite16Value[3] = 0x19;
  1351. uchWrite16Value[4] = 0x00;
  1352. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1353. if(bResult)
  1354. {
  1355. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1356. return(FALSE);
  1357. }
  1358. else
  1359. return(FALSE);
  1360. //SubAddr 0x12 Reg 0x00 Val 0x7300
  1361. uchWrite16Value[0] = 0x12;
  1362. uchWrite16Value[1] = 0x00;
  1363. uchWrite16Value[2] = 0x00;
  1364. uchWrite16Value[3] = 0x73;
  1365. uchWrite16Value[4] = 0x00;
  1366. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1367. if(bResult)
  1368. {
  1369. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1370. return(FALSE);
  1371. }
  1372. else
  1373. return(FALSE);
  1374. break;
  1375. case AUDIOSOURCE_TVAUDIO:
  1376. i2cPacket.uchChipAddress = m_uchAudioAddress;
  1377. i2cPacket.cbReadCount = 0;
  1378. i2cPacket.cbWriteCount = 5;
  1379. i2cPacket.usFlags = I2COPERATION_WRITE;
  1380. i2cPacket.puchWriteBuffer = uchWrite16Value;
  1381. //SubAddr 0x12 Reg 0x13 Val 0x3f60
  1382. uchWrite16Value[0] = 0x12;
  1383. uchWrite16Value[1] = 0x00;
  1384. uchWrite16Value[2] = 0x13;
  1385. uchWrite16Value[3] = 0x3f;
  1386. uchWrite16Value[4] = 0x60;
  1387. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1388. if(bResult)
  1389. {
  1390. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1391. return(FALSE);
  1392. }
  1393. else
  1394. return(FALSE);
  1395. //SubAddr 0x12 Reg 0xD Val 0x0000
  1396. uchWrite16Value[0] = 0x12;
  1397. uchWrite16Value[1] = 0x00;
  1398. uchWrite16Value[2] = 0x0d;
  1399. uchWrite16Value[3] = 0x00;
  1400. uchWrite16Value[4] = 0x00;
  1401. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1402. if(bResult)
  1403. {
  1404. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1405. return(FALSE);
  1406. }
  1407. else
  1408. return(FALSE);
  1409. //SubAddr 0x10 Reg 0x30 Val 0x2003
  1410. uchWrite16Value[0] = 0x10;
  1411. uchWrite16Value[1] = 0x00;
  1412. uchWrite16Value[2] = 0x30;
  1413. uchWrite16Value[3] = 0x20;
  1414. #ifdef I2S_CAPTURE
  1415. #pragma message ("\n!!! PAY ATTENTION: Driver has been build with ITT CHIP I2S CAPTURE CONFIGURED !!!\n")
  1416. uchWrite16Value[4] = 0xe3;
  1417. #else
  1418. uchWrite16Value[4] = 0x03;
  1419. #endif
  1420. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1421. if(bResult)
  1422. {
  1423. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1424. return(FALSE);
  1425. }
  1426. else
  1427. return(FALSE);
  1428. //SubAddr 0x10 Reg 0x20 Val 0x0020
  1429. uchWrite16Value[0] = 0x10;
  1430. uchWrite16Value[1] = 0x00;
  1431. uchWrite16Value[2] = 0x20;
  1432. uchWrite16Value[3] = 0x00;
  1433. uchWrite16Value[4] = 0x20;
  1434. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1435. if(bResult)
  1436. {
  1437. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1438. return(FALSE);
  1439. }
  1440. else
  1441. return(FALSE);
  1442. //SubAddr 0x12 Reg 0xE Val 0x2403
  1443. uchWrite16Value[0] = 0x12;
  1444. uchWrite16Value[1] = 0x00;
  1445. uchWrite16Value[2] = 0x0e;
  1446. uchWrite16Value[3] = 0x24;
  1447. uchWrite16Value[4] = 0x03;
  1448. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1449. if(bResult)
  1450. {
  1451. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1452. return(FALSE);
  1453. }
  1454. else
  1455. return(FALSE);
  1456. //SubAddr 0x12 Reg 0x08 Val 0x0320
  1457. uchWrite16Value[0] = 0x12;
  1458. uchWrite16Value[1] = 0x00;
  1459. uchWrite16Value[2] = 0x08;
  1460. uchWrite16Value[3] = 0x03;
  1461. uchWrite16Value[4] = 0x20;
  1462. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1463. if(bResult)
  1464. {
  1465. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1466. return(FALSE);
  1467. }
  1468. else
  1469. return(FALSE);
  1470. //SubAddr 0x12 Reg 0x00 Val 0x7300
  1471. uchWrite16Value[0] = 0x12;
  1472. uchWrite16Value[1] = 0x00;
  1473. uchWrite16Value[2] = 0x00;
  1474. uchWrite16Value[3] = 0x73;
  1475. uchWrite16Value[4] = 0x00;
  1476. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1477. if(bResult)
  1478. {
  1479. if( i2cPacket.uchI2CResult != I2CSCRIPT_NOERROR)
  1480. return(FALSE);
  1481. }
  1482. else
  1483. return(FALSE);
  1484. break;
  1485. default:
  1486. return(FALSE);
  1487. }//switch
  1488. return(TRUE);
  1489. //break;
  1490. default :
  1491. return( FALSE);
  1492. }
  1493. if( bI2CAccess)
  1494. {
  1495. if( pCScript == NULL)
  1496. return( FALSE);
  1497. i2cPacket.uchChipAddress = uchI2CAddr;
  1498. i2cPacket.cbReadCount = cbRDCount;
  1499. i2cPacket.cbWriteCount = cbWRCount;
  1500. i2cPacket.puchReadBuffer = &uchReadValue;
  1501. i2cPacket.puchWriteBuffer = uchWriteValue;
  1502. i2cPacket.usFlags = usI2CMode;
  1503. i2cPacket.uchORValue = uchORMask;
  1504. i2cPacket.uchANDValue = uchANDMask;
  1505. // synchronous execution
  1506. bResult = pCScript->PerformI2CPacketOperation( &i2cPacket);
  1507. OutputDebugInfo(( "CATIHwConfig: ConnectAudioSource( %d) = %d\n", nAudioSource, bResult));
  1508. if( bResult)
  1509. bResult = ( i2cPacket.uchI2CResult == I2CSCRIPT_NOERROR);
  1510. return( bResult);
  1511. }
  1512. else
  1513. {
  1514. // use GPIO interface to switch Audio source
  1515. bResult = FALSE;
  1516. ENSURE
  1517. {
  1518. if(( m_gpioProviderInterface.gpioOpen == NULL) ||
  1519. ( m_gpioProviderInterface.gpioAccess == NULL))
  1520. FAIL;
  1521. uchReadValue = AUDIO_MUX_PINS; // use as a PinMask
  1522. gpioAccessBlock.Pins = &uchReadValue;
  1523. gpioAccessBlock.Flags = GPIO_FLAGS_BYTE;
  1524. gpioAccessBlock.nBytes = 1;
  1525. gpioAccessBlock.nBufferSize = 1;
  1526. gpioAccessBlock.AsynchCompleteCallback = NULL;
  1527. // lock GPIO provider
  1528. if( !LockGPIOProviderEx( &gpioAccessBlock))
  1529. FAIL;
  1530. uchReadValue = AUDIO_MUX_PINS; // use as a PinMask
  1531. gpioAccessBlock.Command = GPIO_COMMAND_READ_BUFFER;
  1532. gpioAccessBlock.Flags = GPIO_FLAGS_BYTE;
  1533. gpioAccessBlock.dwCookie = m_dwGPIOAccessKey;
  1534. gpioAccessBlock.nBytes = 1;
  1535. gpioAccessBlock.nBufferSize = 1;
  1536. gpioAccessBlock.Pins = &uchReadValue;
  1537. gpioAccessBlock.Buffer = uchWriteValue;
  1538. gpioAccessBlock.AsynchCompleteCallback = NULL;
  1539. if( !AccessGPIOProvider( m_pdoDriver, &gpioAccessBlock))
  1540. FAIL;
  1541. uchWriteValue[0] &= uchANDMask;
  1542. uchWriteValue[0] |= uchORMask;
  1543. gpioAccessBlock.Command = GPIO_COMMAND_WRITE_BUFFER;
  1544. if( !AccessGPIOProvider( m_pdoDriver, &gpioAccessBlock))
  1545. FAIL;
  1546. bResult = TRUE;
  1547. }END_ENSURE;
  1548. // nothing bad will happen if we try to release the provider even we
  1549. // have not obtained it at the first place
  1550. uchReadValue = AUDIO_MUX_PINS; // use as a PinMask
  1551. gpioAccessBlock.Pins = &uchReadValue;
  1552. gpioAccessBlock.Flags = GPIO_FLAGS_BYTE;
  1553. gpioAccessBlock.nBytes = 1;
  1554. gpioAccessBlock.nBufferSize = 1;
  1555. gpioAccessBlock.AsynchCompleteCallback = NULL;
  1556. ReleaseGPIOProvider( &gpioAccessBlock);
  1557. return( bResult);
  1558. }
  1559. }
  1560. /*^^*
  1561. * GPIOIoSynchCompletionRoutine()
  1562. * Purpose : This routine is for use with synchronous IRP processing.
  1563. * All it does is signal an event, so the driver knows it and can continue.
  1564. *
  1565. * Inputs : PDEVICE_OBJECT DriverObject : Pointer to driver object created by system
  1566. * PIRP pIrp : Irp that just completed
  1567. * PVOID Event : Event we'll signal to say Irp is done
  1568. *
  1569. * Outputs : none
  1570. * Author : IKLEBANOV
  1571. *^^*/
  1572. extern "C"
  1573. NTSTATUS GPIOIoSynchCompletionRoutine( IN PDEVICE_OBJECT pDeviceObject,
  1574. IN PIRP pIrp,
  1575. IN PVOID Event)
  1576. {
  1577. KeSetEvent(( PKEVENT)Event, 0, FALSE);
  1578. return( STATUS_MORE_PROCESSING_REQUIRED);
  1579. }
  1580. /*^^*
  1581. * InitializeAttachGPIOProvider()
  1582. * Purpose : determines the pointer to the parent GPIO Provider interface
  1583. * This function will be called at Low priority
  1584. *
  1585. * Inputs : GPIOINTERFACE * pGPIOInterface : pointer to the Interface to be filled in
  1586. * PDEVICE_OBJECT pDeviceObject : MiniDriver device object, which is a child of GPIO Master
  1587. *
  1588. * Outputs : BOOL - returns TRUE, if the interface was found
  1589. * Author : IKLEBANOV
  1590. *^^*/
  1591. BOOL CATIHwConfiguration::InitializeAttachGPIOProvider( GPIOINTERFACE * pGPIOInterface, PDEVICE_OBJECT pDeviceObject)
  1592. {
  1593. BOOL bResult;
  1594. bResult = LocateAttachGPIOProvider( pGPIOInterface, pDeviceObject, IRP_MJ_PNP);
  1595. if(( pGPIOInterface->gpioOpen == NULL) || ( pGPIOInterface->gpioAccess == NULL))
  1596. {
  1597. OutputDebugError(( "CATIHwConfig(): GPIO interface has NULL pointers\n"));
  1598. bResult = FALSE;
  1599. }
  1600. return( bResult);
  1601. }
  1602. /*^^*
  1603. * LocateAttachGPIOProvider()
  1604. * Purpose : gets the pointer to the parent GPIO Provider interface
  1605. * This function will be called at Low priority
  1606. *
  1607. * Inputs : GPIOINTERFACE * pGPIOInterface : pointer to the Interface to be filled in
  1608. * PDEVICE_OBJECT pDeviceObject : MiniDriver device object, which is a child of I2C Master
  1609. * int nIrpMajorFunction : IRP major function to query the GPIO Interface
  1610. *
  1611. * Outputs : BOOL - returns TRUE, if the interface was found
  1612. * Author : IKLEBANOV
  1613. *^^*/
  1614. BOOL CATIHwConfiguration::LocateAttachGPIOProvider( GPIOINTERFACE * pGPIOInterface, PDEVICE_OBJECT pDeviceObject, UCHAR nIrpMajorFunction)
  1615. {
  1616. PIRP pIrp;
  1617. BOOL bResult = FALSE;
  1618. ENSURE
  1619. {
  1620. PIO_STACK_LOCATION pNextStack;
  1621. NTSTATUS ntStatus;
  1622. KEVENT Event;
  1623. pIrp = IoAllocateIrp( pDeviceObject->StackSize, FALSE);
  1624. if( pIrp == NULL)
  1625. {
  1626. OutputDebugError(( "CATIHwConfig(): can not allocate IRP\n"));
  1627. FAIL;
  1628. }
  1629. pNextStack = IoGetNextIrpStackLocation( pIrp);
  1630. if( pNextStack == NULL)
  1631. {
  1632. OutputDebugError(( "CATIHwConfig(): can not allocate NextStack\n"));
  1633. FAIL;
  1634. }
  1635. pIrp->IoStatus.Status = STATUS_NOT_SUPPORTED;
  1636. pNextStack->MajorFunction = nIrpMajorFunction;
  1637. pNextStack->MinorFunction = IRP_MN_QUERY_INTERFACE;
  1638. KeInitializeEvent( &Event, NotificationEvent, FALSE);
  1639. IoSetCompletionRoutine( pIrp,
  1640. GPIOIoSynchCompletionRoutine,
  1641. &Event, TRUE, TRUE, TRUE);
  1642. pNextStack->Parameters.QueryInterface.InterfaceType = ( struct _GUID *)&GUID_GPIO_INTERFACE;
  1643. pNextStack->Parameters.QueryInterface.Size = sizeof( GPIOINTERFACE);
  1644. pNextStack->Parameters.QueryInterface.Version = 1;
  1645. pNextStack->Parameters.QueryInterface.Interface = ( PINTERFACE)pGPIOInterface;
  1646. pNextStack->Parameters.QueryInterface.InterfaceSpecificData = NULL;
  1647. ntStatus = IoCallDriver( pDeviceObject, pIrp);
  1648. if( ntStatus == STATUS_PENDING)
  1649. KeWaitForSingleObject( &Event,
  1650. Suspended, KernelMode, FALSE, NULL);
  1651. if(( pGPIOInterface->gpioOpen == NULL) || ( pGPIOInterface->gpioAccess == NULL))
  1652. FAIL;
  1653. bResult = TRUE;
  1654. } END_ENSURE;
  1655. if( pIrp != NULL)
  1656. IoFreeIrp( pIrp);
  1657. return( bResult);
  1658. }
  1659. /*^^*
  1660. * LockGPIOProviderEx()
  1661. * Purpose : locks the GPIOProvider for exclusive use
  1662. *
  1663. * Inputs : PGPIOControl pgpioAccessBlock : pointer to GPIO control structure
  1664. *
  1665. * Outputs : BOOL : retunrs TRUE, if the GPIOProvider is locked
  1666. * Author : IKLEBANOV
  1667. *^^*/
  1668. BOOL CATIHwConfiguration::LockGPIOProviderEx( PGPIOControl pgpioAccessBlock)
  1669. {
  1670. NTSTATUS ntStatus;
  1671. LARGE_INTEGER liStartTime, liCurrentTime;
  1672. KeQuerySystemTime( &liStartTime);
  1673. ENSURE
  1674. {
  1675. if(( m_gpioProviderInterface.gpioOpen == NULL) ||
  1676. ( m_gpioProviderInterface.gpioAccess == NULL) ||
  1677. ( m_pdoDriver == NULL))
  1678. FAIL;
  1679. pgpioAccessBlock->Status = GPIO_STATUS_NOERROR;
  1680. pgpioAccessBlock->Command = GPIO_COMMAND_OPEN_PINS;
  1681. while( TRUE)
  1682. {
  1683. KeQuerySystemTime( &liCurrentTime);
  1684. if(( liCurrentTime.QuadPart - liStartTime.QuadPart) >= GPIO_TIMELIMIT_OPENPROVIDER)
  1685. {
  1686. // time has expired for attempting to lock GPIO provider
  1687. return (FALSE);
  1688. }
  1689. ntStatus = m_gpioProviderInterface.gpioOpen( m_pdoDriver, TRUE, pgpioAccessBlock);
  1690. if(( NT_SUCCESS( ntStatus)) && ( pgpioAccessBlock->Status == GPIO_STATUS_NOERROR))
  1691. break;
  1692. }
  1693. // the GPIO Provider has granted access - save dwCookie for further use
  1694. m_dwGPIOAccessKey = pgpioAccessBlock->dwCookie;
  1695. return( TRUE);
  1696. } END_ENSURE;
  1697. return( FALSE);
  1698. }
  1699. /*^^*
  1700. * ReleaseGPIOProvider()
  1701. * Purpose : releases the GPIOProvider for other clients' use
  1702. *
  1703. * Inputs : PGPIOControl pgpioAccessBlock : pointer to a composed GPIO access block
  1704. *
  1705. * Outputs : BOOL : retunrs TRUE, if the GPIOProvider is released
  1706. * Author : IKLEBANOV
  1707. *^^*/
  1708. BOOL CATIHwConfiguration::ReleaseGPIOProvider( PGPIOControl pgpioAccessBlock)
  1709. {
  1710. NTSTATUS ntStatus;
  1711. ENSURE
  1712. {
  1713. if(( m_gpioProviderInterface.gpioOpen == NULL) ||
  1714. ( m_gpioProviderInterface.gpioAccess == NULL) ||
  1715. ( m_pdoDriver == NULL))
  1716. FAIL;
  1717. pgpioAccessBlock->Status = GPIO_STATUS_NOERROR;
  1718. pgpioAccessBlock->Command = GPIO_COMMAND_CLOSE_PINS;
  1719. pgpioAccessBlock->dwCookie = m_dwGPIOAccessKey;
  1720. ntStatus = m_gpioProviderInterface.gpioOpen( m_pdoDriver, FALSE, pgpioAccessBlock);
  1721. if( !NT_SUCCESS( ntStatus))
  1722. {
  1723. OutputDebugError(( "CATIHwConfig: ReleaseGPIOProvider() NTSTATUS = %x\n", ntStatus));
  1724. FAIL;
  1725. }
  1726. if( pgpioAccessBlock->Status != GPIO_STATUS_NOERROR)
  1727. {
  1728. OutputDebugError(( "CATIHwConfig: ReleaseGPIOProvider() Status = %x\n", pgpioAccessBlock->Status));
  1729. FAIL;
  1730. }
  1731. m_dwGPIOAccessKey = 0;
  1732. return ( TRUE);
  1733. } END_ENSURE;
  1734. return( FALSE);
  1735. }
  1736. /*^^*
  1737. * AccessGPIOProvider()
  1738. * Purpose : provide synchronous type of access to GPIOProvider
  1739. *
  1740. * Inputs : PDEVICE_OBJECT pdoDriver : pointer to the client's device object
  1741. * PGPIOControl pgpioAccessBlock : pointer to a composed GPIO access block
  1742. *
  1743. * Outputs : BOOL, TRUE if acsepted by the GPIO Provider
  1744. *
  1745. * Author : IKLEBANOV
  1746. *^^*/
  1747. BOOL CATIHwConfiguration::AccessGPIOProvider( PDEVICE_OBJECT pdoClient, PGPIOControl pgpioAccessBlock)
  1748. {
  1749. NTSTATUS ntStatus;
  1750. ENSURE
  1751. {
  1752. if(( m_gpioProviderInterface.gpioOpen == NULL) ||
  1753. ( m_gpioProviderInterface.gpioAccess == NULL) ||
  1754. ( m_pdoDriver == NULL))
  1755. FAIL;
  1756. ntStatus = m_gpioProviderInterface.gpioAccess( pdoClient, pgpioAccessBlock);
  1757. if( !NT_SUCCESS( ntStatus))
  1758. {
  1759. OutputDebugError(( "CATIHwConfig: AccessGPIOProvider() NTSTATUS = %x\n", ntStatus));
  1760. FAIL;
  1761. }
  1762. if( pgpioAccessBlock->Status != GPIO_STATUS_NOERROR)
  1763. {
  1764. OutputDebugError(( "CATIHwConfig: AccessGPIOProvider() Status = %x\n", pgpioAccessBlock->Status));
  1765. FAIL;
  1766. }
  1767. return TRUE;
  1768. } END_ENSURE;
  1769. return( FALSE);
  1770. }
  1771. /*^^*
  1772. * SetTunerPowerState
  1773. * Purpose : Sets Tuner power mode
  1774. * Inputs : CI2CScript * pCScript : pointer to the I2C Provider class
  1775. * BOOL bPowerState : TRUE, if turne the power on
  1776. *
  1777. * Outputs : BOOL, TRUE if successfull
  1778. * Author : TOM
  1779. *^^*/
  1780. BOOL CATIHwConfiguration::SetTunerPowerState( CI2CScript * pCScript,
  1781. BOOL bPowerState)
  1782. {
  1783. UCHAR uchORMask = 0x0;
  1784. UCHAR uchANDMask = 0xFF;
  1785. UCHAR uchPinsMask, uchValue;
  1786. BOOL bResult;
  1787. GPIOControl gpioAccessBlock;
  1788. switch( m_usTunerPowerConfiguration)
  1789. {
  1790. case ATI_TUNER_POWER_CONFIG_1:
  1791. if( bPowerState)
  1792. uchANDMask &= 0xF7;
  1793. else
  1794. uchORMask |= 0x08;
  1795. break;
  1796. default :
  1797. return( FALSE);
  1798. }
  1799. // use GPIO interface to turn Tuner power ON / OFF
  1800. bResult = FALSE;
  1801. ENSURE
  1802. {
  1803. if(( m_gpioProviderInterface.gpioOpen == NULL) ||
  1804. ( m_gpioProviderInterface.gpioAccess == NULL))
  1805. FAIL;
  1806. uchPinsMask = TUNER_PM_PINS; // use as a PinMask
  1807. gpioAccessBlock.Pins = &uchPinsMask;
  1808. gpioAccessBlock.Flags = GPIO_FLAGS_BYTE;
  1809. gpioAccessBlock.nBytes = 1;
  1810. gpioAccessBlock.nBufferSize = 1;
  1811. gpioAccessBlock.AsynchCompleteCallback = NULL;
  1812. // try to get GPIO Provider
  1813. if( !LockGPIOProviderEx( &gpioAccessBlock))
  1814. FAIL;
  1815. uchPinsMask = TUNER_PM_PINS; // use as a PinMask
  1816. gpioAccessBlock.Command = GPIO_COMMAND_READ_BUFFER;
  1817. gpioAccessBlock.Flags = GPIO_FLAGS_BYTE;
  1818. gpioAccessBlock.dwCookie = m_dwGPIOAccessKey;
  1819. gpioAccessBlock.nBytes = 1;
  1820. gpioAccessBlock.nBufferSize = 1;
  1821. gpioAccessBlock.Pins = &uchPinsMask;
  1822. gpioAccessBlock.Buffer = &uchValue;
  1823. gpioAccessBlock.AsynchCompleteCallback = NULL;
  1824. if( !AccessGPIOProvider( m_pdoDriver, &gpioAccessBlock))
  1825. FAIL;
  1826. uchValue &= uchANDMask;
  1827. uchValue |= uchORMask;
  1828. gpioAccessBlock.Command = GPIO_COMMAND_WRITE_BUFFER;
  1829. if( !AccessGPIOProvider( m_pdoDriver, &gpioAccessBlock))
  1830. FAIL;
  1831. bResult = TRUE;
  1832. } END_ENSURE;
  1833. // nothing bad will happen if we try to release the provider even we
  1834. // have not obtained it at the first place
  1835. uchValue = TUNER_PM_PINS; // use as a PinMask
  1836. gpioAccessBlock.Pins = &uchValue;
  1837. gpioAccessBlock.Flags = GPIO_FLAGS_BYTE;
  1838. gpioAccessBlock.nBytes = 1;
  1839. gpioAccessBlock.nBufferSize = 1;
  1840. gpioAccessBlock.AsynchCompleteCallback = NULL;
  1841. ReleaseGPIOProvider( &gpioAccessBlock);
  1842. return( bResult);
  1843. }
  1844. /*^^*
  1845. * ValidateConfigurationE2PROM
  1846. * Purpose : Checks the integrity ( check-sum) of I2C driven configuration EEPROM
  1847. * Inputs : CI2CScript * pCScript : pointer to the I2C Provider class
  1848. *
  1849. * Outputs : BOOL, TRUE if the information inside EEPROM is valid
  1850. * Author : TOM
  1851. *^^*/
  1852. BOOL CATIHwConfiguration::ValidateConfigurationE2PROM( CI2CScript * pCScript)
  1853. {
  1854. I2CPacket i2cPacket;
  1855. UCHAR uchReadValue=0, uchWriteValue, uchCheckSum=0;
  1856. UINT nIndex;
  1857. BOOL bResult = ( BOOL)m_usE2PROMValidation;
  1858. if( m_usE2PROMValidation == ( USHORT)-1)
  1859. {
  1860. // the validation has not been done yet.
  1861. bResult = FALSE;
  1862. ENSURE
  1863. {
  1864. // Let's always start from byte 0.
  1865. i2cPacket.uchChipAddress = AIWPRO_CONFIGURATIONE2PROM_ADDRESS;
  1866. i2cPacket.cbWriteCount = 1;
  1867. i2cPacket.cbReadCount = 1;
  1868. i2cPacket.puchReadBuffer = &uchCheckSum;
  1869. uchWriteValue = 0;
  1870. i2cPacket.puchWriteBuffer = &uchWriteValue;
  1871. i2cPacket.usFlags = I2COPERATION_READ | I2COPERATION_RANDOMACCESS;
  1872. if( !pCScript->ExecuteI2CPacket( &i2cPacket))
  1873. FAIL;
  1874. for( nIndex = 1; nIndex < AIWPRO_CONFIGURATIONE2PROM_LENGTH; nIndex ++)
  1875. {
  1876. // let's use auto-increment address mode
  1877. i2cPacket.usFlags = I2COPERATION_READ;
  1878. i2cPacket.cbWriteCount = 0;
  1879. i2cPacket.puchWriteBuffer = NULL;
  1880. i2cPacket.puchReadBuffer = &uchReadValue;
  1881. if( !pCScript->ExecuteI2CPacket( &i2cPacket))
  1882. FAIL;
  1883. uchCheckSum ^= uchReadValue;
  1884. }
  1885. if( nIndex != AIWPRO_CONFIGURATIONE2PROM_LENGTH)
  1886. FAIL;
  1887. bResult = ( uchCheckSum == 0);
  1888. } END_ENSURE;
  1889. m_usE2PROMValidation = ( USHORT)bResult;
  1890. }
  1891. return( bResult);
  1892. }
  1893. /*^^*
  1894. * ReadConfigurationE2PROM
  1895. * Purpose : Reads a single byte from I2C driver configuration EEPROM by offset
  1896. * Inputs : CI2CScript * pCScript : pointer to the I2C Provider class
  1897. * ULONG ulOffset : byte offset within the EEPROM
  1898. * PUCHAR puchValue : pointer to the buffer to read into
  1899. *
  1900. * Outputs : BOOL, TRUE if I2C read operation succeeded
  1901. * Author : TOM
  1902. *^^*/
  1903. BOOL CATIHwConfiguration::ReadConfigurationE2PROM( CI2CScript * pCScript, ULONG ulOffset, PUCHAR puchValue)
  1904. {
  1905. I2CPacket i2cPacket;
  1906. UCHAR uchReadValue=0, uchWriteValue;
  1907. ENSURE
  1908. {
  1909. if( ulOffset >= AIWPRO_CONFIGURATIONE2PROM_LENGTH)
  1910. FAIL;
  1911. uchWriteValue = ( UCHAR)ulOffset;
  1912. i2cPacket.uchChipAddress = AIWPRO_CONFIGURATIONE2PROM_ADDRESS;
  1913. i2cPacket.cbWriteCount = 1;
  1914. i2cPacket.cbReadCount = 1;
  1915. i2cPacket.puchReadBuffer = &uchReadValue;
  1916. i2cPacket.puchWriteBuffer = &uchWriteValue;
  1917. i2cPacket.usFlags = I2COPERATION_READ | I2COPERATION_RANDOMACCESS;
  1918. if( !pCScript->ExecuteI2CPacket( &i2cPacket))
  1919. FAIL;
  1920. * puchValue = uchReadValue;
  1921. return( TRUE);
  1922. } END_ENSURE;
  1923. return( FALSE);
  1924. }
  1925. //Paul
  1926. ULONG CATIHwConfiguration::ReturnTunerVideoStandard( USHORT usTunerId ) //Paul: For PAL support
  1927. {
  1928. switch( usTunerId )
  1929. {
  1930. case 1:
  1931. return KS_AnalogVideo_NTSC_M;
  1932. break;
  1933. case 2:
  1934. return KS_AnalogVideo_NTSC_M_J;
  1935. break;
  1936. case 3:
  1937. return KS_AnalogVideo_PAL_B | KS_AnalogVideo_PAL_G;
  1938. break;
  1939. case 4:
  1940. return KS_AnalogVideo_PAL_I;
  1941. break;
  1942. case 5:
  1943. return KS_AnalogVideo_PAL_B | KS_AnalogVideo_PAL_G | KS_AnalogVideo_SECAM_L | KS_AnalogVideo_SECAM_L1;
  1944. break;
  1945. case 6:
  1946. return KS_AnalogVideo_NTSC_M;
  1947. break;
  1948. case 7:
  1949. return KS_AnalogVideo_SECAM_D | KS_AnalogVideo_SECAM_K;
  1950. break;
  1951. case 8:
  1952. return KS_AnalogVideo_NTSC_M;
  1953. break;
  1954. case 9:
  1955. return KS_AnalogVideo_PAL_B | KS_AnalogVideo_PAL_G;
  1956. break;
  1957. case 10:
  1958. return KS_AnalogVideo_PAL_I;
  1959. break;
  1960. case 11:
  1961. return KS_AnalogVideo_PAL_B | KS_AnalogVideo_PAL_G | KS_AnalogVideo_SECAM_L | KS_AnalogVideo_SECAM_L1;
  1962. break;
  1963. case 12:
  1964. return KS_AnalogVideo_NTSC_M;
  1965. break;
  1966. case 13:
  1967. return KS_AnalogVideo_PAL_B | KS_AnalogVideo_PAL_D | KS_AnalogVideo_PAL_G | KS_AnalogVideo_PAL_I | KS_AnalogVideo_SECAM_D | KS_AnalogVideo_SECAM_K;
  1968. break;
  1969. case 14:
  1970. return 0;
  1971. break;
  1972. case 15:
  1973. return 0;
  1974. break;
  1975. case 16:
  1976. return KS_AnalogVideo_NTSC_M;
  1977. break;
  1978. case 17:
  1979. return KS_AnalogVideo_NTSC_M;
  1980. break;
  1981. case 18:
  1982. return KS_AnalogVideo_NTSC_M;
  1983. break;
  1984. default:
  1985. return 0; // if we don't recognize the tuner, we say that no video standard is supported
  1986. }
  1987. }
  1988. //Paul
  1989. // bit 5 indicates the number of crystals installed. 0 means we have 2 crystals,
  1990. // 1 means we only have 1, so the tuner determines the standard
  1991. ULONG CATIHwConfiguration::SetVidStdBasedOnI2CExpander( UCHAR ucI2CValue )
  1992. {
  1993. if ( ucI2CValue & 0x20 ) // only 1 crystal
  1994. {
  1995. ULONG ulTunerStd = ReturnTunerVideoStandard( ucI2CValue & 0x0F );
  1996. if ( ulTunerStd & ( KS_AnalogVideo_NTSC_Mask & ~KS_AnalogVideo_NTSC_433 | KS_AnalogVideo_PAL_60 ) ) // Then we should have NTSC-type crystal
  1997. {
  1998. return KS_AnalogVideo_NTSC_Mask & ~KS_AnalogVideo_NTSC_433 | KS_AnalogVideo_PAL_60 | KS_AnalogVideo_PAL_M | KS_AnalogVideo_PAL_N;
  1999. }
  2000. else
  2001. {
  2002. return KS_AnalogVideo_PAL_Mask & ~KS_AnalogVideo_PAL_60 & ~KS_AnalogVideo_PAL_M & ~KS_AnalogVideo_PAL_N | KS_AnalogVideo_SECAM_Mask | KS_AnalogVideo_NTSC_433;
  2003. }
  2004. }
  2005. else
  2006. return KS_AnalogVideo_NTSC_Mask | KS_AnalogVideo_PAL_Mask | KS_AnalogVideo_SECAM_Mask; // we support all standards (is this testable?)
  2007. }
  2008. //Paul
  2009. // The Video In crystal type in MMTable will tell us whether we support NTSC, PAL/SECAM, or both
  2010. ULONG CATIHwConfiguration::SetVidStdBasedOnMMTable( CATIMultimediaTable * pCMultimediaInfo )
  2011. {
  2012. if ( pCMultimediaInfo )
  2013. {
  2014. if ( pCMultimediaInfo->GetVideoInCrystalId( &m_CrystalIDInMMTable ) )
  2015. {
  2016. switch ( m_CrystalIDInMMTable )
  2017. {
  2018. // "NTSC and PAL Crystals Installed (for Bt8xx)"
  2019. case 0:
  2020. return KS_AnalogVideo_NTSC_Mask | KS_AnalogVideo_PAL_Mask; // may need to add SECAM. We will see
  2021. break;
  2022. // "NTSC Crystal Only (for Bt8xx)"
  2023. case 1:
  2024. return KS_AnalogVideo_NTSC_Mask & ~KS_AnalogVideo_NTSC_433 | KS_AnalogVideo_PAL_60 | KS_AnalogVideo_PAL_M | KS_AnalogVideo_PAL_N; // standards that use "NTSC" clock
  2025. break;
  2026. // "PAL Crystal Only (for Bt8xx)"
  2027. case 2:
  2028. return KS_AnalogVideo_PAL_Mask & ~KS_AnalogVideo_PAL_60 & ~KS_AnalogVideo_PAL_M & ~KS_AnalogVideo_PAL_N | KS_AnalogVideo_SECAM_Mask | KS_AnalogVideo_NTSC_433; // standards that use "PAL" clock
  2029. break;
  2030. // "NTSC, PAL, SECAM (for Bt829)"
  2031. case 3:
  2032. return KS_AnalogVideo_NTSC_Mask | KS_AnalogVideo_PAL_Mask | KS_AnalogVideo_SECAM_Mask;
  2033. break;
  2034. }
  2035. }
  2036. }
  2037. return 0;
  2038. }
  2039. //Paul: Used by RT WDM to determine the VIN PLL
  2040. BOOL CATIHwConfiguration::GetMMTableCrystalID( PUCHAR pucCrystalID )
  2041. { if ( ( m_uchI2CExpanderAddress==0xFF ) || ( !pucCrystalID ) )
  2042. {
  2043. return FALSE;
  2044. }
  2045. else
  2046. {
  2047. *pucCrystalID = m_CrystalIDInMMTable;
  2048. return TRUE;
  2049. }
  2050. }