Back to home page

OSCL-LXR

 
 

    


0001 ===============================
0002 Realtek PC Beep Hidden Register
0003 ===============================
0004 
0005 This file documents the "PC Beep Hidden Register", which is present in certain
0006 Realtek HDA codecs and controls a muxer and pair of passthrough mixers that can
0007 route audio between pins but aren't themselves exposed as HDA widgets. As far
0008 as I can tell, these hidden routes are designed to allow flexible PC Beep output
0009 for codecs that don't have mixer widgets in their output paths. Why it's easier
0010 to hide a mixer behind an undocumented vendor register than to just expose it
0011 as a widget, I have no idea.
0012 
0013 Register Description
0014 ====================
0015 
0016 The register is accessed via processing coefficient 0x36 on NID 20h. Bits not
0017 identified below have no discernible effect on my machine, a Dell XPS 13 9350::
0018 
0019   MSB                           LSB
0020   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
0021   | |h|S|L|         | B |R|       | Known bits
0022   +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
0023   |0|0|1|1|  0x7  |0|0x0|1|  0x7  | Reset value
0024   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
0025 
0026 1Ah input select (B): 2 bits
0027   When zero, expose the PC Beep line (from the internal beep generator, when
0028   enabled with the Set Beep Generation verb on NID 01h, or else from the
0029   external PCBEEP pin) on the 1Ah pin node. When nonzero, expose the headphone
0030   jack (or possibly Line In on some machines) input instead. If PC Beep is
0031   selected, the 1Ah boost control has no effect.
0032 
0033 Amplify 1Ah loopback, left (L): 1 bit
0034   Amplify the left channel of 1Ah before mixing it into outputs as specified
0035   by h and S bits. Does not affect the level of 1Ah exposed to other widgets.
0036 
0037 Amplify 1Ah loopback, right (R): 1 bit
0038   Amplify the right channel of 1Ah before mixing it into outputs as specified
0039   by h and S bits. Does not affect the level of 1Ah exposed to other widgets.
0040 
0041 Loopback 1Ah to 21h [active low] (h): 1 bit
0042   When zero, mix 1Ah (possibly with amplification, depending on L and R bits)
0043   into 21h (headphone jack on my machine). Mixed signal respects the mute
0044   setting on 21h.
0045 
0046 Loopback 1Ah to 14h (S): 1 bit
0047   When one, mix 1Ah (possibly with amplification, depending on L and R bits)
0048   into 14h (internal speaker on my machine). Mixed signal **ignores** the mute
0049   setting on 14h and is present whenever 14h is configured as an output.
0050 
0051 Path diagrams
0052 =============
0053 
0054 1Ah input selection (DIV is the PC Beep divider set on NID 01h)::
0055 
0056   <Beep generator>   <PCBEEP pin>    <Headphone jack>
0057           |                |                |
0058           +--DIV--+--!DIV--+       {1Ah boost control}
0059                   |                         |
0060                   +--(b == 0)--+--(b != 0)--+
0061                                |
0062                >1Ah (Beep/Headphone Mic/Line In)<
0063 
0064 Loopback of 1Ah to 21h/14h::
0065 
0066                <1Ah (Beep/Headphone Mic/Line In)>
0067                                |
0068                         {amplify if L/R}
0069                                |
0070                   +-----!h-----+-----S-----+
0071                   |                        |
0072           {21h mute control}               |
0073                   |                        |
0074           >21h (Headphone)<     >14h (Internal Speaker)<
0075 
0076 Background
0077 ==========
0078 
0079 All Realtek HDA codecs have a vendor-defined widget with node ID 20h which
0080 provides access to a bank of registers that control various codec functions.
0081 Registers are read and written via the standard HDA processing coefficient
0082 verbs (Set/Get Coefficient Index, Set/Get Processing Coefficient). The node is
0083 named "Realtek Vendor Registers" in public datasheets' verb listings and,
0084 apart from that, is entirely undocumented.
0085 
0086 This particular register, exposed at coefficient 0x36 and named in commits from
0087 Realtek, is of note: unlike most registers, which seem to control detailed
0088 amplifier parameters not in scope of the HDA specification, it controls audio
0089 routing which could just as easily have been defined using standard HDA mixer
0090 and selector widgets.
0091 
0092 Specifically, it selects between two sources for the input pin widget with Node
0093 ID (NID) 1Ah: the widget's signal can come either from an audio jack (on my
0094 laptop, a Dell XPS 13 9350, it's the headphone jack, but comments in Realtek
0095 commits indicate that it might be a Line In on some machines) or from the PC
0096 Beep line (which is itself multiplexed between the codec's internal beep
0097 generator and external PCBEEP pin, depending on if the beep generator is
0098 enabled via verbs on NID 01h). Additionally, it can mix (with optional
0099 amplification) that signal onto the 21h and/or 14h output pins.
0100 
0101 The register's reset value is 0x3717, corresponding to PC Beep on 1Ah that is
0102 then amplified and mixed into both the headphones and the speakers. Not only
0103 does this violate the HDA specification, which says that "[a vendor defined
0104 beep input pin] connection may be maintained *only* while the Link reset
0105 (**RST#**) is asserted", it means that we cannot ignore the register if we care
0106 about the input that 1Ah would otherwise expose or if the PCBEEP trace is
0107 poorly shielded and picks up chassis noise (both of which are the case on my
0108 machine).
0109 
0110 Unfortunately, there are lots of ways to get this register configuration wrong.
0111 Linux, it seems, has gone through most of them. For one, the register resets
0112 after S3 suspend: judging by existing code, this isn't the case for all vendor
0113 registers, and it's led to some fixes that improve behavior on cold boot but
0114 don't last after suspend. Other fixes have successfully switched the 1Ah input
0115 away from PC Beep but have failed to disable both loopback paths. On my
0116 machine, this means that the headphone input is amplified and looped back to
0117 the headphone output, which uses the exact same pins! As you might expect, this
0118 causes terrible headphone noise, the character of which is controlled by the
0119 1Ah boost control. (If you've seen instructions online to fix XPS 13 headphone
0120 noise by changing "Headphone Mic Boost" in ALSA, now you know why.)
0121 
0122 The information here has been obtained through black-box reverse engineering of
0123 the ALC256 codec's behavior and is not guaranteed to be correct. It likely
0124 also applies for the ALC255, ALC257, ALC235, and ALC236, since those codecs
0125 seem to be close relatives of the ALC256. (They all share one initialization
0126 function.) Additionally, other codecs like the ALC225 and ALC285 also have this
0127 register, judging by existing fixups in ``patch_realtek.c``, but specific
0128 data (e.g. node IDs, bit positions, pin mappings) for those codecs may differ
0129 from what I've described here.