diff options
Diffstat (limited to 'sound/pci/hda')
-rw-r--r-- | sound/pci/hda/hda_codec.c | 28 | ||||
-rw-r--r-- | sound/pci/hda/hda_codec.h | 1 | ||||
-rw-r--r-- | sound/pci/hda/hda_generic.c | 5 |
3 files changed, 22 insertions, 12 deletions
diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index 026ae726d875..6bfb081d12dd 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c | |||
@@ -432,22 +432,26 @@ void snd_hda_get_codec_name(struct hda_codec *codec, | |||
432 | } | 432 | } |
433 | 433 | ||
434 | /* | 434 | /* |
435 | * look for an AFG node | 435 | * look for an AFG and MFG nodes |
436 | * | ||
437 | * return 0 if not found | ||
438 | */ | 436 | */ |
439 | static int look_for_afg_node(struct hda_codec *codec) | 437 | static void setup_fg_nodes(struct hda_codec *codec) |
440 | { | 438 | { |
441 | int i, total_nodes; | 439 | int i, total_nodes; |
442 | hda_nid_t nid; | 440 | hda_nid_t nid; |
443 | 441 | ||
444 | total_nodes = snd_hda_get_sub_nodes(codec, AC_NODE_ROOT, &nid); | 442 | total_nodes = snd_hda_get_sub_nodes(codec, AC_NODE_ROOT, &nid); |
445 | for (i = 0; i < total_nodes; i++, nid++) { | 443 | for (i = 0; i < total_nodes; i++, nid++) { |
446 | if ((snd_hda_param_read(codec, nid, AC_PAR_FUNCTION_TYPE) & 0xff) == | 444 | switch((snd_hda_param_read(codec, nid, AC_PAR_FUNCTION_TYPE) & 0xff)) { |
447 | AC_GRP_AUDIO_FUNCTION) | 445 | case AC_GRP_AUDIO_FUNCTION: |
448 | return nid; | 446 | codec->afg = nid; |
447 | break; | ||
448 | case AC_GRP_MODEM_FUNCTION: | ||
449 | codec->mfg = nid; | ||
450 | break; | ||
451 | default: | ||
452 | break; | ||
453 | } | ||
449 | } | 454 | } |
450 | return 0; | ||
451 | } | 455 | } |
452 | 456 | ||
453 | /* | 457 | /* |
@@ -507,10 +511,9 @@ int snd_hda_codec_new(struct hda_bus *bus, unsigned int codec_addr, | |||
507 | codec->subsystem_id = snd_hda_param_read(codec, AC_NODE_ROOT, AC_PAR_SUBSYSTEM_ID); | 511 | codec->subsystem_id = snd_hda_param_read(codec, AC_NODE_ROOT, AC_PAR_SUBSYSTEM_ID); |
508 | codec->revision_id = snd_hda_param_read(codec, AC_NODE_ROOT, AC_PAR_REV_ID); | 512 | codec->revision_id = snd_hda_param_read(codec, AC_NODE_ROOT, AC_PAR_REV_ID); |
509 | 513 | ||
510 | /* FIXME: support for multiple AFGs? */ | 514 | setup_fg_nodes(codec); |
511 | codec->afg = look_for_afg_node(codec); | 515 | if (! codec->afg && ! codec->mfg) { |
512 | if (! codec->afg) { | 516 | snd_printdd("hda_codec: no AFG or MFG node found\n"); |
513 | snd_printdd("hda_codec: no AFG node found\n"); | ||
514 | snd_hda_codec_free(codec); | 517 | snd_hda_codec_free(codec); |
515 | return -ENODEV; | 518 | return -ENODEV; |
516 | } | 519 | } |
@@ -1163,6 +1166,7 @@ int snd_hda_build_controls(struct hda_bus *bus) | |||
1163 | static unsigned int rate_bits[][3] = { | 1166 | static unsigned int rate_bits[][3] = { |
1164 | /* rate in Hz, ALSA rate bitmask, HDA format value */ | 1167 | /* rate in Hz, ALSA rate bitmask, HDA format value */ |
1165 | { 8000, SNDRV_PCM_RATE_8000, 0x0500 }, /* 1/6 x 48 */ | 1168 | { 8000, SNDRV_PCM_RATE_8000, 0x0500 }, /* 1/6 x 48 */ |
1169 | { 9600, SNDRV_PCM_RATE_KNOT, 0x0400 }, /* 1/5 x 48 */ | ||
1166 | { 11025, SNDRV_PCM_RATE_11025, 0x4300 }, /* 1/4 x 44 */ | 1170 | { 11025, SNDRV_PCM_RATE_11025, 0x4300 }, /* 1/4 x 44 */ |
1167 | { 16000, SNDRV_PCM_RATE_16000, 0x0200 }, /* 1/3 x 48 */ | 1171 | { 16000, SNDRV_PCM_RATE_16000, 0x0200 }, /* 1/3 x 48 */ |
1168 | { 22050, SNDRV_PCM_RATE_22050, 0x4100 }, /* 1/2 x 44 */ | 1172 | { 22050, SNDRV_PCM_RATE_22050, 0x4100 }, /* 1/2 x 44 */ |
diff --git a/sound/pci/hda/hda_codec.h b/sound/pci/hda/hda_codec.h index dd0d99d2ad27..63a29a8a2860 100644 --- a/sound/pci/hda/hda_codec.h +++ b/sound/pci/hda/hda_codec.h | |||
@@ -514,6 +514,7 @@ struct hda_codec { | |||
514 | struct list_head list; /* list point */ | 514 | struct list_head list; /* list point */ |
515 | 515 | ||
516 | hda_nid_t afg; /* AFG node id */ | 516 | hda_nid_t afg; /* AFG node id */ |
517 | hda_nid_t mfg; /* MFG node id */ | ||
517 | 518 | ||
518 | /* ids */ | 519 | /* ids */ |
519 | u32 vendor_id; | 520 | u32 vendor_id; |
diff --git a/sound/pci/hda/hda_generic.c b/sound/pci/hda/hda_generic.c index 2d046abb5911..1229227af5b5 100644 --- a/sound/pci/hda/hda_generic.c +++ b/sound/pci/hda/hda_generic.c | |||
@@ -881,6 +881,11 @@ int snd_hda_parse_generic_codec(struct hda_codec *codec) | |||
881 | struct hda_gspec *spec; | 881 | struct hda_gspec *spec; |
882 | int err; | 882 | int err; |
883 | 883 | ||
884 | if(!codec->afg) { | ||
885 | snd_printdd("hda_generic: no generic modem yet\n"); | ||
886 | return -ENODEV; | ||
887 | } | ||
888 | |||
884 | spec = kcalloc(1, sizeof(*spec), GFP_KERNEL); | 889 | spec = kcalloc(1, sizeof(*spec), GFP_KERNEL); |
885 | if (spec == NULL) { | 890 | if (spec == NULL) { |
886 | printk(KERN_ERR "hda_generic: can't allocate spec\n"); | 891 | printk(KERN_ERR "hda_generic: can't allocate spec\n"); |