Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 216686
b: refs/heads/master
c: 9ad0e49
h: refs/heads/master
v: v3
  • Loading branch information
Kailang Yang authored and Takashi Iwai committed Sep 14, 2010
1 parent 506f06a commit 5bc6a88
Show file tree
Hide file tree
Showing 2 changed files with 99 additions and 1 deletion.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 4a4d4a6985dd37a3c96534027f054be796bf95f6
refs/heads/master: 9ad0e496519d99eb2c34f01e41500a775122c744
98 changes: 98 additions & 0 deletions trunk/sound/pci/hda/patch_realtek.c
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
#include <linux/slab.h>
#include <linux/pci.h>
#include <sound/core.h>
#include <sound/jack.h>
#include "hda_codec.h"
#include "hda_local.h"
#include "hda_beep.h"
Expand Down Expand Up @@ -282,6 +283,12 @@ struct alc_mic_route {
unsigned char amix_idx;
};

struct alc_jack {
hda_nid_t nid;
int type;
struct snd_jack *jack;
};

#define MUX_IDX_UNDEF ((unsigned char)-1)

struct alc_customize_define {
Expand Down Expand Up @@ -357,6 +364,9 @@ struct alc_spec {
/* PCM information */
struct hda_pcm pcm_rec[3]; /* used in alc_build_pcms() */

/* jack detection */
struct snd_array jacks;

/* dynamic controls, init_verbs and input_mux */
struct auto_pin_cfg autocfg;
struct alc_customize_define cdefine;
Expand Down Expand Up @@ -990,6 +1000,91 @@ static void alc_fix_pll_init(struct hda_codec *codec, hda_nid_t nid,
alc_fix_pll(codec);
}

#ifdef CONFIG_SND_HDA_INPUT_JACK
static void alc_free_jack_priv(struct snd_jack *jack)
{
struct alc_jack *jacks = jack->private_data;
jacks->nid = 0;
jacks->jack = NULL;
}

static int alc_add_jack(struct hda_codec *codec,
hda_nid_t nid, int type)
{
struct alc_spec *spec;
struct alc_jack *jack;
const char *name;
int err;

spec = codec->spec;
snd_array_init(&spec->jacks, sizeof(*jack), 32);
jack = snd_array_new(&spec->jacks);
if (!jack)
return -ENOMEM;

jack->nid = nid;
jack->type = type;
name = (type == SND_JACK_HEADPHONE) ? "Headphone" : "Mic" ;

err = snd_jack_new(codec->bus->card, name, type, &jack->jack);
if (err < 0)
return err;
jack->jack->private_data = jack;
jack->jack->private_free = alc_free_jack_priv;
return 0;
}

static void alc_report_jack(struct hda_codec *codec, hda_nid_t nid)
{
struct alc_spec *spec = codec->spec;
struct alc_jack *jacks = spec->jacks.list;

if (jacks) {
int i;
for (i = 0; i < spec->jacks.used; i++) {
if (jacks->nid == nid) {
unsigned int present;
present = snd_hda_jack_detect(codec, nid);

present = (present) ? jacks->type : 0;

snd_jack_report(jacks->jack, present);
}
jacks++;
}
}
}

static int alc_init_jacks(struct hda_codec *codec)
{
struct alc_spec *spec = codec->spec;
int err;
unsigned int hp_nid = spec->autocfg.hp_pins[0];
unsigned int mic_nid = spec->ext_mic.pin;

err = alc_add_jack(codec, hp_nid, SND_JACK_HEADPHONE);
if (err < 0)
return err;
alc_report_jack(codec, hp_nid);

err = alc_add_jack(codec, mic_nid, SND_JACK_MICROPHONE);
if (err < 0)
return err;
alc_report_jack(codec, mic_nid);

return 0;
}
#else
static inline void alc_report_jack(struct hda_codec *codec, hda_nid_t nid)
{
}

static inline int alc_init_jacks(struct hda_codec *codec)
{
return 0;
}
#endif

static void alc_automute_speaker(struct hda_codec *codec, int pinctl)
{
struct alc_spec *spec = codec->spec;
Expand All @@ -1006,6 +1101,7 @@ static void alc_automute_speaker(struct hda_codec *codec, int pinctl)
spec->jack_present = 1;
break;
}
alc_report_jack(codec, spec->autocfg.hp_pins[i]);
}

mute = spec->jack_present ? HDA_AMP_MUTE : 0;
Expand Down Expand Up @@ -1111,6 +1207,7 @@ static void alc_mic_automute(struct hda_codec *codec)
AC_VERB_SET_CONNECT_SEL,
alive->mux_idx);
}
alc_report_jack(codec, spec->ext_mic.pin);

/* FIXME: analog mixer */
}
Expand Down Expand Up @@ -14496,6 +14593,7 @@ static void alc269_auto_init(struct hda_codec *codec)
alc269_auto_init_hp_out(codec);
alc269_auto_init_analog_input(codec);
alc_auto_init_digital(codec);
alc_init_jacks(codec);
if (spec->unsol_event)
alc_inithook(codec);
}
Expand Down

0 comments on commit 5bc6a88

Please sign in to comment.