diff options
Diffstat (limited to 'firmware/target')
-rw-r--r-- | firmware/target/arm/imx233/dma-imx233.c | 34 |
1 files changed, 34 insertions, 0 deletions
diff --git a/firmware/target/arm/imx233/dma-imx233.c b/firmware/target/arm/imx233/dma-imx233.c index 390add481b..fa8ee074bb 100644 --- a/firmware/target/arm/imx233/dma-imx233.c +++ b/firmware/target/arm/imx233/dma-imx233.c | |||
@@ -32,8 +32,42 @@ | |||
32 | // statistics about unaligned transfers | 32 | // statistics about unaligned transfers |
33 | static int apb_nr_unaligned[32]; | 33 | static int apb_nr_unaligned[32]; |
34 | 34 | ||
35 | static void safe_reset_channel(int chan) | ||
36 | { | ||
37 | bool apbx_running = !BF_RD(APBX_CTRL0, SFTRST) && !BF_RD(APBX_CTRL0, CLKGATE); | ||
38 | bool apbh_running = !BF_RD(APBH_CTRL0, SFTRST) && !BF_RD(APBH_CTRL0, CLKGATE); | ||
39 | if(APB_IS_APBX_CHANNEL(chan)) | ||
40 | { | ||
41 | if(!apbx_running) | ||
42 | return; /* don't reset if block is not running */ | ||
43 | } | ||
44 | else | ||
45 | { | ||
46 | if(!apbh_running) | ||
47 | return; /* don't reset if block is not running */ | ||
48 | if(BF_RD(APBH_CTRL0, CLKGATE_CHANNEL) & (1 << chan)) | ||
49 | return; /* don't reset a gated channel */ | ||
50 | } | ||
51 | imx233_dma_reset_channel(chan); | ||
52 | } | ||
53 | |||
35 | void imx233_dma_init(void) | 54 | void imx233_dma_init(void) |
36 | { | 55 | { |
56 | /* BUG The stmp3700 (and probably stmp3780) have a hardware bug related to | ||
57 | * resetting the block when channel is running. It appears that at least | ||
58 | * for the LCDIF channel, resetting the block while the channel is running | ||
59 | * will make the channel hang. Once the channel hang, it cannot be recovered | ||
60 | * except by a chip reset. On most devices this situation will never arise | ||
61 | * but on the Creative ZEN (X-Fi), the OF bootloader leaves the channel | ||
62 | * running (to display the logo) when booting. It is unclear if this bug only | ||
63 | * affects the APBH or also the APBX. I believe it is related to the errata about | ||
64 | * channels not clearing the fifo on abrupt termination which affects both | ||
65 | * dma engines. Also note that we can't safely reset 'all' the channels by | ||
66 | * setting the reset mask to 0xffff since non-implemented channels don't clear | ||
67 | * their reset bit... Also reset won't work on gated channels and won't work if | ||
68 | * block is in reset or gated, in which case this situation is assumed not | ||
69 | * to exists */ | ||
70 | safe_reset_channel(APB_LCDIF); | ||
37 | /* Enable APHB and APBX */ | 71 | /* Enable APHB and APBX */ |
38 | imx233_reset_block(&HW_APBH_CTRL0); | 72 | imx233_reset_block(&HW_APBH_CTRL0); |
39 | imx233_reset_block(&HW_APBX_CTRL0); | 73 | imx233_reset_block(&HW_APBX_CTRL0); |