added loopback example with adc samples and dac playback
[pcm-lib.git] / source / pcm.h
blobab80b208ee225564bf17394792937bf6cc390bfd
1 /*
2 * This program is free software; you can redistribute it and/or modify
3 * it under the terms of the GNU General Public License version 2 as
4 * published by the Free Software Foundation.
5 * pcm.h -
6 * <liu090@sina.com>
7 */
8 #ifndef __PCM_H__
9 #define __PCM_H__
12 #include "os_utils.h"
13 #include "soc_cfg.h"
15 #include "pcm_lib.h"
17 /* pcm runtime ************************************************/
18 #define SNDRV_PCM_TRIGGER_STOP 0
19 #define SNDRV_PCM_TRIGGER_START 1
20 #define SNDRV_PCM_TRIGGER_PAUSE_PUSH 3
21 #define SNDRV_PCM_TRIGGER_PAUSE_RELEASE 4
22 #define SNDRV_PCM_TRIGGER_SUSPEND 5
23 #define SNDRV_PCM_TRIGGER_RESUME 6
25 struct pcm_format_data {
26 unsigned char width; /* bit width */
27 unsigned char phys; /* physical bit width */
28 signed char le; /* 0 = big-endian, 1 = little-endian, -1 = others */
29 signed char signd; /* 0 = unsigned, 1 = signed, -1 = others */
30 unsigned char silence[8]; /* silence data to fill */
33 /* pcm struct */
34 struct snd_pcm_rt_status {
35 snd_pcm_state_t state; /* RO: state - SNDRV_PCM_STATE_XXXX */
36 /* int pad1; */ /* Needed for 64 bit alignment */
37 snd_pcm_uframes_t hw_ptr; /* RO: hw ptr (0...boundary-1) */
38 /*struct timespec tstamp;*/ /* Timestamp */
39 /* snd_pcm_state_t suspended_state;*/ /* RO: suspended stream state */
42 struct snd_pcm_rt_control {
43 snd_pcm_uframes_t appl_ptr; /* RW: appl ptr (0...boundary-1) */
44 /* snd_pcm_uframes_t avail_min;*/ /* RW: min available frames for wakeup */
47 #define SNDRV_PCM_POS_XRUN ((snd_pcm_uframes_t)-1)
49 /* If you change this don't forget to change rates[] table in pcm_native.c */
50 #define SNDRV_PCM_RATE_5512 (1<<0) /* 5512Hz */
51 #define SNDRV_PCM_RATE_8000 (1<<1) /* 8000Hz */
52 #define SNDRV_PCM_RATE_11025 (1<<2) /* 11025Hz */
53 #define SNDRV_PCM_RATE_16000 (1<<3) /* 16000Hz */
54 #define SNDRV_PCM_RATE_22050 (1<<4) /* 22050Hz */
55 #define SNDRV_PCM_RATE_32000 (1<<5) /* 32000Hz */
56 #define SNDRV_PCM_RATE_44100 (1<<6) /* 44100Hz */
57 #define SNDRV_PCM_RATE_48000 (1<<7) /* 48000Hz */
58 #define SNDRV_PCM_RATE_64000 (1<<8) /* 64000Hz */
59 #define SNDRV_PCM_RATE_88200 (1<<9) /* 88200Hz */
60 #define SNDRV_PCM_RATE_96000 (1<<10) /* 96000Hz */
61 #define SNDRV_PCM_RATE_176400 (1<<11) /* 176400Hz */
62 #define SNDRV_PCM_RATE_192000 (1<<12) /* 192000Hz */
64 #define SNDRV_PCM_RATE_CONTINUOUS (1<<30) /* continuous range */
65 #define SNDRV_PCM_RATE_KNOT (1<<31) /* supports more non-continuos rates */
67 #define SNDRV_PCM_RATE_8000_44100 (SNDRV_PCM_RATE_8000|SNDRV_PCM_RATE_11025|\
68 SNDRV_PCM_RATE_16000|SNDRV_PCM_RATE_22050|\
69 SNDRV_PCM_RATE_32000|SNDRV_PCM_RATE_44100)
70 #define SNDRV_PCM_RATE_8000_48000 (SNDRV_PCM_RATE_8000_44100|SNDRV_PCM_RATE_48000)
71 #define SNDRV_PCM_RATE_8000_96000 (SNDRV_PCM_RATE_8000_48000|SNDRV_PCM_RATE_64000|\
72 SNDRV_PCM_RATE_88200|SNDRV_PCM_RATE_96000)
73 #define SNDRV_PCM_RATE_8000_192000 (SNDRV_PCM_RATE_8000_96000|SNDRV_PCM_RATE_176400|\
74 SNDRV_PCM_RATE_192000)
76 #define _SNDRV_PCM_FMTBIT(fmt) (1ULL << (int)SNDRV_PCM_FORMAT_##fmt) /* SNDRV_PCM_FORMAT_S16_LE */
77 #define SNDRV_PCM_FMTBIT_S8 _SNDRV_PCM_FMTBIT(S8)
78 #define SNDRV_PCM_FMTBIT_U8 _SNDRV_PCM_FMTBIT(U8)
79 #define SNDRV_PCM_FMTBIT_S16_LE _SNDRV_PCM_FMTBIT(S16_LE)
80 #define SNDRV_PCM_FMTBIT_S16_BE _SNDRV_PCM_FMTBIT(S16_BE)
81 #define SNDRV_PCM_FMTBIT_U16_LE _SNDRV_PCM_FMTBIT(U16_LE)
82 #define SNDRV_PCM_FMTBIT_U16_BE _SNDRV_PCM_FMTBIT(U16_BE)
83 #define SNDRV_PCM_FMTBIT_S24_LE _SNDRV_PCM_FMTBIT(S24_LE)
84 #define SNDRV_PCM_FMTBIT_S24_BE _SNDRV_PCM_FMTBIT(S24_BE)
85 #define SNDRV_PCM_FMTBIT_U24_LE _SNDRV_PCM_FMTBIT(U24_LE)
86 #define SNDRV_PCM_FMTBIT_U24_BE _SNDRV_PCM_FMTBIT(U24_BE)
87 #define SNDRV_PCM_FMTBIT_S32_LE _SNDRV_PCM_FMTBIT(S32_LE)
88 #define SNDRV_PCM_FMTBIT_S32_BE _SNDRV_PCM_FMTBIT(S32_BE)
89 #define SNDRV_PCM_FMTBIT_U32_LE _SNDRV_PCM_FMTBIT(U32_LE)
90 #define SNDRV_PCM_FMTBIT_U32_BE _SNDRV_PCM_FMTBIT(U32_BE)
91 #define SNDRV_PCM_FMTBIT_FLOAT_LE _SNDRV_PCM_FMTBIT(FLOAT_LE)
92 #define SNDRV_PCM_FMTBIT_FLOAT_BE _SNDRV_PCM_FMTBIT(FLOAT_BE)
93 #define SNDRV_PCM_FMTBIT_FLOAT64_LE _SNDRV_PCM_FMTBIT(FLOAT64_LE)
94 #define SNDRV_PCM_FMTBIT_FLOAT64_BE _SNDRV_PCM_FMTBIT(FLOAT64_BE)
95 #define SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_LE _SNDRV_PCM_FMTBIT(IEC958_SUBFRAME_LE)
96 #define SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_BE _SNDRV_PCM_FMTBIT(IEC958_SUBFRAME_BE)
97 #define SNDRV_PCM_FMTBIT_MU_LAW _SNDRV_PCM_FMTBIT(MU_LAW)
98 #define SNDRV_PCM_FMTBIT_A_LAW _SNDRV_PCM_FMTBIT(A_LAW)
99 #define SNDRV_PCM_FMTBIT_IMA_ADPCM _SNDRV_PCM_FMTBIT(IMA_ADPCM)
100 #define SNDRV_PCM_FMTBIT_MPEG _SNDRV_PCM_FMTBIT(MPEG)
101 #define SNDRV_PCM_FMTBIT_GSM _SNDRV_PCM_FMTBIT(GSM)
102 #define SNDRV_PCM_FMTBIT_SPECIAL _SNDRV_PCM_FMTBIT(SPECIAL)
103 #define SNDRV_PCM_FMTBIT_S24_3LE _SNDRV_PCM_FMTBIT(S24_3LE)
104 #define SNDRV_PCM_FMTBIT_U24_3LE _SNDRV_PCM_FMTBIT(U24_3LE)
105 #define SNDRV_PCM_FMTBIT_S24_3BE _SNDRV_PCM_FMTBIT(S24_3BE)
106 #define SNDRV_PCM_FMTBIT_U24_3BE _SNDRV_PCM_FMTBIT(U24_3BE)
107 #define SNDRV_PCM_FMTBIT_S20_3LE _SNDRV_PCM_FMTBIT(S20_3LE)
108 #define SNDRV_PCM_FMTBIT_U20_3LE _SNDRV_PCM_FMTBIT(U20_3LE)
109 #define SNDRV_PCM_FMTBIT_S20_3BE _SNDRV_PCM_FMTBIT(S20_3BE)
110 #define SNDRV_PCM_FMTBIT_U20_3BE _SNDRV_PCM_FMTBIT(U20_3BE)
111 #define SNDRV_PCM_FMTBIT_S18_3LE _SNDRV_PCM_FMTBIT(S18_3LE)
112 #define SNDRV_PCM_FMTBIT_U18_3LE _SNDRV_PCM_FMTBIT(U18_3LE)
113 #define SNDRV_PCM_FMTBIT_S18_3BE _SNDRV_PCM_FMTBIT(S18_3BE)
114 #define SNDRV_PCM_FMTBIT_U18_3BE _SNDRV_PCM_FMTBIT(U18_3BE)
115 #define SNDRV_PCM_FMTBIT_G723_24 _SNDRV_PCM_FMTBIT(G723_24)
116 #define SNDRV_PCM_FMTBIT_G723_24_1B _SNDRV_PCM_FMTBIT(G723_24_1B)
117 #define SNDRV_PCM_FMTBIT_G723_40 _SNDRV_PCM_FMTBIT(G723_40)
118 #define SNDRV_PCM_FMTBIT_G723_40_1B _SNDRV_PCM_FMTBIT(G723_40_1B)
120 #ifdef SNDRV_LITTLE_ENDIAN
121 #define SNDRV_PCM_FMTBIT_S16 SNDRV_PCM_FMTBIT_S16_LE
122 #define SNDRV_PCM_FMTBIT_U16 SNDRV_PCM_FMTBIT_U16_LE
123 #define SNDRV_PCM_FMTBIT_S24 SNDRV_PCM_FMTBIT_S24_LE
124 #define SNDRV_PCM_FMTBIT_U24 SNDRV_PCM_FMTBIT_U24_LE
125 #define SNDRV_PCM_FMTBIT_S32 SNDRV_PCM_FMTBIT_S32_LE
126 #define SNDRV_PCM_FMTBIT_U32 SNDRV_PCM_FMTBIT_U32_LE
127 #define SNDRV_PCM_FMTBIT_FLOAT SNDRV_PCM_FMTBIT_FLOAT_LE
128 #define SNDRV_PCM_FMTBIT_FLOAT64 SNDRV_PCM_FMTBIT_FLOAT64_LE
129 #define SNDRV_PCM_FMTBIT_IEC958_SUBFRAME SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_LE
130 #endif
131 #ifdef SNDRV_BIG_ENDIAN
132 #define SNDRV_PCM_FMTBIT_S16 SNDRV_PCM_FMTBIT_S16_BE
133 #define SNDRV_PCM_FMTBIT_U16 SNDRV_PCM_FMTBIT_U16_BE
134 #define SNDRV_PCM_FMTBIT_S24 SNDRV_PCM_FMTBIT_S24_BE
135 #define SNDRV_PCM_FMTBIT_U24 SNDRV_PCM_FMTBIT_U24_BE
136 #define SNDRV_PCM_FMTBIT_S32 SNDRV_PCM_FMTBIT_S32_BE
137 #define SNDRV_PCM_FMTBIT_U32 SNDRV_PCM_FMTBIT_U32_BE
138 #define SNDRV_PCM_FMTBIT_FLOAT SNDRV_PCM_FMTBIT_FLOAT_BE
139 #define SNDRV_PCM_FMTBIT_FLOAT64 SNDRV_PCM_FMTBIT_FLOAT64_BE
140 #define SNDRV_PCM_FMTBIT_IEC958_SUBFRAME SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_BE
141 #endif
143 struct snd_pcm_runtime {
144 int stream; /* driect (p or c) */
145 snd_pcm_uframes_t avail_max;
147 snd_pcm_uframes_t hw_ptr_base;
148 snd_pcm_uframes_t hw_ptr_interrupt; /* Position at interrupt time */
149 unsigned long hw_ptr_ticks; /* Time when hw_ptr is updated */
150 unsigned long hw_ptr_buffer_ticks; /* buffer time in ticks */
151 unsigned long hw_ptr_ticks_inteval; /* dma rate */
153 /* -- HW params -- */
154 snd_pcm_access_t access; /* access mode */
155 snd_pcm_format_t format; /* SNDRV_PCM_FORMAT_* */
156 unsigned int rate; /* rate in Hz ,sample rate */
157 unsigned int channels; /* channels */
158 snd_pcm_uframes_t period_size; /* interrput period ( sample unit ) */
159 unsigned int periods; /* periods */
160 snd_pcm_uframes_t buffer_size;
161 snd_pcm_uframes_t min_align; /* Min alignment for the format */
162 /* if min_align is aligned 8bit ,then min_align =1 frame */
164 unsigned int frame_bits;
165 unsigned int sample_bits;
166 unsigned int sample_phy_bits;
167 unsigned int sample_aligned_bits; /* dma buffer 's sample aligned bits ,
168 default is same as sample_bits */
170 /* -- SW params -- */
171 snd_pcm_uframes_t start_threshold;
172 snd_pcm_uframes_t stop_threshold;
173 snd_pcm_uframes_t silence_threshold; /* Silence filling happens when
174 noise is nearest than this */
175 snd_pcm_uframes_t silence_size; /* Silence filling size */
176 snd_pcm_uframes_t boundary; /* sample unit */
178 snd_pcm_uframes_t silence_start; /* starting pointer to silence area */
179 snd_pcm_uframes_t silence_filled; /* size filled with silence */
181 /* -- rw pointer -- */
182 struct snd_pcm_rt_status *status; /* playback read pointer */
184 struct snd_pcm_rt_control *control; /* playback write pointer */
186 /* -- hardware description -- */
187 /* struct snd_pcm_hardware hw; */
189 /* -- DMA -- */
190 unsigned char *dma_area;
191 unsigned int dma_bytes; /* size of DMA area */
193 //unsigned int reserve1;
195 /* -- private section -- */
196 void *private_data; /* pointer to struct pcm_runtime_data *iprtd */
197 /* void (*private_free)(struct snd_pcm_runtime *runtime); */
201 static inline int snd_pcm_running(struct snd_pcm_runtime *runtime) /* RUNNING */
203 return (runtime->status->state == SNDRV_PCM_STATE_RUNNING);
206 #if 0
207 static inline void snd_pcm_set_runtime_buffer(struct snd_pcm_runtime *runtime,
208 struct snd_dma_buffer *bufp)
210 if (bufp) {
211 runtime->dma_area = bufp->area;
212 runtime->dma_bytes = bufp->bytes;
213 } else {
214 runtime->dma_area = NULL;
215 runtime->dma_bytes = 0;
218 #endif
220 static inline /*ssize_t*/int bytes_to_samples(struct snd_pcm_runtime *runtime, ssize_t size)
222 return size * 8 / runtime->sample_bits;
225 static inline snd_pcm_sframes_t bytes_to_frames(struct snd_pcm_runtime *runtime, ssize_t size)
227 return size * 8 / runtime->frame_bits;
230 static inline /*ssize_t*/int samples_to_bytes(struct snd_pcm_runtime *runtime, ssize_t size)
232 return size * runtime->sample_bits / 8;
235 static inline int frames_to_bytes(struct snd_pcm_runtime *runtime, snd_pcm_sframes_t size)
237 return size * runtime->frame_bits / 8;
240 #if 0
241 static inline int frame_aligned(struct snd_pcm_runtime *runtime, ssize_t bytes)
243 return bytes % runtime->byte_align == 0;
245 #endif
248 * result is: 0 ... (boundary - 1)
250 static inline snd_pcm_uframes_t snd_pcm_playback_avail(struct snd_pcm_runtime *runtime)
252 snd_pcm_sframes_t avail = runtime->status->hw_ptr + runtime->buffer_size - runtime->control->appl_ptr;
254 if (avail < 0)
255 avail += runtime->boundary;
256 else if ((snd_pcm_uframes_t) avail >= runtime->boundary)
257 avail -= runtime->boundary;
258 return avail;
262 * result is: 0 ... (boundary - 1)
264 static inline snd_pcm_uframes_t snd_pcm_capture_avail(struct snd_pcm_runtime *runtime)
266 snd_pcm_sframes_t avail = runtime->status->hw_ptr - runtime->control->appl_ptr;
267 if (avail < 0)
268 avail += runtime->boundary;
269 return avail;
272 static inline snd_pcm_sframes_t snd_pcm_playback_hw_avail(struct snd_pcm_runtime *runtime)
274 return runtime->buffer_size - snd_pcm_playback_avail(runtime);
278 * interface hardware audio formats.
280 * Describes the physical PCM data formating and clocking. Add new formats
281 * to the end.
283 #define SND_SOC_INTFFMT_I2S 0 /* I2S mode */
284 #define SND_SOC_INTFFMT_RIGHT_J 1 /* Right Justified mode */
285 #define SND_SOC_INTFFMT_LEFT_J 2 /* Left Justified mode */
286 #define SND_SOC_INTFFMT_DSP_A 3 /* L data MSB after FRM LRC */
287 #define SND_SOC_INTFFMT_DSP_B 4 /* L data MSB during FRM LRC */
288 #define SND_SOC_INTFFMT_AC97 5 /* AC97 */
289 #define SND_SOC_INTFFMT_PDM 6 /* Pulse density modulation */
291 /* left and right justified also known as MSB and LSB respectively */
292 #define SND_SOC_INTFFMT_MSB SND_SOC_INTFFMT_LEFT_J
293 #define SND_SOC_INTFFMT_LSB SND_SOC_INTFFMT_RIGHT_J
296 * interface Clock gating.
298 * interface bit clocks can be be gated (disabled) when the interface is not
299 * sending or receiving PCM data in a frame. This can be used to save power.
301 #define SND_SOC_INTFFMT_CONT (0 << 4) /* continuous clock */
302 #define SND_SOC_INTFFMT_GATED (1 << 4) /* clock is gated */
305 * DAI hardware signal inversions.
307 * Specifies whether the DAI can also support inverted clocks for the specified
308 * format.
310 #define SND_SOC_INTFFMT_NB_NF (0 << 8) /* normal bit clock + frame */
311 #define SND_SOC_INTFFMT_NB_IF (1 << 8) /* normal BCLK + inv FRM */
312 #define SND_SOC_INTFFMT_IB_NF (2 << 8) /* invert BCLK + nor FRM */
313 #define SND_SOC_INTFFMT_IB_IF (3 << 8) /* invert BCLK + FRM */
316 * DAI hardware clock masters.
318 * This is wrt the codec, the inverse is true for the interface
319 * i.e. if the codec is clk and FRM master then the interface is
320 * clk and frame slave.
322 #define SND_SOC_INTFFMT_CBM_CFM (0 << 12) /* codec clk & FRM master */
323 #define SND_SOC_INTFFMT_CBS_CFM (1 << 12) /* codec clk slave & FRM master */
324 #define SND_SOC_INTFFMT_CBM_CFS (2 << 12) /* codec clk master & frame slave */
325 #define SND_SOC_INTFFMT_CBS_CFS (3 << 12) /* codec clk & FRM slave */
327 #define SND_SOC_INTFFMT_FORMAT_MASK 0x000f
328 #define SND_SOC_INTFFMT_CLOCK_MASK 0x00f0
329 #define SND_SOC_INTFFMT_INV_MASK 0x0f00
330 #define SND_SOC_INTFFMT_MASTER_MASK 0xf000
332 #define PCM_RUNTIME_CHECK(runtime) \
333 snd_BUG_ON(!(runtime) || !(runtime)->private_data)
335 #define MAX_PERIODS 8
336 #define MIN_PERIODS 2
338 //#define CHECK_DOUBLE_ACKED_INTRS
340 void audio_dma_irq(void *data,uint_8 chan);
342 /* soc codec interface function delare */
343 #include "soc-codec/soc_codec.h"
345 #endif // __PCM_H__