[Gta04-owner] Headset detection.
NeilBrown
neilb at suse.de
Sat Aug 25 00:49:24 CEST 2012
On Wed, 22 Aug 2012 11:08:43 +1000 NeilBrown <neilb at suse.de> wrote:
> On Tue, 21 Aug 2012 12:30:47 +0200 "Dr. H. Nikolaus Schaller"
> <hns at goldelico.com> wrote:
>
> > Hi Neil,
> >
> > Am 18.08.2012 um 02:13 schrieb NeilBrown:
> >
> > > I don't suppose there is an existing standard....
> >
> > Not really.
> >
> > Generally you can only say:
> > short on Mic = green phone key (answer call on headset)
> > some kOhm on Mic = there is a Mic
> > high Z = there is no Mic
>
> So 'short on Mic' cannot be distinguished from a 3-contact headset (no
> microphone, 'shield' is larger and shorts together 'shield' and 'ring-1').
> I guess a transition from 'some kOhm' to 'short-on-Mic' means the button was
> pressed, where as a transition from 'high Z' to 'short on Mic' means a
> 3-contact headset was plugged in.
>
> Also if we want button presses to work well I probably need to increase the
> poll rate when something is plugged in.
>
> I don't have a working 2.5mm headset, or a working 3.5-2.5 4-contact
> converter so I cannot experiment very much.
> I'll see if I can get hold of one...
I got hold of one (next day delivery! I was impressed :-)
The following patch which I have committed detects whether a mic is present
or not, and can detect a button which shorts the mic line.
I'm perplexed by the numbers though.
- open circuit (nothing plugged in) gives a very low reading (20) - negligible
current flowing. That makes sense.
- closed circuit (3-pin connector or button pressed) gives a high readings,
(800ish). Max current allowed by internal resistors is flowing. That also
makes sense.
- mic present gives an *even*higher* reading!! 830 to 850. What could cause
that? How can the mic cause more current to flow? I thought there might be
leakage from the headphone driver but I couldn't measure any.
>
> If someone else wants to experiment, just report the values that appear in
> /sys/class/hwmon/hwmon0/device/in7_input
> when different events happen with some headset (with my any kernel which
> enables this driver, just as my 3.5 branch).
Note that you need to have /dev/input/jack open (e.g. evtest /dev/input/jack)
for these readings to be valid.
Finally: while I can play music through my headset with no trouble, the mic
doesn't work very well - I can hear what I say but it is very very quiet.
Has anyone else tried with a head-set microphone? Any luck?
Among the things I tried was
alsactl -f /opt/qtmoko/etc/alsa/gsmheadset.state restore
This is weird - when I play music I hear it coming from the earpiece even
though that is muted. When I unmute the earpiece it keeps playing. When I
mute again it goes silent. Something must be wrong in the driver.
NeilBrown
commit 169e831d949b83f7b7bb536b9b5009468af98cd2
Author: NeilBrown <neilb at suse.de>
Date: Sat Aug 25 08:44:51 2012 +1000
GTA04 audio headset jack detect.
Enhance jack detection to differentiate with and without a microphone,
and to report a button-press when the microphone is shorted.
Signed-off-by: NeilBrown <neilb at suse.de>
diff --git a/GTA04/udev-rules/input.rules b/GTA04/udev-rules/input.rules
index a96feb8..2cc8df9 100644
--- a/GTA04/udev-rules/input.rules
+++ b/GTA04/udev-rules/input.rules
@@ -4,4 +4,4 @@ SUBSYSTEM=="input", KERNEL=="event[0-9]*", ATTRS{modalias}=="input:*-e0,3,*a0,1,
SUBSYSTEM=="input", KERNEL=="event[0-9]*", ATTRS{modalias}=="input:*-e0,1,*k74,*", SYMLINK+="input/power"
SUBSYSTEM=="input", KERNEL=="event[0-9]*", ATTRS{modalias}=="input:*-e0,1,*kA9,*", SYMLINK+="input/aux"
SUBSYSTEM=="input", KERNEL=="event[0-9]*", ATTRS{modalias}=="input:*-e0,1,*kF0,*", SYMLINK+="input/incoming"
-SUBSYSTEM=="input", KERNEL=="event[0-9]*", ATTRS{modalias}=="input:*-e0,5,*w[24678D]*", SYMLINK+="input/jack"
+SUBSYSTEM=="input", KERNEL=="event[0-9]*", ATTRS{modalias}=="input:*-e0*,5,*w[24678D]*", SYMLINK+="input/jack"
diff --git a/sound/soc/omap/gta04-audio.c b/sound/soc/omap/gta04-audio.c
index 1048098..804bce9 100644
--- a/sound/soc/omap/gta04-audio.c
+++ b/sound/soc/omap/gta04-audio.c
@@ -145,20 +145,63 @@ static struct {
struct delayed_work jack_work;
struct snd_soc_codec *codec;
int open;
+ /* When any jack is present, we:
+ * - poll more quickly to catch button presses
+ * - assume a 'short' is 'button press', not 'headset has
+ * no mic
+ * 'present' stores SND_JACK_HEADPHONE and SND_JACK_MICROPHONE
+ * indication what we thing is present.
+ */
+ int present;
} jack;
static void gta04_audio_jack_work(struct work_struct *work)
{
long val;
+ long delay = msecs_to_jiffies(500);
+ int jackbits;
+
+ /* choose delay *before* checking presence so we still get
+ * one long delay on first insertion to help with debounce.
+ */
+ if (jack.present)
+ delay = msecs_to_jiffies(50);
val = twl4030_get_madc_conversion(7);
- if (val < 100)
- snd_soc_jack_report(&jack.hs_jack, 0, SND_JACK_HEADSET);
- else
- snd_soc_jack_report(&jack.hs_jack, SND_JACK_HEADSET,
- SND_JACK_HEADSET);
+ /* On my device:
+ * open circuit = around 20
+ * short circuit = around 800
+ * microphone = around 830-840 !!!
+ */
+ if (val < 100) {
+ /* open circuit */
+ jackbits = 0;
+ jack.present = 0;
+ /* debounce */
+ delay = msecs_to_jiffies(500);
+ } else if (val < 820) {
+ /* short */
+ if (jack.present == 0) {
+ /* Inserted headset with no mic */
+ jack.present = SND_JACK_HEADPHONE;
+ jackbits = jack.present;
+ } else if (jack.present & SND_JACK_MICROPHONE) {
+ /* mic shorter == button press */
+ jackbits = SND_JACK_BTN_0 | jack.present;
+ } else {
+ /* headphones still present */
+ jackbits = jack.present;
+ }
+ } else {
+ /* There is a microphone there */
+ jack.present = SND_JACK_HEADSET;
+ jackbits = jack.present;
+ }
+ snd_soc_jack_report(&jack.hs_jack, jackbits,
+ SND_JACK_HEADSET | SND_JACK_BTN_0);
+
if (jack.open)
- schedule_delayed_work(&jack.jack_work, msecs_to_jiffies(500));
+ schedule_delayed_work(&jack.jack_work, delay);
}
static int gta04_audio_suspend(struct snd_soc_card *card)
@@ -237,7 +280,8 @@ static int omap3gta04_init(struct snd_soc_pcm_runtime *runtime)
* but we need to poll :-(
*/
ret = snd_soc_jack_new(codec, "Headset Jack",
- SND_JACK_HEADSET, &jack.hs_jack);
+ SND_JACK_HEADSET | SND_JACK_BTN_0,
+ &jack.hs_jack);
if (ret)
return ret;
INIT_DELAYED_WORK(&jack.jack_work, gta04_audio_jack_work);
NeilBrown
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 828 bytes
Desc: not available
URL: <http://lists.goldelico.com/pipermail/gta04-owner/attachments/20120825/9ef7888e/attachment-0001.bin>
More information about the Gta04-owner
mailing list