1 /*
2  * Copyright (c) 2018 Intel Corporation.
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 /**
8  * @file
9  * @brief Public API header file for Audio Codec
10  *
11  * This file contains the Audio Codec APIs
12  */
13 
14 #ifndef ZEPHYR_INCLUDE_AUDIO_CODEC_H_
15 #define ZEPHYR_INCLUDE_AUDIO_CODEC_H_
16 
17 /**
18  * @brief Abstraction for audio codecs
19  *
20  * @defgroup audio_codec_interface Audio Codec Interface
21  * @ingroup audio_interface
22  * @{
23  */
24 
25 #include <zephyr/drivers/i2s.h>
26 
27 #ifdef __cplusplus
28 extern "C" {
29 #endif
30 
31 /**
32  * PCM audio sample rates
33  */
34 typedef enum {
35 	AUDIO_PCM_RATE_8K	= 8000,		/**< 8 kHz sample rate */
36 	AUDIO_PCM_RATE_16K	= 16000,	/**< 16 kHz sample rate */
37 	AUDIO_PCM_RATE_24K	= 24000,	/**< 24 kHz sample rate */
38 	AUDIO_PCM_RATE_32K	= 32000,	/**< 32 kHz sample rate */
39 	AUDIO_PCM_RATE_44P1K	= 44100,	/**< 44.1 kHz sample rate */
40 	AUDIO_PCM_RATE_48K	= 48000,	/**< 48 kHz sample rate */
41 	AUDIO_PCM_RATE_96K	= 96000,	/**< 96 kHz sample rate */
42 	AUDIO_PCM_RATE_192K	= 192000,	/**< 192 kHz sample rate */
43 } audio_pcm_rate_t;
44 
45 /**
46  * PCM audio sample bit widths
47  */
48 typedef enum {
49 	AUDIO_PCM_WIDTH_16_BITS	= 16,	/**< 16-bit sample width */
50 	AUDIO_PCM_WIDTH_20_BITS	= 20,	/**< 20-bit sample width */
51 	AUDIO_PCM_WIDTH_24_BITS	= 24,	/**< 24-bit sample width */
52 	AUDIO_PCM_WIDTH_32_BITS	= 32,	/**< 32-bit sample width */
53 } audio_pcm_width_t;
54 
55 /**
56  * Digital Audio Interface (DAI) type
57  */
58 typedef enum {
59 	AUDIO_DAI_TYPE_I2S,	/**< I2S Interface */
60 	AUDIO_DAI_TYPE_INVALID,	/**< Other interfaces can be added here */
61 } audio_dai_type_t;
62 
63 /**
64  * Codec properties that can be set by audio_codec_set_property().
65  */
66 typedef enum {
67 	AUDIO_PROPERTY_OUTPUT_VOLUME,	/**< Output volume */
68 	AUDIO_PROPERTY_OUTPUT_MUTE,	/**< Output mute/unmute */
69 } audio_property_t;
70 
71 /**
72  * Audio channel identifiers to use in audio_codec_set_property().
73  */
74 typedef enum {
75 	AUDIO_CHANNEL_FRONT_LEFT,	/**< Front left channel */
76 	AUDIO_CHANNEL_FRONT_RIGHT,	/**< Front right channel */
77 	AUDIO_CHANNEL_LFE,		/**< Low frequency effect channel */
78 	AUDIO_CHANNEL_FRONT_CENTER,	/**< Front center channel */
79 	AUDIO_CHANNEL_REAR_LEFT,	/**< Rear left channel */
80 	AUDIO_CHANNEL_REAR_RIGHT,	/**< Rear right channel */
81 	AUDIO_CHANNEL_REAR_CENTER,	/**< Rear center channel */
82 	AUDIO_CHANNEL_SIDE_LEFT,	/**< Side left channel */
83 	AUDIO_CHANNEL_SIDE_RIGHT,	/**< Side right channel */
84 	AUDIO_CHANNEL_ALL,		/**< All channels */
85 } audio_channel_t;
86 
87 /**
88  * @brief Digital Audio Interface Configuration.
89  *
90  * Configuration is dependent on DAI type
91  */
92 typedef union {
93 	struct i2s_config i2s;	/**< I2S configuration */
94 				/* Other DAI types go here */
95 } audio_dai_cfg_t;
96 
97 /**
98  * Codec configuration parameters
99  */
100 struct audio_codec_cfg {
101 	uint32_t		mclk_freq;	/**< MCLK input frequency in Hz */
102 	audio_dai_type_t	dai_type;	/**< Digital interface type */
103 	audio_dai_cfg_t		dai_cfg;	/**< DAI configuration info */
104 };
105 
106 /**
107  * Codec property values
108  */
109 typedef union {
110 	int	vol;	/**< Volume level in 0.5dB resolution */
111 	bool	mute;	/**< Mute if @a true, unmute if @a false */
112 } audio_property_value_t;
113 
114 /**
115  * @cond INTERNAL_HIDDEN
116  *
117  * For internal use only, skip these in public documentation.
118  */
119 struct audio_codec_api {
120 	int (*configure)(const struct device *dev,
121 			 struct audio_codec_cfg *cfg);
122 	void (*start_output)(const struct device *dev);
123 	void (*stop_output)(const struct device *dev);
124 	int (*set_property)(const struct device *dev,
125 			    audio_property_t property,
126 			    audio_channel_t channel,
127 			    audio_property_value_t val);
128 	int (*apply_properties)(const struct device *dev);
129 };
130 /**
131  * @endcond
132  */
133 
134 /**
135  * @brief Configure the audio codec
136  *
137  * Configure the audio codec device according to the configuration
138  * parameters provided as input
139  *
140  * @param dev Pointer to the device structure for codec driver instance.
141  * @param cfg Pointer to the structure containing the codec configuration.
142  *
143  * @return 0 on success, negative error code on failure
144  */
audio_codec_configure(const struct device * dev,struct audio_codec_cfg * cfg)145 static inline int audio_codec_configure(const struct device *dev,
146 					struct audio_codec_cfg *cfg)
147 {
148 	const struct audio_codec_api *api =
149 		(const struct audio_codec_api *)dev->api;
150 
151 	return api->configure(dev, cfg);
152 }
153 
154 /**
155  * @brief Set codec to start output audio playback
156  *
157  * Setup the audio codec device to start the audio playback
158  *
159  * @param dev Pointer to the device structure for codec driver instance.
160  */
audio_codec_start_output(const struct device * dev)161 static inline void audio_codec_start_output(const struct device *dev)
162 {
163 	const struct audio_codec_api *api =
164 		(const struct audio_codec_api *)dev->api;
165 
166 	api->start_output(dev);
167 }
168 
169 /**
170  * @brief Set codec to stop output audio playback
171  *
172  * Setup the audio codec device to stop the audio playback
173  *
174  * @param dev Pointer to the device structure for codec driver instance.
175  */
audio_codec_stop_output(const struct device * dev)176 static inline void audio_codec_stop_output(const struct device *dev)
177 {
178 	const struct audio_codec_api *api =
179 		(const struct audio_codec_api *)dev->api;
180 
181 	api->stop_output(dev);
182 }
183 
184 /**
185  * @brief Set a codec property defined by audio_property_t
186  *
187  * Set a property such as volume level, clock configuration etc.
188  *
189  * @param dev Pointer to the device structure for codec driver instance.
190  * @param property The codec property to set
191  * @param channel The audio channel for which the property has to be set
192  * @param val pointer to a property value of type audio_codec_property_value_t
193  *
194  * @return 0 on success, negative error code on failure
195  */
audio_codec_set_property(const struct device * dev,audio_property_t property,audio_channel_t channel,audio_property_value_t val)196 static inline int audio_codec_set_property(const struct device *dev,
197 					   audio_property_t property,
198 					   audio_channel_t channel,
199 					   audio_property_value_t val)
200 {
201 	const struct audio_codec_api *api =
202 		(const struct audio_codec_api *)dev->api;
203 
204 	return api->set_property(dev, property, channel, val);
205 }
206 
207 /**
208  * @brief Atomically apply any cached properties
209  *
210  * Following one or more invocations of audio_codec_set_property, that may have
211  * been cached by the driver, audio_codec_apply_properties can be invoked to
212  * apply all the properties as atomic as possible
213  *
214  * @param dev Pointer to the device structure for codec driver instance.
215  *
216  * @return 0 on success, negative error code on failure
217  */
audio_codec_apply_properties(const struct device * dev)218 static inline int audio_codec_apply_properties(const struct device *dev)
219 {
220 	const struct audio_codec_api *api =
221 		(const struct audio_codec_api *)dev->api;
222 
223 	return api->apply_properties(dev);
224 }
225 
226 #ifdef __cplusplus
227 }
228 #endif
229 
230 /**
231  * @}
232  */
233 
234 #endif /* ZEPHYR_INCLUDE_AUDIO_CODEC_H_ */
235