xref: /reactos/drivers/wdm/audio/drivers/ac97/common.h (revision 9c79a798)
1 /********************************************************************************
2 **    Copyright (c) 1998-2000 Microsoft Corporation. All Rights Reserved.
3 **
4 **       Portions Copyright (c) 1998-1999 Intel Corporation
5 **
6 ********************************************************************************/
7 
8 /* The file common.h was reviewed by LCA in June 2011 and is acceptable for use by Microsoft. */
9 
10 #ifndef _COMMON_H_
11 #define _COMMON_H_
12 
13 #include "shared.h"
14 
15 /*****************************************************************************
16  * Structs
17  *****************************************************************************
18  */
19 
20 //
21 // Contains pin and node configuration of the AC97 codec.
22 //
23 typedef struct
24 {
25     // For nodes.
26     struct
27     {
28         BOOL    bNodeConfig;
29     } Nodes[NODEC_TOP_ELEMENT];
30 
31     // For pins.
32     struct
33     {
34         BOOL    bPinConfig;
35         PWCHAR  sRegistryName;
36     } Pins[PINC_TOP_ELEMENT];
37 } tHardwareConfig;
38 
39 //
40 // We cache the AC97 registers.  Additionally, we want some default values
41 // when the driver comes up first that are different from the HW default
42 // values. The string in the structure is the name of the registry entry
43 // that can be used instead of the hard coded default value.
44 //
45 typedef struct
46 {
47     WORD    wCache;
48     WORD    wFlags;
49     PWCHAR  sRegistryName;
50     WORD    wWantedDefault;
51 } tAC97Registers;
52 
53 
54 /*****************************************************************************
55  * Constants
56  *****************************************************************************
57  */
58 
59 //
60 // This means shadow register are to be read at least once to initialize.
61 //
62 const WORD SHREG_INVALID = 0x0001;
63 
64 //
65 // This means shadow register should be overwritten with default value at
66 // driver init.
67 //
68 const WORD SHREG_INIT = 0x0002;
69 
70 //
71 // This constant is used to prevent register caching.
72 //
73 const WORD SHREG_NOCACHE = 0x0004;
74 
75 
76 /*****************************************************************************
77  * Classes
78  *****************************************************************************
79  */
80 
81 /*****************************************************************************
82  * CAC97AdapterCommon
83  *****************************************************************************
84  * This is the common adapter object shared by all miniports to access the
85  * hardware.
86  */
87 class CAC97AdapterCommon : public IAC97AdapterCommon,
88                        public IAdapterPowerManagement,
89                        public CUnknown
90 {
91 private:
92     static tAC97Registers m_stAC97Registers[64];    // The shadow registers.
93     static tHardwareConfig m_stHardwareConfig;      // The hardware configuration.
94     PDEVICE_OBJECT m_pDeviceObject;     // Device object used for registry access.
95     PWORD          m_pCodecBase;        // The AC97 I/O port address.
96     PUCHAR         m_pBusMasterBase;    // The Bus Master base address.
97     BOOL           m_bDirectRead;       // Used during init time.
98     DEVICE_POWER_STATE   m_PowerState;  // Current power state of the device.
99     PAC97MINIPORTTOPOLOGY m_Topology;    // Miniport Topology pointer.
100 
101 
102     /*************************************************************************
103      * CAC97AdapterCommon methods
104      *************************************************************************
105      */
106 
107     //
108     // Resets AC97 audio registers.
109     //
110     NTSTATUS InitAC97 (void);
111 
112     //
113     // Checks for existance of registers.
114     //
115     NTSTATUS ProbeHWConfig (void);
116 
117     //
118     // Checks for 6th bit support in the volume control.
119     //
120     NTSTATUS Check6thBitSupport (IN AC97Register, IN TopoNodeConfig);
121 
122     //
123     // Returns true if you should disable the input or output pin.
124     //
125     BOOL DisableAC97Pin (IN  TopoPinConfig);
126 
127 #if (DBG)
128     //
129     // Dumps the probed configuration.
130     //
131     void DumpConfig (void);
132 #endif
133 
134     //
135     // Sets AC97 registers to default.
136     //
137     NTSTATUS SetAC97Default (void);
138 
139     //
140     // Aquires the semaphore for AC97 register access.
141     //
142     NTSTATUS AcquireCodecSemiphore (void);
143 
144     //
145     // Checks if there is a AC97 link between AC97 and codec.
146     //
147     NTSTATUS PrimaryCodecReady (void);
148 
149     //
150     // Powers up the Codec.
151     //
152     NTSTATUS PowerUpCodec (void);
153 
154     //
155     // Saves native audio bus master control registers values to be used
156     // upon suspend.
157     //
158     NTSTATUS ReadNABMCtrlRegs (void);
159 
160     //
161     // Writes back native audio bus master control resgister to be used upon
162     // resume.
163     //
164     NTSTATUS RestoreNABMCtrlRegs (void);
165 
166 public:
167     DECLARE_STD_UNKNOWN();
168     DEFINE_STD_CONSTRUCTOR(CAC97AdapterCommon);
169     ~CAC97AdapterCommon();
170 
171     /*************************************************************************
172      * IAdapterPowerManagement methods
173      *************************************************************************
174      */
175     IMP_IAdapterPowerManagement;
176 
177     /*************************************************************************
178      * IAC97AdapterCommon methods
179      *************************************************************************
180      */
181 
182     //
183     // Initialize the adapter common object -> initialize and probe HW.
184     //
185     STDMETHODIMP_(NTSTATUS) Init
186     (
187         IN  PRESOURCELIST ResourceList,
188         IN  PDEVICE_OBJECT DeviceObject
189     );
190 
191     //
192     // Returns if pin exists.
193     //
GetPinConfig(IN TopoPinConfig pin)194     STDMETHODIMP_(BOOL) GetPinConfig
195     (
196         IN  TopoPinConfig pin
197     )
198     {
199         return m_stHardwareConfig.Pins[pin].bPinConfig;
200     };
201 
202     //
203     // Sets the pin configuration (exist/not exist).
204     //
SetPinConfig(IN TopoPinConfig pin,IN BOOL config)205     STDMETHODIMP_(void) SetPinConfig
206     (
207         IN  TopoPinConfig pin,
208         IN  BOOL config
209     )
210     {
211         m_stHardwareConfig.Pins[pin].bPinConfig = config;
212     };
213 
214     //
215     // Return if node exists.
216     //
GetNodeConfig(IN TopoNodeConfig node)217     STDMETHODIMP_(BOOL) GetNodeConfig
218     (
219         IN  TopoNodeConfig node
220     )
221     {
222         return m_stHardwareConfig.Nodes[node].bNodeConfig;
223     };
224 
225     //
226     // Sets the node configuration (exist/not exist).
227     //
SetNodeConfig(IN TopoNodeConfig node,IN BOOL config)228     STDMETHODIMP_(void) SetNodeConfig
229     (
230         IN  TopoNodeConfig node,
231         IN  BOOL config
232     )
233     {
234         m_stHardwareConfig.Nodes[node].bNodeConfig = config;
235     };
236 
237     //
238     // Returns the AC97 register that is assosiated with the node.
239     //
GetNodeReg(IN TopoNodes node)240     STDMETHODIMP_(AC97Register) GetNodeReg
241     (   IN  TopoNodes node
242     )
243     {
244         return stMapNodeToReg[node].reg;
245     };
246 
247     //
248     // Returns the AC97 register mask that is assosiated with the node.
249     //
GetNodeMask(IN TopoNodes node)250     STDMETHODIMP_(WORD) GetNodeMask
251     (
252         IN  TopoNodes node
253     )
254     {
255         return stMapNodeToReg[node].mask;
256     };
257 
258     //
259     // Reads a AC97 register.
260     //
261     STDMETHODIMP_(NTSTATUS) ReadCodecRegister
262     (
263         _In_range_(0, AC97REG_INVALID)  AC97Register Register,
264         _Out_ PWORD wData
265     );
266 
267     //
268     // Writes a AC97 register.
269     //
270     STDMETHODIMP_(NTSTATUS) WriteCodecRegister
271     (
272         _In_range_(0, AC97REG_INVALID)  AC97Register Register,
273         _In_  WORD wData,
274         _In_  WORD wMask
275     );
276 
277     //
278     // Reads a 8 bit AC97 bus master register.
279     //
280     STDMETHODIMP_(UCHAR) ReadBMControlRegister8
281     (
282         IN  ULONG ulOffset
283     );
284 
285     //
286     // Reads a 16 bit AC97 bus master register.
287     //
288     STDMETHODIMP_(USHORT) ReadBMControlRegister16
289     (
290         IN  ULONG ulOffset
291     );
292 
293     //
294     // Reads a 32 bit AC97 bus master register.
295     //
296     STDMETHODIMP_(ULONG) ReadBMControlRegister32
297     (
298         IN  ULONG ulOffset
299     );
300 
301     //
302     // Writes a 8 bit AC97 bus master register.
303     //
304     STDMETHODIMP_(void) WriteBMControlRegister
305     (
306         IN  ULONG ulOffset,
307         IN  UCHAR Value
308     );
309 
310     //
311     // writes a 16 bit AC97 bus master register.
312     //
313     STDMETHODIMP_(void) WriteBMControlRegister
314     (
315         IN  ULONG ulOffset,
316         IN  USHORT Value
317     );
318 
319     // writes a 32 bit AC97 bus master register.
320     STDMETHODIMP_(void) WriteBMControlRegister
321     (
322         IN  ULONG ulOffset,
323         IN  ULONG Value
324     );
325 
326     //
327     // Write back cached mixer values to codec registers.
328     //
329     STDMETHODIMP_(NTSTATUS) RestoreCodecRegisters();
330 
331     //
332     // Programs a sample rate.
333     //
334     STDMETHODIMP_(NTSTATUS) ProgramSampleRate
335     (
336         IN  AC97Register Register,
337         IN  DWORD dwSampleRate
338     );
339 
340     //
341     // Stores the topology pointer. Used for DRM only.
342     //
SetMiniportTopology(PAC97MINIPORTTOPOLOGY topo)343     STDMETHODIMP_(void) SetMiniportTopology (PAC97MINIPORTTOPOLOGY topo)
344     {
345         m_Topology = topo;
346     };
347 
348     //
349     // Returns the topology pointer. Used for DRM only.
350     //
GetMiniportTopology(void)351     STDMETHODIMP_(PAC97MINIPORTTOPOLOGY) GetMiniportTopology (void)
352     {
353         return m_Topology;
354     };
355 
356     //
357     // This function reads the default channel config and is called only by the
358     // wave miniport.
359     //
360     STDMETHODIMP_(void) ReadChannelConfigDefault
361     (
362         PDWORD  pdwChannelConfig,
363         PWORD   pwChannels
364     );
365 
366     //
367     // This function writes the default channel config and is called only by the
368     // wave miniport.
369     //
370     STDMETHODIMP_(void) WriteChannelConfigDefault
371     (
372         DWORD   dwChannelConfig
373     );
374 
375     /*************************************************************************
376      * Friends
377      *************************************************************************
378      */
379 
380     friend NTSTATUS NewAdapterCommon
381     (
382         OUT PADAPTERCOMMON *OutAdapterCommon,
383         IN  PRESOURCELIST ResourceList
384     );
385 };
386 
387 #endif  //_COMMON_H_
388