VirtualBox

source: vbox/trunk/src/VBox/Devices/Audio/DevIchAc97.cpp@ 31263

Last change on this file since 31263 was 28800, checked in by vboxsync, 15 years ago

Automated rebranding to Oracle copyright/license strings via filemuncher

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 56.4 KB
Line 
1/* $Id: DevIchAc97.cpp 28800 2010-04-27 08:22:32Z vboxsync $ */
2/** @file
3 * DevIchAc97 - VBox ICH AC97 Audio Controller.
4 */
5
6/*
7 * Copyright (C) 2006-2008 Oracle Corporation
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 */
17
18/*******************************************************************************
19* Header Files *
20*******************************************************************************/
21#define LOG_GROUP LOG_GROUP_DEV_AUDIO
22#include <VBox/pdmdev.h>
23#include <iprt/assert.h>
24#include <iprt/uuid.h>
25#include <iprt/string.h>
26
27#include "../Builtins.h"
28
29extern "C" {
30#include "audio.h"
31}
32
33#undef LOG_VOICES
34#ifndef VBOX
35//#define USE_MIXER
36#else
37#define USE_MIXER
38#endif
39
40#define AC97_SSM_VERSION 1
41
42enum {
43 AC97_Reset = 0x00,
44 AC97_Master_Volume_Mute = 0x02,
45 AC97_Headphone_Volume_Mute = 0x04,
46 AC97_Master_Volume_Mono_Mute = 0x06,
47 AC97_Master_Tone_RL = 0x08,
48 AC97_PC_BEEP_Volume_Mute = 0x0A,
49 AC97_Phone_Volume_Mute = 0x0C,
50 AC97_Mic_Volume_Mute = 0x0E,
51 AC97_Line_In_Volume_Mute = 0x10,
52 AC97_CD_Volume_Mute = 0x12,
53 AC97_Video_Volume_Mute = 0x14,
54 AC97_Aux_Volume_Mute = 0x16,
55 AC97_PCM_Out_Volume_Mute = 0x18,
56 AC97_Record_Select = 0x1A,
57 AC97_Record_Gain_Mute = 0x1C,
58 AC97_Record_Gain_Mic_Mute = 0x1E,
59 AC97_General_Purpose = 0x20,
60 AC97_3D_Control = 0x22,
61 AC97_AC_97_RESERVED = 0x24,
62 AC97_Powerdown_Ctrl_Stat = 0x26,
63 AC97_Extended_Audio_ID = 0x28,
64 AC97_Extended_Audio_Ctrl_Stat = 0x2A,
65 AC97_PCM_Front_DAC_Rate = 0x2C,
66 AC97_PCM_Surround_DAC_Rate = 0x2E,
67 AC97_PCM_LFE_DAC_Rate = 0x30,
68 AC97_PCM_LR_ADC_Rate = 0x32,
69 AC97_MIC_ADC_Rate = 0x34,
70 AC97_6Ch_Vol_C_LFE_Mute = 0x36,
71 AC97_6Ch_Vol_L_R_Surround_Mute = 0x38,
72 AC97_Vendor_Reserved = 0x58,
73 AC97_Vendor_ID1 = 0x7c,
74 AC97_Vendor_ID2 = 0x7e
75};
76
77#ifndef VBOX
78# define SOFT_VOLUME
79#else
80# undef SOFT_VOLUME
81#endif
82#define SR_FIFOE RT_BIT(4) /* rwc, fifo error */
83#define SR_BCIS RT_BIT(3) /* rwc, buffer completion interrupt status */
84#define SR_LVBCI RT_BIT(2) /* rwc, last valid buffer completion interrupt */
85#define SR_CELV RT_BIT(1) /* ro, current equals last valid */
86#define SR_DCH RT_BIT(0) /* ro, controller halted */
87#define SR_VALID_MASK (RT_BIT(5) - 1)
88#define SR_WCLEAR_MASK (SR_FIFOE | SR_BCIS | SR_LVBCI)
89#define SR_RO_MASK (SR_DCH | SR_CELV)
90#define SR_INT_MASK (SR_FIFOE | SR_BCIS | SR_LVBCI)
91
92#define CR_IOCE RT_BIT(4) /* rw */
93#define CR_FEIE RT_BIT(3) /* rw */
94#define CR_LVBIE RT_BIT(2) /* rw */
95#define CR_RR RT_BIT(1) /* rw */
96#define CR_RPBM RT_BIT(0) /* rw */
97#define CR_VALID_MASK (RT_BIT(5) - 1)
98#define CR_DONT_CLEAR_MASK (CR_IOCE | CR_FEIE | CR_LVBIE)
99
100#define GC_WR 4 /* rw */
101#define GC_CR 2 /* rw */
102#define GC_VALID_MASK (RT_BIT(6) - 1)
103
104#define GS_MD3 RT_BIT(17) /* rw */
105#define GS_AD3 RT_BIT(16) /* rw */
106#define GS_RCS RT_BIT(15) /* rwc */
107#define GS_B3S12 RT_BIT(14) /* ro */
108#define GS_B2S12 RT_BIT(13) /* ro */
109#define GS_B1S12 RT_BIT(12) /* ro */
110#define GS_S1R1 RT_BIT(11) /* rwc */
111#define GS_S0R1 RT_BIT(10) /* rwc */
112#define GS_S1CR RT_BIT(9) /* ro */
113#define GS_S0CR RT_BIT(8) /* ro */
114#define GS_MINT RT_BIT(7) /* ro */
115#define GS_POINT RT_BIT(6) /* ro */
116#define GS_PIINT RT_BIT(5) /* ro */
117#define GS_RSRVD (RT_BIT(4)|RT_BIT(3))
118#define GS_MOINT RT_BIT(2) /* ro */
119#define GS_MIINT RT_BIT(1) /* ro */
120#define GS_GSCI RT_BIT(0) /* rwc */
121#define GS_RO_MASK (GS_B3S12| \
122 GS_B2S12| \
123 GS_B1S12| \
124 GS_S1CR| \
125 GS_S0CR| \
126 GS_MINT| \
127 GS_POINT| \
128 GS_PIINT| \
129 GS_RSRVD| \
130 GS_MOINT| \
131 GS_MIINT)
132#define GS_VALID_MASK (RT_BIT(18) - 1)
133#define GS_WCLEAR_MASK (GS_RCS|GS_S1R1|GS_S0R1|GS_GSCI)
134
135/** Buffer Descriptor */
136#define BD_IOC RT_BIT(31) /* Interrupt on Completion */
137#define BD_BUP RT_BIT(30) /* Buffer Underrun Policy */
138
139#define EACS_VRA 1
140#define EACS_VRM 8
141
142#define VOL_MASK 0x1f
143#define MUTE_SHIFT 15
144
145#define REC_MASK 7
146enum
147{
148 REC_MIC = 0,
149 REC_CD,
150 REC_VIDEO,
151 REC_AUX,
152 REC_LINE_IN,
153 REC_STEREO_MIX,
154 REC_MONO_MIX,
155 REC_PHONE
156};
157
158typedef struct BD
159{
160 uint32_t addr;
161 uint32_t ctl_len;
162} BD;
163
164typedef struct AC97BusMasterRegs
165{
166 uint32_t bdbar; /* rw 0, buffer descriptor list base address register */
167 uint8_t civ; /* ro 0, current index value */
168 uint8_t lvi; /* rw 0, last valid index */
169 uint16_t sr; /* rw 1, status register */
170 uint16_t picb; /* ro 0, position in current buffer */
171 uint8_t piv; /* ro 0, prefetched index value */
172 uint8_t cr; /* rw 0, control register */
173 int bd_valid; /* initialized? */
174 BD bd;
175} AC97BusMasterRegs;
176
177typedef struct AC97LinkState
178{
179 QEMUSoundCard card;
180 /** Global Control (Bus Master Control Register) */
181 uint32_t glob_cnt;
182 /** Global Status (Bus Master Control Register) */
183 uint32_t glob_sta;
184 /** Codec Access Semaphore Register (Bus Master Control Register) */
185 uint32_t cas;
186 uint32_t last_samp;
187 /** Bus Master Control Registers for PCM in, PCM out, and Mic in */
188 AC97BusMasterRegs bm_regs[3];
189 uint8_t mixer_data[256];
190 /** PCM in */
191 SWVoiceIn *voice_pi;
192 /** PCM out */
193 SWVoiceOut *voice_po;
194 /** Mic in */
195 SWVoiceIn *voice_mc;
196 uint8_t silence[128];
197 int bup_flag;
198 /** Pointer to the device instance. */
199 PPDMDEVINSR3 pDevIns;
200 /** Pointer to the connector of the attached audio driver. */
201 PPDMIAUDIOCONNECTOR pDrv;
202 /** Pointer to the attached audio driver. */
203 PPDMIBASE pDrvBase;
204 /** The base interface for LUN\#0. */
205 PDMIBASE IBase;
206 /** Base port of the I/O space region. */
207 RTIOPORT IOPortBase[2];
208} AC97LinkState;
209
210#define ICHAC97STATE_2_DEVINS(pAC97) ((pAC97)->pDevIns)
211#define PCIDEV_2_ICHAC97STATE(pPciDev) ((PCIAC97LinkState *)(pPciDev))
212
213enum
214{
215 BUP_SET = RT_BIT(0),
216 BUP_LAST = RT_BIT(1)
217};
218
219typedef struct PCIAC97LinkState
220{
221 PCIDevice dev;
222 AC97LinkState ac97;
223} PCIAC97LinkState;
224
225#define MKREGS(prefix, start) \
226 enum { \
227 prefix ## _BDBAR = start, \
228 prefix ## _CIV = start + 4, \
229 prefix ## _LVI = start + 5, \
230 prefix ## _SR = start + 6, \
231 prefix ## _PICB = start + 8, \
232 prefix ## _PIV = start + 10, \
233 prefix ## _CR = start + 11 \
234 }
235
236enum
237{
238 PI_INDEX = 0, /* PCM in */
239 PO_INDEX, /* PCM out */
240 MC_INDEX, /* Mic in */
241 LAST_INDEX
242};
243
244MKREGS (PI, PI_INDEX * 16);
245MKREGS (PO, PO_INDEX * 16);
246MKREGS (MC, MC_INDEX * 16);
247
248enum
249{
250 GLOB_CNT = 0x2c,
251 GLOB_STA = 0x30,
252 CAS = 0x34
253};
254
255#define GET_BM(index) (((index) >> 4) & 3)
256
257static void po_callback (void *opaque, int free);
258static void pi_callback (void *opaque, int avail);
259static void mc_callback (void *opaque, int avail);
260
261static void warm_reset (AC97LinkState *s)
262{
263 (void) s;
264}
265
266static void cold_reset (AC97LinkState * s)
267{
268 (void) s;
269}
270
271/** Fetch Buffer Descriptor at _CIV */
272static void fetch_bd (AC97LinkState *s, AC97BusMasterRegs *r)
273{
274 PPDMDEVINS pDevIns = ICHAC97STATE_2_DEVINS(s);
275 uint8_t b[8];
276
277 PDMDevHlpPhysRead (pDevIns, r->bdbar + r->civ * 8, b, sizeof(b));
278 r->bd_valid = 1;
279#if !defined(RT_ARCH_X86) && !defined(RT_ARCH_AMD64)
280# error Please adapt the code (audio buffers are little endian)!
281#else
282 r->bd.addr = (*(uint32_t *) &b[0]) & ~3;
283 r->bd.ctl_len = (*(uint32_t *) &b[4]);
284#endif
285 r->picb = r->bd.ctl_len & 0xffff;
286 Log (("ac97: bd %2d addr=%#x ctl=%#06x len=%#x(%d bytes)\n",
287 r->civ, r->bd.addr, r->bd.ctl_len >> 16,
288 r->bd.ctl_len & 0xffff, (r->bd.ctl_len & 0xffff) << 1));
289}
290
291/**
292 * Update the BM status register
293 */
294static void update_sr (AC97LinkState *s, AC97BusMasterRegs *r, uint32_t new_sr)
295{
296 PPDMDEVINS pDevIns = ICHAC97STATE_2_DEVINS(s);
297 int event = 0;
298 int level = 0;
299 uint32_t new_mask = new_sr & SR_INT_MASK;
300 uint32_t old_mask = r->sr & SR_INT_MASK;
301 uint32_t masks[] = {GS_PIINT, GS_POINT, GS_MINT};
302
303 if (new_mask ^ old_mask)
304 {
305 /** @todo is IRQ deasserted when only one of status bits is cleared? */
306 if (!new_mask)
307 {
308 event = 1;
309 level = 0;
310 }
311 else if ((new_mask & SR_LVBCI) && (r->cr & CR_LVBIE))
312 {
313 event = 1;
314 level = 1;
315 }
316 else if ((new_mask & SR_BCIS) && (r->cr & CR_IOCE))
317 {
318 event = 1;
319 level = 1;
320 }
321 }
322
323 r->sr = new_sr;
324
325 Log (("ac97: IOC%d LVB%d sr=%#x event=%d level=%d\n",
326 r->sr & SR_BCIS, r->sr & SR_LVBCI, r->sr, event, level));
327
328 if (event)
329 {
330 if (level)
331 s->glob_sta |= masks[r - s->bm_regs];
332 else
333 s->glob_sta &= ~masks[r - s->bm_regs];
334
335 Log (("ac97: set irq level=%d\n", !!level));
336 PDMDevHlpPCISetIrq (pDevIns, 0, !!level);
337 }
338}
339
340static void voice_set_active (AC97LinkState *s, int bm_index, int on)
341{
342 switch (bm_index)
343 {
344 case PI_INDEX: AUD_set_active_in (s->voice_pi, on); break;
345 case PO_INDEX: AUD_set_active_out(s->voice_po, on); break;
346 case MC_INDEX: AUD_set_active_in (s->voice_mc, on); break;
347 default: AssertFailed ();
348 break;
349 }
350}
351
352static void reset_bm_regs (AC97LinkState *s, AC97BusMasterRegs *r)
353{
354 Log (("ac97: reset_bm_regs\n"));
355 r->bdbar = 0;
356 r->civ = 0;
357 r->lvi = 0;
358 /** @todo do we need to do that? */
359 update_sr (s, r, SR_DCH);
360 r->picb = 0;
361 r->piv = 0;
362 r->cr = r->cr & CR_DONT_CLEAR_MASK;
363 r->bd_valid = 0;
364
365 voice_set_active (s, r - s->bm_regs, 0);
366 memset (s->silence, 0, sizeof (s->silence));
367}
368
369static void mixer_store (AC97LinkState *s, uint32_t i, uint16_t v)
370{
371 if (i + 2 > sizeof (s->mixer_data))
372 {
373 Log (("ac97: mixer_store: index %d out of bounds %d\n",
374 i, sizeof (s->mixer_data)));
375 return;
376 }
377
378 s->mixer_data[i + 0] = v & 0xff;
379 s->mixer_data[i + 1] = v >> 8;
380}
381
382static uint16_t mixer_load (AC97LinkState *s, uint32_t i)
383{
384 uint16_t val;
385
386 if (i + 2 > sizeof (s->mixer_data))
387 {
388 Log (("ac97: mixer_store: index %d out of bounds %d\n",
389 i, sizeof (s->mixer_data)));
390 val = 0xffff;
391 }
392 else
393 val = s->mixer_data[i + 0] | (s->mixer_data[i + 1] << 8);
394
395 return val;
396}
397
398static void open_voice (AC97LinkState *s, int index, int freq)
399{
400 audsettings_t as;
401
402 if (freq)
403 {
404 as.freq = freq;
405 as.nchannels = 2;
406 as.fmt = AUD_FMT_S16;
407 as.endianness = 0;
408
409 switch (index)
410 {
411 case PI_INDEX: /* PCM in */
412 s->voice_pi = AUD_open_in (&s->card, s->voice_pi, "ac97.pi",
413 s, pi_callback, &as);
414#ifdef LOG_VOICES
415 LogRel (("AC97: open PI freq=%d (%s)\n", freq, s->voice_pi ? "ok" : "FAIL"));
416#endif
417 break;
418
419 case PO_INDEX: /* PCM out */
420 s->voice_po = AUD_open_out (&s->card, s->voice_po, "ac97.po",
421 s, po_callback, &as);
422#ifdef LOG_VOICES
423 LogRel (("AC97: open PO freq=%d (%s)\n", freq, s->voice_po ? "ok" : "FAIL"));
424#endif
425 break;
426
427 case MC_INDEX: /* Mic in */
428 s->voice_mc = AUD_open_in (&s->card, s->voice_mc, "ac97.mc",
429 s, mc_callback, &as);
430#ifdef LOG_VOICES
431 LogRel (("AC97: open MC freq=%d (%s)\n", freq, s->voice_mc ? "ok" : "FAIL"));
432#endif
433 break;
434 }
435 }
436 else
437 {
438 switch (index)
439 {
440 case PI_INDEX:
441 AUD_close_in (&s->card, s->voice_pi);
442#ifdef LOG_VOICES
443 LogRel (("AC97: Closing PCM IN\n"));
444#endif
445 s->voice_pi = NULL;
446 break;
447
448 case PO_INDEX:
449 AUD_close_out (&s->card, s->voice_po);
450#ifdef LOG_VOICES
451 LogRel (("AC97: Closing PCM OUT\n"));
452#endif
453 s->voice_po = NULL;
454 break;
455
456 case MC_INDEX:
457 AUD_close_in (&s->card, s->voice_mc);
458#ifdef LOG_VOICES
459 LogRel (("AC97: Closing MIC IN\n"));
460#endif
461 s->voice_mc = NULL;
462 break;
463 }
464 }
465}
466
467static void reset_voices (AC97LinkState *s, uint8_t active[LAST_INDEX])
468{
469 uint16_t freq;
470
471 freq = mixer_load (s, AC97_PCM_LR_ADC_Rate);
472 open_voice (s, PI_INDEX, freq);
473 AUD_set_active_in (s->voice_pi, active[PI_INDEX]);
474
475 freq = mixer_load (s, AC97_PCM_Front_DAC_Rate);
476 open_voice (s, PO_INDEX, freq);
477 AUD_set_active_out (s->voice_po, active[PO_INDEX]);
478
479 freq = mixer_load (s, AC97_MIC_ADC_Rate);
480 open_voice (s, MC_INDEX, freq);
481 AUD_set_active_in (s->voice_mc, active[MC_INDEX]);
482}
483
484#ifdef USE_MIXER
485
486static void set_volume (AC97LinkState *s, int index,
487 audmixerctl_t mt, uint32_t val)
488{
489 int mute = (val >> MUTE_SHIFT) & 1;
490 uint8_t rvol = VOL_MASK - (val & VOL_MASK);
491 uint8_t lvol = VOL_MASK - ((val >> 8) & VOL_MASK);
492 rvol = 255 * rvol / VOL_MASK;
493 lvol = 255 * lvol / VOL_MASK;
494
495# ifdef SOFT_VOLUME
496 if (index == AC97_Master_Volume_Mute)
497 AUD_set_volume_out (s->voice_po, mute, lvol, rvol);
498 else
499 AUD_set_volume (mt, &mute, &lvol, &rvol);
500# else
501 AUD_set_volume (mt, &mute, &lvol, &rvol);
502# endif
503
504 rvol = VOL_MASK - ((VOL_MASK * rvol) / 255);
505 lvol = VOL_MASK - ((VOL_MASK * lvol) / 255);
506
507 /*
508 * From AC'97 SoundMax Codec AD1981A: "Because AC '97 defines 6-bit volume registers, to
509 * maintain compatibility whenever the D5 or D13 bits are set to `1,' their respective
510 * lower five volume bits are automatically set to `1' by the Codec logic. On readback,
511 * all lower 5 bits will read ones whenever these bits are set to `1.'"
512 *
513 * Linux ALSA depends on this behavior.
514 */
515 if (val & RT_BIT(5))
516 val |= RT_BIT(4) | RT_BIT(3) | RT_BIT(2) | RT_BIT(1) | RT_BIT(0);
517 if (val & RT_BIT(13))
518 val |= RT_BIT(12) | RT_BIT(11) | RT_BIT(10) | RT_BIT(9) | RT_BIT(8);
519
520 mixer_store (s, index, val);
521}
522
523static audrecsource_t ac97_to_aud_record_source (uint8_t i)
524{
525 switch (i)
526 {
527 case REC_MIC: return AUD_REC_MIC;
528 case REC_CD: return AUD_REC_CD;
529 case REC_VIDEO: return AUD_REC_VIDEO;
530 case REC_AUX: return AUD_REC_AUX;
531 case REC_LINE_IN: return AUD_REC_LINE_IN;
532 case REC_PHONE: return AUD_REC_PHONE;
533 default: Log (("ac97: Unknown record source %d, using MIC\n", i));
534 return AUD_REC_MIC;
535 }
536}
537
538static uint8_t aud_to_ac97_record_source (audrecsource_t rs)
539{
540 switch (rs)
541 {
542 case AUD_REC_MIC: return REC_MIC;
543 case AUD_REC_CD: return REC_CD;
544 case AUD_REC_VIDEO: return REC_VIDEO;
545 case AUD_REC_AUX: return REC_AUX;
546 case AUD_REC_LINE_IN: return REC_LINE_IN;
547 case AUD_REC_PHONE: return REC_PHONE;
548 default: Log (("ac97: Unknown audio recording source %d using MIC\n", rs));
549 return REC_MIC;
550 }
551}
552
553static void record_select (AC97LinkState *s, uint32_t val)
554{
555 uint8_t rs = val & REC_MASK;
556 uint8_t ls = (val >> 8) & REC_MASK;
557 audrecsource_t ars = ac97_to_aud_record_source (rs);
558 audrecsource_t als = ac97_to_aud_record_source (ls);
559 AUD_set_record_source (&als, &ars);
560 rs = aud_to_ac97_record_source (ars);
561 ls = aud_to_ac97_record_source (als);
562 mixer_store (s, AC97_Record_Select, rs | (ls << 8));
563}
564
565#endif /* USE_MIXER */
566
567static void mixer_reset (AC97LinkState *s)
568{
569 uint8_t active[LAST_INDEX];
570
571 Log (("ac97: mixer_reset\n"));
572 memset (s->mixer_data, 0, sizeof (s->mixer_data));
573 memset (active, 0, sizeof (active));
574 mixer_store (s, AC97_Reset , 0x0000); /* 6940 */
575 mixer_store (s, AC97_Master_Volume_Mono_Mute , 0x8000);
576 mixer_store (s, AC97_PC_BEEP_Volume_Mute , 0x0000);
577
578 mixer_store (s, AC97_Phone_Volume_Mute , 0x8008);
579 mixer_store (s, AC97_Mic_Volume_Mute , 0x8008);
580 mixer_store (s, AC97_CD_Volume_Mute , 0x8808);
581 mixer_store (s, AC97_Aux_Volume_Mute , 0x8808);
582 mixer_store (s, AC97_Record_Gain_Mic_Mute , 0x8000);
583 mixer_store (s, AC97_General_Purpose , 0x0000);
584 mixer_store (s, AC97_3D_Control , 0x0000);
585 mixer_store (s, AC97_Powerdown_Ctrl_Stat , 0x000f);
586
587 /*
588 * Sigmatel 9700 (STAC9700)
589 */
590 mixer_store (s, AC97_Vendor_ID1 , 0x8384);
591 mixer_store (s, AC97_Vendor_ID2 , 0x7600); /* 7608 */
592
593 mixer_store (s, AC97_Extended_Audio_ID , 0x0809);
594 mixer_store (s, AC97_Extended_Audio_Ctrl_Stat, 0x0009);
595 mixer_store (s, AC97_PCM_Front_DAC_Rate , 0xbb80);
596 mixer_store (s, AC97_PCM_Surround_DAC_Rate , 0xbb80);
597 mixer_store (s, AC97_PCM_LFE_DAC_Rate , 0xbb80);
598 mixer_store (s, AC97_PCM_LR_ADC_Rate , 0xbb80);
599 mixer_store (s, AC97_MIC_ADC_Rate , 0xbb80);
600
601#ifdef USE_MIXER
602 record_select (s, 0);
603 set_volume (s, AC97_Master_Volume_Mute, AUD_MIXER_VOLUME, 0x8000);
604 set_volume (s, AC97_PCM_Out_Volume_Mute, AUD_MIXER_PCM, 0x8808);
605 set_volume (s, AC97_Line_In_Volume_Mute, AUD_MIXER_LINE_IN, 0x8808);
606#else
607 mixer_store (s, AC97_Record_Select, 0);
608 mixer_store (s, AC97_Master_Volume_Mute, 0x8000);
609 mixer_store (s, AC97_PCM_Out_Volume_Mute, 0x8808);
610 mixer_store (s, AC97_Line_In_Volume_Mute, 0x8808);
611#endif
612
613 reset_voices (s, active);
614}
615
616static int write_audio (AC97LinkState *s, AC97BusMasterRegs *r,
617 int max, int *stop)
618{
619 PPDMDEVINS pDevIns = ICHAC97STATE_2_DEVINS(s);
620 uint8_t tmpbuf[4096];
621 uint32_t addr = r->bd.addr;
622 uint32_t temp = r->picb << 1;
623 uint32_t written = 0;
624 int to_copy = 0;
625
626 temp = audio_MIN (temp, (uint32_t) max);
627 if (!temp)
628 {
629 *stop = 1;
630 return 0;
631 }
632
633 while (temp)
634 {
635 int copied;
636 to_copy = audio_MIN (temp, sizeof (tmpbuf));
637 PDMDevHlpPhysRead (pDevIns, addr, tmpbuf, to_copy);
638 copied = AUD_write (s->voice_po, tmpbuf, to_copy);
639 Log (("ac97: write_audio max=%x to_copy=%x copied=%x\n",
640 max, to_copy, copied));
641 if (!copied)
642 {
643 *stop = 1;
644 break;
645 }
646 temp -= copied;
647 addr += copied;
648 written += copied;
649 }
650
651 if (!temp)
652 {
653 if (to_copy < 4)
654 {
655 Log (("ac97: whoops\n"));
656 s->last_samp = 0;
657 }
658 else
659 s->last_samp = *(uint32_t *) &tmpbuf[to_copy - 4];
660 }
661
662 r->bd.addr = addr;
663 return written;
664}
665
666static void write_bup (AC97LinkState *s, int elapsed)
667{
668 int written = 0;
669
670 Log (("ac97: write_bup\n"));
671 if (!(s->bup_flag & BUP_SET))
672 {
673 if (s->bup_flag & BUP_LAST)
674 {
675 unsigned int i;
676 uint32_t *p = (uint32_t*)s->silence;
677 for (i = 0; i < sizeof (s->silence) / 4; i++)
678 *p++ = s->last_samp;
679 }
680 else
681 memset (s->silence, 0, sizeof (s->silence));
682
683 s->bup_flag |= BUP_SET;
684 }
685
686 while (elapsed)
687 {
688 unsigned int temp = audio_MIN ((unsigned int)elapsed, sizeof (s->silence));
689 while (temp)
690 {
691 int copied = AUD_write (s->voice_po, s->silence, temp);
692 if (!copied)
693 return;
694 temp -= copied;
695 elapsed -= copied;
696 written += copied;
697 }
698 }
699}
700
701static int read_audio (AC97LinkState *s, AC97BusMasterRegs *r,
702 int max, int *stop)
703{
704 PPDMDEVINS pDevIns = ICHAC97STATE_2_DEVINS(s);
705 uint8_t tmpbuf[4096];
706 uint32_t addr = r->bd.addr;
707 uint32_t temp = r->picb << 1;
708 uint32_t nread = 0;
709 int to_copy = 0;
710 SWVoiceIn *voice = (r - s->bm_regs) == MC_INDEX ? s->voice_mc : s->voice_pi;
711
712 temp = audio_MIN (temp, (uint32_t) max);
713 if (!temp)
714 {
715 *stop = 1;
716 return 0;
717 }
718
719 while (temp)
720 {
721 int acquired;
722 to_copy = audio_MIN (temp, sizeof (tmpbuf));
723 acquired = AUD_read (voice, tmpbuf, to_copy);
724 if (!acquired)
725 {
726 *stop = 1;
727 break;
728 }
729 PDMDevHlpPhysWrite (pDevIns, addr, tmpbuf, acquired);
730 temp -= acquired;
731 addr += acquired;
732 nread += acquired;
733 }
734
735 r->bd.addr = addr;
736 return nread;
737}
738
739static void transfer_audio (AC97LinkState *s, int index, int elapsed)
740{
741 AC97BusMasterRegs *r = &s->bm_regs[index];
742 int written = 0, stop = 0;
743
744 if (r->sr & SR_DCH)
745 {
746 if (r->cr & CR_RPBM)
747 {
748 switch (index)
749 {
750 case PO_INDEX:
751 write_bup (s, elapsed);
752 break;
753 }
754 }
755 return;
756 }
757
758 while ((elapsed >> 1) && !stop)
759 {
760 int temp;
761
762 if (!r->bd_valid)
763 {
764 Log (("ac97: invalid bd\n"));
765 fetch_bd (s, r);
766 }
767
768 if (!r->picb)
769 {
770 Log (("ac97: fresh bd %d is empty %#x %#x\n",
771 r->civ, r->bd.addr, r->bd.ctl_len));
772 if (r->civ == r->lvi)
773 {
774 r->sr |= SR_DCH; /* CELV? */
775 s->bup_flag = 0;
776 break;
777 }
778 r->sr &= ~SR_CELV;
779 r->civ = r->piv;
780 r->piv = (r->piv + 1) % 32;
781 fetch_bd (s, r);
782 return;
783 }
784
785 switch (index)
786 {
787 case PO_INDEX:
788 temp = write_audio (s, r, elapsed, &stop);
789 written += temp;
790 elapsed -= temp;
791 r->picb -= (temp >> 1);
792 break;
793
794 case PI_INDEX:
795 case MC_INDEX:
796 temp = read_audio (s, r, elapsed, &stop);
797 elapsed -= temp;
798 r->picb -= (temp >> 1);
799 break;
800 }
801
802 Log (("r->picb = %d\n", r->picb));
803
804 if (!r->picb)
805 {
806 uint32_t new_sr = r->sr & ~SR_CELV;
807
808 if (r->bd.ctl_len & BD_IOC)
809 new_sr |= SR_BCIS;
810
811 if (r->civ == r->lvi)
812 {
813 Log (("ac97: Underrun civ (%d) == lvi (%d)\n", r->civ, r->lvi));
814 new_sr |= SR_LVBCI | SR_DCH | SR_CELV;
815 stop = 1;
816 s->bup_flag = (r->bd.ctl_len & BD_BUP) ? BUP_LAST : 0;
817 }
818 else
819 {
820 r->civ = r->piv;
821 r->piv = (r->piv + 1) % 32;
822 fetch_bd (s, r);
823 }
824 update_sr (s, r, new_sr);
825 }
826 }
827}
828
829static void pi_callback (void *opaque, int avail)
830{
831 transfer_audio ((AC97LinkState*)opaque, PI_INDEX, avail);
832}
833
834static void mc_callback (void *opaque, int avail)
835{
836 transfer_audio ((AC97LinkState*)opaque, MC_INDEX, avail);
837}
838
839static void po_callback (void *opaque, int free)
840{
841 transfer_audio ((AC97LinkState*)opaque, PO_INDEX, free);
842}
843
844/**
845 * Port I/O Handler for IN operations.
846 *
847 * @returns VBox status code.
848 *
849 * @param pDevIns The device instance.
850 * @param pvUser User argument.
851 * @param uPort Port number used for the IN operation.
852 * @param pu32 Where to store the result.
853 * @param cb Number of bytes read.
854 */
855static DECLCALLBACK(int) ichac97IOPortNABMRead (PPDMDEVINS pDevIns, void *pvUser,
856 RTIOPORT Port, uint32_t *pu32, unsigned cb)
857{
858 PCIAC97LinkState *d = (PCIAC97LinkState*)pvUser;
859 AC97LinkState *s = &d->ac97;
860
861 switch (cb)
862 {
863 case 1:
864 {
865 AC97BusMasterRegs *r = NULL;
866 uint32_t index = Port - d->ac97.IOPortBase[1];
867 *pu32 = ~0U;
868
869 switch (index)
870 {
871 case CAS:
872 /* Codec Access Semaphore Register */
873 Log (("ac97: CAS %d\n", s->cas));
874 *pu32 = s->cas;
875 s->cas = 1;
876 break;
877 case PI_CIV:
878 case PO_CIV:
879 case MC_CIV:
880 /* Current Index Value Register */
881 r = &s->bm_regs[GET_BM (index)];
882 *pu32 = r->civ;
883 Log (("ac97: CIV[%d] -> %#x\n", GET_BM (index), *pu32));
884 break;
885 case PI_LVI:
886 case PO_LVI:
887 case MC_LVI:
888 /* Last Valid Index Register */
889 r = &s->bm_regs[GET_BM (index)];
890 *pu32 = r->lvi;
891 Log (("ac97: LVI[%d] -> %#x\n", GET_BM (index), *pu32));
892 break;
893 case PI_PIV:
894 case PO_PIV:
895 case MC_PIV:
896 /* Prefetched Index Value Register */
897 r = &s->bm_regs[GET_BM (index)];
898 *pu32 = r->piv;
899 Log (("ac97: PIV[%d] -> %#x\n", GET_BM (index), *pu32));
900 break;
901 case PI_CR:
902 case PO_CR:
903 case MC_CR:
904 /* Control Register */
905 r = &s->bm_regs[GET_BM (index)];
906 *pu32 = r->cr;
907 Log (("ac97: CR[%d] -> %#x\n", GET_BM (index), *pu32));
908 break;
909 case PI_SR:
910 case PO_SR:
911 case MC_SR:
912 /* Status Register (lower part) */
913 r = &s->bm_regs[GET_BM (index)];
914 *pu32 = r->sr & 0xff;
915 Log (("ac97: SRb[%d] -> %#x\n", GET_BM (index), *pu32));
916 break;
917 default:
918 Log (("ac97: U nabm readb %#x -> %#x\n", Port, *pu32));
919 break;
920 }
921 break;
922 }
923
924 case 2:
925 {
926 AC97BusMasterRegs *r = NULL;
927 uint32_t index = Port - d->ac97.IOPortBase[1];
928 *pu32 = ~0U;
929
930 switch (index)
931 {
932 case PI_SR:
933 case PO_SR:
934 case MC_SR:
935 /* Status Register */
936 r = &s->bm_regs[GET_BM (index)];
937 *pu32 = r->sr;
938 Log (("ac97: SR[%d] -> %#x\n", GET_BM (index), *pu32));
939 break;
940 case PI_PICB:
941 case PO_PICB:
942 case MC_PICB:
943 /* Position in Current Buffer Register */
944 r = &s->bm_regs[GET_BM (index)];
945 *pu32 = r->picb;
946 Log (("ac97: PICB[%d] -> %#x\n", GET_BM (index), *pu32));
947 break;
948 default:
949 Log (("ac97: U nabm readw %#x -> %#x\n", Port, *pu32));
950 break;
951 }
952 break;
953 }
954
955 case 4:
956 {
957 AC97BusMasterRegs *r = NULL;
958 uint32_t index = Port - d->ac97.IOPortBase[1];
959 *pu32 = ~0U;
960
961 switch (index)
962 {
963 case PI_BDBAR:
964 case PO_BDBAR:
965 case MC_BDBAR:
966 /* Buffer Descriptor Base Address Register */
967 r = &s->bm_regs[GET_BM (index)];
968 *pu32 = r->bdbar;
969 Log (("ac97: BMADDR[%d] -> %#x\n", GET_BM (index), *pu32));
970 break;
971 case PI_CIV:
972 case PO_CIV:
973 case MC_CIV:
974 /* 32-bit access: Current Index Value Register +
975 * Last Valid Index Register +
976 * Status Register */
977 r = &s->bm_regs[GET_BM (index)];
978 *pu32 = r->civ | (r->lvi << 8) | (r->sr << 16);
979 Log (("ac97: CIV LVI SR[%d] -> %#x, %#x, %#x\n", GET_BM (index),
980 r->civ, r->lvi, r->sr));
981 break;
982 case PI_PICB:
983 case PO_PICB:
984 case MC_PICB:
985 /* 32-bit access: Position in Current Buffer Register +
986 * Prefetched Index Value Register +
987 * Control Register */
988 r = &s->bm_regs[GET_BM (index)];
989 *pu32 = r->picb | (r->piv << 16) | (r->cr << 24);
990 Log (("ac97: PICB PIV CR[%d] -> %#x %#x %#x %#x\n", GET_BM (index),
991 *pu32, r->picb, r->piv, r->cr));
992 break;
993 case GLOB_CNT:
994 /* Global Control */
995 *pu32 = s->glob_cnt;
996 Log (("ac97: glob_cnt -> %#x\n", *pu32));
997 break;
998 case GLOB_STA:
999 /* Global Status */
1000 *pu32 = s->glob_sta | GS_S0CR;
1001 Log (("ac97: glob_sta -> %#x\n", *pu32));
1002 break;
1003 default:
1004 Log (("ac97: U nabm readl %#x -> %#x\n", Port, *pu32));
1005 break;
1006 }
1007 break;
1008 }
1009
1010 default:
1011 return VERR_IOM_IOPORT_UNUSED;
1012 }
1013 return VINF_SUCCESS;
1014}
1015
1016/**
1017 * Port I/O Handler for OUT operations.
1018 *
1019 * @returns VBox status code.
1020 *
1021 * @param pDevIns The device instance.
1022 * @param pvUser User argument.
1023 * @param uPort Port number used for the IN operation.
1024 * @param u32 The value to output.
1025 * @param cb The value size in bytes.
1026 */
1027static DECLCALLBACK(int) ichac97IOPortNABMWrite (PPDMDEVINS pDevIns, void *pvUser,
1028 RTIOPORT Port, uint32_t u32, unsigned cb)
1029{
1030 PCIAC97LinkState *d = (PCIAC97LinkState*)pvUser;
1031 AC97LinkState *s = &d->ac97;
1032
1033 switch (cb)
1034 {
1035 case 1:
1036 {
1037 AC97BusMasterRegs *r = NULL;
1038 uint32_t index = Port - d->ac97.IOPortBase[1];
1039 switch (index)
1040 {
1041 case PI_LVI:
1042 case PO_LVI:
1043 case MC_LVI:
1044 /* Last Valid Index */
1045 r = &s->bm_regs[GET_BM (index)];
1046 if ((r->cr & CR_RPBM) && (r->sr & SR_DCH)) {
1047 r->sr &= ~(SR_DCH | SR_CELV);
1048 r->civ = r->piv;
1049 r->piv = (r->piv + 1) % 32;
1050 fetch_bd (s, r);
1051 }
1052 r->lvi = u32 % 32;
1053 Log (("ac97: LVI[%d] <- %#x\n", GET_BM (index), u32));
1054 break;
1055 case PI_CR:
1056 case PO_CR:
1057 case MC_CR:
1058 /* Control Register */
1059 r = &s->bm_regs[GET_BM (index)];
1060 if (u32 & CR_RR)
1061 reset_bm_regs (s, r);
1062 else
1063 {
1064 r->cr = u32 & CR_VALID_MASK;
1065 if (!(r->cr & CR_RPBM))
1066 {
1067 voice_set_active (s, r - s->bm_regs, 0);
1068 r->sr |= SR_DCH;
1069 }
1070 else
1071 {
1072 r->civ = r->piv;
1073 r->piv = (r->piv + 1) % 32;
1074 fetch_bd (s, r);
1075 r->sr &= ~SR_DCH;
1076 voice_set_active (s, r - s->bm_regs, 1);
1077 }
1078 }
1079 Log (("ac97: CR[%d] <- %#x (cr %#x)\n", GET_BM (index), u32, r->cr));
1080 break;
1081 case PI_SR:
1082 case PO_SR:
1083 case MC_SR:
1084 /* Status Register */
1085 r = &s->bm_regs[GET_BM (index)];
1086 r->sr |= u32 & ~(SR_RO_MASK | SR_WCLEAR_MASK);
1087 update_sr (s, r, r->sr & ~(u32 & SR_WCLEAR_MASK));
1088 Log (("ac97: SR[%d] <- %#x (sr %#x)\n", GET_BM (index), u32, r->sr));
1089 break;
1090 default:
1091 Log (("ac97: U nabm writeb %#x <- %#x\n", Port, u32));
1092 break;
1093 }
1094 break;
1095 }
1096
1097 case 2:
1098 {
1099 AC97BusMasterRegs *r = NULL;
1100 uint32_t index = Port - d->ac97.IOPortBase[1];
1101 switch (index)
1102 {
1103 case PI_SR:
1104 case PO_SR:
1105 case MC_SR:
1106 /* Status Register */
1107 r = &s->bm_regs[GET_BM (index)];
1108 r->sr |= u32 & ~(SR_RO_MASK | SR_WCLEAR_MASK);
1109 update_sr (s, r, r->sr & ~(u32 & SR_WCLEAR_MASK));
1110 Log (("ac97: SR[%d] <- %#x (sr %#x)\n", GET_BM (index), u32, r->sr));
1111 break;
1112 default:
1113 Log (("ac97: U nabm writew %#x <- %#x\n", Port, u32));
1114 break;
1115 }
1116 break;
1117 }
1118
1119 case 4:
1120 {
1121 AC97BusMasterRegs *r = NULL;
1122 uint32_t index = Port - d->ac97.IOPortBase[1];
1123 switch (index)
1124 {
1125 case PI_BDBAR:
1126 case PO_BDBAR:
1127 case MC_BDBAR:
1128 /* Buffer Descriptor list Base Address Register */
1129 r = &s->bm_regs[GET_BM (index)];
1130 r->bdbar = u32 & ~3;
1131 Log (("ac97: BDBAR[%d] <- %#x (bdbar %#x)\n",
1132 GET_BM (index), u32, r->bdbar));
1133 break;
1134 case GLOB_CNT:
1135 /* Global Control */
1136 if (u32 & GC_WR)
1137 warm_reset (s);
1138 if (u32 & GC_CR)
1139 cold_reset (s);
1140 if (!(u32 & (GC_WR | GC_CR)))
1141 s->glob_cnt = u32 & GC_VALID_MASK;
1142 Log (("ac97: glob_cnt <- %#x (glob_cnt %#x)\n", u32, s->glob_cnt));
1143 break;
1144 case GLOB_STA:
1145 /* Global Status */
1146 s->glob_sta &= ~(u32 & GS_WCLEAR_MASK);
1147 s->glob_sta |= (u32 & ~(GS_WCLEAR_MASK | GS_RO_MASK)) & GS_VALID_MASK;
1148 Log (("ac97: glob_sta <- %#x (glob_sta %#x)\n", u32, s->glob_sta));
1149 break;
1150 default:
1151 Log (("ac97: U nabm writel %#x <- %#x\n", Port, u32));
1152 break;
1153 }
1154 break;
1155 }
1156
1157 default:
1158 AssertMsgFailed(("Port=%#x cb=%d u32=%#x\n", Port, cb, u32));
1159 break;
1160 }
1161 return VINF_SUCCESS;
1162}
1163
1164/**
1165 * Port I/O Handler for IN operations.
1166 *
1167 * @returns VBox status code.
1168 *
1169 * @param pDevIns The device instance.
1170 * @param pvUser User argument.
1171 * @param uPort Port number used for the IN operation.
1172 * @param pu32 Where to store the result.
1173 * @param cb Number of bytes read.
1174 */
1175static DECLCALLBACK(int) ichac97IOPortNAMRead (PPDMDEVINS pDevIns, void *pvUser,
1176 RTIOPORT Port, uint32_t *pu32, unsigned cb)
1177{
1178 PCIAC97LinkState *d = (PCIAC97LinkState*)pvUser;
1179 AC97LinkState *s = &d->ac97;
1180
1181 switch (cb)
1182 {
1183 case 1:
1184 {
1185 Log (("ac97: U nam readb %#x\n", Port));
1186 s->cas = 0;
1187 *pu32 = ~0U;
1188 break;
1189 }
1190
1191 case 2:
1192 {
1193 uint32_t index = Port - d->ac97.IOPortBase[0];
1194 *pu32 = ~0U;
1195 s->cas = 0;
1196 switch (index)
1197 {
1198 default:
1199 *pu32 = mixer_load (s, index);
1200 Log (("ac97: nam readw %#x -> %#x\n", Port, *pu32));
1201 break;
1202 }
1203 break;
1204 }
1205
1206 case 4:
1207 {
1208 Log (("ac97: U nam readl %#x\n", Port));
1209 s->cas = 0;
1210 *pu32 = ~0U;
1211 break;
1212 }
1213
1214 default:
1215 return VERR_IOM_IOPORT_UNUSED;
1216 }
1217 return VINF_SUCCESS;
1218}
1219
1220/**
1221 * Port I/O Handler for OUT operations.
1222 *
1223 * @returns VBox status code.
1224 *
1225 * @param pDevIns The device instance.
1226 * @param pvUser User argument.
1227 * @param uPort Port number used for the IN operation.
1228 * @param u32 The value to output.
1229 * @param cb The value size in bytes.
1230 */
1231static DECLCALLBACK(int) ichac97IOPortNAMWrite (PPDMDEVINS pDevIns, void *pvUser,
1232 RTIOPORT Port, uint32_t u32, unsigned cb)
1233{
1234 PCIAC97LinkState *d = (PCIAC97LinkState*)pvUser;
1235 AC97LinkState *s = &d->ac97;
1236
1237 switch (cb)
1238 {
1239 case 1:
1240 {
1241 Log (("ac97: U nam writeb %#x <- %#x\n", Port, u32));
1242 s->cas = 0;
1243 break;
1244 }
1245
1246 case 2:
1247 {
1248 uint32_t index = Port - d->ac97.IOPortBase[0];
1249 s->cas = 0;
1250 switch (index)
1251 {
1252 case AC97_Reset:
1253 mixer_reset (s);
1254 break;
1255 case AC97_Powerdown_Ctrl_Stat:
1256 u32 &= ~0xf;
1257 u32 |= mixer_load (s, index) & 0xf;
1258 mixer_store (s, index, u32);
1259 break;
1260#ifdef USE_MIXER
1261 case AC97_Master_Volume_Mute:
1262 set_volume (s, index, AUD_MIXER_VOLUME, u32);
1263 break;
1264 case AC97_PCM_Out_Volume_Mute:
1265 set_volume (s, index, AUD_MIXER_PCM, u32);
1266 break;
1267 case AC97_Line_In_Volume_Mute:
1268 set_volume (s, index, AUD_MIXER_LINE_IN, u32);
1269 break;
1270 case AC97_Record_Select:
1271 record_select (s, u32);
1272 break;
1273#else /* !USE_MIXER */
1274 case AC97_Master_Volume_Mute:
1275 case AC97_PCM_Out_Volume_Mute:
1276 case AC97_Line_In_Volume_Mute:
1277 case AC97_Record_Select:
1278 mixer_store (s, index, u32);
1279 break;
1280#endif /* !USE_MIXER */
1281 case AC97_Vendor_ID1:
1282 case AC97_Vendor_ID2:
1283 Log (("ac97: Attempt to write vendor ID to %#x\n", u32));
1284 break;
1285 case AC97_Extended_Audio_ID:
1286 Log (("ac97: Attempt to write extended audio ID to %#x\n", u32));
1287 break;
1288 case AC97_Extended_Audio_Ctrl_Stat:
1289 if (!(u32 & EACS_VRA))
1290 {
1291 mixer_store (s, AC97_PCM_Front_DAC_Rate, 0xbb80);
1292 mixer_store (s, AC97_PCM_LR_ADC_Rate, 0xbb80);
1293 open_voice (s, PI_INDEX, 48000);
1294 open_voice (s, PO_INDEX, 48000);
1295 }
1296 if (!(u32 & EACS_VRM))
1297 {
1298 mixer_store (s, AC97_MIC_ADC_Rate, 0xbb80);
1299 open_voice (s, MC_INDEX, 48000);
1300 }
1301 Log (("ac97: Setting extended audio control to %#x\n", u32));
1302 mixer_store (s, AC97_Extended_Audio_Ctrl_Stat, u32);
1303 break;
1304 case AC97_PCM_Front_DAC_Rate:
1305 if (mixer_load (s, AC97_Extended_Audio_Ctrl_Stat) & EACS_VRA)
1306 {
1307 mixer_store (s, index, u32);
1308 Log(("ac97: Set front DAC rate to %d\n", u32));
1309 open_voice (s, PO_INDEX, u32);
1310 }
1311 else
1312 {
1313 Log (("ac97: Attempt to set front DAC rate to %d, "
1314 "but VRA is not set\n",
1315 u32));
1316 }
1317 break;
1318 case AC97_MIC_ADC_Rate:
1319 if (mixer_load (s, AC97_Extended_Audio_Ctrl_Stat) & EACS_VRM)
1320 {
1321 mixer_store (s, index, u32);
1322 Log (("ac97: Set MIC ADC rate to %d\n", u32));
1323 open_voice (s, MC_INDEX, u32);
1324 }
1325 else
1326 {
1327 Log (("ac97: Attempt to set MIC ADC rate to %d, "
1328 "but VRM is not set\n",
1329 u32));
1330 }
1331 break;
1332 case AC97_PCM_LR_ADC_Rate:
1333 if (mixer_load (s, AC97_Extended_Audio_Ctrl_Stat) & EACS_VRA)
1334 {
1335 mixer_store (s, index, u32);
1336 Log (("ac97: Set front LR ADC rate to %d\n", u32));
1337 open_voice (s, PI_INDEX, u32);
1338 }
1339 else
1340 {
1341 Log (("ac97: Attempt to set LR ADC rate to %d, but VRA is not set\n",
1342 u32));
1343 }
1344 break;
1345 default:
1346 Log (("ac97: U nam writew %#x <- %#x\n", Port, u32));
1347 mixer_store (s, index, u32);
1348 break;
1349 }
1350 break;
1351 }
1352
1353 case 4:
1354 {
1355 Log (("ac97: U nam writel %#x <- %#x\n", Port, u32));
1356 s->cas = 0;
1357 break;
1358 }
1359
1360 default:
1361 AssertMsgFailed(("Port=%#x cb=%d u32=%#x\n", Port, cb, u32));
1362 break;
1363 }
1364 return VINF_SUCCESS;
1365}
1366
1367/**
1368 * Callback function for mapping a PCI I/O region.
1369 *
1370 * @return VBox status code.
1371 * @param pPciDev Pointer to PCI device.
1372 * Use pPciDev->pDevIns to get the device instance.
1373 * @param iRegion The region number.
1374 * @param GCPhysAddress Physical address of the region.
1375 * If iType is PCI_ADDRESS_SPACE_IO, this is an
1376 * I/O port, else it's a physical address.
1377 * This address is *NOT* relative
1378 * to pci_mem_base like earlier!
1379 * @param enmType One of the PCI_ADDRESS_SPACE_* values.
1380 */
1381static DECLCALLBACK(int) ichac97IOPortMap (PPCIDEVICE pPciDev, int iRegion,
1382 RTGCPHYS GCPhysAddress, uint32_t cb,
1383 PCIADDRESSSPACE enmType)
1384{
1385 int rc;
1386 PPDMDEVINS pDevIns = pPciDev->pDevIns;
1387 RTIOPORT Port = (RTIOPORT)GCPhysAddress;
1388 PCIAC97LinkState *pThis = PCIDEV_2_ICHAC97STATE(pPciDev);
1389
1390 Assert(enmType == PCI_ADDRESS_SPACE_IO);
1391 Assert(cb >= 0x20);
1392
1393 if (iRegion == 0)
1394 rc = PDMDevHlpIOPortRegister (pDevIns, Port, 256, pThis,
1395 ichac97IOPortNAMWrite, ichac97IOPortNAMRead,
1396 NULL, NULL, "ICHAC97 NAM");
1397 else
1398 rc = PDMDevHlpIOPortRegister (pDevIns, Port, 64, pThis,
1399 ichac97IOPortNABMWrite, ichac97IOPortNABMRead,
1400 NULL, NULL, "ICHAC97 NABM");
1401 if (RT_FAILURE(rc))
1402 return rc;
1403
1404 pThis->ac97.IOPortBase[iRegion] = Port;
1405 return VINF_SUCCESS;
1406}
1407
1408/**
1409 * Saves a state of the AC'97 device.
1410 *
1411 * @returns VBox status code.
1412 * @param pDevIns The device instance.
1413 * @param pSSMHandle The handle to save the state to.
1414 */
1415static DECLCALLBACK(int) ichac97SaveExec (PPDMDEVINS pDevIns, PSSMHANDLE pSSMHandle)
1416{
1417 PCIAC97LinkState *pThis = PDMINS_2_DATA(pDevIns, PCIAC97LinkState *);
1418 size_t i;
1419 uint8_t active[LAST_INDEX];
1420 AC97LinkState *s = &pThis->ac97;
1421
1422 SSMR3PutU32 (pSSMHandle, s->glob_cnt);
1423 SSMR3PutU32 (pSSMHandle, s->glob_sta);
1424 SSMR3PutU32 (pSSMHandle, s->cas);
1425
1426 for (i = 0; i < sizeof (s->bm_regs) / sizeof (s->bm_regs[0]); ++i)
1427 {
1428 AC97BusMasterRegs *r = &s->bm_regs[i];
1429 SSMR3PutU32 (pSSMHandle, r->bdbar);
1430 SSMR3PutU8 (pSSMHandle, r->civ);
1431 SSMR3PutU8 (pSSMHandle, r->lvi);
1432 SSMR3PutU16 (pSSMHandle, r->sr);
1433 SSMR3PutU16 (pSSMHandle, r->picb);
1434 SSMR3PutU8 (pSSMHandle, r->piv);
1435 SSMR3PutU8 (pSSMHandle, r->cr);
1436 SSMR3PutS32 (pSSMHandle, r->bd_valid);
1437 SSMR3PutU32 (pSSMHandle, r->bd.addr);
1438 SSMR3PutU32 (pSSMHandle, r->bd.ctl_len);
1439 }
1440 SSMR3PutMem (pSSMHandle, s->mixer_data, sizeof (s->mixer_data));
1441
1442 active[PI_INDEX] = AUD_is_active_in (s->voice_pi) ? 1 : 0;
1443 active[PO_INDEX] = AUD_is_active_out (s->voice_po) ? 1 : 0;
1444 active[MC_INDEX] = AUD_is_active_in (s->voice_mc) ? 1 : 0;
1445 SSMR3PutMem (pSSMHandle, active, sizeof (active));
1446
1447 return VINF_SUCCESS;
1448}
1449
1450/**
1451 * Loads a saved AC'97 device state.
1452 *
1453 * @returns VBox status code.
1454 * @param pDevIns The device instance.
1455 * @param pSSMHandle The handle to the saved state.
1456 * @param uVersion The data unit version number.
1457 * @param uPass The data pass.
1458 */
1459static DECLCALLBACK(int) ichac97LoadExec (PPDMDEVINS pDevIns, PSSMHANDLE pSSMHandle,
1460 uint32_t uVersion, uint32_t uPass)
1461{
1462 PCIAC97LinkState *pThis = PDMINS_2_DATA(pDevIns, PCIAC97LinkState *);
1463 AC97LinkState *s = &pThis->ac97;
1464 uint8_t active[LAST_INDEX];
1465 size_t i;
1466
1467 AssertMsgReturn (uVersion == AC97_SSM_VERSION, ("%d\n", uVersion), VERR_SSM_UNSUPPORTED_DATA_UNIT_VERSION);
1468 Assert (uPass == SSM_PASS_FINAL); NOREF(uPass);
1469
1470 SSMR3GetU32 (pSSMHandle, &s->glob_cnt);
1471 SSMR3GetU32 (pSSMHandle, &s->glob_sta);
1472 SSMR3GetU32 (pSSMHandle, &s->cas);
1473
1474 for (i = 0; i < sizeof (s->bm_regs) / sizeof (s->bm_regs[0]); ++i)
1475 {
1476 AC97BusMasterRegs *r = &s->bm_regs[i];
1477 SSMR3GetU32 (pSSMHandle, &r->bdbar);
1478 SSMR3GetU8 (pSSMHandle, &r->civ);
1479 SSMR3GetU8 (pSSMHandle, &r->lvi);
1480 SSMR3GetU16 (pSSMHandle, &r->sr);
1481 SSMR3GetU16 (pSSMHandle, &r->picb);
1482 SSMR3GetU8 (pSSMHandle, &r->piv);
1483 SSMR3GetU8 (pSSMHandle, &r->cr);
1484 SSMR3GetS32 (pSSMHandle, &r->bd_valid);
1485 SSMR3GetU32 (pSSMHandle, &r->bd.addr);
1486 SSMR3GetU32 (pSSMHandle, &r->bd.ctl_len);
1487 }
1488 SSMR3GetMem (pSSMHandle, s->mixer_data, sizeof (s->mixer_data));
1489 SSMR3GetMem (pSSMHandle, active, sizeof (active));
1490
1491#ifdef USE_MIXER
1492 record_select (s, mixer_load (s, AC97_Record_Select));
1493# define V_(a, b) set_volume (s, a, b, mixer_load (s, a))
1494 V_ (AC97_Master_Volume_Mute, AUD_MIXER_VOLUME);
1495 V_ (AC97_PCM_Out_Volume_Mute, AUD_MIXER_PCM);
1496 V_ (AC97_Line_In_Volume_Mute, AUD_MIXER_LINE_IN);
1497# undef V_
1498#endif /* USE_MIXER */
1499 reset_voices (s, active);
1500
1501 s->bup_flag = 0;
1502 s->last_samp = 0;
1503
1504 return VINF_SUCCESS;
1505}
1506
1507/**
1508 * Reset notification.
1509 *
1510 * @returns VBox status.
1511 * @param pDevIns The device instance data.
1512 *
1513 * @remark The original sources didn't install a reset handler, but it seems to
1514 * make sense to me so we'll do it.
1515 */
1516static DECLCALLBACK(void) ac97Reset (PPDMDEVINS pDevIns)
1517{
1518 PCIAC97LinkState *pThis = PDMINS_2_DATA(pDevIns, PCIAC97LinkState *);
1519
1520 /*
1521 * Reset the device state (will need pDrv later).
1522 */
1523 reset_bm_regs (&pThis->ac97, &pThis->ac97.bm_regs[0]);
1524 reset_bm_regs (&pThis->ac97, &pThis->ac97.bm_regs[1]);
1525 reset_bm_regs (&pThis->ac97, &pThis->ac97.bm_regs[2]);
1526
1527 /*
1528 * Reset the mixer too. The Windows XP driver seems to rely on
1529 * this. At least it wants to read the vendor id before it resets
1530 * the codec manually.
1531 */
1532 mixer_reset (&pThis->ac97);
1533}
1534
1535/**
1536 * @interface_method_impl{PDMIBASE,pfnQueryInterface}
1537 */
1538static DECLCALLBACK(void *) ichac97QueryInterface (struct PDMIBASE *pInterface,
1539 const char *pszIID)
1540{
1541 PCIAC97LinkState *pThis = RT_FROM_MEMBER(pInterface, PCIAC97LinkState, ac97.IBase);
1542 Assert(&pThis->ac97.IBase == pInterface);
1543
1544 PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pThis->ac97.IBase);
1545 return NULL;
1546}
1547
1548/**
1549 * @interface_method_impl{PDMDEVREG,pfnConstruct}
1550 */
1551static DECLCALLBACK(int) ichac97Construct (PPDMDEVINS pDevIns, int iInstance,
1552 PCFGMNODE pCfgHandle)
1553{
1554 PCIAC97LinkState *pThis = PDMINS_2_DATA(pDevIns, PCIAC97LinkState *);
1555 AC97LinkState *s = &pThis->ac97;
1556 int rc;
1557
1558 Assert(iInstance == 0);
1559 PDMDEV_CHECK_VERSIONS_RETURN(pDevIns);
1560
1561 /*
1562 * Validations.
1563 */
1564 if (!CFGMR3AreValuesValid (pCfgHandle, "\0"))
1565 return PDMDEV_SET_ERROR (pDevIns, VERR_PDM_DEVINS_UNKNOWN_CFG_VALUES,
1566 N_ ("Invalid configuration for the AC97 device"));
1567
1568 /*
1569 * Initialize data (most of it anyway).
1570 */
1571 s->pDevIns = pDevIns;
1572 /* IBase */
1573 s->IBase.pfnQueryInterface = ichac97QueryInterface;
1574
1575 /* PCI Device (the assertions will be removed later) */
1576 PCIDevSetVendorId (&pThis->dev, 0x8086); /* 00 ro - intel. */ Assert (pThis->dev.config[0x00] == 0x86); Assert (pThis->dev.config[0x01] == 0x80);
1577 PCIDevSetDeviceId (&pThis->dev, 0x2415); /* 02 ro - 82801 / 82801aa(?). */Assert (pThis->dev.config[0x02] == 0x15); Assert (pThis->dev.config[0x03] == 0x24);
1578 PCIDevSetCommand (&pThis->dev, 0x0000); /* 04 rw,ro - pcicmd. */ Assert (pThis->dev.config[0x04] == 0x00); Assert (pThis->dev.config[0x05] == 0x00);
1579 PCIDevSetStatus (&pThis->dev, 0x0280); /* 06 rwc?,ro? - pcists. */ Assert (pThis->dev.config[0x06] == 0x80); Assert (pThis->dev.config[0x07] == 0x02);
1580 PCIDevSetRevisionId (&pThis->dev, 0x01); /* 08 ro - rid. */ Assert (pThis->dev.config[0x08] == 0x01);
1581 PCIDevSetClassProg (&pThis->dev, 0x00); /* 09 ro - pi. */ Assert (pThis->dev.config[0x09] == 0x00);
1582 PCIDevSetClassSub (&pThis->dev, 0x01); /* 0a ro - scc; 01 == Audio. */ Assert (pThis->dev.config[0x0a] == 0x01);
1583 PCIDevSetClassBase (&pThis->dev, 0x04); /* 0b ro - bcc; 04 == multimedia. */ Assert (pThis->dev.config[0x0b] == 0x04);
1584 PCIDevSetHeaderType (&pThis->dev, 0x00); /* 0e ro - headtyp. */ Assert (pThis->dev.config[0x0e] == 0x00);
1585 PCIDevSetBaseAddress (&pThis->dev, 0, /* 10 rw - nambar - native audio mixer base. */
1586 true /* fIoSpace */, false /* fPrefetchable */, false /* f64Bit */, 0x00000000); Assert (pThis->dev.config[0x10] == 0x01); Assert (pThis->dev.config[0x11] == 0x00); Assert (pThis->dev.config[0x12] == 0x00); Assert (pThis->dev.config[0x13] == 0x00);
1587 PCIDevSetBaseAddress (&pThis->dev, 1, /* 14 rw - nabmbar - native audio bus mastering. */
1588 true /* fIoSpace */, false /* fPrefetchable */, false /* f64Bit */, 0x00000000); Assert (pThis->dev.config[0x14] == 0x01); Assert (pThis->dev.config[0x15] == 0x00); Assert (pThis->dev.config[0x16] == 0x00); Assert (pThis->dev.config[0x17] == 0x00);
1589 PCIDevSetSubSystemVendorId (&pThis->dev, 0x8086); /* 2c ro - intel.) */ Assert (pThis->dev.config[0x2c] == 0x86); Assert (pThis->dev.config[0x2d] == 0x80);
1590 PCIDevSetSubSystemId (&pThis->dev, 0x0000); /* 2e ro. */ Assert (pThis->dev.config[0x2e] == 0x00); Assert (pThis->dev.config[0x2f] == 0x00);
1591 PCIDevSetInterruptLine (&pThis->dev, 0x00); /* 3c rw. */ Assert (pThis->dev.config[0x3c] == 0x00);
1592 PCIDevSetInterruptPin (&pThis->dev, 0x01); /* 3d ro - INTA#. */ Assert (pThis->dev.config[0x3d] == 0x01);
1593
1594 /*
1595 * Register the PCI device, it's I/O regions, the timer and the
1596 * saved state item.
1597 */
1598 rc = PDMDevHlpPCIRegister (pDevIns, &pThis->dev);
1599 if (RT_FAILURE (rc))
1600 return rc;
1601
1602 rc = PDMDevHlpPCIIORegionRegister (pDevIns, 0, 256, PCI_ADDRESS_SPACE_IO,
1603 ichac97IOPortMap);
1604 if (RT_FAILURE (rc))
1605 return rc;
1606
1607 rc = PDMDevHlpPCIIORegionRegister (pDevIns, 1, 64, PCI_ADDRESS_SPACE_IO,
1608 ichac97IOPortMap);
1609 if (RT_FAILURE (rc))
1610 return rc;
1611
1612 rc = PDMDevHlpSSMRegister (pDevIns, AC97_SSM_VERSION, sizeof(*pThis), ichac97SaveExec, ichac97LoadExec);
1613 if (RT_FAILURE (rc))
1614 return rc;
1615
1616 /*
1617 * Attach driver.
1618 */
1619 rc = PDMDevHlpDriverAttach (pDevIns, 0, &s->IBase,
1620 &s->pDrvBase, "Audio Driver Port");
1621 if (rc == VERR_PDM_NO_ATTACHED_DRIVER)
1622 Log (("ac97: No attached driver!\n"));
1623 else if (RT_FAILURE (rc))
1624 {
1625 AssertMsgFailed (("Failed to attach AC97 LUN #0! rc=%Rrc\n", rc));
1626 return rc;
1627 }
1628
1629 AUD_register_card ("ICH0", &s->card);
1630
1631 ac97Reset (pDevIns);
1632
1633 if (!s->voice_pi)
1634 LogRel (("AC97: WARNING: Unable to open PCM IN!\n"));
1635 if (!s->voice_mc)
1636 LogRel (("AC97: WARNING: Unable to open PCM MC!\n"));
1637 if (!s->voice_po)
1638 LogRel (("AC97: WARNING: Unable to open PCM OUT!\n"));
1639
1640 if (!s->voice_pi && !s->voice_po && !s->voice_mc)
1641 {
1642 /* Was not able initialize *any* voice. Select the NULL audio driver instead */
1643 AUD_close_in (&s->card, s->voice_pi);
1644 AUD_close_out (&s->card, s->voice_po);
1645 AUD_close_in (&s->card, s->voice_mc);
1646 s->voice_po = NULL;
1647 s->voice_pi = NULL;
1648 s->voice_mc = NULL;
1649 AUD_init_null ();
1650 ac97Reset (pDevIns);
1651
1652 PDMDevHlpVMSetRuntimeError (pDevIns, 0 /*fFlags*/, "HostAudioNotResponding",
1653 N_ ("No audio devices could be opened. Selecting the NULL audio backend "
1654 "with the consequence that no sound is audible"));
1655 }
1656 else if (!s->voice_pi || !s->voice_po || !s->voice_mc)
1657 {
1658 char szMissingVoices[128];
1659 size_t len = 0;
1660 if (!s->voice_pi)
1661 len = RTStrPrintf (szMissingVoices, sizeof(szMissingVoices), "PCM_in");
1662 if (!s->voice_po)
1663 len += RTStrPrintf (szMissingVoices + len, sizeof(szMissingVoices) - len, len ? ", PCM_out" : "PCM_out");
1664 if (!s->voice_mc)
1665 len += RTStrPrintf (szMissingVoices + len, sizeof(szMissingVoices) - len, len ? ", PCM_mic" : "PCM_mic");
1666
1667 PDMDevHlpVMSetRuntimeError (pDevIns, 0 /*fFlags*/, "HostAudioNotResponding",
1668 N_ ("Some audio devices (%s) could not be opened. Guest applications generating audio "
1669 "output or depending on audio input may hang. Make sure your host audio device "
1670 "is working properly. Check the logfile for error messages of the audio "
1671 "subsystem"), szMissingVoices);
1672 }
1673
1674 return VINF_SUCCESS;
1675}
1676
1677/**
1678 * The device registration structure.
1679 */
1680const PDMDEVREG g_DeviceICHAC97 =
1681{
1682 /* u32Version */
1683 PDM_DEVREG_VERSION,
1684 /* szName */
1685 "ichac97",
1686 /* szRCMod */
1687 "",
1688 /* szR0Mod */
1689 "",
1690 /* pszDescription */
1691 "ICH AC'97 Audio Controller",
1692 /* fFlags */
1693 PDM_DEVREG_FLAGS_DEFAULT_BITS,
1694 /* fClass */
1695 PDM_DEVREG_CLASS_AUDIO,
1696 /* cMaxInstances */
1697 1,
1698 /* cbInstance */
1699 sizeof(PCIAC97LinkState),
1700 /* pfnConstruct */
1701 ichac97Construct,
1702 /* pfnDestruct */
1703 NULL,
1704 /* pfnRelocate */
1705 NULL,
1706 /* pfnIOCtl */
1707 NULL,
1708 /* pfnPowerOn */
1709 NULL,
1710 /* pfnReset */
1711 ac97Reset,
1712 /* pfnSuspend */
1713 NULL,
1714 /* pfnResume */
1715 NULL,
1716 /* pfnAttach */
1717 NULL,
1718 /* pfnDetach */
1719 NULL,
1720 /* pfnQueryInterface. */
1721 NULL,
1722 /* pfnInitComplete */
1723 NULL,
1724 /* pfnPowerOff */
1725 NULL,
1726 /* pfnSoftReset */
1727 NULL,
1728 /* u32VersionEnd */
1729 PDM_DEVREG_VERSION
1730};
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette