mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-09 13:49:24 -04:00
misc: cs40l20: Add digital scale control
Exposed a means to apply attenuation to the device's digital signal path with the dig_scale control. Change-Id: I66cd3bc425e770faf8b2ee0fd89ffbb20a394d5c Signed-off-by: Jeff LaBundy <jeff.labundy@cirrus.com> Signed-off-by: Ravi Vembu <raviv@motorola.com>
This commit is contained in:
parent
cb96274331
commit
38fb393fa4
2 changed files with 66 additions and 0 deletions
|
|
@ -60,6 +60,7 @@ struct cs40l20_private {
|
|||
unsigned char diag_state;
|
||||
unsigned int f0_measured;
|
||||
unsigned int redc_measured;
|
||||
unsigned int dig_scale;
|
||||
#ifdef CONFIG_ANDROID_TIMED_OUTPUT
|
||||
struct timed_output_dev timed_dev;
|
||||
struct hrtimer vibe_timer;
|
||||
|
|
@ -318,6 +319,46 @@ static ssize_t cs40l20_redc_measured_show(struct device *dev,
|
|||
return snprintf(buf, PAGE_SIZE, "%d\n", redc_measured);
|
||||
}
|
||||
|
||||
static ssize_t cs40l20_dig_scale_show(struct device *dev,
|
||||
struct device_attribute *attr, char *buf)
|
||||
{
|
||||
struct cs40l20_private *cs40l20 = cs40l20_get_private(dev);
|
||||
|
||||
return snprintf(buf, PAGE_SIZE, "%d\n", cs40l20->dig_scale);
|
||||
}
|
||||
|
||||
static ssize_t cs40l20_dig_scale_store(struct device *dev,
|
||||
struct device_attribute *attr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
struct cs40l20_private *cs40l20 = cs40l20_get_private(dev);
|
||||
int ret;
|
||||
unsigned int dig_scale;
|
||||
|
||||
ret = kstrtou32(buf, 10, &dig_scale);
|
||||
if (ret)
|
||||
return -EINVAL;
|
||||
|
||||
if (dig_scale > CS40L20_DIG_SCALE_MAX)
|
||||
return -EINVAL;
|
||||
|
||||
mutex_lock(&cs40l20->lock);
|
||||
ret = regmap_update_bits(cs40l20->regmap, CS40L20_AMP_DIG_VOL_CTRL,
|
||||
CS40L20_AMP_VOL_PCM_MASK,
|
||||
((0x800 - dig_scale) & 0x7FF)
|
||||
<< CS40L20_AMP_VOL_PCM_SHIFT);
|
||||
mutex_unlock(&cs40l20->lock);
|
||||
|
||||
if (ret) {
|
||||
pr_err("Failed to store digital scale\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
cs40l20->dig_scale = dig_scale;
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
static DEVICE_ATTR(cp_trigger_index, 0660, cs40l20_cp_trigger_index_show,
|
||||
cs40l20_cp_trigger_index_store);
|
||||
static DEVICE_ATTR(gpio1_rise_index, 0660, cs40l20_gpio1_rise_index_show,
|
||||
|
|
@ -328,6 +369,8 @@ static DEVICE_ATTR(f0_measured, 0660, cs40l20_f0_measured_show, NULL);
|
|||
static DEVICE_ATTR(f0_stored, 0660, cs40l20_f0_stored_show,
|
||||
cs40l20_f0_stored_store);
|
||||
static DEVICE_ATTR(redc_measured, 0660, cs40l20_redc_measured_show, NULL);
|
||||
static DEVICE_ATTR(dig_scale, 0660, cs40l20_dig_scale_show,
|
||||
cs40l20_dig_scale_store);
|
||||
|
||||
static struct attribute *cs40l20_dev_attrs[] = {
|
||||
&dev_attr_cp_trigger_index.attr,
|
||||
|
|
@ -336,6 +379,7 @@ static struct attribute *cs40l20_dev_attrs[] = {
|
|||
&dev_attr_f0_measured.attr,
|
||||
&dev_attr_f0_stored.attr,
|
||||
&dev_attr_redc_measured.attr,
|
||||
&dev_attr_dig_scale.attr,
|
||||
NULL,
|
||||
};
|
||||
|
||||
|
|
@ -412,6 +456,14 @@ static void cs40l20_vibe_start_worker(struct work_struct *work)
|
|||
case CS40L20_INDEX_DIAG:
|
||||
cs40l20->diag_state = CS40L20_DIAG_STATE_INIT;
|
||||
|
||||
ret = regmap_update_bits(cs40l20->regmap,
|
||||
CS40L20_AMP_DIG_VOL_CTRL,
|
||||
CS40L20_AMP_VOL_PCM_MASK, 0);
|
||||
if (ret) {
|
||||
dev_err(dev, "Failed to reset digital scale\n");
|
||||
goto err_mutex;
|
||||
}
|
||||
|
||||
ret = regmap_write(regmap,
|
||||
cs40l20_dsp_reg(cs40l20, "CLOSED_LOOP",
|
||||
CS40L20_XM_UNPACKED_TYPE), 0);
|
||||
|
|
@ -470,6 +522,14 @@ static void cs40l20_vibe_stop_worker(struct work_struct *work)
|
|||
CS40L20_XM_UNPACKED_TYPE), 0);
|
||||
if (ret)
|
||||
dev_err(dev, "Failed to disable stimulus mode\n");
|
||||
|
||||
ret = regmap_update_bits(cs40l20->regmap,
|
||||
CS40L20_AMP_DIG_VOL_CTRL,
|
||||
CS40L20_AMP_VOL_PCM_MASK,
|
||||
((0x800 - cs40l20->dig_scale) & 0x7FF)
|
||||
<< CS40L20_AMP_VOL_PCM_SHIFT);
|
||||
if (ret)
|
||||
dev_err(dev, "Failed to restore digital scale\n");
|
||||
break;
|
||||
|
||||
default:
|
||||
|
|
@ -1152,6 +1212,7 @@ static int cs40l20_init(struct cs40l20_private *cs40l20)
|
|||
cs40l20->cp_trailer_index = 0;
|
||||
cs40l20->vibe_init_success = false;
|
||||
cs40l20->diag_state = CS40L20_DIAG_STATE_INIT;
|
||||
cs40l20->dig_scale = 0;
|
||||
|
||||
if (cs40l20->pdata.refclk_gpio2) {
|
||||
ret = regmap_update_bits(regmap, CS40L20_GPIO_PAD_CONTROL,
|
||||
|
|
|
|||
|
|
@ -642,6 +642,9 @@
|
|||
#define CS40L20_BST_LBST_VAL_MASK 0x00000003
|
||||
#define CS40L20_BST_LBST_VAL_SHIFT 0
|
||||
|
||||
#define CS40L20_AMP_VOL_PCM_MASK 0x00003FF8
|
||||
#define CS40L20_AMP_VOL_PCM_SHIFT 3
|
||||
|
||||
#define CS40L20_PDN_DONE_MASK 0x00800000
|
||||
#define CS40L20_PDN_DONE_SHIFT 23
|
||||
#define CS40L20_PUP_DONE_MASK 0x01000000
|
||||
|
|
@ -726,6 +729,8 @@
|
|||
#define CS40L20_TEST_KEY_RELOCK_CODE1 0xCC
|
||||
#define CS40L20_TEST_KEY_RELOCK_CODE2 0x33
|
||||
|
||||
#define CS40L20_DIG_SCALE_MAX 816 /* -102 dB */
|
||||
|
||||
#define CS40L20_MAX_WLEN 4096
|
||||
|
||||
#define CS40L20_DEVICE_NAME "vibrator"
|
||||
|
|
|
|||
Loading…
Reference in a new issue