brintos

brintos / linux-shallow public Read only

0
0
Text · 3.5 KiB · bc21144 Raw
141 lines · c
1// SPDX-License-Identifier: GPL-2.0-or-later2/*3 * Driver for Digigram VXpocket soundcards4 *5 * VX-pocket mixer6 *7 * Copyright (c) 2002 by Takashi Iwai <tiwai@suse.de>8 */9 10#include <sound/core.h>11#include <sound/control.h>12#include <sound/tlv.h>13#include "vxpocket.h"14 15#define MIC_LEVEL_MIN	016#define MIC_LEVEL_MAX	817 18/*19 * mic level control (for VXPocket)20 */21static int vx_mic_level_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)22{23	uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;24	uinfo->count = 1;25	uinfo->value.integer.min = 0;26	uinfo->value.integer.max = MIC_LEVEL_MAX;27	return 0;28}29 30static int vx_mic_level_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)31{32	struct vx_core *_chip = snd_kcontrol_chip(kcontrol);33	struct snd_vxpocket *chip = to_vxpocket(_chip);34	ucontrol->value.integer.value[0] = chip->mic_level;35	return 0;36}37 38static int vx_mic_level_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)39{40	struct vx_core *_chip = snd_kcontrol_chip(kcontrol);41	struct snd_vxpocket *chip = to_vxpocket(_chip);42	unsigned int val = ucontrol->value.integer.value[0];43 44	if (val > MIC_LEVEL_MAX)45		return -EINVAL;46	mutex_lock(&_chip->mixer_mutex);47	if (chip->mic_level != ucontrol->value.integer.value[0]) {48		vx_set_mic_level(_chip, ucontrol->value.integer.value[0]);49		chip->mic_level = ucontrol->value.integer.value[0];50		mutex_unlock(&_chip->mixer_mutex);51		return 1;52	}53	mutex_unlock(&_chip->mixer_mutex);54	return 0;55}56 57static const DECLARE_TLV_DB_SCALE(db_scale_mic, -21, 3, 0);58 59static const struct snd_kcontrol_new vx_control_mic_level = {60	.iface =	SNDRV_CTL_ELEM_IFACE_MIXER,61	.access =	(SNDRV_CTL_ELEM_ACCESS_READWRITE |62			 SNDRV_CTL_ELEM_ACCESS_TLV_READ),63	.name =		"Mic Capture Volume",64	.info =		vx_mic_level_info,65	.get =		vx_mic_level_get,66	.put =		vx_mic_level_put,67	.tlv = { .p = db_scale_mic },68};69 70/*71 * mic boost level control (for VXP440)72 */73#define vx_mic_boost_info		snd_ctl_boolean_mono_info74 75static int vx_mic_boost_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)76{77	struct vx_core *_chip = snd_kcontrol_chip(kcontrol);78	struct snd_vxpocket *chip = to_vxpocket(_chip);79	ucontrol->value.integer.value[0] = chip->mic_level;80	return 0;81}82 83static int vx_mic_boost_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)84{85	struct vx_core *_chip = snd_kcontrol_chip(kcontrol);86	struct snd_vxpocket *chip = to_vxpocket(_chip);87	int val = !!ucontrol->value.integer.value[0];88	mutex_lock(&_chip->mixer_mutex);89	if (chip->mic_level != val) {90		vx_set_mic_boost(_chip, val);91		chip->mic_level = val;92		mutex_unlock(&_chip->mixer_mutex);93		return 1;94	}95	mutex_unlock(&_chip->mixer_mutex);96	return 0;97}98 99static const struct snd_kcontrol_new vx_control_mic_boost = {100	.iface =	SNDRV_CTL_ELEM_IFACE_MIXER,101	.name =		"Mic Boost",102	.info =		vx_mic_boost_info,103	.get =		vx_mic_boost_get,104	.put =		vx_mic_boost_put,105};106 107 108int vxp_add_mic_controls(struct vx_core *_chip)109{110	struct snd_vxpocket *chip = to_vxpocket(_chip);111	int err;112 113	/* mute input levels */114	chip->mic_level = 0;115	switch (_chip->type) {116	case VX_TYPE_VXPOCKET:117		vx_set_mic_level(_chip, 0);118		break;119	case VX_TYPE_VXP440:120		vx_set_mic_boost(_chip, 0);121		break;122	}123 124	/* mic level */125	switch (_chip->type) {126	case VX_TYPE_VXPOCKET:127		err = snd_ctl_add(_chip->card, snd_ctl_new1(&vx_control_mic_level, chip));128		if (err < 0)129			return err;130		break;131	case VX_TYPE_VXP440:132		err = snd_ctl_add(_chip->card, snd_ctl_new1(&vx_control_mic_boost, chip));133		if (err < 0)134			return err;135		break;136	}137 138	return 0;139}140 141