patch_via.c 104 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430343134323433343434353436343734383439344034413442344334443445344634473448344934503451345234533454345534563457345834593460346134623463346434653466346734683469347034713472347334743475347634773478347934803481348234833484348534863487348834893490349134923493349434953496349734983499350035013502350335043505350635073508350935103511351235133514351535163517351835193520352135223523352435253526352735283529353035313532353335343535353635373538353935403541354235433544354535463547354835493550355135523553355435553556355735583559356035613562356335643565356635673568356935703571357235733574357535763577357835793580358135823583358435853586358735883589359035913592359335943595359635973598359936003601360236033604360536063607360836093610361136123613361436153616361736183619362036213622362336243625362636273628362936303631363236333634363536363637363836393640364136423643364436453646364736483649365036513652365336543655365636573658365936603661366236633664366536663667366836693670367136723673367436753676367736783679368036813682368336843685368636873688368936903691369236933694369536963697369836993700370137023703370437053706370737083709371037113712371337143715371637173718371937203721372237233724372537263727372837293730373137323733373437353736373737383739374037413742374337443745374637473748374937503751375237533754375537563757375837593760376137623763376437653766376737683769377037713772377337743775377637773778377937803781378237833784378537863787378837893790379137923793379437953796379737983799380038013802380338043805380638073808380938103811381238133814381538163817381838193820382138223823382438253826382738283829383038313832383338343835383638373838383938403841384238433844384538463847384838493850385138523853385438553856385738583859386038613862386338643865
  1. /*
  2. * Universal Interface for Intel High Definition Audio Codec
  3. *
  4. * HD audio interface patch for VIA VT1702/VT1708/VT1709 codec
  5. *
  6. * Copyright (c) 2006-2008 Lydia Wang <lydiawang@viatech.com>
  7. * Takashi Iwai <tiwai@suse.de>
  8. *
  9. * This driver is free software; you can redistribute it and/or modify
  10. * it under the terms of the GNU General Public License as published by
  11. * the Free Software Foundation; either version 2 of the License, or
  12. * (at your option) any later version.
  13. *
  14. * This driver is distributed in the hope that it will be useful,
  15. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  17. * GNU General Public License for more details.
  18. *
  19. * You should have received a copy of the GNU General Public License
  20. * along with this program; if not, write to the Free Software
  21. * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  22. */
  23. /* * * * * * * * * * * * * * Release History * * * * * * * * * * * * * * * * */
  24. /* */
  25. /* 2006-03-03 Lydia Wang Create the basic patch to support VT1708 codec */
  26. /* 2006-03-14 Lydia Wang Modify hard code for some pin widget nid */
  27. /* 2006-08-02 Lydia Wang Add support to VT1709 codec */
  28. /* 2006-09-08 Lydia Wang Fix internal loopback recording source select bug */
  29. /* 2007-09-12 Lydia Wang Add EAPD enable during driver initialization */
  30. /* 2007-09-17 Lydia Wang Add VT1708B codec support */
  31. /* 2007-11-14 Lydia Wang Add VT1708A codec HP and CD pin connect config */
  32. /* 2008-02-03 Lydia Wang Fix Rear channels and Back channels inverse issue */
  33. /* 2008-03-06 Lydia Wang Add VT1702 codec and VT1708S codec support */
  34. /* 2008-04-09 Lydia Wang Add mute front speaker when HP plugin */
  35. /* 2008-04-09 Lydia Wang Add Independent HP feature */
  36. /* 2008-05-28 Lydia Wang Add second S/PDIF Out support for VT1702 */
  37. /* 2008-09-15 Logan Li Add VT1708S Mic Boost workaround/backdoor */
  38. /* */
  39. /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
  40. #include <linux/init.h>
  41. #include <linux/delay.h>
  42. #include <linux/slab.h>
  43. #include <sound/core.h>
  44. #include <sound/asoundef.h>
  45. #include "hda_codec.h"
  46. #include "hda_local.h"
  47. /* amp values */
  48. #define AMP_VAL_IDX_SHIFT 19
  49. #define AMP_VAL_IDX_MASK (0x0f<<19)
  50. /* Pin Widget NID */
  51. #define VT1708_HP_NID 0x13
  52. #define VT1708_DIGOUT_NID 0x14
  53. #define VT1708_DIGIN_NID 0x16
  54. #define VT1708_DIGIN_PIN 0x26
  55. #define VT1708_HP_PIN_NID 0x20
  56. #define VT1708_CD_PIN_NID 0x24
  57. #define VT1709_HP_DAC_NID 0x28
  58. #define VT1709_DIGOUT_NID 0x13
  59. #define VT1709_DIGIN_NID 0x17
  60. #define VT1709_DIGIN_PIN 0x25
  61. #define VT1708B_HP_NID 0x25
  62. #define VT1708B_DIGOUT_NID 0x12
  63. #define VT1708B_DIGIN_NID 0x15
  64. #define VT1708B_DIGIN_PIN 0x21
  65. #define VT1708S_HP_NID 0x25
  66. #define VT1708S_DIGOUT_NID 0x12
  67. #define VT1702_HP_NID 0x17
  68. #define VT1702_DIGOUT_NID 0x11
  69. enum VIA_HDA_CODEC {
  70. UNKNOWN = -1,
  71. VT1708,
  72. VT1709_10CH,
  73. VT1709_6CH,
  74. VT1708B_8CH,
  75. VT1708B_4CH,
  76. VT1708S,
  77. VT1708BCE,
  78. VT1702,
  79. CODEC_TYPES,
  80. };
  81. static enum VIA_HDA_CODEC get_codec_type(struct hda_codec *codec)
  82. {
  83. u32 vendor_id = codec->vendor_id;
  84. u16 ven_id = vendor_id >> 16;
  85. u16 dev_id = vendor_id & 0xffff;
  86. enum VIA_HDA_CODEC codec_type;
  87. /* get codec type */
  88. if (ven_id != 0x1106)
  89. codec_type = UNKNOWN;
  90. else if (dev_id >= 0x1708 && dev_id <= 0x170b)
  91. codec_type = VT1708;
  92. else if (dev_id >= 0xe710 && dev_id <= 0xe713)
  93. codec_type = VT1709_10CH;
  94. else if (dev_id >= 0xe714 && dev_id <= 0xe717)
  95. codec_type = VT1709_6CH;
  96. else if (dev_id >= 0xe720 && dev_id <= 0xe723) {
  97. codec_type = VT1708B_8CH;
  98. if (snd_hda_param_read(codec, 0x16, AC_PAR_CONNLIST_LEN) == 0x7)
  99. codec_type = VT1708BCE;
  100. } else if (dev_id >= 0xe724 && dev_id <= 0xe727)
  101. codec_type = VT1708B_4CH;
  102. else if ((dev_id & 0xfff) == 0x397
  103. && (dev_id >> 12) < 8)
  104. codec_type = VT1708S;
  105. else if ((dev_id & 0xfff) == 0x398
  106. && (dev_id >> 12) < 8)
  107. codec_type = VT1702;
  108. else
  109. codec_type = UNKNOWN;
  110. return codec_type;
  111. };
  112. #define VIA_HP_EVENT 0x01
  113. #define VIA_GPIO_EVENT 0x02
  114. #define VIA_JACK_EVENT 0x04
  115. enum {
  116. VIA_CTL_WIDGET_VOL,
  117. VIA_CTL_WIDGET_MUTE,
  118. VIA_CTL_WIDGET_ANALOG_MUTE,
  119. };
  120. enum {
  121. AUTO_SEQ_FRONT = 0,
  122. AUTO_SEQ_SURROUND,
  123. AUTO_SEQ_CENLFE,
  124. AUTO_SEQ_SIDE
  125. };
  126. /* Some VT1708S based boards gets the micboost setting wrong, so we have
  127. * to apply some brute-force and re-write the TLV's by software. */
  128. static int mic_boost_tlv(struct snd_kcontrol *kcontrol, int op_flag,
  129. unsigned int size, unsigned int __user *_tlv)
  130. {
  131. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  132. hda_nid_t nid = get_amp_nid(kcontrol);
  133. if (get_codec_type(codec) == VT1708S
  134. && (nid == 0x1a || nid == 0x1e)) {
  135. if (size < 4 * sizeof(unsigned int))
  136. return -ENOMEM;
  137. if (put_user(1, _tlv)) /* SNDRV_CTL_TLVT_DB_SCALE */
  138. return -EFAULT;
  139. if (put_user(2 * sizeof(unsigned int), _tlv + 1))
  140. return -EFAULT;
  141. if (put_user(0, _tlv + 2)) /* offset = 0 */
  142. return -EFAULT;
  143. if (put_user(1000, _tlv + 3)) /* step size = 10 dB */
  144. return -EFAULT;
  145. }
  146. return 0;
  147. }
  148. static int mic_boost_volume_info(struct snd_kcontrol *kcontrol,
  149. struct snd_ctl_elem_info *uinfo)
  150. {
  151. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  152. hda_nid_t nid = get_amp_nid(kcontrol);
  153. if (get_codec_type(codec) == VT1708S
  154. && (nid == 0x1a || nid == 0x1e)) {
  155. uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
  156. uinfo->count = 2;
  157. uinfo->value.integer.min = 0;
  158. uinfo->value.integer.max = 3;
  159. }
  160. return 0;
  161. }
  162. static void analog_low_current_mode(struct hda_codec *codec, int stream_idle);
  163. static void set_jack_power_state(struct hda_codec *codec);
  164. static int analog_input_switch_put(struct snd_kcontrol *kcontrol,
  165. struct snd_ctl_elem_value *ucontrol)
  166. {
  167. int change = snd_hda_mixer_amp_switch_put(kcontrol, ucontrol);
  168. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  169. set_jack_power_state(codec);
  170. analog_low_current_mode(snd_kcontrol_chip(kcontrol), -1);
  171. return change;
  172. }
  173. /* modify .put = snd_hda_mixer_amp_switch_put */
  174. #define ANALOG_INPUT_MUTE \
  175. { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
  176. .name = NULL, \
  177. .index = 0, \
  178. .info = snd_hda_mixer_amp_switch_info, \
  179. .get = snd_hda_mixer_amp_switch_get, \
  180. .put = analog_input_switch_put, \
  181. .private_value = HDA_COMPOSE_AMP_VAL(0, 3, 0, 0) }
  182. static struct snd_kcontrol_new vt1708_control_templates[] = {
  183. HDA_CODEC_VOLUME(NULL, 0, 0, 0),
  184. HDA_CODEC_MUTE(NULL, 0, 0, 0),
  185. ANALOG_INPUT_MUTE,
  186. };
  187. struct via_spec {
  188. /* codec parameterization */
  189. struct snd_kcontrol_new *mixers[4];
  190. unsigned int num_mixers;
  191. struct hda_verb *init_verbs[5];
  192. unsigned int num_iverbs;
  193. char *stream_name_analog;
  194. struct hda_pcm_stream *stream_analog_playback;
  195. struct hda_pcm_stream *stream_analog_capture;
  196. char *stream_name_digital;
  197. struct hda_pcm_stream *stream_digital_playback;
  198. struct hda_pcm_stream *stream_digital_capture;
  199. /* playback */
  200. struct hda_multi_out multiout;
  201. hda_nid_t slave_dig_outs[2];
  202. /* capture */
  203. unsigned int num_adc_nids;
  204. hda_nid_t *adc_nids;
  205. hda_nid_t mux_nids[3];
  206. hda_nid_t dig_in_nid;
  207. hda_nid_t dig_in_pin;
  208. /* capture source */
  209. const struct hda_input_mux *input_mux;
  210. unsigned int cur_mux[3];
  211. /* PCM information */
  212. struct hda_pcm pcm_rec[3];
  213. /* dynamic controls, init_verbs and input_mux */
  214. struct auto_pin_cfg autocfg;
  215. struct snd_array kctls;
  216. struct hda_input_mux private_imux[2];
  217. hda_nid_t private_dac_nids[AUTO_CFG_MAX_OUTS];
  218. /* HP mode source */
  219. const struct hda_input_mux *hp_mux;
  220. unsigned int hp_independent_mode;
  221. unsigned int hp_independent_mode_index;
  222. unsigned int smart51_enabled;
  223. enum VIA_HDA_CODEC codec_type;
  224. #ifdef CONFIG_SND_HDA_POWER_SAVE
  225. struct hda_loopback_check loopback;
  226. #endif
  227. };
  228. static hda_nid_t vt1708_adc_nids[2] = {
  229. /* ADC1-2 */
  230. 0x15, 0x27
  231. };
  232. static hda_nid_t vt1709_adc_nids[3] = {
  233. /* ADC1-2 */
  234. 0x14, 0x15, 0x16
  235. };
  236. static hda_nid_t vt1708B_adc_nids[2] = {
  237. /* ADC1-2 */
  238. 0x13, 0x14
  239. };
  240. static hda_nid_t vt1708S_adc_nids[2] = {
  241. /* ADC1-2 */
  242. 0x13, 0x14
  243. };
  244. static hda_nid_t vt1702_adc_nids[3] = {
  245. /* ADC1-2 */
  246. 0x12, 0x20, 0x1F
  247. };
  248. /* add dynamic controls */
  249. static int via_add_control(struct via_spec *spec, int type, const char *name,
  250. unsigned long val)
  251. {
  252. struct snd_kcontrol_new *knew;
  253. snd_array_init(&spec->kctls, sizeof(*knew), 32);
  254. knew = snd_array_new(&spec->kctls);
  255. if (!knew)
  256. return -ENOMEM;
  257. *knew = vt1708_control_templates[type];
  258. knew->name = kstrdup(name, GFP_KERNEL);
  259. if (!knew->name)
  260. return -ENOMEM;
  261. knew->private_value = val;
  262. return 0;
  263. }
  264. static void via_free_kctls(struct hda_codec *codec)
  265. {
  266. struct via_spec *spec = codec->spec;
  267. if (spec->kctls.list) {
  268. struct snd_kcontrol_new *kctl = spec->kctls.list;
  269. int i;
  270. for (i = 0; i < spec->kctls.used; i++)
  271. kfree(kctl[i].name);
  272. }
  273. snd_array_free(&spec->kctls);
  274. }
  275. /* create input playback/capture controls for the given pin */
  276. static int via_new_analog_input(struct via_spec *spec, const char *ctlname,
  277. int idx, int mix_nid)
  278. {
  279. char name[32];
  280. int err;
  281. sprintf(name, "%s Playback Volume", ctlname);
  282. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  283. HDA_COMPOSE_AMP_VAL(mix_nid, 3, idx, HDA_INPUT));
  284. if (err < 0)
  285. return err;
  286. sprintf(name, "%s Playback Switch", ctlname);
  287. err = via_add_control(spec, VIA_CTL_WIDGET_ANALOG_MUTE, name,
  288. HDA_COMPOSE_AMP_VAL(mix_nid, 3, idx, HDA_INPUT));
  289. if (err < 0)
  290. return err;
  291. return 0;
  292. }
  293. static void via_auto_set_output_and_unmute(struct hda_codec *codec,
  294. hda_nid_t nid, int pin_type,
  295. int dac_idx)
  296. {
  297. /* set as output */
  298. snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_PIN_WIDGET_CONTROL,
  299. pin_type);
  300. snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_AMP_GAIN_MUTE,
  301. AMP_OUT_UNMUTE);
  302. if (snd_hda_query_pin_caps(codec, nid) & AC_PINCAP_EAPD)
  303. snd_hda_codec_write(codec, nid, 0,
  304. AC_VERB_SET_EAPD_BTLENABLE, 0x02);
  305. }
  306. static void via_auto_init_multi_out(struct hda_codec *codec)
  307. {
  308. struct via_spec *spec = codec->spec;
  309. int i;
  310. for (i = 0; i <= AUTO_SEQ_SIDE; i++) {
  311. hda_nid_t nid = spec->autocfg.line_out_pins[i];
  312. if (nid)
  313. via_auto_set_output_and_unmute(codec, nid, PIN_OUT, i);
  314. }
  315. }
  316. static void via_auto_init_hp_out(struct hda_codec *codec)
  317. {
  318. struct via_spec *spec = codec->spec;
  319. hda_nid_t pin;
  320. pin = spec->autocfg.hp_pins[0];
  321. if (pin) /* connect to front */
  322. via_auto_set_output_and_unmute(codec, pin, PIN_HP, 0);
  323. }
  324. static void via_auto_init_analog_input(struct hda_codec *codec)
  325. {
  326. struct via_spec *spec = codec->spec;
  327. int i;
  328. for (i = 0; i < AUTO_PIN_LAST; i++) {
  329. hda_nid_t nid = spec->autocfg.input_pins[i];
  330. snd_hda_codec_write(codec, nid, 0,
  331. AC_VERB_SET_PIN_WIDGET_CONTROL,
  332. (i <= AUTO_PIN_FRONT_MIC ?
  333. PIN_VREF50 : PIN_IN));
  334. }
  335. }
  336. static int is_smart51_pins(struct via_spec *spec, hda_nid_t pin);
  337. static void set_pin_power_state(struct hda_codec *codec, hda_nid_t nid,
  338. unsigned int *affected_parm)
  339. {
  340. unsigned parm;
  341. unsigned def_conf = snd_hda_codec_get_pincfg(codec, nid);
  342. unsigned no_presence = (def_conf & AC_DEFCFG_MISC)
  343. >> AC_DEFCFG_MISC_SHIFT
  344. & AC_DEFCFG_MISC_NO_PRESENCE; /* do not support pin sense */
  345. unsigned present = snd_hda_codec_read(codec, nid, 0,
  346. AC_VERB_GET_PIN_SENSE, 0) >> 31;
  347. struct via_spec *spec = codec->spec;
  348. if ((spec->smart51_enabled && is_smart51_pins(spec, nid))
  349. || ((no_presence || present)
  350. && get_defcfg_connect(def_conf) != AC_JACK_PORT_NONE)) {
  351. *affected_parm = AC_PWRST_D0; /* if it's connected */
  352. parm = AC_PWRST_D0;
  353. } else
  354. parm = AC_PWRST_D3;
  355. snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_POWER_STATE, parm);
  356. }
  357. static void set_jack_power_state(struct hda_codec *codec)
  358. {
  359. struct via_spec *spec = codec->spec;
  360. int imux_is_smixer;
  361. unsigned int parm;
  362. if (spec->codec_type == VT1702) {
  363. imux_is_smixer = snd_hda_codec_read(
  364. codec, 0x13, 0, AC_VERB_GET_CONNECT_SEL, 0x00) == 3;
  365. /* inputs */
  366. /* PW 1/2/5 (14h/15h/18h) */
  367. parm = AC_PWRST_D3;
  368. set_pin_power_state(codec, 0x14, &parm);
  369. set_pin_power_state(codec, 0x15, &parm);
  370. set_pin_power_state(codec, 0x18, &parm);
  371. if (imux_is_smixer)
  372. parm = AC_PWRST_D0; /* SW0 = stereo mixer (idx 3) */
  373. /* SW0 (13h), AIW 0/1/2 (12h/1fh/20h) */
  374. snd_hda_codec_write(codec, 0x13, 0, AC_VERB_SET_POWER_STATE,
  375. parm);
  376. snd_hda_codec_write(codec, 0x12, 0, AC_VERB_SET_POWER_STATE,
  377. parm);
  378. snd_hda_codec_write(codec, 0x1f, 0, AC_VERB_SET_POWER_STATE,
  379. parm);
  380. snd_hda_codec_write(codec, 0x20, 0, AC_VERB_SET_POWER_STATE,
  381. parm);
  382. /* outputs */
  383. /* PW 3/4 (16h/17h) */
  384. parm = AC_PWRST_D3;
  385. set_pin_power_state(codec, 0x16, &parm);
  386. set_pin_power_state(codec, 0x17, &parm);
  387. /* MW0 (1ah), AOW 0/1 (10h/1dh) */
  388. snd_hda_codec_write(codec, 0x1a, 0, AC_VERB_SET_POWER_STATE,
  389. imux_is_smixer ? AC_PWRST_D0 : parm);
  390. snd_hda_codec_write(codec, 0x10, 0, AC_VERB_SET_POWER_STATE,
  391. parm);
  392. snd_hda_codec_write(codec, 0x1d, 0, AC_VERB_SET_POWER_STATE,
  393. parm);
  394. } else if (spec->codec_type == VT1708B_8CH
  395. || spec->codec_type == VT1708B_4CH
  396. || spec->codec_type == VT1708S) {
  397. /* SW0 (17h) = stereo mixer */
  398. int is_8ch = spec->codec_type != VT1708B_4CH;
  399. imux_is_smixer = snd_hda_codec_read(
  400. codec, 0x17, 0, AC_VERB_GET_CONNECT_SEL, 0x00)
  401. == ((spec->codec_type == VT1708S) ? 5 : 0);
  402. /* inputs */
  403. /* PW 1/2/5 (1ah/1bh/1eh) */
  404. parm = AC_PWRST_D3;
  405. set_pin_power_state(codec, 0x1a, &parm);
  406. set_pin_power_state(codec, 0x1b, &parm);
  407. set_pin_power_state(codec, 0x1e, &parm);
  408. if (imux_is_smixer)
  409. parm = AC_PWRST_D0;
  410. /* SW0 (17h), AIW 0/1 (13h/14h) */
  411. snd_hda_codec_write(codec, 0x17, 0, AC_VERB_SET_POWER_STATE,
  412. parm);
  413. snd_hda_codec_write(codec, 0x13, 0, AC_VERB_SET_POWER_STATE,
  414. parm);
  415. snd_hda_codec_write(codec, 0x14, 0, AC_VERB_SET_POWER_STATE,
  416. parm);
  417. /* outputs */
  418. /* PW0 (19h), SW1 (18h), AOW1 (11h) */
  419. parm = AC_PWRST_D3;
  420. set_pin_power_state(codec, 0x19, &parm);
  421. snd_hda_codec_write(codec, 0x18, 0, AC_VERB_SET_POWER_STATE,
  422. parm);
  423. snd_hda_codec_write(codec, 0x11, 0, AC_VERB_SET_POWER_STATE,
  424. parm);
  425. /* PW6 (22h), SW2 (26h), AOW2 (24h) */
  426. if (is_8ch) {
  427. parm = AC_PWRST_D3;
  428. set_pin_power_state(codec, 0x22, &parm);
  429. snd_hda_codec_write(codec, 0x26, 0,
  430. AC_VERB_SET_POWER_STATE, parm);
  431. snd_hda_codec_write(codec, 0x24, 0,
  432. AC_VERB_SET_POWER_STATE, parm);
  433. }
  434. /* PW 3/4/7 (1ch/1dh/23h) */
  435. parm = AC_PWRST_D3;
  436. /* force to D0 for internal Speaker */
  437. set_pin_power_state(codec, 0x1c, &parm);
  438. set_pin_power_state(codec, 0x1d, &parm);
  439. if (is_8ch)
  440. set_pin_power_state(codec, 0x23, &parm);
  441. /* MW0 (16h), Sw3 (27h), AOW 0/3 (10h/25h) */
  442. snd_hda_codec_write(codec, 0x16, 0, AC_VERB_SET_POWER_STATE,
  443. imux_is_smixer ? AC_PWRST_D0 : parm);
  444. snd_hda_codec_write(codec, 0x10, 0, AC_VERB_SET_POWER_STATE,
  445. parm);
  446. if (is_8ch) {
  447. snd_hda_codec_write(codec, 0x25, 0,
  448. AC_VERB_SET_POWER_STATE, parm);
  449. snd_hda_codec_write(codec, 0x27, 0,
  450. AC_VERB_SET_POWER_STATE, parm);
  451. }
  452. }
  453. }
  454. /*
  455. * input MUX handling
  456. */
  457. static int via_mux_enum_info(struct snd_kcontrol *kcontrol,
  458. struct snd_ctl_elem_info *uinfo)
  459. {
  460. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  461. struct via_spec *spec = codec->spec;
  462. return snd_hda_input_mux_info(spec->input_mux, uinfo);
  463. }
  464. static int via_mux_enum_get(struct snd_kcontrol *kcontrol,
  465. struct snd_ctl_elem_value *ucontrol)
  466. {
  467. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  468. struct via_spec *spec = codec->spec;
  469. unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
  470. ucontrol->value.enumerated.item[0] = spec->cur_mux[adc_idx];
  471. return 0;
  472. }
  473. static int via_mux_enum_put(struct snd_kcontrol *kcontrol,
  474. struct snd_ctl_elem_value *ucontrol)
  475. {
  476. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  477. struct via_spec *spec = codec->spec;
  478. unsigned int adc_idx = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
  479. if (!spec->mux_nids[adc_idx])
  480. return -EINVAL;
  481. /* switch to D0 beofre change index */
  482. if (snd_hda_codec_read(codec, spec->mux_nids[adc_idx], 0,
  483. AC_VERB_GET_POWER_STATE, 0x00) != AC_PWRST_D0)
  484. snd_hda_codec_write(codec, spec->mux_nids[adc_idx], 0,
  485. AC_VERB_SET_POWER_STATE, AC_PWRST_D0);
  486. /* update jack power state */
  487. set_jack_power_state(codec);
  488. return snd_hda_input_mux_put(codec, spec->input_mux, ucontrol,
  489. spec->mux_nids[adc_idx],
  490. &spec->cur_mux[adc_idx]);
  491. }
  492. static int via_independent_hp_info(struct snd_kcontrol *kcontrol,
  493. struct snd_ctl_elem_info *uinfo)
  494. {
  495. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  496. struct via_spec *spec = codec->spec;
  497. return snd_hda_input_mux_info(spec->hp_mux, uinfo);
  498. }
  499. static int via_independent_hp_get(struct snd_kcontrol *kcontrol,
  500. struct snd_ctl_elem_value *ucontrol)
  501. {
  502. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  503. struct via_spec *spec = codec->spec;
  504. hda_nid_t nid = spec->autocfg.hp_pins[0];
  505. unsigned int pinsel = snd_hda_codec_read(codec, nid, 0,
  506. AC_VERB_GET_CONNECT_SEL,
  507. 0x00);
  508. ucontrol->value.enumerated.item[0] = pinsel;
  509. return 0;
  510. }
  511. static void activate_ctl(struct hda_codec *codec, const char *name, int active)
  512. {
  513. struct snd_kcontrol *ctl = snd_hda_find_mixer_ctl(codec, name);
  514. if (ctl) {
  515. ctl->vd[0].access &= ~SNDRV_CTL_ELEM_ACCESS_INACTIVE;
  516. ctl->vd[0].access |= active
  517. ? 0 : SNDRV_CTL_ELEM_ACCESS_INACTIVE;
  518. snd_ctl_notify(codec->bus->card,
  519. SNDRV_CTL_EVENT_MASK_VALUE, &ctl->id);
  520. }
  521. }
  522. static int update_side_mute_status(struct hda_codec *codec)
  523. {
  524. /* mute side channel */
  525. struct via_spec *spec = codec->spec;
  526. unsigned int parm = spec->hp_independent_mode
  527. ? AMP_OUT_MUTE : AMP_OUT_UNMUTE;
  528. hda_nid_t sw3;
  529. switch (spec->codec_type) {
  530. case VT1708:
  531. sw3 = 0x1b;
  532. break;
  533. case VT1709_10CH:
  534. sw3 = 0x29;
  535. break;
  536. case VT1708B_8CH:
  537. case VT1708S:
  538. sw3 = 0x27;
  539. break;
  540. default:
  541. sw3 = 0;
  542. break;
  543. }
  544. if (sw3)
  545. snd_hda_codec_write(codec, sw3, 0, AC_VERB_SET_AMP_GAIN_MUTE,
  546. parm);
  547. return 0;
  548. }
  549. static int via_independent_hp_put(struct snd_kcontrol *kcontrol,
  550. struct snd_ctl_elem_value *ucontrol)
  551. {
  552. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  553. struct via_spec *spec = codec->spec;
  554. hda_nid_t nid = spec->autocfg.hp_pins[0];
  555. unsigned int pinsel = ucontrol->value.enumerated.item[0];
  556. /* Get Independent Mode index of headphone pin widget */
  557. spec->hp_independent_mode = spec->hp_independent_mode_index == pinsel
  558. ? 1 : 0;
  559. snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_CONNECT_SEL, pinsel);
  560. if (spec->multiout.hp_nid && spec->multiout.hp_nid
  561. != spec->multiout.dac_nids[HDA_FRONT])
  562. snd_hda_codec_setup_stream(codec, spec->multiout.hp_nid,
  563. 0, 0, 0);
  564. update_side_mute_status(codec);
  565. /* update HP volume/swtich active state */
  566. if (spec->codec_type == VT1708S
  567. || spec->codec_type == VT1702) {
  568. activate_ctl(codec, "Headphone Playback Volume",
  569. spec->hp_independent_mode);
  570. activate_ctl(codec, "Headphone Playback Switch",
  571. spec->hp_independent_mode);
  572. }
  573. return 0;
  574. }
  575. static struct snd_kcontrol_new via_hp_mixer[] = {
  576. {
  577. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  578. .name = "Independent HP",
  579. .count = 1,
  580. .info = via_independent_hp_info,
  581. .get = via_independent_hp_get,
  582. .put = via_independent_hp_put,
  583. },
  584. { } /* end */
  585. };
  586. static void notify_aa_path_ctls(struct hda_codec *codec)
  587. {
  588. int i;
  589. struct snd_ctl_elem_id id;
  590. const char *labels[] = {"Mic", "Front Mic", "Line"};
  591. memset(&id, 0, sizeof(id));
  592. id.iface = SNDRV_CTL_ELEM_IFACE_MIXER;
  593. for (i = 0; i < ARRAY_SIZE(labels); i++) {
  594. sprintf(id.name, "%s Playback Volume", labels[i]);
  595. snd_ctl_notify(codec->bus->card, SNDRV_CTL_EVENT_MASK_VALUE,
  596. &id);
  597. }
  598. }
  599. static void mute_aa_path(struct hda_codec *codec, int mute)
  600. {
  601. struct via_spec *spec = codec->spec;
  602. hda_nid_t nid_mixer;
  603. int start_idx;
  604. int end_idx;
  605. int i;
  606. /* get nid of MW0 and start & end index */
  607. switch (spec->codec_type) {
  608. case VT1708:
  609. nid_mixer = 0x17;
  610. start_idx = 2;
  611. end_idx = 4;
  612. break;
  613. case VT1709_10CH:
  614. case VT1709_6CH:
  615. nid_mixer = 0x18;
  616. start_idx = 2;
  617. end_idx = 4;
  618. break;
  619. case VT1708B_8CH:
  620. case VT1708B_4CH:
  621. case VT1708S:
  622. nid_mixer = 0x16;
  623. start_idx = 2;
  624. end_idx = 4;
  625. break;
  626. default:
  627. return;
  628. }
  629. /* check AA path's mute status */
  630. for (i = start_idx; i <= end_idx; i++) {
  631. int val = mute ? HDA_AMP_MUTE : HDA_AMP_UNMUTE;
  632. snd_hda_codec_amp_stereo(codec, nid_mixer, HDA_INPUT, i,
  633. HDA_AMP_MUTE, val);
  634. }
  635. }
  636. static int is_smart51_pins(struct via_spec *spec, hda_nid_t pin)
  637. {
  638. int res = 0;
  639. int index;
  640. for (index = AUTO_PIN_MIC; index < AUTO_PIN_FRONT_LINE; index++) {
  641. if (pin == spec->autocfg.input_pins[index]) {
  642. res = 1;
  643. break;
  644. }
  645. }
  646. return res;
  647. }
  648. static int via_smart51_info(struct snd_kcontrol *kcontrol,
  649. struct snd_ctl_elem_info *uinfo)
  650. {
  651. uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN;
  652. uinfo->count = 1;
  653. uinfo->value.integer.min = 0;
  654. uinfo->value.integer.max = 1;
  655. return 0;
  656. }
  657. static int via_smart51_get(struct snd_kcontrol *kcontrol,
  658. struct snd_ctl_elem_value *ucontrol)
  659. {
  660. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  661. struct via_spec *spec = codec->spec;
  662. int index[] = { AUTO_PIN_MIC, AUTO_PIN_FRONT_MIC, AUTO_PIN_LINE };
  663. int on = 1;
  664. int i;
  665. for (i = 0; i < ARRAY_SIZE(index); i++) {
  666. hda_nid_t nid = spec->autocfg.input_pins[index[i]];
  667. if (nid) {
  668. int ctl =
  669. snd_hda_codec_read(codec, nid, 0,
  670. AC_VERB_GET_PIN_WIDGET_CONTROL,
  671. 0);
  672. if (i == AUTO_PIN_FRONT_MIC
  673. && spec->hp_independent_mode)
  674. continue; /* ignore FMic for independent HP */
  675. if (ctl & AC_PINCTL_IN_EN
  676. && !(ctl & AC_PINCTL_OUT_EN))
  677. on = 0;
  678. }
  679. }
  680. *ucontrol->value.integer.value = on;
  681. return 0;
  682. }
  683. static int via_smart51_put(struct snd_kcontrol *kcontrol,
  684. struct snd_ctl_elem_value *ucontrol)
  685. {
  686. struct hda_codec *codec = snd_kcontrol_chip(kcontrol);
  687. struct via_spec *spec = codec->spec;
  688. int out_in = *ucontrol->value.integer.value
  689. ? AC_PINCTL_OUT_EN : AC_PINCTL_IN_EN;
  690. int index[] = { AUTO_PIN_MIC, AUTO_PIN_FRONT_MIC, AUTO_PIN_LINE };
  691. int i;
  692. for (i = 0; i < ARRAY_SIZE(index); i++) {
  693. hda_nid_t nid = spec->autocfg.input_pins[index[i]];
  694. if (i == AUTO_PIN_FRONT_MIC
  695. && spec->hp_independent_mode)
  696. continue; /* don't retask FMic for independent HP */
  697. if (nid) {
  698. unsigned int parm = snd_hda_codec_read(
  699. codec, nid, 0,
  700. AC_VERB_GET_PIN_WIDGET_CONTROL, 0);
  701. parm &= ~(AC_PINCTL_IN_EN | AC_PINCTL_OUT_EN);
  702. parm |= out_in;
  703. snd_hda_codec_write(codec, nid, 0,
  704. AC_VERB_SET_PIN_WIDGET_CONTROL,
  705. parm);
  706. if (out_in == AC_PINCTL_OUT_EN) {
  707. mute_aa_path(codec, 1);
  708. notify_aa_path_ctls(codec);
  709. }
  710. }
  711. if (i == AUTO_PIN_FRONT_MIC) {
  712. if (spec->codec_type == VT1708S) {
  713. /* input = index 1 (AOW3) */
  714. snd_hda_codec_write(
  715. codec, nid, 0,
  716. AC_VERB_SET_CONNECT_SEL, 1);
  717. snd_hda_codec_amp_stereo(
  718. codec, nid, HDA_OUTPUT,
  719. 0, HDA_AMP_MUTE, HDA_AMP_UNMUTE);
  720. }
  721. }
  722. }
  723. spec->smart51_enabled = *ucontrol->value.integer.value;
  724. set_jack_power_state(codec);
  725. return 1;
  726. }
  727. static struct snd_kcontrol_new via_smart51_mixer[] = {
  728. {
  729. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  730. .name = "Smart 5.1",
  731. .count = 1,
  732. .info = via_smart51_info,
  733. .get = via_smart51_get,
  734. .put = via_smart51_put,
  735. },
  736. {} /* end */
  737. };
  738. /* capture mixer elements */
  739. static struct snd_kcontrol_new vt1708_capture_mixer[] = {
  740. HDA_CODEC_VOLUME("Capture Volume", 0x15, 0x0, HDA_INPUT),
  741. HDA_CODEC_MUTE("Capture Switch", 0x15, 0x0, HDA_INPUT),
  742. HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x27, 0x0, HDA_INPUT),
  743. HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x27, 0x0, HDA_INPUT),
  744. {
  745. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  746. /* The multiple "Capture Source" controls confuse alsamixer
  747. * So call somewhat different..
  748. */
  749. /* .name = "Capture Source", */
  750. .name = "Input Source",
  751. .count = 1,
  752. .info = via_mux_enum_info,
  753. .get = via_mux_enum_get,
  754. .put = via_mux_enum_put,
  755. },
  756. { } /* end */
  757. };
  758. /* check AA path's mute statue */
  759. static int is_aa_path_mute(struct hda_codec *codec)
  760. {
  761. int mute = 1;
  762. hda_nid_t nid_mixer;
  763. int start_idx;
  764. int end_idx;
  765. int i;
  766. struct via_spec *spec = codec->spec;
  767. /* get nid of MW0 and start & end index */
  768. switch (spec->codec_type) {
  769. case VT1708B_8CH:
  770. case VT1708B_4CH:
  771. case VT1708S:
  772. nid_mixer = 0x16;
  773. start_idx = 2;
  774. end_idx = 4;
  775. break;
  776. case VT1702:
  777. nid_mixer = 0x1a;
  778. start_idx = 1;
  779. end_idx = 3;
  780. break;
  781. default:
  782. return 0;
  783. }
  784. /* check AA path's mute status */
  785. for (i = start_idx; i <= end_idx; i++) {
  786. unsigned int con_list = snd_hda_codec_read(
  787. codec, nid_mixer, 0, AC_VERB_GET_CONNECT_LIST, i/4*4);
  788. int shift = 8 * (i % 4);
  789. hda_nid_t nid_pin = (con_list & (0xff << shift)) >> shift;
  790. unsigned int defconf = snd_hda_codec_get_pincfg(codec, nid_pin);
  791. if (get_defcfg_connect(defconf) == AC_JACK_PORT_COMPLEX) {
  792. /* check mute status while the pin is connected */
  793. int mute_l = snd_hda_codec_amp_read(codec, nid_mixer, 0,
  794. HDA_INPUT, i) >> 7;
  795. int mute_r = snd_hda_codec_amp_read(codec, nid_mixer, 1,
  796. HDA_INPUT, i) >> 7;
  797. if (!mute_l || !mute_r) {
  798. mute = 0;
  799. break;
  800. }
  801. }
  802. }
  803. return mute;
  804. }
  805. /* enter/exit analog low-current mode */
  806. static void analog_low_current_mode(struct hda_codec *codec, int stream_idle)
  807. {
  808. struct via_spec *spec = codec->spec;
  809. static int saved_stream_idle = 1; /* saved stream idle status */
  810. int enable = is_aa_path_mute(codec);
  811. unsigned int verb = 0;
  812. unsigned int parm = 0;
  813. if (stream_idle == -1) /* stream status did not change */
  814. enable = enable && saved_stream_idle;
  815. else {
  816. enable = enable && stream_idle;
  817. saved_stream_idle = stream_idle;
  818. }
  819. /* decide low current mode's verb & parameter */
  820. switch (spec->codec_type) {
  821. case VT1708B_8CH:
  822. case VT1708B_4CH:
  823. verb = 0xf70;
  824. parm = enable ? 0x02 : 0x00; /* 0x02: 2/3x, 0x00: 1x */
  825. break;
  826. case VT1708S:
  827. verb = 0xf73;
  828. parm = enable ? 0x51 : 0xe1; /* 0x51: 4/28x, 0xe1: 1x */
  829. break;
  830. case VT1702:
  831. verb = 0xf73;
  832. parm = enable ? 0x01 : 0x1d; /* 0x01: 4/40x, 0x1d: 1x */
  833. break;
  834. default:
  835. return; /* other codecs are not supported */
  836. }
  837. /* send verb */
  838. snd_hda_codec_write(codec, codec->afg, 0, verb, parm);
  839. }
  840. /*
  841. * generic initialization of ADC, input mixers and output mixers
  842. */
  843. static struct hda_verb vt1708_volume_init_verbs[] = {
  844. /*
  845. * Unmute ADC0-1 and set the default input to mic-in
  846. */
  847. {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  848. {0x27, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  849. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
  850. * mixer widget
  851. */
  852. /* Amp Indices: CD = 1, Mic1 = 2, Line = 3, Mic2 = 4 */
  853. {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  854. {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  855. {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  856. {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  857. {0x17, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
  858. /*
  859. * Set up output mixers (0x19 - 0x1b)
  860. */
  861. /* set vol=0 to output mixers */
  862. {0x19, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  863. {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  864. {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  865. /* Setup default input to PW4 */
  866. {0x20, AC_VERB_SET_CONNECT_SEL, 0x1},
  867. /* PW9 Output enable */
  868. {0x25, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  869. { }
  870. };
  871. static int via_playback_pcm_open(struct hda_pcm_stream *hinfo,
  872. struct hda_codec *codec,
  873. struct snd_pcm_substream *substream)
  874. {
  875. struct via_spec *spec = codec->spec;
  876. int idle = substream->pstr->substream_opened == 1
  877. && substream->ref_count == 0;
  878. analog_low_current_mode(codec, idle);
  879. return snd_hda_multi_out_analog_open(codec, &spec->multiout, substream,
  880. hinfo);
  881. }
  882. static int via_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
  883. struct hda_codec *codec,
  884. unsigned int stream_tag,
  885. unsigned int format,
  886. struct snd_pcm_substream *substream)
  887. {
  888. struct via_spec *spec = codec->spec;
  889. return snd_hda_multi_out_analog_prepare(codec, &spec->multiout,
  890. stream_tag, format, substream);
  891. }
  892. static int via_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
  893. struct hda_codec *codec,
  894. struct snd_pcm_substream *substream)
  895. {
  896. struct via_spec *spec = codec->spec;
  897. return snd_hda_multi_out_analog_cleanup(codec, &spec->multiout);
  898. }
  899. static void playback_multi_pcm_prep_0(struct hda_codec *codec,
  900. unsigned int stream_tag,
  901. unsigned int format,
  902. struct snd_pcm_substream *substream)
  903. {
  904. struct via_spec *spec = codec->spec;
  905. struct hda_multi_out *mout = &spec->multiout;
  906. hda_nid_t *nids = mout->dac_nids;
  907. int chs = substream->runtime->channels;
  908. int i;
  909. mutex_lock(&codec->spdif_mutex);
  910. if (mout->dig_out_nid && mout->dig_out_used != HDA_DIG_EXCLUSIVE) {
  911. if (chs == 2 &&
  912. snd_hda_is_supported_format(codec, mout->dig_out_nid,
  913. format) &&
  914. !(codec->spdif_status & IEC958_AES0_NONAUDIO)) {
  915. mout->dig_out_used = HDA_DIG_ANALOG_DUP;
  916. /* turn off SPDIF once; otherwise the IEC958 bits won't
  917. * be updated */
  918. if (codec->spdif_ctls & AC_DIG1_ENABLE)
  919. snd_hda_codec_write(codec, mout->dig_out_nid, 0,
  920. AC_VERB_SET_DIGI_CONVERT_1,
  921. codec->spdif_ctls &
  922. ~AC_DIG1_ENABLE & 0xff);
  923. snd_hda_codec_setup_stream(codec, mout->dig_out_nid,
  924. stream_tag, 0, format);
  925. /* turn on again (if needed) */
  926. if (codec->spdif_ctls & AC_DIG1_ENABLE)
  927. snd_hda_codec_write(codec, mout->dig_out_nid, 0,
  928. AC_VERB_SET_DIGI_CONVERT_1,
  929. codec->spdif_ctls & 0xff);
  930. } else {
  931. mout->dig_out_used = 0;
  932. snd_hda_codec_setup_stream(codec, mout->dig_out_nid,
  933. 0, 0, 0);
  934. }
  935. }
  936. mutex_unlock(&codec->spdif_mutex);
  937. /* front */
  938. snd_hda_codec_setup_stream(codec, nids[HDA_FRONT], stream_tag,
  939. 0, format);
  940. if (mout->hp_nid && mout->hp_nid != nids[HDA_FRONT] &&
  941. !spec->hp_independent_mode)
  942. /* headphone out will just decode front left/right (stereo) */
  943. snd_hda_codec_setup_stream(codec, mout->hp_nid, stream_tag,
  944. 0, format);
  945. /* extra outputs copied from front */
  946. for (i = 0; i < ARRAY_SIZE(mout->extra_out_nid); i++)
  947. if (mout->extra_out_nid[i])
  948. snd_hda_codec_setup_stream(codec,
  949. mout->extra_out_nid[i],
  950. stream_tag, 0, format);
  951. /* surrounds */
  952. for (i = 1; i < mout->num_dacs; i++) {
  953. if (chs >= (i + 1) * 2) /* independent out */
  954. snd_hda_codec_setup_stream(codec, nids[i], stream_tag,
  955. i * 2, format);
  956. else /* copy front */
  957. snd_hda_codec_setup_stream(codec, nids[i], stream_tag,
  958. 0, format);
  959. }
  960. }
  961. static int via_playback_multi_pcm_prepare(struct hda_pcm_stream *hinfo,
  962. struct hda_codec *codec,
  963. unsigned int stream_tag,
  964. unsigned int format,
  965. struct snd_pcm_substream *substream)
  966. {
  967. struct via_spec *spec = codec->spec;
  968. struct hda_multi_out *mout = &spec->multiout;
  969. hda_nid_t *nids = mout->dac_nids;
  970. if (substream->number == 0)
  971. playback_multi_pcm_prep_0(codec, stream_tag, format,
  972. substream);
  973. else {
  974. if (mout->hp_nid && mout->hp_nid != nids[HDA_FRONT] &&
  975. spec->hp_independent_mode)
  976. snd_hda_codec_setup_stream(codec, mout->hp_nid,
  977. stream_tag, 0, format);
  978. }
  979. return 0;
  980. }
  981. static int via_playback_multi_pcm_cleanup(struct hda_pcm_stream *hinfo,
  982. struct hda_codec *codec,
  983. struct snd_pcm_substream *substream)
  984. {
  985. struct via_spec *spec = codec->spec;
  986. struct hda_multi_out *mout = &spec->multiout;
  987. hda_nid_t *nids = mout->dac_nids;
  988. int i;
  989. if (substream->number == 0) {
  990. for (i = 0; i < mout->num_dacs; i++)
  991. snd_hda_codec_setup_stream(codec, nids[i], 0, 0, 0);
  992. if (mout->hp_nid && !spec->hp_independent_mode)
  993. snd_hda_codec_setup_stream(codec, mout->hp_nid,
  994. 0, 0, 0);
  995. for (i = 0; i < ARRAY_SIZE(mout->extra_out_nid); i++)
  996. if (mout->extra_out_nid[i])
  997. snd_hda_codec_setup_stream(codec,
  998. mout->extra_out_nid[i],
  999. 0, 0, 0);
  1000. mutex_lock(&codec->spdif_mutex);
  1001. if (mout->dig_out_nid &&
  1002. mout->dig_out_used == HDA_DIG_ANALOG_DUP) {
  1003. snd_hda_codec_setup_stream(codec, mout->dig_out_nid,
  1004. 0, 0, 0);
  1005. mout->dig_out_used = 0;
  1006. }
  1007. mutex_unlock(&codec->spdif_mutex);
  1008. } else {
  1009. if (mout->hp_nid && mout->hp_nid != nids[HDA_FRONT] &&
  1010. spec->hp_independent_mode)
  1011. snd_hda_codec_setup_stream(codec, mout->hp_nid,
  1012. 0, 0, 0);
  1013. }
  1014. return 0;
  1015. }
  1016. /*
  1017. * Digital out
  1018. */
  1019. static int via_dig_playback_pcm_open(struct hda_pcm_stream *hinfo,
  1020. struct hda_codec *codec,
  1021. struct snd_pcm_substream *substream)
  1022. {
  1023. struct via_spec *spec = codec->spec;
  1024. return snd_hda_multi_out_dig_open(codec, &spec->multiout);
  1025. }
  1026. static int via_dig_playback_pcm_close(struct hda_pcm_stream *hinfo,
  1027. struct hda_codec *codec,
  1028. struct snd_pcm_substream *substream)
  1029. {
  1030. struct via_spec *spec = codec->spec;
  1031. return snd_hda_multi_out_dig_close(codec, &spec->multiout);
  1032. }
  1033. static int via_dig_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
  1034. struct hda_codec *codec,
  1035. unsigned int stream_tag,
  1036. unsigned int format,
  1037. struct snd_pcm_substream *substream)
  1038. {
  1039. struct via_spec *spec = codec->spec;
  1040. return snd_hda_multi_out_dig_prepare(codec, &spec->multiout,
  1041. stream_tag, format, substream);
  1042. }
  1043. static int via_dig_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
  1044. struct hda_codec *codec,
  1045. struct snd_pcm_substream *substream)
  1046. {
  1047. struct via_spec *spec = codec->spec;
  1048. snd_hda_multi_out_dig_cleanup(codec, &spec->multiout);
  1049. return 0;
  1050. }
  1051. /*
  1052. * Analog capture
  1053. */
  1054. static int via_capture_pcm_prepare(struct hda_pcm_stream *hinfo,
  1055. struct hda_codec *codec,
  1056. unsigned int stream_tag,
  1057. unsigned int format,
  1058. struct snd_pcm_substream *substream)
  1059. {
  1060. struct via_spec *spec = codec->spec;
  1061. snd_hda_codec_setup_stream(codec, spec->adc_nids[substream->number],
  1062. stream_tag, 0, format);
  1063. return 0;
  1064. }
  1065. static int via_capture_pcm_cleanup(struct hda_pcm_stream *hinfo,
  1066. struct hda_codec *codec,
  1067. struct snd_pcm_substream *substream)
  1068. {
  1069. struct via_spec *spec = codec->spec;
  1070. snd_hda_codec_cleanup_stream(codec, spec->adc_nids[substream->number]);
  1071. return 0;
  1072. }
  1073. static struct hda_pcm_stream vt1708_pcm_analog_playback = {
  1074. .substreams = 2,
  1075. .channels_min = 2,
  1076. .channels_max = 8,
  1077. .nid = 0x10, /* NID to query formats and rates */
  1078. .ops = {
  1079. .open = via_playback_pcm_open,
  1080. .prepare = via_playback_multi_pcm_prepare,
  1081. .cleanup = via_playback_multi_pcm_cleanup
  1082. },
  1083. };
  1084. static struct hda_pcm_stream vt1708_pcm_analog_s16_playback = {
  1085. .substreams = 1,
  1086. .channels_min = 2,
  1087. .channels_max = 8,
  1088. .nid = 0x10, /* NID to query formats and rates */
  1089. /* We got noisy outputs on the right channel on VT1708 when
  1090. * 24bit samples are used. Until any workaround is found,
  1091. * disable the 24bit format, so far.
  1092. */
  1093. .formats = SNDRV_PCM_FMTBIT_S16_LE,
  1094. .ops = {
  1095. .open = via_playback_pcm_open,
  1096. .prepare = via_playback_pcm_prepare,
  1097. .cleanup = via_playback_pcm_cleanup
  1098. },
  1099. };
  1100. static struct hda_pcm_stream vt1708_pcm_analog_capture = {
  1101. .substreams = 2,
  1102. .channels_min = 2,
  1103. .channels_max = 2,
  1104. .nid = 0x15, /* NID to query formats and rates */
  1105. .ops = {
  1106. .prepare = via_capture_pcm_prepare,
  1107. .cleanup = via_capture_pcm_cleanup
  1108. },
  1109. };
  1110. static struct hda_pcm_stream vt1708_pcm_digital_playback = {
  1111. .substreams = 1,
  1112. .channels_min = 2,
  1113. .channels_max = 2,
  1114. /* NID is set in via_build_pcms */
  1115. .ops = {
  1116. .open = via_dig_playback_pcm_open,
  1117. .close = via_dig_playback_pcm_close,
  1118. .prepare = via_dig_playback_pcm_prepare,
  1119. .cleanup = via_dig_playback_pcm_cleanup
  1120. },
  1121. };
  1122. static struct hda_pcm_stream vt1708_pcm_digital_capture = {
  1123. .substreams = 1,
  1124. .channels_min = 2,
  1125. .channels_max = 2,
  1126. };
  1127. static int via_build_controls(struct hda_codec *codec)
  1128. {
  1129. struct via_spec *spec = codec->spec;
  1130. int err;
  1131. int i;
  1132. for (i = 0; i < spec->num_mixers; i++) {
  1133. err = snd_hda_add_new_ctls(codec, spec->mixers[i]);
  1134. if (err < 0)
  1135. return err;
  1136. }
  1137. if (spec->multiout.dig_out_nid) {
  1138. err = snd_hda_create_spdif_out_ctls(codec,
  1139. spec->multiout.dig_out_nid);
  1140. if (err < 0)
  1141. return err;
  1142. err = snd_hda_create_spdif_share_sw(codec,
  1143. &spec->multiout);
  1144. if (err < 0)
  1145. return err;
  1146. spec->multiout.share_spdif = 1;
  1147. }
  1148. if (spec->dig_in_nid) {
  1149. err = snd_hda_create_spdif_in_ctls(codec, spec->dig_in_nid);
  1150. if (err < 0)
  1151. return err;
  1152. }
  1153. /* init power states */
  1154. set_jack_power_state(codec);
  1155. analog_low_current_mode(codec, 1);
  1156. via_free_kctls(codec); /* no longer needed */
  1157. return 0;
  1158. }
  1159. static int via_build_pcms(struct hda_codec *codec)
  1160. {
  1161. struct via_spec *spec = codec->spec;
  1162. struct hda_pcm *info = spec->pcm_rec;
  1163. codec->num_pcms = 1;
  1164. codec->pcm_info = info;
  1165. info->name = spec->stream_name_analog;
  1166. info->stream[SNDRV_PCM_STREAM_PLAYBACK] = *(spec->stream_analog_playback);
  1167. info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid = spec->multiout.dac_nids[0];
  1168. info->stream[SNDRV_PCM_STREAM_CAPTURE] = *(spec->stream_analog_capture);
  1169. info->stream[SNDRV_PCM_STREAM_CAPTURE].nid = spec->adc_nids[0];
  1170. info->stream[SNDRV_PCM_STREAM_PLAYBACK].channels_max =
  1171. spec->multiout.max_channels;
  1172. if (spec->multiout.dig_out_nid || spec->dig_in_nid) {
  1173. codec->num_pcms++;
  1174. info++;
  1175. info->name = spec->stream_name_digital;
  1176. info->pcm_type = HDA_PCM_TYPE_SPDIF;
  1177. if (spec->multiout.dig_out_nid) {
  1178. info->stream[SNDRV_PCM_STREAM_PLAYBACK] =
  1179. *(spec->stream_digital_playback);
  1180. info->stream[SNDRV_PCM_STREAM_PLAYBACK].nid =
  1181. spec->multiout.dig_out_nid;
  1182. }
  1183. if (spec->dig_in_nid) {
  1184. info->stream[SNDRV_PCM_STREAM_CAPTURE] =
  1185. *(spec->stream_digital_capture);
  1186. info->stream[SNDRV_PCM_STREAM_CAPTURE].nid =
  1187. spec->dig_in_nid;
  1188. }
  1189. }
  1190. return 0;
  1191. }
  1192. static void via_free(struct hda_codec *codec)
  1193. {
  1194. struct via_spec *spec = codec->spec;
  1195. if (!spec)
  1196. return;
  1197. via_free_kctls(codec);
  1198. kfree(codec->spec);
  1199. }
  1200. /* mute internal speaker if HP is plugged */
  1201. static void via_hp_automute(struct hda_codec *codec)
  1202. {
  1203. unsigned int present;
  1204. struct via_spec *spec = codec->spec;
  1205. present = snd_hda_codec_read(codec, spec->autocfg.hp_pins[0], 0,
  1206. AC_VERB_GET_PIN_SENSE, 0) & 0x80000000;
  1207. snd_hda_codec_amp_stereo(codec, spec->autocfg.line_out_pins[0],
  1208. HDA_OUTPUT, 0, HDA_AMP_MUTE,
  1209. present ? HDA_AMP_MUTE : 0);
  1210. }
  1211. static void via_gpio_control(struct hda_codec *codec)
  1212. {
  1213. unsigned int gpio_data;
  1214. unsigned int vol_counter;
  1215. unsigned int vol;
  1216. unsigned int master_vol;
  1217. struct via_spec *spec = codec->spec;
  1218. gpio_data = snd_hda_codec_read(codec, codec->afg, 0,
  1219. AC_VERB_GET_GPIO_DATA, 0) & 0x03;
  1220. vol_counter = (snd_hda_codec_read(codec, codec->afg, 0,
  1221. 0xF84, 0) & 0x3F0000) >> 16;
  1222. vol = vol_counter & 0x1F;
  1223. master_vol = snd_hda_codec_read(codec, 0x1A, 0,
  1224. AC_VERB_GET_AMP_GAIN_MUTE,
  1225. AC_AMP_GET_INPUT);
  1226. if (gpio_data == 0x02) {
  1227. /* unmute line out */
  1228. snd_hda_codec_amp_stereo(codec, spec->autocfg.line_out_pins[0],
  1229. HDA_OUTPUT, 0, HDA_AMP_MUTE, 0);
  1230. if (vol_counter & 0x20) {
  1231. /* decrease volume */
  1232. if (vol > master_vol)
  1233. vol = master_vol;
  1234. snd_hda_codec_amp_stereo(codec, 0x1A, HDA_INPUT,
  1235. 0, HDA_AMP_VOLMASK,
  1236. master_vol-vol);
  1237. } else {
  1238. /* increase volume */
  1239. snd_hda_codec_amp_stereo(codec, 0x1A, HDA_INPUT, 0,
  1240. HDA_AMP_VOLMASK,
  1241. ((master_vol+vol) > 0x2A) ? 0x2A :
  1242. (master_vol+vol));
  1243. }
  1244. } else if (!(gpio_data & 0x02)) {
  1245. /* mute line out */
  1246. snd_hda_codec_amp_stereo(codec,
  1247. spec->autocfg.line_out_pins[0],
  1248. HDA_OUTPUT, 0, HDA_AMP_MUTE,
  1249. HDA_AMP_MUTE);
  1250. }
  1251. }
  1252. /* unsolicited event for jack sensing */
  1253. static void via_unsol_event(struct hda_codec *codec,
  1254. unsigned int res)
  1255. {
  1256. res >>= 26;
  1257. if (res & VIA_HP_EVENT)
  1258. via_hp_automute(codec);
  1259. if (res & VIA_GPIO_EVENT)
  1260. via_gpio_control(codec);
  1261. if (res & VIA_JACK_EVENT)
  1262. set_jack_power_state(codec);
  1263. }
  1264. static int via_init(struct hda_codec *codec)
  1265. {
  1266. struct via_spec *spec = codec->spec;
  1267. int i;
  1268. for (i = 0; i < spec->num_iverbs; i++)
  1269. snd_hda_sequence_write(codec, spec->init_verbs[i]);
  1270. spec->codec_type = get_codec_type(codec);
  1271. if (spec->codec_type == VT1708BCE)
  1272. spec->codec_type = VT1708S; /* VT1708BCE & VT1708S are almost
  1273. same */
  1274. /* Lydia Add for EAPD enable */
  1275. if (!spec->dig_in_nid) { /* No Digital In connection */
  1276. if (spec->dig_in_pin) {
  1277. snd_hda_codec_write(codec, spec->dig_in_pin, 0,
  1278. AC_VERB_SET_PIN_WIDGET_CONTROL,
  1279. PIN_OUT);
  1280. snd_hda_codec_write(codec, spec->dig_in_pin, 0,
  1281. AC_VERB_SET_EAPD_BTLENABLE, 0x02);
  1282. }
  1283. } else /* enable SPDIF-input pin */
  1284. snd_hda_codec_write(codec, spec->autocfg.dig_in_pin, 0,
  1285. AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_IN);
  1286. /* assign slave outs */
  1287. if (spec->slave_dig_outs[0])
  1288. codec->slave_dig_outs = spec->slave_dig_outs;
  1289. return 0;
  1290. }
  1291. #ifdef CONFIG_SND_HDA_POWER_SAVE
  1292. static int via_check_power_status(struct hda_codec *codec, hda_nid_t nid)
  1293. {
  1294. struct via_spec *spec = codec->spec;
  1295. return snd_hda_check_amp_list_power(codec, &spec->loopback, nid);
  1296. }
  1297. #endif
  1298. /*
  1299. */
  1300. static struct hda_codec_ops via_patch_ops = {
  1301. .build_controls = via_build_controls,
  1302. .build_pcms = via_build_pcms,
  1303. .init = via_init,
  1304. .free = via_free,
  1305. #ifdef CONFIG_SND_HDA_POWER_SAVE
  1306. .check_power_status = via_check_power_status,
  1307. #endif
  1308. };
  1309. /* fill in the dac_nids table from the parsed pin configuration */
  1310. static int vt1708_auto_fill_dac_nids(struct via_spec *spec,
  1311. const struct auto_pin_cfg *cfg)
  1312. {
  1313. int i;
  1314. hda_nid_t nid;
  1315. spec->multiout.num_dacs = cfg->line_outs;
  1316. spec->multiout.dac_nids = spec->private_dac_nids;
  1317. for(i = 0; i < 4; i++) {
  1318. nid = cfg->line_out_pins[i];
  1319. if (nid) {
  1320. /* config dac list */
  1321. switch (i) {
  1322. case AUTO_SEQ_FRONT:
  1323. spec->multiout.dac_nids[i] = 0x10;
  1324. break;
  1325. case AUTO_SEQ_CENLFE:
  1326. spec->multiout.dac_nids[i] = 0x12;
  1327. break;
  1328. case AUTO_SEQ_SURROUND:
  1329. spec->multiout.dac_nids[i] = 0x11;
  1330. break;
  1331. case AUTO_SEQ_SIDE:
  1332. spec->multiout.dac_nids[i] = 0x13;
  1333. break;
  1334. }
  1335. }
  1336. }
  1337. return 0;
  1338. }
  1339. /* add playback controls from the parsed DAC table */
  1340. static int vt1708_auto_create_multi_out_ctls(struct via_spec *spec,
  1341. const struct auto_pin_cfg *cfg)
  1342. {
  1343. char name[32];
  1344. static const char *chname[4] = { "Front", "Surround", "C/LFE", "Side" };
  1345. hda_nid_t nid, nid_vol = 0;
  1346. int i, err;
  1347. for (i = 0; i <= AUTO_SEQ_SIDE; i++) {
  1348. nid = cfg->line_out_pins[i];
  1349. if (!nid)
  1350. continue;
  1351. if (i != AUTO_SEQ_FRONT)
  1352. nid_vol = 0x18 + i;
  1353. if (i == AUTO_SEQ_CENLFE) {
  1354. /* Center/LFE */
  1355. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1356. "Center Playback Volume",
  1357. HDA_COMPOSE_AMP_VAL(nid_vol, 1, 0,
  1358. HDA_OUTPUT));
  1359. if (err < 0)
  1360. return err;
  1361. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1362. "LFE Playback Volume",
  1363. HDA_COMPOSE_AMP_VAL(nid_vol, 2, 0,
  1364. HDA_OUTPUT));
  1365. if (err < 0)
  1366. return err;
  1367. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1368. "Center Playback Switch",
  1369. HDA_COMPOSE_AMP_VAL(nid_vol, 1, 0,
  1370. HDA_OUTPUT));
  1371. if (err < 0)
  1372. return err;
  1373. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1374. "LFE Playback Switch",
  1375. HDA_COMPOSE_AMP_VAL(nid_vol, 2, 0,
  1376. HDA_OUTPUT));
  1377. if (err < 0)
  1378. return err;
  1379. } else if (i == AUTO_SEQ_FRONT){
  1380. /* add control to mixer index 0 */
  1381. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1382. "Master Front Playback Volume",
  1383. HDA_COMPOSE_AMP_VAL(0x17, 3, 0,
  1384. HDA_INPUT));
  1385. if (err < 0)
  1386. return err;
  1387. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1388. "Master Front Playback Switch",
  1389. HDA_COMPOSE_AMP_VAL(0x17, 3, 0,
  1390. HDA_INPUT));
  1391. if (err < 0)
  1392. return err;
  1393. /* add control to PW3 */
  1394. sprintf(name, "%s Playback Volume", chname[i]);
  1395. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  1396. HDA_COMPOSE_AMP_VAL(nid, 3, 0,
  1397. HDA_OUTPUT));
  1398. if (err < 0)
  1399. return err;
  1400. sprintf(name, "%s Playback Switch", chname[i]);
  1401. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  1402. HDA_COMPOSE_AMP_VAL(nid, 3, 0,
  1403. HDA_OUTPUT));
  1404. if (err < 0)
  1405. return err;
  1406. } else {
  1407. sprintf(name, "%s Playback Volume", chname[i]);
  1408. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  1409. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  1410. HDA_OUTPUT));
  1411. if (err < 0)
  1412. return err;
  1413. sprintf(name, "%s Playback Switch", chname[i]);
  1414. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  1415. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  1416. HDA_OUTPUT));
  1417. if (err < 0)
  1418. return err;
  1419. }
  1420. }
  1421. return 0;
  1422. }
  1423. static void create_hp_imux(struct via_spec *spec)
  1424. {
  1425. int i;
  1426. struct hda_input_mux *imux = &spec->private_imux[1];
  1427. static const char *texts[] = { "OFF", "ON", NULL};
  1428. /* for hp mode select */
  1429. i = 0;
  1430. while (texts[i] != NULL) {
  1431. imux->items[imux->num_items].label = texts[i];
  1432. imux->items[imux->num_items].index = i;
  1433. imux->num_items++;
  1434. i++;
  1435. }
  1436. spec->hp_mux = &spec->private_imux[1];
  1437. }
  1438. static int vt1708_auto_create_hp_ctls(struct via_spec *spec, hda_nid_t pin)
  1439. {
  1440. int err;
  1441. if (!pin)
  1442. return 0;
  1443. spec->multiout.hp_nid = VT1708_HP_NID; /* AOW3 */
  1444. spec->hp_independent_mode_index = 1;
  1445. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1446. "Headphone Playback Volume",
  1447. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  1448. if (err < 0)
  1449. return err;
  1450. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1451. "Headphone Playback Switch",
  1452. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  1453. if (err < 0)
  1454. return err;
  1455. create_hp_imux(spec);
  1456. return 0;
  1457. }
  1458. /* create playback/capture controls for input pins */
  1459. static int vt1708_auto_create_analog_input_ctls(struct via_spec *spec,
  1460. const struct auto_pin_cfg *cfg)
  1461. {
  1462. static char *labels[] = {
  1463. "Mic", "Front Mic", "Line", "Front Line", "CD", "Aux", NULL
  1464. };
  1465. struct hda_input_mux *imux = &spec->private_imux[0];
  1466. int i, err, idx = 0;
  1467. /* for internal loopback recording select */
  1468. imux->items[imux->num_items].label = "Stereo Mixer";
  1469. imux->items[imux->num_items].index = idx;
  1470. imux->num_items++;
  1471. for (i = 0; i < AUTO_PIN_LAST; i++) {
  1472. if (!cfg->input_pins[i])
  1473. continue;
  1474. switch (cfg->input_pins[i]) {
  1475. case 0x1d: /* Mic */
  1476. idx = 2;
  1477. break;
  1478. case 0x1e: /* Line In */
  1479. idx = 3;
  1480. break;
  1481. case 0x21: /* Front Mic */
  1482. idx = 4;
  1483. break;
  1484. case 0x24: /* CD */
  1485. idx = 1;
  1486. break;
  1487. }
  1488. err = via_new_analog_input(spec, labels[i], idx, 0x17);
  1489. if (err < 0)
  1490. return err;
  1491. imux->items[imux->num_items].label = labels[i];
  1492. imux->items[imux->num_items].index = idx;
  1493. imux->num_items++;
  1494. }
  1495. return 0;
  1496. }
  1497. #ifdef CONFIG_SND_HDA_POWER_SAVE
  1498. static struct hda_amp_list vt1708_loopbacks[] = {
  1499. { 0x17, HDA_INPUT, 1 },
  1500. { 0x17, HDA_INPUT, 2 },
  1501. { 0x17, HDA_INPUT, 3 },
  1502. { 0x17, HDA_INPUT, 4 },
  1503. { } /* end */
  1504. };
  1505. #endif
  1506. static void vt1708_set_pinconfig_connect(struct hda_codec *codec, hda_nid_t nid)
  1507. {
  1508. unsigned int def_conf;
  1509. unsigned char seqassoc;
  1510. def_conf = snd_hda_codec_get_pincfg(codec, nid);
  1511. seqassoc = (unsigned char) get_defcfg_association(def_conf);
  1512. seqassoc = (seqassoc << 4) | get_defcfg_sequence(def_conf);
  1513. if (get_defcfg_connect(def_conf) == AC_JACK_PORT_NONE) {
  1514. if (seqassoc == 0xff) {
  1515. def_conf = def_conf & (~(AC_JACK_PORT_BOTH << 30));
  1516. snd_hda_codec_set_pincfg(codec, nid, def_conf);
  1517. }
  1518. }
  1519. return;
  1520. }
  1521. static int vt1708_parse_auto_config(struct hda_codec *codec)
  1522. {
  1523. struct via_spec *spec = codec->spec;
  1524. int err;
  1525. /* Add HP and CD pin config connect bit re-config action */
  1526. vt1708_set_pinconfig_connect(codec, VT1708_HP_PIN_NID);
  1527. vt1708_set_pinconfig_connect(codec, VT1708_CD_PIN_NID);
  1528. err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL);
  1529. if (err < 0)
  1530. return err;
  1531. err = vt1708_auto_fill_dac_nids(spec, &spec->autocfg);
  1532. if (err < 0)
  1533. return err;
  1534. if (!spec->autocfg.line_outs && !spec->autocfg.hp_pins[0])
  1535. return 0; /* can't find valid BIOS pin config */
  1536. err = vt1708_auto_create_multi_out_ctls(spec, &spec->autocfg);
  1537. if (err < 0)
  1538. return err;
  1539. err = vt1708_auto_create_hp_ctls(spec, spec->autocfg.hp_pins[0]);
  1540. if (err < 0)
  1541. return err;
  1542. err = vt1708_auto_create_analog_input_ctls(spec, &spec->autocfg);
  1543. if (err < 0)
  1544. return err;
  1545. spec->multiout.max_channels = spec->multiout.num_dacs * 2;
  1546. if (spec->autocfg.dig_outs)
  1547. spec->multiout.dig_out_nid = VT1708_DIGOUT_NID;
  1548. spec->dig_in_pin = VT1708_DIGIN_PIN;
  1549. if (spec->autocfg.dig_in_pin)
  1550. spec->dig_in_nid = VT1708_DIGIN_NID;
  1551. if (spec->kctls.list)
  1552. spec->mixers[spec->num_mixers++] = spec->kctls.list;
  1553. spec->init_verbs[spec->num_iverbs++] = vt1708_volume_init_verbs;
  1554. spec->input_mux = &spec->private_imux[0];
  1555. if (spec->hp_mux)
  1556. spec->mixers[spec->num_mixers++] = via_hp_mixer;
  1557. spec->mixers[spec->num_mixers++] = via_smart51_mixer;
  1558. return 1;
  1559. }
  1560. /* init callback for auto-configuration model -- overriding the default init */
  1561. static int via_auto_init(struct hda_codec *codec)
  1562. {
  1563. via_init(codec);
  1564. via_auto_init_multi_out(codec);
  1565. via_auto_init_hp_out(codec);
  1566. via_auto_init_analog_input(codec);
  1567. return 0;
  1568. }
  1569. static int get_mux_nids(struct hda_codec *codec)
  1570. {
  1571. struct via_spec *spec = codec->spec;
  1572. hda_nid_t nid, conn[8];
  1573. unsigned int type;
  1574. int i, n;
  1575. for (i = 0; i < spec->num_adc_nids; i++) {
  1576. nid = spec->adc_nids[i];
  1577. while (nid) {
  1578. type = get_wcaps_type(get_wcaps(codec, nid));
  1579. if (type == AC_WID_PIN)
  1580. break;
  1581. n = snd_hda_get_connections(codec, nid, conn,
  1582. ARRAY_SIZE(conn));
  1583. if (n <= 0)
  1584. break;
  1585. if (n > 1) {
  1586. spec->mux_nids[i] = nid;
  1587. break;
  1588. }
  1589. nid = conn[0];
  1590. }
  1591. }
  1592. return 0;
  1593. }
  1594. static int patch_vt1708(struct hda_codec *codec)
  1595. {
  1596. struct via_spec *spec;
  1597. int err;
  1598. /* create a codec specific record */
  1599. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  1600. if (spec == NULL)
  1601. return -ENOMEM;
  1602. codec->spec = spec;
  1603. /* automatic parse from the BIOS config */
  1604. err = vt1708_parse_auto_config(codec);
  1605. if (err < 0) {
  1606. via_free(codec);
  1607. return err;
  1608. } else if (!err) {
  1609. printk(KERN_INFO "hda_codec: Cannot set up configuration "
  1610. "from BIOS. Using genenic mode...\n");
  1611. }
  1612. spec->stream_name_analog = "VT1708 Analog";
  1613. spec->stream_analog_playback = &vt1708_pcm_analog_playback;
  1614. /* disable 32bit format on VT1708 */
  1615. if (codec->vendor_id == 0x11061708)
  1616. spec->stream_analog_playback = &vt1708_pcm_analog_s16_playback;
  1617. spec->stream_analog_capture = &vt1708_pcm_analog_capture;
  1618. spec->stream_name_digital = "VT1708 Digital";
  1619. spec->stream_digital_playback = &vt1708_pcm_digital_playback;
  1620. spec->stream_digital_capture = &vt1708_pcm_digital_capture;
  1621. if (!spec->adc_nids && spec->input_mux) {
  1622. spec->adc_nids = vt1708_adc_nids;
  1623. spec->num_adc_nids = ARRAY_SIZE(vt1708_adc_nids);
  1624. get_mux_nids(codec);
  1625. spec->mixers[spec->num_mixers] = vt1708_capture_mixer;
  1626. spec->num_mixers++;
  1627. }
  1628. codec->patch_ops = via_patch_ops;
  1629. codec->patch_ops.init = via_auto_init;
  1630. #ifdef CONFIG_SND_HDA_POWER_SAVE
  1631. spec->loopback.amplist = vt1708_loopbacks;
  1632. #endif
  1633. return 0;
  1634. }
  1635. /* capture mixer elements */
  1636. static struct snd_kcontrol_new vt1709_capture_mixer[] = {
  1637. HDA_CODEC_VOLUME("Capture Volume", 0x14, 0x0, HDA_INPUT),
  1638. HDA_CODEC_MUTE("Capture Switch", 0x14, 0x0, HDA_INPUT),
  1639. HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x15, 0x0, HDA_INPUT),
  1640. HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x15, 0x0, HDA_INPUT),
  1641. HDA_CODEC_VOLUME_IDX("Capture Volume", 2, 0x16, 0x0, HDA_INPUT),
  1642. HDA_CODEC_MUTE_IDX("Capture Switch", 2, 0x16, 0x0, HDA_INPUT),
  1643. {
  1644. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  1645. /* The multiple "Capture Source" controls confuse alsamixer
  1646. * So call somewhat different..
  1647. */
  1648. /* .name = "Capture Source", */
  1649. .name = "Input Source",
  1650. .count = 1,
  1651. .info = via_mux_enum_info,
  1652. .get = via_mux_enum_get,
  1653. .put = via_mux_enum_put,
  1654. },
  1655. { } /* end */
  1656. };
  1657. static struct hda_verb vt1709_uniwill_init_verbs[] = {
  1658. {0x20, AC_VERB_SET_UNSOLICITED_ENABLE,
  1659. AC_USRSP_EN | VIA_HP_EVENT | VIA_JACK_EVENT},
  1660. { }
  1661. };
  1662. /*
  1663. * generic initialization of ADC, input mixers and output mixers
  1664. */
  1665. static struct hda_verb vt1709_10ch_volume_init_verbs[] = {
  1666. /*
  1667. * Unmute ADC0-2 and set the default input to mic-in
  1668. */
  1669. {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  1670. {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  1671. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  1672. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
  1673. * mixer widget
  1674. */
  1675. /* Amp Indices: AOW0=0, CD = 1, Mic1 = 2, Line = 3, Mic2 = 4 */
  1676. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  1677. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  1678. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  1679. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  1680. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
  1681. /*
  1682. * Set up output selector (0x1a, 0x1b, 0x29)
  1683. */
  1684. /* set vol=0 to output mixers */
  1685. {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  1686. {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  1687. {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  1688. /*
  1689. * Unmute PW3 and PW4
  1690. */
  1691. {0x1f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  1692. {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  1693. /* Set input of PW4 as AOW4 */
  1694. {0x20, AC_VERB_SET_CONNECT_SEL, 0x1},
  1695. /* PW9 Output enable */
  1696. {0x24, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  1697. { }
  1698. };
  1699. static struct hda_pcm_stream vt1709_10ch_pcm_analog_playback = {
  1700. .substreams = 1,
  1701. .channels_min = 2,
  1702. .channels_max = 10,
  1703. .nid = 0x10, /* NID to query formats and rates */
  1704. .ops = {
  1705. .open = via_playback_pcm_open,
  1706. .prepare = via_playback_pcm_prepare,
  1707. .cleanup = via_playback_pcm_cleanup
  1708. },
  1709. };
  1710. static struct hda_pcm_stream vt1709_6ch_pcm_analog_playback = {
  1711. .substreams = 1,
  1712. .channels_min = 2,
  1713. .channels_max = 6,
  1714. .nid = 0x10, /* NID to query formats and rates */
  1715. .ops = {
  1716. .open = via_playback_pcm_open,
  1717. .prepare = via_playback_pcm_prepare,
  1718. .cleanup = via_playback_pcm_cleanup
  1719. },
  1720. };
  1721. static struct hda_pcm_stream vt1709_pcm_analog_capture = {
  1722. .substreams = 2,
  1723. .channels_min = 2,
  1724. .channels_max = 2,
  1725. .nid = 0x14, /* NID to query formats and rates */
  1726. .ops = {
  1727. .prepare = via_capture_pcm_prepare,
  1728. .cleanup = via_capture_pcm_cleanup
  1729. },
  1730. };
  1731. static struct hda_pcm_stream vt1709_pcm_digital_playback = {
  1732. .substreams = 1,
  1733. .channels_min = 2,
  1734. .channels_max = 2,
  1735. /* NID is set in via_build_pcms */
  1736. .ops = {
  1737. .open = via_dig_playback_pcm_open,
  1738. .close = via_dig_playback_pcm_close
  1739. },
  1740. };
  1741. static struct hda_pcm_stream vt1709_pcm_digital_capture = {
  1742. .substreams = 1,
  1743. .channels_min = 2,
  1744. .channels_max = 2,
  1745. };
  1746. static int vt1709_auto_fill_dac_nids(struct via_spec *spec,
  1747. const struct auto_pin_cfg *cfg)
  1748. {
  1749. int i;
  1750. hda_nid_t nid;
  1751. if (cfg->line_outs == 4) /* 10 channels */
  1752. spec->multiout.num_dacs = cfg->line_outs+1; /* AOW0~AOW4 */
  1753. else if (cfg->line_outs == 3) /* 6 channels */
  1754. spec->multiout.num_dacs = cfg->line_outs; /* AOW0~AOW2 */
  1755. spec->multiout.dac_nids = spec->private_dac_nids;
  1756. if (cfg->line_outs == 4) { /* 10 channels */
  1757. for (i = 0; i < cfg->line_outs; i++) {
  1758. nid = cfg->line_out_pins[i];
  1759. if (nid) {
  1760. /* config dac list */
  1761. switch (i) {
  1762. case AUTO_SEQ_FRONT:
  1763. /* AOW0 */
  1764. spec->multiout.dac_nids[i] = 0x10;
  1765. break;
  1766. case AUTO_SEQ_CENLFE:
  1767. /* AOW2 */
  1768. spec->multiout.dac_nids[i] = 0x12;
  1769. break;
  1770. case AUTO_SEQ_SURROUND:
  1771. /* AOW3 */
  1772. spec->multiout.dac_nids[i] = 0x11;
  1773. break;
  1774. case AUTO_SEQ_SIDE:
  1775. /* AOW1 */
  1776. spec->multiout.dac_nids[i] = 0x27;
  1777. break;
  1778. default:
  1779. break;
  1780. }
  1781. }
  1782. }
  1783. spec->multiout.dac_nids[cfg->line_outs] = 0x28; /* AOW4 */
  1784. } else if (cfg->line_outs == 3) { /* 6 channels */
  1785. for(i = 0; i < cfg->line_outs; i++) {
  1786. nid = cfg->line_out_pins[i];
  1787. if (nid) {
  1788. /* config dac list */
  1789. switch(i) {
  1790. case AUTO_SEQ_FRONT:
  1791. /* AOW0 */
  1792. spec->multiout.dac_nids[i] = 0x10;
  1793. break;
  1794. case AUTO_SEQ_CENLFE:
  1795. /* AOW2 */
  1796. spec->multiout.dac_nids[i] = 0x12;
  1797. break;
  1798. case AUTO_SEQ_SURROUND:
  1799. /* AOW1 */
  1800. spec->multiout.dac_nids[i] = 0x11;
  1801. break;
  1802. default:
  1803. break;
  1804. }
  1805. }
  1806. }
  1807. }
  1808. return 0;
  1809. }
  1810. /* add playback controls from the parsed DAC table */
  1811. static int vt1709_auto_create_multi_out_ctls(struct via_spec *spec,
  1812. const struct auto_pin_cfg *cfg)
  1813. {
  1814. char name[32];
  1815. static const char *chname[4] = { "Front", "Surround", "C/LFE", "Side" };
  1816. hda_nid_t nid = 0;
  1817. int i, err;
  1818. for (i = 0; i <= AUTO_SEQ_SIDE; i++) {
  1819. nid = cfg->line_out_pins[i];
  1820. if (!nid)
  1821. continue;
  1822. if (i == AUTO_SEQ_CENLFE) {
  1823. /* Center/LFE */
  1824. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1825. "Center Playback Volume",
  1826. HDA_COMPOSE_AMP_VAL(0x1b, 1, 0,
  1827. HDA_OUTPUT));
  1828. if (err < 0)
  1829. return err;
  1830. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1831. "LFE Playback Volume",
  1832. HDA_COMPOSE_AMP_VAL(0x1b, 2, 0,
  1833. HDA_OUTPUT));
  1834. if (err < 0)
  1835. return err;
  1836. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1837. "Center Playback Switch",
  1838. HDA_COMPOSE_AMP_VAL(0x1b, 1, 0,
  1839. HDA_OUTPUT));
  1840. if (err < 0)
  1841. return err;
  1842. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1843. "LFE Playback Switch",
  1844. HDA_COMPOSE_AMP_VAL(0x1b, 2, 0,
  1845. HDA_OUTPUT));
  1846. if (err < 0)
  1847. return err;
  1848. } else if (i == AUTO_SEQ_FRONT){
  1849. /* add control to mixer index 0 */
  1850. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1851. "Master Front Playback Volume",
  1852. HDA_COMPOSE_AMP_VAL(0x18, 3, 0,
  1853. HDA_INPUT));
  1854. if (err < 0)
  1855. return err;
  1856. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1857. "Master Front Playback Switch",
  1858. HDA_COMPOSE_AMP_VAL(0x18, 3, 0,
  1859. HDA_INPUT));
  1860. if (err < 0)
  1861. return err;
  1862. /* add control to PW3 */
  1863. sprintf(name, "%s Playback Volume", chname[i]);
  1864. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  1865. HDA_COMPOSE_AMP_VAL(nid, 3, 0,
  1866. HDA_OUTPUT));
  1867. if (err < 0)
  1868. return err;
  1869. sprintf(name, "%s Playback Switch", chname[i]);
  1870. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  1871. HDA_COMPOSE_AMP_VAL(nid, 3, 0,
  1872. HDA_OUTPUT));
  1873. if (err < 0)
  1874. return err;
  1875. } else if (i == AUTO_SEQ_SURROUND) {
  1876. sprintf(name, "%s Playback Volume", chname[i]);
  1877. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  1878. HDA_COMPOSE_AMP_VAL(0x1a, 3, 0,
  1879. HDA_OUTPUT));
  1880. if (err < 0)
  1881. return err;
  1882. sprintf(name, "%s Playback Switch", chname[i]);
  1883. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  1884. HDA_COMPOSE_AMP_VAL(0x1a, 3, 0,
  1885. HDA_OUTPUT));
  1886. if (err < 0)
  1887. return err;
  1888. } else if (i == AUTO_SEQ_SIDE) {
  1889. sprintf(name, "%s Playback Volume", chname[i]);
  1890. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  1891. HDA_COMPOSE_AMP_VAL(0x29, 3, 0,
  1892. HDA_OUTPUT));
  1893. if (err < 0)
  1894. return err;
  1895. sprintf(name, "%s Playback Switch", chname[i]);
  1896. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  1897. HDA_COMPOSE_AMP_VAL(0x29, 3, 0,
  1898. HDA_OUTPUT));
  1899. if (err < 0)
  1900. return err;
  1901. }
  1902. }
  1903. return 0;
  1904. }
  1905. static int vt1709_auto_create_hp_ctls(struct via_spec *spec, hda_nid_t pin)
  1906. {
  1907. int err;
  1908. if (!pin)
  1909. return 0;
  1910. if (spec->multiout.num_dacs == 5) /* 10 channels */
  1911. spec->multiout.hp_nid = VT1709_HP_DAC_NID;
  1912. else if (spec->multiout.num_dacs == 3) /* 6 channels */
  1913. spec->multiout.hp_nid = 0;
  1914. spec->hp_independent_mode_index = 1;
  1915. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  1916. "Headphone Playback Volume",
  1917. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  1918. if (err < 0)
  1919. return err;
  1920. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  1921. "Headphone Playback Switch",
  1922. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  1923. if (err < 0)
  1924. return err;
  1925. return 0;
  1926. }
  1927. /* create playback/capture controls for input pins */
  1928. static int vt1709_auto_create_analog_input_ctls(struct via_spec *spec,
  1929. const struct auto_pin_cfg *cfg)
  1930. {
  1931. static char *labels[] = {
  1932. "Mic", "Front Mic", "Line", "Front Line", "CD", "Aux", NULL
  1933. };
  1934. struct hda_input_mux *imux = &spec->private_imux[0];
  1935. int i, err, idx = 0;
  1936. /* for internal loopback recording select */
  1937. imux->items[imux->num_items].label = "Stereo Mixer";
  1938. imux->items[imux->num_items].index = idx;
  1939. imux->num_items++;
  1940. for (i = 0; i < AUTO_PIN_LAST; i++) {
  1941. if (!cfg->input_pins[i])
  1942. continue;
  1943. switch (cfg->input_pins[i]) {
  1944. case 0x1d: /* Mic */
  1945. idx = 2;
  1946. break;
  1947. case 0x1e: /* Line In */
  1948. idx = 3;
  1949. break;
  1950. case 0x21: /* Front Mic */
  1951. idx = 4;
  1952. break;
  1953. case 0x23: /* CD */
  1954. idx = 1;
  1955. break;
  1956. }
  1957. err = via_new_analog_input(spec, labels[i], idx, 0x18);
  1958. if (err < 0)
  1959. return err;
  1960. imux->items[imux->num_items].label = labels[i];
  1961. imux->items[imux->num_items].index = idx;
  1962. imux->num_items++;
  1963. }
  1964. return 0;
  1965. }
  1966. static int vt1709_parse_auto_config(struct hda_codec *codec)
  1967. {
  1968. struct via_spec *spec = codec->spec;
  1969. int err;
  1970. err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL);
  1971. if (err < 0)
  1972. return err;
  1973. err = vt1709_auto_fill_dac_nids(spec, &spec->autocfg);
  1974. if (err < 0)
  1975. return err;
  1976. if (!spec->autocfg.line_outs && !spec->autocfg.hp_pins[0])
  1977. return 0; /* can't find valid BIOS pin config */
  1978. err = vt1709_auto_create_multi_out_ctls(spec, &spec->autocfg);
  1979. if (err < 0)
  1980. return err;
  1981. err = vt1709_auto_create_hp_ctls(spec, spec->autocfg.hp_pins[0]);
  1982. if (err < 0)
  1983. return err;
  1984. err = vt1709_auto_create_analog_input_ctls(spec, &spec->autocfg);
  1985. if (err < 0)
  1986. return err;
  1987. spec->multiout.max_channels = spec->multiout.num_dacs * 2;
  1988. if (spec->autocfg.dig_outs)
  1989. spec->multiout.dig_out_nid = VT1709_DIGOUT_NID;
  1990. spec->dig_in_pin = VT1709_DIGIN_PIN;
  1991. if (spec->autocfg.dig_in_pin)
  1992. spec->dig_in_nid = VT1709_DIGIN_NID;
  1993. if (spec->kctls.list)
  1994. spec->mixers[spec->num_mixers++] = spec->kctls.list;
  1995. spec->input_mux = &spec->private_imux[0];
  1996. if (spec->hp_mux)
  1997. spec->mixers[spec->num_mixers++] = via_hp_mixer;
  1998. spec->mixers[spec->num_mixers++] = via_smart51_mixer;
  1999. return 1;
  2000. }
  2001. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2002. static struct hda_amp_list vt1709_loopbacks[] = {
  2003. { 0x18, HDA_INPUT, 1 },
  2004. { 0x18, HDA_INPUT, 2 },
  2005. { 0x18, HDA_INPUT, 3 },
  2006. { 0x18, HDA_INPUT, 4 },
  2007. { } /* end */
  2008. };
  2009. #endif
  2010. static int patch_vt1709_10ch(struct hda_codec *codec)
  2011. {
  2012. struct via_spec *spec;
  2013. int err;
  2014. /* create a codec specific record */
  2015. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  2016. if (spec == NULL)
  2017. return -ENOMEM;
  2018. codec->spec = spec;
  2019. err = vt1709_parse_auto_config(codec);
  2020. if (err < 0) {
  2021. via_free(codec);
  2022. return err;
  2023. } else if (!err) {
  2024. printk(KERN_INFO "hda_codec: Cannot set up configuration. "
  2025. "Using genenic mode...\n");
  2026. }
  2027. spec->init_verbs[spec->num_iverbs++] = vt1709_10ch_volume_init_verbs;
  2028. spec->init_verbs[spec->num_iverbs++] = vt1709_uniwill_init_verbs;
  2029. spec->stream_name_analog = "VT1709 Analog";
  2030. spec->stream_analog_playback = &vt1709_10ch_pcm_analog_playback;
  2031. spec->stream_analog_capture = &vt1709_pcm_analog_capture;
  2032. spec->stream_name_digital = "VT1709 Digital";
  2033. spec->stream_digital_playback = &vt1709_pcm_digital_playback;
  2034. spec->stream_digital_capture = &vt1709_pcm_digital_capture;
  2035. if (!spec->adc_nids && spec->input_mux) {
  2036. spec->adc_nids = vt1709_adc_nids;
  2037. spec->num_adc_nids = ARRAY_SIZE(vt1709_adc_nids);
  2038. get_mux_nids(codec);
  2039. spec->mixers[spec->num_mixers] = vt1709_capture_mixer;
  2040. spec->num_mixers++;
  2041. }
  2042. codec->patch_ops = via_patch_ops;
  2043. codec->patch_ops.init = via_auto_init;
  2044. codec->patch_ops.unsol_event = via_unsol_event;
  2045. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2046. spec->loopback.amplist = vt1709_loopbacks;
  2047. #endif
  2048. return 0;
  2049. }
  2050. /*
  2051. * generic initialization of ADC, input mixers and output mixers
  2052. */
  2053. static struct hda_verb vt1709_6ch_volume_init_verbs[] = {
  2054. /*
  2055. * Unmute ADC0-2 and set the default input to mic-in
  2056. */
  2057. {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2058. {0x15, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2059. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2060. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
  2061. * mixer widget
  2062. */
  2063. /* Amp Indices: AOW0=0, CD = 1, Mic1 = 2, Line = 3, Mic2 = 4 */
  2064. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2065. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  2066. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  2067. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  2068. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
  2069. /*
  2070. * Set up output selector (0x1a, 0x1b, 0x29)
  2071. */
  2072. /* set vol=0 to output mixers */
  2073. {0x1a, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2074. {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2075. {0x29, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2076. /*
  2077. * Unmute PW3 and PW4
  2078. */
  2079. {0x1f, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2080. {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2081. /* Set input of PW4 as MW0 */
  2082. {0x20, AC_VERB_SET_CONNECT_SEL, 0},
  2083. /* PW9 Output enable */
  2084. {0x24, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  2085. { }
  2086. };
  2087. static int patch_vt1709_6ch(struct hda_codec *codec)
  2088. {
  2089. struct via_spec *spec;
  2090. int err;
  2091. /* create a codec specific record */
  2092. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  2093. if (spec == NULL)
  2094. return -ENOMEM;
  2095. codec->spec = spec;
  2096. err = vt1709_parse_auto_config(codec);
  2097. if (err < 0) {
  2098. via_free(codec);
  2099. return err;
  2100. } else if (!err) {
  2101. printk(KERN_INFO "hda_codec: Cannot set up configuration. "
  2102. "Using genenic mode...\n");
  2103. }
  2104. spec->init_verbs[spec->num_iverbs++] = vt1709_6ch_volume_init_verbs;
  2105. spec->init_verbs[spec->num_iverbs++] = vt1709_uniwill_init_verbs;
  2106. spec->stream_name_analog = "VT1709 Analog";
  2107. spec->stream_analog_playback = &vt1709_6ch_pcm_analog_playback;
  2108. spec->stream_analog_capture = &vt1709_pcm_analog_capture;
  2109. spec->stream_name_digital = "VT1709 Digital";
  2110. spec->stream_digital_playback = &vt1709_pcm_digital_playback;
  2111. spec->stream_digital_capture = &vt1709_pcm_digital_capture;
  2112. if (!spec->adc_nids && spec->input_mux) {
  2113. spec->adc_nids = vt1709_adc_nids;
  2114. spec->num_adc_nids = ARRAY_SIZE(vt1709_adc_nids);
  2115. get_mux_nids(codec);
  2116. spec->mixers[spec->num_mixers] = vt1709_capture_mixer;
  2117. spec->num_mixers++;
  2118. }
  2119. codec->patch_ops = via_patch_ops;
  2120. codec->patch_ops.init = via_auto_init;
  2121. codec->patch_ops.unsol_event = via_unsol_event;
  2122. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2123. spec->loopback.amplist = vt1709_loopbacks;
  2124. #endif
  2125. return 0;
  2126. }
  2127. /* capture mixer elements */
  2128. static struct snd_kcontrol_new vt1708B_capture_mixer[] = {
  2129. HDA_CODEC_VOLUME("Capture Volume", 0x13, 0x0, HDA_INPUT),
  2130. HDA_CODEC_MUTE("Capture Switch", 0x13, 0x0, HDA_INPUT),
  2131. HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x14, 0x0, HDA_INPUT),
  2132. HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x14, 0x0, HDA_INPUT),
  2133. {
  2134. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  2135. /* The multiple "Capture Source" controls confuse alsamixer
  2136. * So call somewhat different..
  2137. */
  2138. /* .name = "Capture Source", */
  2139. .name = "Input Source",
  2140. .count = 1,
  2141. .info = via_mux_enum_info,
  2142. .get = via_mux_enum_get,
  2143. .put = via_mux_enum_put,
  2144. },
  2145. { } /* end */
  2146. };
  2147. /*
  2148. * generic initialization of ADC, input mixers and output mixers
  2149. */
  2150. static struct hda_verb vt1708B_8ch_volume_init_verbs[] = {
  2151. /*
  2152. * Unmute ADC0-1 and set the default input to mic-in
  2153. */
  2154. {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2155. {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2156. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
  2157. * mixer widget
  2158. */
  2159. /* Amp Indices: CD = 1, Mic1 = 2, Line = 3, Mic2 = 4 */
  2160. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2161. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  2162. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  2163. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  2164. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
  2165. /*
  2166. * Set up output mixers
  2167. */
  2168. /* set vol=0 to output mixers */
  2169. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2170. {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2171. {0x27, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2172. /* Setup default input to PW4 */
  2173. {0x1d, AC_VERB_SET_CONNECT_SEL, 0x1},
  2174. /* PW9 Output enable */
  2175. {0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  2176. /* PW10 Input enable */
  2177. {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
  2178. { }
  2179. };
  2180. static struct hda_verb vt1708B_4ch_volume_init_verbs[] = {
  2181. /*
  2182. * Unmute ADC0-1 and set the default input to mic-in
  2183. */
  2184. {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2185. {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2186. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
  2187. * mixer widget
  2188. */
  2189. /* Amp Indices: CD = 1, Mic1 = 2, Line = 3, Mic2 = 4 */
  2190. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2191. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  2192. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  2193. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  2194. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
  2195. /*
  2196. * Set up output mixers
  2197. */
  2198. /* set vol=0 to output mixers */
  2199. {0x18, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2200. {0x26, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2201. {0x27, AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_ZERO},
  2202. /* Setup default input of PW4 to MW0 */
  2203. {0x1d, AC_VERB_SET_CONNECT_SEL, 0x0},
  2204. /* PW9 Output enable */
  2205. {0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  2206. /* PW10 Input enable */
  2207. {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x20},
  2208. { }
  2209. };
  2210. static struct hda_verb vt1708B_uniwill_init_verbs[] = {
  2211. {0x1d, AC_VERB_SET_UNSOLICITED_ENABLE,
  2212. AC_USRSP_EN | VIA_HP_EVENT | VIA_JACK_EVENT},
  2213. {0x19, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2214. {0x1a, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2215. {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2216. {0x1c, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2217. {0x1e, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2218. {0x22, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2219. {0x23, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2220. { }
  2221. };
  2222. static int via_pcm_open_close(struct hda_pcm_stream *hinfo,
  2223. struct hda_codec *codec,
  2224. struct snd_pcm_substream *substream)
  2225. {
  2226. int idle = substream->pstr->substream_opened == 1
  2227. && substream->ref_count == 0;
  2228. analog_low_current_mode(codec, idle);
  2229. return 0;
  2230. }
  2231. static struct hda_pcm_stream vt1708B_8ch_pcm_analog_playback = {
  2232. .substreams = 2,
  2233. .channels_min = 2,
  2234. .channels_max = 8,
  2235. .nid = 0x10, /* NID to query formats and rates */
  2236. .ops = {
  2237. .open = via_playback_pcm_open,
  2238. .prepare = via_playback_multi_pcm_prepare,
  2239. .cleanup = via_playback_multi_pcm_cleanup,
  2240. .close = via_pcm_open_close
  2241. },
  2242. };
  2243. static struct hda_pcm_stream vt1708B_4ch_pcm_analog_playback = {
  2244. .substreams = 2,
  2245. .channels_min = 2,
  2246. .channels_max = 4,
  2247. .nid = 0x10, /* NID to query formats and rates */
  2248. .ops = {
  2249. .open = via_playback_pcm_open,
  2250. .prepare = via_playback_multi_pcm_prepare,
  2251. .cleanup = via_playback_multi_pcm_cleanup
  2252. },
  2253. };
  2254. static struct hda_pcm_stream vt1708B_pcm_analog_capture = {
  2255. .substreams = 2,
  2256. .channels_min = 2,
  2257. .channels_max = 2,
  2258. .nid = 0x13, /* NID to query formats and rates */
  2259. .ops = {
  2260. .open = via_pcm_open_close,
  2261. .prepare = via_capture_pcm_prepare,
  2262. .cleanup = via_capture_pcm_cleanup,
  2263. .close = via_pcm_open_close
  2264. },
  2265. };
  2266. static struct hda_pcm_stream vt1708B_pcm_digital_playback = {
  2267. .substreams = 1,
  2268. .channels_min = 2,
  2269. .channels_max = 2,
  2270. /* NID is set in via_build_pcms */
  2271. .ops = {
  2272. .open = via_dig_playback_pcm_open,
  2273. .close = via_dig_playback_pcm_close,
  2274. .prepare = via_dig_playback_pcm_prepare,
  2275. .cleanup = via_dig_playback_pcm_cleanup
  2276. },
  2277. };
  2278. static struct hda_pcm_stream vt1708B_pcm_digital_capture = {
  2279. .substreams = 1,
  2280. .channels_min = 2,
  2281. .channels_max = 2,
  2282. };
  2283. /* fill in the dac_nids table from the parsed pin configuration */
  2284. static int vt1708B_auto_fill_dac_nids(struct via_spec *spec,
  2285. const struct auto_pin_cfg *cfg)
  2286. {
  2287. int i;
  2288. hda_nid_t nid;
  2289. spec->multiout.num_dacs = cfg->line_outs;
  2290. spec->multiout.dac_nids = spec->private_dac_nids;
  2291. for (i = 0; i < 4; i++) {
  2292. nid = cfg->line_out_pins[i];
  2293. if (nid) {
  2294. /* config dac list */
  2295. switch (i) {
  2296. case AUTO_SEQ_FRONT:
  2297. spec->multiout.dac_nids[i] = 0x10;
  2298. break;
  2299. case AUTO_SEQ_CENLFE:
  2300. spec->multiout.dac_nids[i] = 0x24;
  2301. break;
  2302. case AUTO_SEQ_SURROUND:
  2303. spec->multiout.dac_nids[i] = 0x11;
  2304. break;
  2305. case AUTO_SEQ_SIDE:
  2306. spec->multiout.dac_nids[i] = 0x25;
  2307. break;
  2308. }
  2309. }
  2310. }
  2311. return 0;
  2312. }
  2313. /* add playback controls from the parsed DAC table */
  2314. static int vt1708B_auto_create_multi_out_ctls(struct via_spec *spec,
  2315. const struct auto_pin_cfg *cfg)
  2316. {
  2317. char name[32];
  2318. static const char *chname[4] = { "Front", "Surround", "C/LFE", "Side" };
  2319. hda_nid_t nid_vols[] = {0x16, 0x18, 0x26, 0x27};
  2320. hda_nid_t nid, nid_vol = 0;
  2321. int i, err;
  2322. for (i = 0; i <= AUTO_SEQ_SIDE; i++) {
  2323. nid = cfg->line_out_pins[i];
  2324. if (!nid)
  2325. continue;
  2326. nid_vol = nid_vols[i];
  2327. if (i == AUTO_SEQ_CENLFE) {
  2328. /* Center/LFE */
  2329. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2330. "Center Playback Volume",
  2331. HDA_COMPOSE_AMP_VAL(nid_vol, 1, 0,
  2332. HDA_OUTPUT));
  2333. if (err < 0)
  2334. return err;
  2335. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2336. "LFE Playback Volume",
  2337. HDA_COMPOSE_AMP_VAL(nid_vol, 2, 0,
  2338. HDA_OUTPUT));
  2339. if (err < 0)
  2340. return err;
  2341. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2342. "Center Playback Switch",
  2343. HDA_COMPOSE_AMP_VAL(nid_vol, 1, 0,
  2344. HDA_OUTPUT));
  2345. if (err < 0)
  2346. return err;
  2347. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2348. "LFE Playback Switch",
  2349. HDA_COMPOSE_AMP_VAL(nid_vol, 2, 0,
  2350. HDA_OUTPUT));
  2351. if (err < 0)
  2352. return err;
  2353. } else if (i == AUTO_SEQ_FRONT) {
  2354. /* add control to mixer index 0 */
  2355. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2356. "Master Front Playback Volume",
  2357. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  2358. HDA_INPUT));
  2359. if (err < 0)
  2360. return err;
  2361. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2362. "Master Front Playback Switch",
  2363. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  2364. HDA_INPUT));
  2365. if (err < 0)
  2366. return err;
  2367. /* add control to PW3 */
  2368. sprintf(name, "%s Playback Volume", chname[i]);
  2369. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  2370. HDA_COMPOSE_AMP_VAL(nid, 3, 0,
  2371. HDA_OUTPUT));
  2372. if (err < 0)
  2373. return err;
  2374. sprintf(name, "%s Playback Switch", chname[i]);
  2375. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  2376. HDA_COMPOSE_AMP_VAL(nid, 3, 0,
  2377. HDA_OUTPUT));
  2378. if (err < 0)
  2379. return err;
  2380. } else {
  2381. sprintf(name, "%s Playback Volume", chname[i]);
  2382. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  2383. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  2384. HDA_OUTPUT));
  2385. if (err < 0)
  2386. return err;
  2387. sprintf(name, "%s Playback Switch", chname[i]);
  2388. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  2389. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  2390. HDA_OUTPUT));
  2391. if (err < 0)
  2392. return err;
  2393. }
  2394. }
  2395. return 0;
  2396. }
  2397. static int vt1708B_auto_create_hp_ctls(struct via_spec *spec, hda_nid_t pin)
  2398. {
  2399. int err;
  2400. if (!pin)
  2401. return 0;
  2402. spec->multiout.hp_nid = VT1708B_HP_NID; /* AOW3 */
  2403. spec->hp_independent_mode_index = 1;
  2404. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2405. "Headphone Playback Volume",
  2406. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  2407. if (err < 0)
  2408. return err;
  2409. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2410. "Headphone Playback Switch",
  2411. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  2412. if (err < 0)
  2413. return err;
  2414. create_hp_imux(spec);
  2415. return 0;
  2416. }
  2417. /* create playback/capture controls for input pins */
  2418. static int vt1708B_auto_create_analog_input_ctls(struct via_spec *spec,
  2419. const struct auto_pin_cfg *cfg)
  2420. {
  2421. static char *labels[] = {
  2422. "Mic", "Front Mic", "Line", "Front Line", "CD", "Aux", NULL
  2423. };
  2424. struct hda_input_mux *imux = &spec->private_imux[0];
  2425. int i, err, idx = 0;
  2426. /* for internal loopback recording select */
  2427. imux->items[imux->num_items].label = "Stereo Mixer";
  2428. imux->items[imux->num_items].index = idx;
  2429. imux->num_items++;
  2430. for (i = 0; i < AUTO_PIN_LAST; i++) {
  2431. if (!cfg->input_pins[i])
  2432. continue;
  2433. switch (cfg->input_pins[i]) {
  2434. case 0x1a: /* Mic */
  2435. idx = 2;
  2436. break;
  2437. case 0x1b: /* Line In */
  2438. idx = 3;
  2439. break;
  2440. case 0x1e: /* Front Mic */
  2441. idx = 4;
  2442. break;
  2443. case 0x1f: /* CD */
  2444. idx = 1;
  2445. break;
  2446. }
  2447. err = via_new_analog_input(spec, labels[i], idx, 0x16);
  2448. if (err < 0)
  2449. return err;
  2450. imux->items[imux->num_items].label = labels[i];
  2451. imux->items[imux->num_items].index = idx;
  2452. imux->num_items++;
  2453. }
  2454. return 0;
  2455. }
  2456. static int vt1708B_parse_auto_config(struct hda_codec *codec)
  2457. {
  2458. struct via_spec *spec = codec->spec;
  2459. int err;
  2460. err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL);
  2461. if (err < 0)
  2462. return err;
  2463. err = vt1708B_auto_fill_dac_nids(spec, &spec->autocfg);
  2464. if (err < 0)
  2465. return err;
  2466. if (!spec->autocfg.line_outs && !spec->autocfg.hp_pins[0])
  2467. return 0; /* can't find valid BIOS pin config */
  2468. err = vt1708B_auto_create_multi_out_ctls(spec, &spec->autocfg);
  2469. if (err < 0)
  2470. return err;
  2471. err = vt1708B_auto_create_hp_ctls(spec, spec->autocfg.hp_pins[0]);
  2472. if (err < 0)
  2473. return err;
  2474. err = vt1708B_auto_create_analog_input_ctls(spec, &spec->autocfg);
  2475. if (err < 0)
  2476. return err;
  2477. spec->multiout.max_channels = spec->multiout.num_dacs * 2;
  2478. if (spec->autocfg.dig_outs)
  2479. spec->multiout.dig_out_nid = VT1708B_DIGOUT_NID;
  2480. spec->dig_in_pin = VT1708B_DIGIN_PIN;
  2481. if (spec->autocfg.dig_in_pin)
  2482. spec->dig_in_nid = VT1708B_DIGIN_NID;
  2483. if (spec->kctls.list)
  2484. spec->mixers[spec->num_mixers++] = spec->kctls.list;
  2485. spec->input_mux = &spec->private_imux[0];
  2486. if (spec->hp_mux)
  2487. spec->mixers[spec->num_mixers++] = via_hp_mixer;
  2488. spec->mixers[spec->num_mixers++] = via_smart51_mixer;
  2489. return 1;
  2490. }
  2491. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2492. static struct hda_amp_list vt1708B_loopbacks[] = {
  2493. { 0x16, HDA_INPUT, 1 },
  2494. { 0x16, HDA_INPUT, 2 },
  2495. { 0x16, HDA_INPUT, 3 },
  2496. { 0x16, HDA_INPUT, 4 },
  2497. { } /* end */
  2498. };
  2499. #endif
  2500. static int patch_vt1708S(struct hda_codec *codec);
  2501. static int patch_vt1708B_8ch(struct hda_codec *codec)
  2502. {
  2503. struct via_spec *spec;
  2504. int err;
  2505. if (get_codec_type(codec) == VT1708BCE)
  2506. return patch_vt1708S(codec);
  2507. /* create a codec specific record */
  2508. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  2509. if (spec == NULL)
  2510. return -ENOMEM;
  2511. codec->spec = spec;
  2512. /* automatic parse from the BIOS config */
  2513. err = vt1708B_parse_auto_config(codec);
  2514. if (err < 0) {
  2515. via_free(codec);
  2516. return err;
  2517. } else if (!err) {
  2518. printk(KERN_INFO "hda_codec: Cannot set up configuration "
  2519. "from BIOS. Using genenic mode...\n");
  2520. }
  2521. spec->init_verbs[spec->num_iverbs++] = vt1708B_8ch_volume_init_verbs;
  2522. spec->init_verbs[spec->num_iverbs++] = vt1708B_uniwill_init_verbs;
  2523. spec->stream_name_analog = "VT1708B Analog";
  2524. spec->stream_analog_playback = &vt1708B_8ch_pcm_analog_playback;
  2525. spec->stream_analog_capture = &vt1708B_pcm_analog_capture;
  2526. spec->stream_name_digital = "VT1708B Digital";
  2527. spec->stream_digital_playback = &vt1708B_pcm_digital_playback;
  2528. spec->stream_digital_capture = &vt1708B_pcm_digital_capture;
  2529. if (!spec->adc_nids && spec->input_mux) {
  2530. spec->adc_nids = vt1708B_adc_nids;
  2531. spec->num_adc_nids = ARRAY_SIZE(vt1708B_adc_nids);
  2532. get_mux_nids(codec);
  2533. spec->mixers[spec->num_mixers] = vt1708B_capture_mixer;
  2534. spec->num_mixers++;
  2535. }
  2536. codec->patch_ops = via_patch_ops;
  2537. codec->patch_ops.init = via_auto_init;
  2538. codec->patch_ops.unsol_event = via_unsol_event;
  2539. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2540. spec->loopback.amplist = vt1708B_loopbacks;
  2541. #endif
  2542. return 0;
  2543. }
  2544. static int patch_vt1708B_4ch(struct hda_codec *codec)
  2545. {
  2546. struct via_spec *spec;
  2547. int err;
  2548. /* create a codec specific record */
  2549. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  2550. if (spec == NULL)
  2551. return -ENOMEM;
  2552. codec->spec = spec;
  2553. /* automatic parse from the BIOS config */
  2554. err = vt1708B_parse_auto_config(codec);
  2555. if (err < 0) {
  2556. via_free(codec);
  2557. return err;
  2558. } else if (!err) {
  2559. printk(KERN_INFO "hda_codec: Cannot set up configuration "
  2560. "from BIOS. Using genenic mode...\n");
  2561. }
  2562. spec->init_verbs[spec->num_iverbs++] = vt1708B_4ch_volume_init_verbs;
  2563. spec->init_verbs[spec->num_iverbs++] = vt1708B_uniwill_init_verbs;
  2564. spec->stream_name_analog = "VT1708B Analog";
  2565. spec->stream_analog_playback = &vt1708B_4ch_pcm_analog_playback;
  2566. spec->stream_analog_capture = &vt1708B_pcm_analog_capture;
  2567. spec->stream_name_digital = "VT1708B Digital";
  2568. spec->stream_digital_playback = &vt1708B_pcm_digital_playback;
  2569. spec->stream_digital_capture = &vt1708B_pcm_digital_capture;
  2570. if (!spec->adc_nids && spec->input_mux) {
  2571. spec->adc_nids = vt1708B_adc_nids;
  2572. spec->num_adc_nids = ARRAY_SIZE(vt1708B_adc_nids);
  2573. get_mux_nids(codec);
  2574. spec->mixers[spec->num_mixers] = vt1708B_capture_mixer;
  2575. spec->num_mixers++;
  2576. }
  2577. codec->patch_ops = via_patch_ops;
  2578. codec->patch_ops.init = via_auto_init;
  2579. codec->patch_ops.unsol_event = via_unsol_event;
  2580. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2581. spec->loopback.amplist = vt1708B_loopbacks;
  2582. #endif
  2583. return 0;
  2584. }
  2585. /* Patch for VT1708S */
  2586. /* VT1708S software backdoor based override for buggy hardware micboost
  2587. * setting */
  2588. #define MIC_BOOST_VOLUME(xname, nid) { \
  2589. .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
  2590. .name = xname, \
  2591. .index = 0, \
  2592. .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | \
  2593. SNDRV_CTL_ELEM_ACCESS_TLV_READ | \
  2594. SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK, \
  2595. .info = mic_boost_volume_info, \
  2596. .get = snd_hda_mixer_amp_volume_get, \
  2597. .put = snd_hda_mixer_amp_volume_put, \
  2598. .tlv = { .c = mic_boost_tlv }, \
  2599. .private_value = HDA_COMPOSE_AMP_VAL(nid, 3, 0, HDA_INPUT) }
  2600. /* capture mixer elements */
  2601. static struct snd_kcontrol_new vt1708S_capture_mixer[] = {
  2602. HDA_CODEC_VOLUME("Capture Volume", 0x13, 0x0, HDA_INPUT),
  2603. HDA_CODEC_MUTE("Capture Switch", 0x13, 0x0, HDA_INPUT),
  2604. HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x14, 0x0, HDA_INPUT),
  2605. HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x14, 0x0, HDA_INPUT),
  2606. MIC_BOOST_VOLUME("Mic Boost Capture Volume", 0x1A),
  2607. MIC_BOOST_VOLUME("Front Mic Boost Capture Volume", 0x1E),
  2608. {
  2609. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  2610. /* The multiple "Capture Source" controls confuse alsamixer
  2611. * So call somewhat different..
  2612. */
  2613. /* .name = "Capture Source", */
  2614. .name = "Input Source",
  2615. .count = 1,
  2616. .info = via_mux_enum_info,
  2617. .get = via_mux_enum_get,
  2618. .put = via_mux_enum_put,
  2619. },
  2620. { } /* end */
  2621. };
  2622. static struct hda_verb vt1708S_volume_init_verbs[] = {
  2623. /* Unmute ADC0-1 and set the default input to mic-in */
  2624. {0x13, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2625. {0x14, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2626. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the
  2627. * analog-loopback mixer widget */
  2628. /* Amp Indices: CD = 1, Mic1 = 2, Line = 3, Mic2 = 4 */
  2629. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  2630. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  2631. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  2632. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  2633. {0x16, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(4)},
  2634. /* Setup default input of PW4 to MW0 */
  2635. {0x1d, AC_VERB_SET_CONNECT_SEL, 0x0},
  2636. /* PW9, PW10 Output enable */
  2637. {0x20, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  2638. {0x21, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  2639. /* Enable Mic Boost Volume backdoor */
  2640. {0x1, 0xf98, 0x1},
  2641. { }
  2642. };
  2643. static struct hda_verb vt1708S_uniwill_init_verbs[] = {
  2644. {0x1d, AC_VERB_SET_UNSOLICITED_ENABLE,
  2645. AC_USRSP_EN | VIA_HP_EVENT | VIA_JACK_EVENT},
  2646. {0x19, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2647. {0x1a, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2648. {0x1b, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2649. {0x1c, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2650. {0x1e, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2651. {0x22, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2652. {0x23, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  2653. { }
  2654. };
  2655. static struct hda_pcm_stream vt1708S_pcm_analog_playback = {
  2656. .substreams = 2,
  2657. .channels_min = 2,
  2658. .channels_max = 8,
  2659. .nid = 0x10, /* NID to query formats and rates */
  2660. .ops = {
  2661. .open = via_playback_pcm_open,
  2662. .prepare = via_playback_pcm_prepare,
  2663. .cleanup = via_playback_pcm_cleanup,
  2664. .close = via_pcm_open_close
  2665. },
  2666. };
  2667. static struct hda_pcm_stream vt1708S_pcm_analog_capture = {
  2668. .substreams = 2,
  2669. .channels_min = 2,
  2670. .channels_max = 2,
  2671. .nid = 0x13, /* NID to query formats and rates */
  2672. .ops = {
  2673. .open = via_pcm_open_close,
  2674. .prepare = via_capture_pcm_prepare,
  2675. .cleanup = via_capture_pcm_cleanup,
  2676. .close = via_pcm_open_close
  2677. },
  2678. };
  2679. static struct hda_pcm_stream vt1708S_pcm_digital_playback = {
  2680. .substreams = 1,
  2681. .channels_min = 2,
  2682. .channels_max = 2,
  2683. /* NID is set in via_build_pcms */
  2684. .ops = {
  2685. .open = via_dig_playback_pcm_open,
  2686. .close = via_dig_playback_pcm_close,
  2687. .prepare = via_dig_playback_pcm_prepare,
  2688. .cleanup = via_dig_playback_pcm_cleanup
  2689. },
  2690. };
  2691. /* fill in the dac_nids table from the parsed pin configuration */
  2692. static int vt1708S_auto_fill_dac_nids(struct via_spec *spec,
  2693. const struct auto_pin_cfg *cfg)
  2694. {
  2695. int i;
  2696. hda_nid_t nid;
  2697. spec->multiout.num_dacs = cfg->line_outs;
  2698. spec->multiout.dac_nids = spec->private_dac_nids;
  2699. for (i = 0; i < 4; i++) {
  2700. nid = cfg->line_out_pins[i];
  2701. if (nid) {
  2702. /* config dac list */
  2703. switch (i) {
  2704. case AUTO_SEQ_FRONT:
  2705. spec->multiout.dac_nids[i] = 0x10;
  2706. break;
  2707. case AUTO_SEQ_CENLFE:
  2708. spec->multiout.dac_nids[i] = 0x24;
  2709. break;
  2710. case AUTO_SEQ_SURROUND:
  2711. spec->multiout.dac_nids[i] = 0x11;
  2712. break;
  2713. case AUTO_SEQ_SIDE:
  2714. spec->multiout.dac_nids[i] = 0x25;
  2715. break;
  2716. }
  2717. }
  2718. }
  2719. return 0;
  2720. }
  2721. /* add playback controls from the parsed DAC table */
  2722. static int vt1708S_auto_create_multi_out_ctls(struct via_spec *spec,
  2723. const struct auto_pin_cfg *cfg)
  2724. {
  2725. char name[32];
  2726. static const char *chname[4] = { "Front", "Surround", "C/LFE", "Side" };
  2727. hda_nid_t nid_vols[] = {0x10, 0x11, 0x24, 0x25};
  2728. hda_nid_t nid_mutes[] = {0x1C, 0x18, 0x26, 0x27};
  2729. hda_nid_t nid, nid_vol, nid_mute;
  2730. int i, err;
  2731. for (i = 0; i <= AUTO_SEQ_SIDE; i++) {
  2732. nid = cfg->line_out_pins[i];
  2733. if (!nid)
  2734. continue;
  2735. nid_vol = nid_vols[i];
  2736. nid_mute = nid_mutes[i];
  2737. if (i == AUTO_SEQ_CENLFE) {
  2738. /* Center/LFE */
  2739. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2740. "Center Playback Volume",
  2741. HDA_COMPOSE_AMP_VAL(nid_vol, 1, 0,
  2742. HDA_OUTPUT));
  2743. if (err < 0)
  2744. return err;
  2745. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2746. "LFE Playback Volume",
  2747. HDA_COMPOSE_AMP_VAL(nid_vol, 2, 0,
  2748. HDA_OUTPUT));
  2749. if (err < 0)
  2750. return err;
  2751. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2752. "Center Playback Switch",
  2753. HDA_COMPOSE_AMP_VAL(nid_mute,
  2754. 1, 0,
  2755. HDA_OUTPUT));
  2756. if (err < 0)
  2757. return err;
  2758. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2759. "LFE Playback Switch",
  2760. HDA_COMPOSE_AMP_VAL(nid_mute,
  2761. 2, 0,
  2762. HDA_OUTPUT));
  2763. if (err < 0)
  2764. return err;
  2765. } else if (i == AUTO_SEQ_FRONT) {
  2766. /* add control to mixer index 0 */
  2767. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2768. "Master Front Playback Volume",
  2769. HDA_COMPOSE_AMP_VAL(0x16, 3, 0,
  2770. HDA_INPUT));
  2771. if (err < 0)
  2772. return err;
  2773. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2774. "Master Front Playback Switch",
  2775. HDA_COMPOSE_AMP_VAL(0x16, 3, 0,
  2776. HDA_INPUT));
  2777. if (err < 0)
  2778. return err;
  2779. /* Front */
  2780. sprintf(name, "%s Playback Volume", chname[i]);
  2781. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  2782. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  2783. HDA_OUTPUT));
  2784. if (err < 0)
  2785. return err;
  2786. sprintf(name, "%s Playback Switch", chname[i]);
  2787. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  2788. HDA_COMPOSE_AMP_VAL(nid_mute,
  2789. 3, 0,
  2790. HDA_OUTPUT));
  2791. if (err < 0)
  2792. return err;
  2793. } else {
  2794. sprintf(name, "%s Playback Volume", chname[i]);
  2795. err = via_add_control(spec, VIA_CTL_WIDGET_VOL, name,
  2796. HDA_COMPOSE_AMP_VAL(nid_vol, 3, 0,
  2797. HDA_OUTPUT));
  2798. if (err < 0)
  2799. return err;
  2800. sprintf(name, "%s Playback Switch", chname[i]);
  2801. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE, name,
  2802. HDA_COMPOSE_AMP_VAL(nid_mute,
  2803. 3, 0,
  2804. HDA_OUTPUT));
  2805. if (err < 0)
  2806. return err;
  2807. }
  2808. }
  2809. return 0;
  2810. }
  2811. static int vt1708S_auto_create_hp_ctls(struct via_spec *spec, hda_nid_t pin)
  2812. {
  2813. int err;
  2814. if (!pin)
  2815. return 0;
  2816. spec->multiout.hp_nid = VT1708S_HP_NID; /* AOW3 */
  2817. spec->hp_independent_mode_index = 1;
  2818. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  2819. "Headphone Playback Volume",
  2820. HDA_COMPOSE_AMP_VAL(0x25, 3, 0, HDA_OUTPUT));
  2821. if (err < 0)
  2822. return err;
  2823. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  2824. "Headphone Playback Switch",
  2825. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  2826. if (err < 0)
  2827. return err;
  2828. create_hp_imux(spec);
  2829. return 0;
  2830. }
  2831. /* create playback/capture controls for input pins */
  2832. static int vt1708S_auto_create_analog_input_ctls(struct via_spec *spec,
  2833. const struct auto_pin_cfg *cfg)
  2834. {
  2835. static char *labels[] = {
  2836. "Mic", "Front Mic", "Line", "Front Line", "CD", "Aux", NULL
  2837. };
  2838. struct hda_input_mux *imux = &spec->private_imux[0];
  2839. int i, err, idx = 0;
  2840. /* for internal loopback recording select */
  2841. imux->items[imux->num_items].label = "Stereo Mixer";
  2842. imux->items[imux->num_items].index = 5;
  2843. imux->num_items++;
  2844. for (i = 0; i < AUTO_PIN_LAST; i++) {
  2845. if (!cfg->input_pins[i])
  2846. continue;
  2847. switch (cfg->input_pins[i]) {
  2848. case 0x1a: /* Mic */
  2849. idx = 2;
  2850. break;
  2851. case 0x1b: /* Line In */
  2852. idx = 3;
  2853. break;
  2854. case 0x1e: /* Front Mic */
  2855. idx = 4;
  2856. break;
  2857. case 0x1f: /* CD */
  2858. idx = 1;
  2859. break;
  2860. }
  2861. err = via_new_analog_input(spec, labels[i], idx, 0x16);
  2862. if (err < 0)
  2863. return err;
  2864. imux->items[imux->num_items].label = labels[i];
  2865. imux->items[imux->num_items].index = idx-1;
  2866. imux->num_items++;
  2867. }
  2868. return 0;
  2869. }
  2870. /* fill out digital output widgets; one for master and one for slave outputs */
  2871. static void fill_dig_outs(struct hda_codec *codec)
  2872. {
  2873. struct via_spec *spec = codec->spec;
  2874. int i;
  2875. for (i = 0; i < spec->autocfg.dig_outs; i++) {
  2876. hda_nid_t nid;
  2877. int conn;
  2878. nid = spec->autocfg.dig_out_pins[i];
  2879. if (!nid)
  2880. continue;
  2881. conn = snd_hda_get_connections(codec, nid, &nid, 1);
  2882. if (conn < 1)
  2883. continue;
  2884. if (!spec->multiout.dig_out_nid)
  2885. spec->multiout.dig_out_nid = nid;
  2886. else {
  2887. spec->slave_dig_outs[0] = nid;
  2888. break; /* at most two dig outs */
  2889. }
  2890. }
  2891. }
  2892. static int vt1708S_parse_auto_config(struct hda_codec *codec)
  2893. {
  2894. struct via_spec *spec = codec->spec;
  2895. int err;
  2896. err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL);
  2897. if (err < 0)
  2898. return err;
  2899. err = vt1708S_auto_fill_dac_nids(spec, &spec->autocfg);
  2900. if (err < 0)
  2901. return err;
  2902. if (!spec->autocfg.line_outs && !spec->autocfg.hp_pins[0])
  2903. return 0; /* can't find valid BIOS pin config */
  2904. err = vt1708S_auto_create_multi_out_ctls(spec, &spec->autocfg);
  2905. if (err < 0)
  2906. return err;
  2907. err = vt1708S_auto_create_hp_ctls(spec, spec->autocfg.hp_pins[0]);
  2908. if (err < 0)
  2909. return err;
  2910. err = vt1708S_auto_create_analog_input_ctls(spec, &spec->autocfg);
  2911. if (err < 0)
  2912. return err;
  2913. spec->multiout.max_channels = spec->multiout.num_dacs * 2;
  2914. fill_dig_outs(codec);
  2915. if (spec->kctls.list)
  2916. spec->mixers[spec->num_mixers++] = spec->kctls.list;
  2917. spec->input_mux = &spec->private_imux[0];
  2918. if (spec->hp_mux)
  2919. spec->mixers[spec->num_mixers++] = via_hp_mixer;
  2920. spec->mixers[spec->num_mixers++] = via_smart51_mixer;
  2921. return 1;
  2922. }
  2923. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2924. static struct hda_amp_list vt1708S_loopbacks[] = {
  2925. { 0x16, HDA_INPUT, 1 },
  2926. { 0x16, HDA_INPUT, 2 },
  2927. { 0x16, HDA_INPUT, 3 },
  2928. { 0x16, HDA_INPUT, 4 },
  2929. { } /* end */
  2930. };
  2931. #endif
  2932. static int patch_vt1708S(struct hda_codec *codec)
  2933. {
  2934. struct via_spec *spec;
  2935. int err;
  2936. /* create a codec specific record */
  2937. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  2938. if (spec == NULL)
  2939. return -ENOMEM;
  2940. codec->spec = spec;
  2941. /* automatic parse from the BIOS config */
  2942. err = vt1708S_parse_auto_config(codec);
  2943. if (err < 0) {
  2944. via_free(codec);
  2945. return err;
  2946. } else if (!err) {
  2947. printk(KERN_INFO "hda_codec: Cannot set up configuration "
  2948. "from BIOS. Using genenic mode...\n");
  2949. }
  2950. spec->init_verbs[spec->num_iverbs++] = vt1708S_volume_init_verbs;
  2951. spec->init_verbs[spec->num_iverbs++] = vt1708S_uniwill_init_verbs;
  2952. spec->stream_name_analog = "VT1708S Analog";
  2953. spec->stream_analog_playback = &vt1708S_pcm_analog_playback;
  2954. spec->stream_analog_capture = &vt1708S_pcm_analog_capture;
  2955. spec->stream_name_digital = "VT1708S Digital";
  2956. spec->stream_digital_playback = &vt1708S_pcm_digital_playback;
  2957. if (!spec->adc_nids && spec->input_mux) {
  2958. spec->adc_nids = vt1708S_adc_nids;
  2959. spec->num_adc_nids = ARRAY_SIZE(vt1708S_adc_nids);
  2960. get_mux_nids(codec);
  2961. spec->mixers[spec->num_mixers] = vt1708S_capture_mixer;
  2962. spec->num_mixers++;
  2963. }
  2964. codec->patch_ops = via_patch_ops;
  2965. codec->patch_ops.init = via_auto_init;
  2966. codec->patch_ops.unsol_event = via_unsol_event;
  2967. #ifdef CONFIG_SND_HDA_POWER_SAVE
  2968. spec->loopback.amplist = vt1708S_loopbacks;
  2969. #endif
  2970. /* correct names for VT1708BCE */
  2971. if (get_codec_type(codec) == VT1708BCE) {
  2972. kfree(codec->chip_name);
  2973. codec->chip_name = kstrdup("VT1708BCE", GFP_KERNEL);
  2974. snprintf(codec->bus->card->mixername,
  2975. sizeof(codec->bus->card->mixername),
  2976. "%s %s", codec->vendor_name, codec->chip_name);
  2977. spec->stream_name_analog = "VT1708BCE Analog";
  2978. spec->stream_name_digital = "VT1708BCE Digital";
  2979. }
  2980. return 0;
  2981. }
  2982. /* Patch for VT1702 */
  2983. /* capture mixer elements */
  2984. static struct snd_kcontrol_new vt1702_capture_mixer[] = {
  2985. HDA_CODEC_VOLUME("Capture Volume", 0x12, 0x0, HDA_INPUT),
  2986. HDA_CODEC_MUTE("Capture Switch", 0x12, 0x0, HDA_INPUT),
  2987. HDA_CODEC_VOLUME_IDX("Capture Volume", 1, 0x20, 0x0, HDA_INPUT),
  2988. HDA_CODEC_MUTE_IDX("Capture Switch", 1, 0x20, 0x0, HDA_INPUT),
  2989. HDA_CODEC_VOLUME("Digital Mic Capture Volume", 0x1F, 0x0, HDA_INPUT),
  2990. HDA_CODEC_MUTE("Digital Mic Capture Switch", 0x1F, 0x0, HDA_INPUT),
  2991. HDA_CODEC_VOLUME("Digital Mic Boost Capture Volume", 0x1E, 0x0,
  2992. HDA_INPUT),
  2993. {
  2994. .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
  2995. /* The multiple "Capture Source" controls confuse alsamixer
  2996. * So call somewhat different..
  2997. */
  2998. /* .name = "Capture Source", */
  2999. .name = "Input Source",
  3000. .count = 1,
  3001. .info = via_mux_enum_info,
  3002. .get = via_mux_enum_get,
  3003. .put = via_mux_enum_put,
  3004. },
  3005. { } /* end */
  3006. };
  3007. static struct hda_verb vt1702_volume_init_verbs[] = {
  3008. /*
  3009. * Unmute ADC0-1 and set the default input to mic-in
  3010. */
  3011. {0x12, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  3012. {0x1F, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  3013. {0x20, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  3014. /* Unmute input amps (CD, Line In, Mic 1 & Mic 2) of the analog-loopback
  3015. * mixer widget
  3016. */
  3017. /* Amp Indices: Mic1 = 1, Line = 1, Mic2 = 3 */
  3018. {0x1A, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(0)},
  3019. {0x1A, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(1)},
  3020. {0x1A, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(2)},
  3021. {0x1A, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_UNMUTE(3)},
  3022. {0x1A, AC_VERB_SET_AMP_GAIN_MUTE, AMP_IN_MUTE(4)},
  3023. /* Setup default input of PW4 to MW0 */
  3024. {0x17, AC_VERB_SET_CONNECT_SEL, 0x1},
  3025. /* PW6 PW7 Output enable */
  3026. {0x19, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  3027. {0x1C, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x40},
  3028. { }
  3029. };
  3030. static struct hda_verb vt1702_uniwill_init_verbs[] = {
  3031. {0x17, AC_VERB_SET_UNSOLICITED_ENABLE,
  3032. AC_USRSP_EN | VIA_HP_EVENT | VIA_JACK_EVENT},
  3033. {0x14, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  3034. {0x15, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  3035. {0x16, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  3036. {0x18, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN | VIA_JACK_EVENT},
  3037. { }
  3038. };
  3039. static struct hda_pcm_stream vt1702_pcm_analog_playback = {
  3040. .substreams = 2,
  3041. .channels_min = 2,
  3042. .channels_max = 2,
  3043. .nid = 0x10, /* NID to query formats and rates */
  3044. .ops = {
  3045. .open = via_playback_pcm_open,
  3046. .prepare = via_playback_multi_pcm_prepare,
  3047. .cleanup = via_playback_multi_pcm_cleanup,
  3048. .close = via_pcm_open_close
  3049. },
  3050. };
  3051. static struct hda_pcm_stream vt1702_pcm_analog_capture = {
  3052. .substreams = 3,
  3053. .channels_min = 2,
  3054. .channels_max = 2,
  3055. .nid = 0x12, /* NID to query formats and rates */
  3056. .ops = {
  3057. .open = via_pcm_open_close,
  3058. .prepare = via_capture_pcm_prepare,
  3059. .cleanup = via_capture_pcm_cleanup,
  3060. .close = via_pcm_open_close
  3061. },
  3062. };
  3063. static struct hda_pcm_stream vt1702_pcm_digital_playback = {
  3064. .substreams = 2,
  3065. .channels_min = 2,
  3066. .channels_max = 2,
  3067. /* NID is set in via_build_pcms */
  3068. .ops = {
  3069. .open = via_dig_playback_pcm_open,
  3070. .close = via_dig_playback_pcm_close,
  3071. .prepare = via_dig_playback_pcm_prepare,
  3072. .cleanup = via_dig_playback_pcm_cleanup
  3073. },
  3074. };
  3075. /* fill in the dac_nids table from the parsed pin configuration */
  3076. static int vt1702_auto_fill_dac_nids(struct via_spec *spec,
  3077. const struct auto_pin_cfg *cfg)
  3078. {
  3079. spec->multiout.num_dacs = 1;
  3080. spec->multiout.dac_nids = spec->private_dac_nids;
  3081. if (cfg->line_out_pins[0]) {
  3082. /* config dac list */
  3083. spec->multiout.dac_nids[0] = 0x10;
  3084. }
  3085. return 0;
  3086. }
  3087. /* add playback controls from the parsed DAC table */
  3088. static int vt1702_auto_create_line_out_ctls(struct via_spec *spec,
  3089. const struct auto_pin_cfg *cfg)
  3090. {
  3091. int err;
  3092. if (!cfg->line_out_pins[0])
  3093. return -1;
  3094. /* add control to mixer index 0 */
  3095. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  3096. "Master Front Playback Volume",
  3097. HDA_COMPOSE_AMP_VAL(0x1A, 3, 0, HDA_INPUT));
  3098. if (err < 0)
  3099. return err;
  3100. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  3101. "Master Front Playback Switch",
  3102. HDA_COMPOSE_AMP_VAL(0x1A, 3, 0, HDA_INPUT));
  3103. if (err < 0)
  3104. return err;
  3105. /* Front */
  3106. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  3107. "Front Playback Volume",
  3108. HDA_COMPOSE_AMP_VAL(0x10, 3, 0, HDA_OUTPUT));
  3109. if (err < 0)
  3110. return err;
  3111. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  3112. "Front Playback Switch",
  3113. HDA_COMPOSE_AMP_VAL(0x16, 3, 0, HDA_OUTPUT));
  3114. if (err < 0)
  3115. return err;
  3116. return 0;
  3117. }
  3118. static int vt1702_auto_create_hp_ctls(struct via_spec *spec, hda_nid_t pin)
  3119. {
  3120. int err, i;
  3121. struct hda_input_mux *imux;
  3122. static const char *texts[] = { "ON", "OFF", NULL};
  3123. if (!pin)
  3124. return 0;
  3125. spec->multiout.hp_nid = 0x1D;
  3126. spec->hp_independent_mode_index = 0;
  3127. err = via_add_control(spec, VIA_CTL_WIDGET_VOL,
  3128. "Headphone Playback Volume",
  3129. HDA_COMPOSE_AMP_VAL(0x1D, 3, 0, HDA_OUTPUT));
  3130. if (err < 0)
  3131. return err;
  3132. err = via_add_control(spec, VIA_CTL_WIDGET_MUTE,
  3133. "Headphone Playback Switch",
  3134. HDA_COMPOSE_AMP_VAL(pin, 3, 0, HDA_OUTPUT));
  3135. if (err < 0)
  3136. return err;
  3137. imux = &spec->private_imux[1];
  3138. /* for hp mode select */
  3139. i = 0;
  3140. while (texts[i] != NULL) {
  3141. imux->items[imux->num_items].label = texts[i];
  3142. imux->items[imux->num_items].index = i;
  3143. imux->num_items++;
  3144. i++;
  3145. }
  3146. spec->hp_mux = &spec->private_imux[1];
  3147. return 0;
  3148. }
  3149. /* create playback/capture controls for input pins */
  3150. static int vt1702_auto_create_analog_input_ctls(struct via_spec *spec,
  3151. const struct auto_pin_cfg *cfg)
  3152. {
  3153. static char *labels[] = {
  3154. "Mic", "Front Mic", "Line", "Front Line", "CD", "Aux", NULL
  3155. };
  3156. struct hda_input_mux *imux = &spec->private_imux[0];
  3157. int i, err, idx = 0;
  3158. /* for internal loopback recording select */
  3159. imux->items[imux->num_items].label = "Stereo Mixer";
  3160. imux->items[imux->num_items].index = 3;
  3161. imux->num_items++;
  3162. for (i = 0; i < AUTO_PIN_LAST; i++) {
  3163. if (!cfg->input_pins[i])
  3164. continue;
  3165. switch (cfg->input_pins[i]) {
  3166. case 0x14: /* Mic */
  3167. idx = 1;
  3168. break;
  3169. case 0x15: /* Line In */
  3170. idx = 2;
  3171. break;
  3172. case 0x18: /* Front Mic */
  3173. idx = 3;
  3174. break;
  3175. }
  3176. err = via_new_analog_input(spec, labels[i], idx, 0x1A);
  3177. if (err < 0)
  3178. return err;
  3179. imux->items[imux->num_items].label = labels[i];
  3180. imux->items[imux->num_items].index = idx-1;
  3181. imux->num_items++;
  3182. }
  3183. return 0;
  3184. }
  3185. static int vt1702_parse_auto_config(struct hda_codec *codec)
  3186. {
  3187. struct via_spec *spec = codec->spec;
  3188. int err;
  3189. err = snd_hda_parse_pin_def_config(codec, &spec->autocfg, NULL);
  3190. if (err < 0)
  3191. return err;
  3192. err = vt1702_auto_fill_dac_nids(spec, &spec->autocfg);
  3193. if (err < 0)
  3194. return err;
  3195. if (!spec->autocfg.line_outs && !spec->autocfg.hp_pins[0])
  3196. return 0; /* can't find valid BIOS pin config */
  3197. err = vt1702_auto_create_line_out_ctls(spec, &spec->autocfg);
  3198. if (err < 0)
  3199. return err;
  3200. err = vt1702_auto_create_hp_ctls(spec, spec->autocfg.hp_pins[0]);
  3201. if (err < 0)
  3202. return err;
  3203. /* limit AA path volume to 0 dB */
  3204. snd_hda_override_amp_caps(codec, 0x1A, HDA_INPUT,
  3205. (0x17 << AC_AMPCAP_OFFSET_SHIFT) |
  3206. (0x17 << AC_AMPCAP_NUM_STEPS_SHIFT) |
  3207. (0x5 << AC_AMPCAP_STEP_SIZE_SHIFT) |
  3208. (1 << AC_AMPCAP_MUTE_SHIFT));
  3209. err = vt1702_auto_create_analog_input_ctls(spec, &spec->autocfg);
  3210. if (err < 0)
  3211. return err;
  3212. spec->multiout.max_channels = spec->multiout.num_dacs * 2;
  3213. fill_dig_outs(codec);
  3214. if (spec->kctls.list)
  3215. spec->mixers[spec->num_mixers++] = spec->kctls.list;
  3216. spec->input_mux = &spec->private_imux[0];
  3217. if (spec->hp_mux)
  3218. spec->mixers[spec->num_mixers++] = via_hp_mixer;
  3219. return 1;
  3220. }
  3221. #ifdef CONFIG_SND_HDA_POWER_SAVE
  3222. static struct hda_amp_list vt1702_loopbacks[] = {
  3223. { 0x1A, HDA_INPUT, 1 },
  3224. { 0x1A, HDA_INPUT, 2 },
  3225. { 0x1A, HDA_INPUT, 3 },
  3226. { 0x1A, HDA_INPUT, 4 },
  3227. { } /* end */
  3228. };
  3229. #endif
  3230. static int patch_vt1702(struct hda_codec *codec)
  3231. {
  3232. struct via_spec *spec;
  3233. int err;
  3234. unsigned int response;
  3235. unsigned char control;
  3236. /* create a codec specific record */
  3237. spec = kzalloc(sizeof(*spec), GFP_KERNEL);
  3238. if (spec == NULL)
  3239. return -ENOMEM;
  3240. codec->spec = spec;
  3241. /* automatic parse from the BIOS config */
  3242. err = vt1702_parse_auto_config(codec);
  3243. if (err < 0) {
  3244. via_free(codec);
  3245. return err;
  3246. } else if (!err) {
  3247. printk(KERN_INFO "hda_codec: Cannot set up configuration "
  3248. "from BIOS. Using genenic mode...\n");
  3249. }
  3250. spec->init_verbs[spec->num_iverbs++] = vt1702_volume_init_verbs;
  3251. spec->init_verbs[spec->num_iverbs++] = vt1702_uniwill_init_verbs;
  3252. spec->stream_name_analog = "VT1702 Analog";
  3253. spec->stream_analog_playback = &vt1702_pcm_analog_playback;
  3254. spec->stream_analog_capture = &vt1702_pcm_analog_capture;
  3255. spec->stream_name_digital = "VT1702 Digital";
  3256. spec->stream_digital_playback = &vt1702_pcm_digital_playback;
  3257. if (!spec->adc_nids && spec->input_mux) {
  3258. spec->adc_nids = vt1702_adc_nids;
  3259. spec->num_adc_nids = ARRAY_SIZE(vt1702_adc_nids);
  3260. get_mux_nids(codec);
  3261. spec->mixers[spec->num_mixers] = vt1702_capture_mixer;
  3262. spec->num_mixers++;
  3263. }
  3264. codec->patch_ops = via_patch_ops;
  3265. codec->patch_ops.init = via_auto_init;
  3266. codec->patch_ops.unsol_event = via_unsol_event;
  3267. #ifdef CONFIG_SND_HDA_POWER_SAVE
  3268. spec->loopback.amplist = vt1702_loopbacks;
  3269. #endif
  3270. /* Open backdoor */
  3271. response = snd_hda_codec_read(codec, codec->afg, 0, 0xF8C, 0);
  3272. control = (unsigned char)(response & 0xff);
  3273. control |= 0x3;
  3274. snd_hda_codec_write(codec, codec->afg, 0, 0xF88, control);
  3275. /* Enable GPIO 0&1 for volume&mute control */
  3276. /* Enable GPIO 2 for DMIC-DATA */
  3277. response = snd_hda_codec_read(codec, codec->afg, 0, 0xF84, 0);
  3278. control = (unsigned char)((response >> 16) & 0x3f);
  3279. snd_hda_codec_write(codec, codec->afg, 0, 0xF82, control);
  3280. return 0;
  3281. }
  3282. /*
  3283. * patch entries
  3284. */
  3285. static struct hda_codec_preset snd_hda_preset_via[] = {
  3286. { .id = 0x11061708, .name = "VT1708", .patch = patch_vt1708},
  3287. { .id = 0x11061709, .name = "VT1708", .patch = patch_vt1708},
  3288. { .id = 0x1106170a, .name = "VT1708", .patch = patch_vt1708},
  3289. { .id = 0x1106170b, .name = "VT1708", .patch = patch_vt1708},
  3290. { .id = 0x1106e710, .name = "VT1709 10-Ch",
  3291. .patch = patch_vt1709_10ch},
  3292. { .id = 0x1106e711, .name = "VT1709 10-Ch",
  3293. .patch = patch_vt1709_10ch},
  3294. { .id = 0x1106e712, .name = "VT1709 10-Ch",
  3295. .patch = patch_vt1709_10ch},
  3296. { .id = 0x1106e713, .name = "VT1709 10-Ch",
  3297. .patch = patch_vt1709_10ch},
  3298. { .id = 0x1106e714, .name = "VT1709 6-Ch",
  3299. .patch = patch_vt1709_6ch},
  3300. { .id = 0x1106e715, .name = "VT1709 6-Ch",
  3301. .patch = patch_vt1709_6ch},
  3302. { .id = 0x1106e716, .name = "VT1709 6-Ch",
  3303. .patch = patch_vt1709_6ch},
  3304. { .id = 0x1106e717, .name = "VT1709 6-Ch",
  3305. .patch = patch_vt1709_6ch},
  3306. { .id = 0x1106e720, .name = "VT1708B 8-Ch",
  3307. .patch = patch_vt1708B_8ch},
  3308. { .id = 0x1106e721, .name = "VT1708B 8-Ch",
  3309. .patch = patch_vt1708B_8ch},
  3310. { .id = 0x1106e722, .name = "VT1708B 8-Ch",
  3311. .patch = patch_vt1708B_8ch},
  3312. { .id = 0x1106e723, .name = "VT1708B 8-Ch",
  3313. .patch = patch_vt1708B_8ch},
  3314. { .id = 0x1106e724, .name = "VT1708B 4-Ch",
  3315. .patch = patch_vt1708B_4ch},
  3316. { .id = 0x1106e725, .name = "VT1708B 4-Ch",
  3317. .patch = patch_vt1708B_4ch},
  3318. { .id = 0x1106e726, .name = "VT1708B 4-Ch",
  3319. .patch = patch_vt1708B_4ch},
  3320. { .id = 0x1106e727, .name = "VT1708B 4-Ch",
  3321. .patch = patch_vt1708B_4ch},
  3322. { .id = 0x11060397, .name = "VT1708S",
  3323. .patch = patch_vt1708S},
  3324. { .id = 0x11061397, .name = "VT1708S",
  3325. .patch = patch_vt1708S},
  3326. { .id = 0x11062397, .name = "VT1708S",
  3327. .patch = patch_vt1708S},
  3328. { .id = 0x11063397, .name = "VT1708S",
  3329. .patch = patch_vt1708S},
  3330. { .id = 0x11064397, .name = "VT1708S",
  3331. .patch = patch_vt1708S},
  3332. { .id = 0x11065397, .name = "VT1708S",
  3333. .patch = patch_vt1708S},
  3334. { .id = 0x11066397, .name = "VT1708S",
  3335. .patch = patch_vt1708S},
  3336. { .id = 0x11067397, .name = "VT1708S",
  3337. .patch = patch_vt1708S},
  3338. { .id = 0x11060398, .name = "VT1702",
  3339. .patch = patch_vt1702},
  3340. { .id = 0x11061398, .name = "VT1702",
  3341. .patch = patch_vt1702},
  3342. { .id = 0x11062398, .name = "VT1702",
  3343. .patch = patch_vt1702},
  3344. { .id = 0x11063398, .name = "VT1702",
  3345. .patch = patch_vt1702},
  3346. { .id = 0x11064398, .name = "VT1702",
  3347. .patch = patch_vt1702},
  3348. { .id = 0x11065398, .name = "VT1702",
  3349. .patch = patch_vt1702},
  3350. { .id = 0x11066398, .name = "VT1702",
  3351. .patch = patch_vt1702},
  3352. { .id = 0x11067398, .name = "VT1702",
  3353. .patch = patch_vt1702},
  3354. {} /* terminator */
  3355. };
  3356. MODULE_ALIAS("snd-hda-codec-id:1106*");
  3357. static struct hda_codec_preset_list via_list = {
  3358. .preset = snd_hda_preset_via,
  3359. .owner = THIS_MODULE,
  3360. };
  3361. MODULE_LICENSE("GPL");
  3362. MODULE_DESCRIPTION("VIA HD-audio codec");
  3363. static int __init patch_via_init(void)
  3364. {
  3365. return snd_hda_add_codec_preset(&via_list);
  3366. }
  3367. static void __exit patch_via_exit(void)
  3368. {
  3369. snd_hda_delete_codec_preset(&via_list);
  3370. }
  3371. module_init(patch_via_init)
  3372. module_exit(patch_via_exit)