• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  *  Jack abstraction layer
4  *
5  *  Copyright 2008 Wolfson Microelectronics
6  */
7 
8 #include <linux/input.h>
9 #include <linux/slab.h>
10 #include <linux/module.h>
11 #include <sound/jack.h>
12 #include <sound/core.h>
13 #include <sound/control.h>
14 
15 struct snd_jack_kctl {
16 	struct snd_kcontrol *kctl;
17 	struct list_head list;  /* list of controls belong to the same jack */
18 	unsigned int mask_bits; /* only masked status bits are reported via kctl */
19 };
20 
21 #ifdef CONFIG_SND_JACK_INPUT_DEV
22 static const int jack_switch_types[SND_JACK_SWITCH_TYPES] = {
23 	SW_HEADPHONE_INSERT,
24 	SW_MICROPHONE_INSERT,
25 	SW_LINEOUT_INSERT,
26 	SW_JACK_PHYSICAL_INSERT,
27 	SW_VIDEOOUT_INSERT,
28 	SW_LINEIN_INSERT,
29 };
30 #endif /* CONFIG_SND_JACK_INPUT_DEV */
31 
snd_jack_dev_disconnect(struct snd_device * device)32 static int snd_jack_dev_disconnect(struct snd_device *device)
33 {
34 #ifdef CONFIG_SND_JACK_INPUT_DEV
35 	struct snd_jack *jack = device->device_data;
36 
37 	if (!jack->input_dev)
38 		return 0;
39 
40 	/* If the input device is registered with the input subsystem
41 	 * then we need to use a different deallocator. */
42 	if (jack->registered)
43 		input_unregister_device(jack->input_dev);
44 	else
45 		input_free_device(jack->input_dev);
46 	jack->input_dev = NULL;
47 #endif /* CONFIG_SND_JACK_INPUT_DEV */
48 	return 0;
49 }
50 
snd_jack_dev_free(struct snd_device * device)51 static int snd_jack_dev_free(struct snd_device *device)
52 {
53 	struct snd_jack *jack = device->device_data;
54 	struct snd_card *card = device->card;
55 	struct snd_jack_kctl *jack_kctl, *tmp_jack_kctl;
56 
57 	down_write(&card->controls_rwsem);
58 	list_for_each_entry_safe(jack_kctl, tmp_jack_kctl, &jack->kctl_list, list) {
59 		list_del_init(&jack_kctl->list);
60 		snd_ctl_remove(card, jack_kctl->kctl);
61 	}
62 	up_write(&card->controls_rwsem);
63 
64 	if (jack->private_free)
65 		jack->private_free(jack);
66 
67 	snd_jack_dev_disconnect(device);
68 
69 	kfree(jack->id);
70 	kfree(jack);
71 
72 	return 0;
73 }
74 
75 #ifdef CONFIG_SND_JACK_INPUT_DEV
snd_jack_dev_register(struct snd_device * device)76 static int snd_jack_dev_register(struct snd_device *device)
77 {
78 	struct snd_jack *jack = device->device_data;
79 	struct snd_card *card = device->card;
80 	int err, i;
81 
82 	snprintf(jack->name, sizeof(jack->name), "%s %s",
83 		 card->shortname, jack->id);
84 
85 	if (!jack->input_dev)
86 		return 0;
87 
88 	jack->input_dev->name = jack->name;
89 
90 	/* Default to the sound card device. */
91 	if (!jack->input_dev->dev.parent)
92 		jack->input_dev->dev.parent = snd_card_get_device_link(card);
93 
94 	/* Add capabilities for any keys that are enabled */
95 	for (i = 0; i < ARRAY_SIZE(jack->key); i++) {
96 		int testbit = SND_JACK_BTN_0 >> i;
97 
98 		if (!(jack->type & testbit))
99 			continue;
100 
101 		if (!jack->key[i])
102 			jack->key[i] = BTN_0 + i;
103 
104 		input_set_capability(jack->input_dev, EV_KEY, jack->key[i]);
105 	}
106 
107 	err = input_register_device(jack->input_dev);
108 	if (err == 0)
109 		jack->registered = 1;
110 
111 	return err;
112 }
113 #endif /* CONFIG_SND_JACK_INPUT_DEV */
114 
snd_jack_kctl_private_free(struct snd_kcontrol * kctl)115 static void snd_jack_kctl_private_free(struct snd_kcontrol *kctl)
116 {
117 	struct snd_jack_kctl *jack_kctl;
118 
119 	jack_kctl = kctl->private_data;
120 	if (jack_kctl) {
121 		list_del(&jack_kctl->list);
122 		kfree(jack_kctl);
123 	}
124 }
125 
snd_jack_kctl_add(struct snd_jack * jack,struct snd_jack_kctl * jack_kctl)126 static void snd_jack_kctl_add(struct snd_jack *jack, struct snd_jack_kctl *jack_kctl)
127 {
128 	list_add_tail(&jack_kctl->list, &jack->kctl_list);
129 }
130 
snd_jack_kctl_new(struct snd_card * card,const char * name,unsigned int mask)131 static struct snd_jack_kctl * snd_jack_kctl_new(struct snd_card *card, const char *name, unsigned int mask)
132 {
133 	struct snd_kcontrol *kctl;
134 	struct snd_jack_kctl *jack_kctl;
135 	int err;
136 
137 	kctl = snd_kctl_jack_new(name, card);
138 	if (!kctl)
139 		return NULL;
140 
141 	err = snd_ctl_add(card, kctl);
142 	if (err < 0)
143 		return NULL;
144 
145 	jack_kctl = kzalloc(sizeof(*jack_kctl), GFP_KERNEL);
146 
147 	if (!jack_kctl)
148 		goto error;
149 
150 	jack_kctl->kctl = kctl;
151 	jack_kctl->mask_bits = mask;
152 
153 	kctl->private_data = jack_kctl;
154 	kctl->private_free = snd_jack_kctl_private_free;
155 
156 	return jack_kctl;
157 error:
158 	snd_ctl_free_one(kctl);
159 	return NULL;
160 }
161 
162 /**
163  * snd_jack_add_new_kctl - Create a new snd_jack_kctl and add it to jack
164  * @jack:  the jack instance which the kctl will attaching to
165  * @name:  the name for the snd_kcontrol object
166  * @mask:  a bitmask of enum snd_jack_type values that can be detected
167  *         by this snd_jack_kctl object.
168  *
169  * Creates a new snd_kcontrol object and adds it to the jack kctl_list.
170  *
171  * Return: Zero if successful, or a negative error code on failure.
172  */
snd_jack_add_new_kctl(struct snd_jack * jack,const char * name,int mask)173 int snd_jack_add_new_kctl(struct snd_jack *jack, const char * name, int mask)
174 {
175 	struct snd_jack_kctl *jack_kctl;
176 
177 	jack_kctl = snd_jack_kctl_new(jack->card, name, mask);
178 	if (!jack_kctl)
179 		return -ENOMEM;
180 
181 	snd_jack_kctl_add(jack, jack_kctl);
182 	return 0;
183 }
184 EXPORT_SYMBOL(snd_jack_add_new_kctl);
185 
186 /**
187  * snd_jack_new - Create a new jack
188  * @card:  the card instance
189  * @id:    an identifying string for this jack
190  * @type:  a bitmask of enum snd_jack_type values that can be detected by
191  *         this jack
192  * @jjack: Used to provide the allocated jack object to the caller.
193  * @initial_kctl: if true, create a kcontrol and add it to the jack list.
194  * @phantom_jack: Don't create a input device for phantom jacks.
195  *
196  * Creates a new jack object.
197  *
198  * Return: Zero if successful, or a negative error code on failure.
199  * On success @jjack will be initialised.
200  */
snd_jack_new(struct snd_card * card,const char * id,int type,struct snd_jack ** jjack,bool initial_kctl,bool phantom_jack)201 int snd_jack_new(struct snd_card *card, const char *id, int type,
202 		 struct snd_jack **jjack, bool initial_kctl, bool phantom_jack)
203 {
204 	struct snd_jack *jack;
205 	struct snd_jack_kctl *jack_kctl = NULL;
206 	int err;
207 	static const struct snd_device_ops ops = {
208 		.dev_free = snd_jack_dev_free,
209 #ifdef CONFIG_SND_JACK_INPUT_DEV
210 		.dev_register = snd_jack_dev_register,
211 		.dev_disconnect = snd_jack_dev_disconnect,
212 #endif /* CONFIG_SND_JACK_INPUT_DEV */
213 	};
214 
215 	if (initial_kctl) {
216 		jack_kctl = snd_jack_kctl_new(card, id, type);
217 		if (!jack_kctl)
218 			return -ENOMEM;
219 	}
220 
221 	jack = kzalloc(sizeof(struct snd_jack), GFP_KERNEL);
222 	if (jack == NULL)
223 		return -ENOMEM;
224 
225 	jack->id = kstrdup(id, GFP_KERNEL);
226 	if (jack->id == NULL) {
227 		kfree(jack);
228 		return -ENOMEM;
229 	}
230 
231 	/* don't creat input device for phantom jack */
232 	if (!phantom_jack) {
233 #ifdef CONFIG_SND_JACK_INPUT_DEV
234 		int i;
235 
236 		jack->input_dev = input_allocate_device();
237 		if (jack->input_dev == NULL) {
238 			err = -ENOMEM;
239 			goto fail_input;
240 		}
241 
242 		jack->input_dev->phys = "ALSA";
243 
244 		jack->type = type;
245 
246 		for (i = 0; i < SND_JACK_SWITCH_TYPES; i++)
247 			if (type & (1 << i))
248 				input_set_capability(jack->input_dev, EV_SW,
249 						     jack_switch_types[i]);
250 
251 #endif /* CONFIG_SND_JACK_INPUT_DEV */
252 	}
253 
254 	err = snd_device_new(card, SNDRV_DEV_JACK, jack, &ops);
255 	if (err < 0)
256 		goto fail_input;
257 
258 	jack->card = card;
259 	INIT_LIST_HEAD(&jack->kctl_list);
260 
261 	if (initial_kctl)
262 		snd_jack_kctl_add(jack, jack_kctl);
263 
264 	*jjack = jack;
265 
266 	return 0;
267 
268 fail_input:
269 #ifdef CONFIG_SND_JACK_INPUT_DEV
270 	input_free_device(jack->input_dev);
271 #endif
272 	kfree(jack->id);
273 	kfree(jack);
274 	return err;
275 }
276 EXPORT_SYMBOL(snd_jack_new);
277 
278 #ifdef CONFIG_SND_JACK_INPUT_DEV
279 /**
280  * snd_jack_set_parent - Set the parent device for a jack
281  *
282  * @jack:   The jack to configure
283  * @parent: The device to set as parent for the jack.
284  *
285  * Set the parent for the jack devices in the device tree.  This
286  * function is only valid prior to registration of the jack.  If no
287  * parent is configured then the parent device will be the sound card.
288  */
snd_jack_set_parent(struct snd_jack * jack,struct device * parent)289 void snd_jack_set_parent(struct snd_jack *jack, struct device *parent)
290 {
291 	WARN_ON(jack->registered);
292 	if (!jack->input_dev)
293 		return;
294 
295 	jack->input_dev->dev.parent = parent;
296 }
297 EXPORT_SYMBOL(snd_jack_set_parent);
298 
299 /**
300  * snd_jack_set_key - Set a key mapping on a jack
301  *
302  * @jack:    The jack to configure
303  * @type:    Jack report type for this key
304  * @keytype: Input layer key type to be reported
305  *
306  * Map a SND_JACK_BTN_* button type to an input layer key, allowing
307  * reporting of keys on accessories via the jack abstraction.  If no
308  * mapping is provided but keys are enabled in the jack type then
309  * BTN_n numeric buttons will be reported.
310  *
311  * If jacks are not reporting via the input API this call will have no
312  * effect.
313  *
314  * Note that this is intended to be use by simple devices with small
315  * numbers of keys that can be reported.  It is also possible to
316  * access the input device directly - devices with complex input
317  * capabilities on accessories should consider doing this rather than
318  * using this abstraction.
319  *
320  * This function may only be called prior to registration of the jack.
321  *
322  * Return: Zero if successful, or a negative error code on failure.
323  */
snd_jack_set_key(struct snd_jack * jack,enum snd_jack_types type,int keytype)324 int snd_jack_set_key(struct snd_jack *jack, enum snd_jack_types type,
325 		     int keytype)
326 {
327 	int key = fls(SND_JACK_BTN_0) - fls(type);
328 
329 	WARN_ON(jack->registered);
330 
331 	if (!keytype || key >= ARRAY_SIZE(jack->key))
332 		return -EINVAL;
333 
334 	jack->type |= type;
335 	jack->key[key] = keytype;
336 	return 0;
337 }
338 EXPORT_SYMBOL(snd_jack_set_key);
339 #endif /* CONFIG_SND_JACK_INPUT_DEV */
340 
341 /**
342  * snd_jack_report - Report the current status of a jack
343  *
344  * @jack:   The jack to report status for
345  * @status: The current status of the jack
346  */
snd_jack_report(struct snd_jack * jack,int status)347 void snd_jack_report(struct snd_jack *jack, int status)
348 {
349 	struct snd_jack_kctl *jack_kctl;
350 #ifdef CONFIG_SND_JACK_INPUT_DEV
351 	struct input_dev *idev;
352 	int i;
353 #endif
354 
355 	if (!jack)
356 		return;
357 
358 	list_for_each_entry(jack_kctl, &jack->kctl_list, list)
359 		snd_kctl_jack_report(jack->card, jack_kctl->kctl,
360 					    status & jack_kctl->mask_bits);
361 
362 #ifdef CONFIG_SND_JACK_INPUT_DEV
363 	idev = input_get_device(jack->input_dev);
364 	if (!idev)
365 		return;
366 
367 	for (i = 0; i < ARRAY_SIZE(jack->key); i++) {
368 		int testbit = SND_JACK_BTN_0 >> i;
369 
370 		if (jack->type & testbit)
371 			input_report_key(idev, jack->key[i],
372 					 status & testbit);
373 	}
374 
375 	for (i = 0; i < ARRAY_SIZE(jack_switch_types); i++) {
376 		int testbit = 1 << i;
377 		if (jack->type & testbit)
378 			input_report_switch(idev,
379 					    jack_switch_types[i],
380 					    status & testbit);
381 	}
382 
383 	input_sync(idev);
384 	input_put_device(idev);
385 #endif /* CONFIG_SND_JACK_INPUT_DEV */
386 }
387 EXPORT_SYMBOL(snd_jack_report);
388