1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
10 * Copyright (C) 2011 by Amaury Pouly
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
18 * KIND, either express or implied.
20 ****************************************************************************/
25 #include "dma-imx233.h"
26 #include "pcm-internal.h"
27 #include "audioout-imx233.h"
29 static int locked
= 0;
30 static struct apb_dma_command_t dac_dma
;
31 static bool pcm_freezed
= false;
35 * Never reset the dma channel, otherwise it will halt the DAC for some reason
38 static void play(const void *addr
, size_t size
)
41 dac_dma
.buffer
= (void *)addr
;
42 dac_dma
.cmd
= HW_APB_CHx_CMD__COMMAND__READ
|
43 HW_APB_CHx_CMD__IRQONCMPLT
|
44 HW_APB_CHx_CMD__SEMAPHORE
|
45 size
<< HW_APB_CHx_CMD__XFER_COUNT_BP
;
46 /* dma subsystem will make sure cached stuff is written to memory */
47 imx233_dma_start_command(APB_AUDIO_DAC
, &dac_dma
);
50 void INT_DAC_DMA(void)
55 if (pcm_play_dma_complete_callback(PCM_DMAST_OK
, &start
, &size
))
58 pcm_play_dma_status_callback(PCM_DMAST_STARTED
);
61 imx233_dma_clear_channel_interrupt(APB_AUDIO_DAC
);
64 void INT_DAC_ERROR(void)
66 /* TODO: Inform of error through pcm_play_dma_complete_callback */
69 void pcm_play_lock(void)
72 imx233_dma_enable_channel_interrupt(APB_AUDIO_DAC
, false);
75 void pcm_play_unlock(void)
78 imx233_dma_enable_channel_interrupt(APB_AUDIO_DAC
, true);
81 void pcm_play_dma_stop(void)
85 void pcm_play_dma_start(const void *addr
, size_t size
)
92 void pcm_play_dma_pause(bool pause
)
94 imx233_dma_freeze_channel(APB_AUDIO_DAC
, pause
);
98 void pcm_play_dma_init(void)
103 void pcm_play_dma_postinit(void)
106 imx233_enable_interrupt(INT_SRC_DAC_DMA
, true);
107 imx233_enable_interrupt(INT_SRC_DAC_ERROR
, true);
108 imx233_dma_enable_channel_interrupt(APB_AUDIO_DAC
, true);
111 void pcm_dma_apply_settings(void)
113 audiohw_set_frequency(pcm_fsel
);
116 size_t pcm_get_bytes_waiting(void)
118 struct imx233_dma_info_t info
= imx233_dma_get_info(APB_AUDIO_DAC
, DMA_INFO_AHB_BYTES
);
119 return info
.ahb_bytes
;
122 const void *pcm_play_dma_get_peak_buffer(int *count
)
125 imx233_dma_freeze_channel(APB_AUDIO_DAC
, true);
126 struct imx233_dma_info_t info
= imx233_dma_get_info(APB_AUDIO_DAC
, DMA_INFO_AHB_BYTES
| DMA_INFO_BAR
);
128 imx233_dma_freeze_channel(APB_AUDIO_DAC
, false);
129 *count
= info
.ahb_bytes
;
130 return (void *)info
.bar
;
137 void pcm_rec_lock(void)
141 void pcm_rec_unlock(void)
145 void pcm_rec_dma_init(void)
149 void pcm_rec_dma_close(void)
153 void pcm_rec_dma_start(void *addr
, size_t size
)
160 void pcm_rec_dma_record_more(void *start, size_t size)
165 void pcm_rec_dma_stop(void)
169 const void *pcm_rec_dma_get_peak_buffer(void)