162306a36Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0 */
262306a36Sopenharmony_ci/*
362306a36Sopenharmony_ci * CS42L43 CODEC driver internal data
462306a36Sopenharmony_ci *
562306a36Sopenharmony_ci * Copyright (C) 2022-2023 Cirrus Logic, Inc. and
662306a36Sopenharmony_ci *                         Cirrus Logic International Semiconductor Ltd.
762306a36Sopenharmony_ci */
862306a36Sopenharmony_ci
962306a36Sopenharmony_ci#include <linux/clk.h>
1062306a36Sopenharmony_ci#include <linux/completion.h>
1162306a36Sopenharmony_ci#include <linux/device.h>
1262306a36Sopenharmony_ci#include <linux/mutex.h>
1362306a36Sopenharmony_ci#include <linux/regmap.h>
1462306a36Sopenharmony_ci#include <linux/soundwire/sdw.h>
1562306a36Sopenharmony_ci#include <linux/types.h>
1662306a36Sopenharmony_ci#include <sound/cs42l43.h>
1762306a36Sopenharmony_ci#include <sound/pcm.h>
1862306a36Sopenharmony_ci#include <sound/soc-jack.h>
1962306a36Sopenharmony_ci
2062306a36Sopenharmony_ci#ifndef CS42L43_ASOC_INT_H
2162306a36Sopenharmony_ci#define CS42L43_ASOC_INT_H
2262306a36Sopenharmony_ci
2362306a36Sopenharmony_ci#define CS42L43_INTERNAL_SYSCLK		24576000
2462306a36Sopenharmony_ci#define CS42L43_DEFAULT_SLOTS		0x3F
2562306a36Sopenharmony_ci
2662306a36Sopenharmony_ci#define CS42L43_PLL_TIMEOUT_MS		200
2762306a36Sopenharmony_ci#define CS42L43_SPK_TIMEOUT_MS		100
2862306a36Sopenharmony_ci#define CS42L43_HP_TIMEOUT_MS		2000
2962306a36Sopenharmony_ci#define CS42L43_LOAD_TIMEOUT_MS		1000
3062306a36Sopenharmony_ci
3162306a36Sopenharmony_ci#define CS42L43_ASP_MAX_CHANNELS	6
3262306a36Sopenharmony_ci#define CS42L43_N_EQ_COEFFS		15
3362306a36Sopenharmony_ci
3462306a36Sopenharmony_ci#define CS42L43_N_BUTTONS	6
3562306a36Sopenharmony_ci
3662306a36Sopenharmony_cistruct cs42l43_codec {
3762306a36Sopenharmony_ci	struct device *dev;
3862306a36Sopenharmony_ci	struct cs42l43 *core;
3962306a36Sopenharmony_ci	struct snd_soc_component *component;
4062306a36Sopenharmony_ci
4162306a36Sopenharmony_ci	struct clk *mclk;
4262306a36Sopenharmony_ci
4362306a36Sopenharmony_ci	int n_slots;
4462306a36Sopenharmony_ci	int slot_width;
4562306a36Sopenharmony_ci	int tx_slots[CS42L43_ASP_MAX_CHANNELS];
4662306a36Sopenharmony_ci	int rx_slots[CS42L43_ASP_MAX_CHANNELS];
4762306a36Sopenharmony_ci	struct snd_pcm_hw_constraint_list constraint;
4862306a36Sopenharmony_ci
4962306a36Sopenharmony_ci	u32 eq_coeffs[CS42L43_N_EQ_COEFFS];
5062306a36Sopenharmony_ci
5162306a36Sopenharmony_ci	unsigned int refclk_src;
5262306a36Sopenharmony_ci	unsigned int refclk_freq;
5362306a36Sopenharmony_ci	struct completion pll_ready;
5462306a36Sopenharmony_ci
5562306a36Sopenharmony_ci	unsigned int decim_cache[4];
5662306a36Sopenharmony_ci	unsigned int adc_ena;
5762306a36Sopenharmony_ci	unsigned int hp_ena;
5862306a36Sopenharmony_ci
5962306a36Sopenharmony_ci	struct completion hp_startup;
6062306a36Sopenharmony_ci	struct completion hp_shutdown;
6162306a36Sopenharmony_ci	struct completion spkr_shutdown;
6262306a36Sopenharmony_ci	struct completion spkl_shutdown;
6362306a36Sopenharmony_ci	struct completion spkr_startup;
6462306a36Sopenharmony_ci	struct completion spkl_startup;
6562306a36Sopenharmony_ci	// Lock to ensure speaker VU updates don't clash
6662306a36Sopenharmony_ci	struct mutex spk_vu_lock;
6762306a36Sopenharmony_ci
6862306a36Sopenharmony_ci	// Lock for all jack detect operations
6962306a36Sopenharmony_ci	struct mutex jack_lock;
7062306a36Sopenharmony_ci	struct snd_soc_jack *jack_hp;
7162306a36Sopenharmony_ci
7262306a36Sopenharmony_ci	bool use_ring_sense;
7362306a36Sopenharmony_ci	unsigned int tip_debounce_ms;
7462306a36Sopenharmony_ci	unsigned int bias_low;
7562306a36Sopenharmony_ci	unsigned int bias_sense_ua;
7662306a36Sopenharmony_ci	unsigned int bias_ramp_ms;
7762306a36Sopenharmony_ci	unsigned int detect_us;
7862306a36Sopenharmony_ci	unsigned int buttons[CS42L43_N_BUTTONS];
7962306a36Sopenharmony_ci
8062306a36Sopenharmony_ci	struct delayed_work tip_sense_work;
8162306a36Sopenharmony_ci	struct delayed_work bias_sense_timeout;
8262306a36Sopenharmony_ci	struct delayed_work button_press_work;
8362306a36Sopenharmony_ci	struct work_struct button_release_work;
8462306a36Sopenharmony_ci	struct completion type_detect;
8562306a36Sopenharmony_ci	struct completion load_detect;
8662306a36Sopenharmony_ci
8762306a36Sopenharmony_ci	bool load_detect_running;
8862306a36Sopenharmony_ci	bool button_detect_running;
8962306a36Sopenharmony_ci	bool jack_present;
9062306a36Sopenharmony_ci	int jack_override;
9162306a36Sopenharmony_ci};
9262306a36Sopenharmony_ci
9362306a36Sopenharmony_ci#if IS_REACHABLE(CONFIG_SND_SOC_CS42L43_SDW)
9462306a36Sopenharmony_ci
9562306a36Sopenharmony_ciint cs42l43_sdw_add_peripheral(struct snd_pcm_substream *substream,
9662306a36Sopenharmony_ci			       struct snd_pcm_hw_params *params,
9762306a36Sopenharmony_ci			       struct snd_soc_dai *dai);
9862306a36Sopenharmony_ciint cs42l43_sdw_remove_peripheral(struct snd_pcm_substream *substream,
9962306a36Sopenharmony_ci				  struct snd_soc_dai *dai);
10062306a36Sopenharmony_ciint cs42l43_sdw_set_stream(struct snd_soc_dai *dai, void *sdw_stream, int direction);
10162306a36Sopenharmony_ci
10262306a36Sopenharmony_ci#else
10362306a36Sopenharmony_ci
10462306a36Sopenharmony_cistatic inline int cs42l43_sdw_add_peripheral(struct snd_pcm_substream *substream,
10562306a36Sopenharmony_ci					     struct snd_pcm_hw_params *params,
10662306a36Sopenharmony_ci					     struct snd_soc_dai *dai)
10762306a36Sopenharmony_ci{
10862306a36Sopenharmony_ci	return -EINVAL;
10962306a36Sopenharmony_ci}
11062306a36Sopenharmony_ci
11162306a36Sopenharmony_ci#define cs42l43_sdw_remove_peripheral NULL
11262306a36Sopenharmony_ci#define cs42l43_sdw_set_stream NULL
11362306a36Sopenharmony_ci
11462306a36Sopenharmony_ci#endif
11562306a36Sopenharmony_ci
11662306a36Sopenharmony_ciint cs42l43_set_jack(struct snd_soc_component *component,
11762306a36Sopenharmony_ci		     struct snd_soc_jack *jack, void *d);
11862306a36Sopenharmony_civoid cs42l43_bias_sense_timeout(struct work_struct *work);
11962306a36Sopenharmony_civoid cs42l43_tip_sense_work(struct work_struct *work);
12062306a36Sopenharmony_civoid cs42l43_button_press_work(struct work_struct *work);
12162306a36Sopenharmony_civoid cs42l43_button_release_work(struct work_struct *work);
12262306a36Sopenharmony_ciirqreturn_t cs42l43_bias_detect_clamp(int irq, void *data);
12362306a36Sopenharmony_ciirqreturn_t cs42l43_button_press(int irq, void *data);
12462306a36Sopenharmony_ciirqreturn_t cs42l43_button_release(int irq, void *data);
12562306a36Sopenharmony_ciirqreturn_t cs42l43_tip_sense(int irq, void *data);
12662306a36Sopenharmony_ciint cs42l43_jack_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol);
12762306a36Sopenharmony_ciint cs42l43_jack_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol);
12862306a36Sopenharmony_ci
12962306a36Sopenharmony_ciextern const struct soc_enum cs42l43_jack_enum;
13062306a36Sopenharmony_ci
13162306a36Sopenharmony_ci#endif /* CS42L43_ASOC_INT_H */
132