linux-omap.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* handling voice calls in ALSA soc (on Droid 4)
@ 2018-06-11 10:25 Pavel Machek
  2018-06-11 11:10 ` Mark Brown
  0 siblings, 1 reply; 5+ messages in thread
From: Pavel Machek @ 2018-06-11 10:25 UTC (permalink / raw)
  To: kernel list, linux-arm-kernel, linux-omap, tony, sre, nekit1000,
	mpartap, merlijn, alsa-devel, tiwai, perex, broonie, lgirdwood

[-- Attachment #1: Type: text/plain, Size: 5178 bytes --]

Hi!

During voice call, I need audio components to be active "as if" aplay
or arecord was running, because modem needs to comunicate with speaker
and microphone.

I hacked something up, but... I believe I'll need help here. Look at
"enable_call" for "interesting" stuff I had to do.

...and also. What is right interface for this? Mixer component that
says if voice call is active or not?

Any ideas?

Thanks,
									Pavel

(edited).
+++ b/sound/soc/codecs/cpcap.c
@@ -330,6 +330,10 @@ static const char * const cpcap_in_left_mux_texts[] = {
 	"Off", "Mic 2", "Ext Left"
 };
 
+static const char * const cpcap_mode_texts[] = {
+	"Normal", "Handsfree", "Call",
+};
+
 /*
  * input muxes use unusual register layout, so that we need to use custom
  * getter/setter methods
@@ -354,6 +358,8 @@ static SOC_ENUM_SINGLE_DECL(cpcap_hs_l_mux_enum, 0, 6, cpcap_out_mux_texts);
 static SOC_ENUM_SINGLE_DECL(cpcap_emu_l_mux_enum, 0, 7, cpcap_out_mux_texts);
 static SOC_ENUM_SINGLE_DECL(cpcap_emu_r_mux_enum, 0, 8, cpcap_out_mux_texts);
 
+static SOC_ENUM_SINGLE_DECL(cpcap_mode_enum, 0, 9, cpcap_mode_texts);
+
 static int cpcap_output_mux_get_enum(struct snd_kcontrol *kcontrol,
 				     struct snd_ctl_elem_value *ucontrol)
 {
@@ -442,6 +448,211 @@ static int cpcap_output_mux_put_enum(struct snd_kcontrol *kcontrol,
 	return 0;
 }
 
+static int mode;
+
+static int cpcap_mode_get_enum(struct snd_kcontrol *kcontrol,
+				     struct snd_ctl_elem_value *ucontrol)
+{
+	ucontrol->value.enumerated.item[0] = mode;
+
+	return 0;
+}
+
+static struct snd_soc_dai *voice_codec_dai_hack;
+
+static int enable_call(struct snd_soc_component *component, int on)
+{
+	struct cpcap_audio *cpcap = snd_soc_component_get_drvdata(component);

+		struct snd_soc_pcm_runtime *rt;
+
+		rt = snd_soc_get_pcm_runtime(component->card, "40126000.mcbsp-cpcap-voice");
+		printk("num_dai: %d, got runtime %lx\n", component->num_dai, rt);
+
+		if (rt) {
+		snd_soc_dapm_stream_event(rt, SNDRV_PCM_STREAM_PLAYBACK, SND_SOC_DAPM_STREAM_START);
+		snd_soc_dapm_stream_event(rt, SNDRV_PCM_STREAM_CAPTURE, SND_SOC_DAPM_STREAM_START);
+		}
+
+		cpcap_set_sysclk(cpcap, CPCAP_DAI_VOICE, 1, 19200000);
+		cpcap_set_samprate(cpcap, CPCAP_DAI_VOICE, 8000);
+		
+		cpcap_voice_set_dai_fmt(voice_codec_dai_hack,
+					SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBM_CFM );
+
+	return 0;
+}
+
+static int cpcap_mode_put_enum(struct snd_kcontrol *kcontrol,
+				     struct snd_ctl_elem_value *ucontrol)
+{
+	struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol);
+	struct cpcap_audio *cpcap = snd_soc_component_get_drvdata(component);
+	unsigned int muxval = ucontrol->value.enumerated.item[0];
+
+	printk("Requested mode %d\n", muxval);
+
+	mode = muxval;
+
+	switch (muxval) {
+	case 1:
+		enable_call(component, 1);
+		break;
+	case 2:
+		enable_call(component, 1);
+
+		regmap_assert(cpcap, CPCAP_REG_TXI, 0xffff, 0x0cc6);
		...
+		break;
+		
+	default:
+		break;
+	}
+
+	return 0;
+}
+
 static int cpcap_input_right_mux_get_enum(struct snd_kcontrol *kcontrol,
 					  struct snd_ctl_elem_value *ucontrol)
 {
@@ -630,6 +841,10 @@ static const struct snd_kcontrol_new cpcap_earpiece_mux =
 	SOC_DAPM_ENUM_EXT("Earpiece", cpcap_earpiece_mux_enum,
 			  cpcap_output_mux_get_enum, cpcap_output_mux_put_enum);
 
+static const struct snd_kcontrol_new cpcap_mode =
+	SOC_DAPM_ENUM_EXT("Mode", cpcap_mode_enum,
+			  cpcap_mode_get_enum, cpcap_mode_put_enum);
+
 static const struct snd_kcontrol_new cpcap_hifi_mono_mixer_controls[] = {
 	SOC_DAPM_SINGLE("HiFi Mono Playback Switch",
 		CPCAP_REG_RXSDOA, CPCAP_BIT_MONO_DAC1, 1, 0),
@@ -771,6 +986,9 @@ static const struct snd_soc_dapm_widget cpcap_dapm_widgets[] = {
 	SND_SOC_DAPM_MUX("EMU Left Playback Route", SND_SOC_NOPM, 0, 0,
 		&cpcap_emu_left_mux),
 
+	SND_SOC_DAPM_MUX("Mode", SND_SOC_NOPM, 0, 0,
+		&cpcap_mode),
+	
 	/* Output Amplifier */
 	SND_SOC_DAPM_PGA("Earpiece PGA",
 		CPCAP_REG_RXOA, CPCAP_BIT_A1_EAR_EN, 0, NULL, 0),
@@ -791,7 +1009,7 @@ static const struct snd_soc_dapm_widget cpcap_dapm_widgets[] = {
 	SND_SOC_DAPM_PGA("EMU Left PGA",
 		CPCAP_REG_RXOA, CPCAP_BIT_EMU_SPKR_L_EN, 0, NULL, 0),
 
-	/* Headet Charge Pump */
+	/* Headset Charge Pump */
 	SND_SOC_DAPM_SUPPLY("Headset Charge Pump",
 		CPCAP_REG_RXOA, CPCAP_BIT_ST_HS_CP_EN, 0, NULL, 0),
 
@@ -1304,6 +1525,7 @@ static int cpcap_voice_set_dai_fmt(struct snd_soc_dai *codec_dai,
 	u16 val = 0x0000;
 	int err;
 
+	voice_codec_dai_hack = codec_dai;
 	dev_dbg(component->dev, "Voice setup dai format (%08x)", fmt);
 
 	/*
@@ -1343,10 +1565,7 @@ static int cpcap_voice_set_dai_fmt(struct snd_soc_dai *codec_dai,
 		break;
 	}
 
-	if (val & BIT(CPCAP_BIT_CLK_INV))
-		val &= ~BIT(CPCAP_BIT_CLK_INV);
-	else
-		val |= BIT(CPCAP_BIT_CLK_INV);
+	val ^= BIT(CPCAP_BIT_CLK_INV);
 
 	switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
 	case SND_SOC_DAIFMT_I2S:

-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

[-- Attachment #2: Digital signature --]
[-- Type: application/pgp-signature, Size: 181 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: handling voice calls in ALSA soc (on Droid 4)
  2018-06-11 10:25 handling voice calls in ALSA soc (on Droid 4) Pavel Machek
@ 2018-06-11 11:10 ` Mark Brown
  2018-06-11 12:01   ` Pavel Machek
  0 siblings, 1 reply; 5+ messages in thread
From: Mark Brown @ 2018-06-11 11:10 UTC (permalink / raw)
  To: Pavel Machek
  Cc: kernel list, linux-arm-kernel, linux-omap, tony, sre, nekit1000,
	mpartap, merlijn, alsa-devel, tiwai, perex, lgirdwood

[-- Attachment #1: Type: text/plain, Size: 497 bytes --]

On Mon, Jun 11, 2018 at 12:25:30PM +0200, Pavel Machek wrote:

> ...and also. What is right interface for this? Mixer component that
> says if voice call is active or not?

Your modem should be represented as a component in the system and have
an input and an output representing the input and output on the cell
network.  See speyside for an example of how this can look in software
though there's a bunch of different ways modems can appear so you might
not have a fully digital link like that.

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 488 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: handling voice calls in ALSA soc (on Droid 4)
  2018-06-11 11:10 ` Mark Brown
@ 2018-06-11 12:01   ` Pavel Machek
  2018-06-11 12:15     ` Mark Brown
  0 siblings, 1 reply; 5+ messages in thread
From: Pavel Machek @ 2018-06-11 12:01 UTC (permalink / raw)
  To: Mark Brown
  Cc: kernel list, linux-arm-kernel, linux-omap, tony, sre, nekit1000,
	mpartap, merlijn, alsa-devel, tiwai, perex, lgirdwood

[-- Attachment #1: Type: text/plain, Size: 902 bytes --]

On Mon 2018-06-11 12:10:11, Mark Brown wrote:
> On Mon, Jun 11, 2018 at 12:25:30PM +0200, Pavel Machek wrote:
> 
> > ...and also. What is right interface for this? Mixer component that
> > says if voice call is active or not?
> 
> Your modem should be represented as a component in the system and have
> an input and an output representing the input and output on the cell
> network.  See speyside for an example of how this can look in software
> though there's a bunch of different ways modems can appear so you might
> not have a fully digital link like that.

Thanks for the pointer.

With setup like that, how does userland tell kernel that the baseband
<-> microphone/speaker connection should be activated?

Best regards,
									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

[-- Attachment #2: Digital signature --]
[-- Type: application/pgp-signature, Size: 181 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: handling voice calls in ALSA soc (on Droid 4)
  2018-06-11 12:01   ` Pavel Machek
@ 2018-06-11 12:15     ` Mark Brown
  2018-06-12 12:18       ` Pavel Machek
  0 siblings, 1 reply; 5+ messages in thread
From: Mark Brown @ 2018-06-11 12:15 UTC (permalink / raw)
  To: Pavel Machek
  Cc: kernel list, linux-arm-kernel, linux-omap, tony, sre, nekit1000,
	mpartap, merlijn, alsa-devel, tiwai, perex, lgirdwood

[-- Attachment #1: Type: text/plain, Size: 444 bytes --]

On Mon, Jun 11, 2018 at 02:01:58PM +0200, Pavel Machek wrote:

> With setup like that, how does userland tell kernel that the baseband
> <-> microphone/speaker connection should be activated?

Audio routing should be done as normal, and ideally the driver for the
modem will be able to figure out if there's an active call or not.  If
userspace has to enable the input and output manually then you can set
up SOC_DAPM_PIN_SWITCH()es as normal.

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 488 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: handling voice calls in ALSA soc (on Droid 4)
  2018-06-11 12:15     ` Mark Brown
@ 2018-06-12 12:18       ` Pavel Machek
  0 siblings, 0 replies; 5+ messages in thread
From: Pavel Machek @ 2018-06-12 12:18 UTC (permalink / raw)
  To: Mark Brown
  Cc: kernel list, linux-arm-kernel, linux-omap, tony, sre, nekit1000,
	mpartap, merlijn, alsa-devel, tiwai, perex, lgirdwood

[-- Attachment #1: Type: text/plain, Size: 1333 bytes --]

Hi!

Sebastian, would you have pointer to original Motorola sources you
used for inspiration?

> > With setup like that, how does userland tell kernel that the baseband
> > <-> microphone/speaker connection should be activated?
> 
> Audio routing should be done as normal, and ideally the driver for the
> modem will be able to figure out if there's an active call or not.  If
> userspace has to enable the input and output manually then you can set
> up SOC_DAPM_PIN_SWITCH()es as normal.

Modem talks AT commands, so the driver is in userspace for now.

I tried SOC_DAPM_PIN_SWITCH(), but it results in alsamixer oopsing, I
guess I'm doing something wrong.

Message from syslogd@devuan at Jun 12 13:51:31 ...
 kernel:[  743.678588] BUG: spinlock bad magic on CPU#1,
 alsamixer/2217

Message from syslogd@devuan at Jun 12 13:51:31 ...
 kernel:[  743.684417]  lock: 0xede423a0, .magic: eee2a6a4, .owner:
 <none>/-1, .owner_cpu: -287136604
 
I'm trying to understand how it is supposed to work, but
https://www.alsa-project.org/main/index.php/DAPM has TODO's at
critical places. If there's better source of information, let me know.

Best regards,
									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

[-- Attachment #2: Digital signature --]
[-- Type: application/pgp-signature, Size: 181 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2018-06-12 12:18 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2018-06-11 10:25 handling voice calls in ALSA soc (on Droid 4) Pavel Machek
2018-06-11 11:10 ` Mark Brown
2018-06-11 12:01   ` Pavel Machek
2018-06-11 12:15     ` Mark Brown
2018-06-12 12:18       ` Pavel Machek

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).