summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLinus Nielsen Feltzing <linus@haxx.se>2004-04-01 14:07:56 +0000
committerLinus Nielsen Feltzing <linus@haxx.se>2004-04-01 14:07:56 +0000
commit5248641b40d1a49545b61b61d269eb40c1ccf0ce (patch)
tree84f3ffe724e834e4acf71ea9f1240c56a749af40
parent3d1348c573aaf8e6f269c719495e198e5e2f8867 (diff)
downloadrockbox-5248641b40d1a49545b61b61d269eb40c1ccf0ce.tar.gz
rockbox-5248641b40d1a49545b61b61d269eb40c1ccf0ce.zip
Some bug fixes in the recording code. The recorded frames weren't CRC protected as intended, and the first frame could be incomplete. Also reduced the I2C communication by shadowing the MAS registers.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@4462 a1c6a512-1295-4272-9138-f99709370657
-rw-r--r--firmware/mpeg.c120
1 files changed, 81 insertions, 39 deletions
diff --git a/firmware/mpeg.c b/firmware/mpeg.c
index a880cc5776..ef0c25a89f 100644
--- a/firmware/mpeg.c
+++ b/firmware/mpeg.c
@@ -16,6 +16,7 @@
16 * KIND, either express or implied. 16 * KIND, either express or implied.
17 * 17 *
18 ****************************************************************************/ 18 ****************************************************************************/
19#undef DEBUG
19#include <stdbool.h> 20#include <stdbool.h>
20#include "config.h" 21#include "config.h"
21#include "debug.h" 22#include "debug.h"
@@ -304,6 +305,13 @@ static int prerecord_index; /* Current index in the prerecord buffer */
304static int prerecording_max_seconds; /* Max number of seconds to store */ 305static int prerecording_max_seconds; /* Max number of seconds to store */
305static int prerecord_count; /* Number of seconds in the prerecord buffer */ 306static int prerecord_count; /* Number of seconds in the prerecord buffer */
306static int prerecord_timeout; /* The tick count of the next prerecord data store */ 307static int prerecord_timeout; /* The tick count of the next prerecord data store */
308
309/* Shadow MAS registers */
310unsigned long shadow_7f0 = 0;
311unsigned long shadow_7f1 = 0;
312unsigned long shadow_7f6 = 0;
313unsigned long shadow_7f9 = 0;
314
307#endif /* #ifdef HAVE_MAS3587F */ 315#endif /* #ifdef HAVE_MAS3587F */
308 316
309static int mpeg_file; 317static int mpeg_file;
@@ -2041,6 +2049,7 @@ static void init_recording(void)
2041 paused = false; 2049 paused = false;
2042 2050
2043 reset_mp3_buffer(); 2051 reset_mp3_buffer();
2052
2044 remove_all_tags(); 2053 remove_all_tags();
2045 2054
2046 if(mpeg_file >= 0) 2055 if(mpeg_file >= 0)
@@ -2092,12 +2101,12 @@ static void init_recording(void)
2092 mas_codec_writereg(7, 0x4000); 2101 mas_codec_writereg(7, 0x4000);
2093 2102
2094 /* No mute */ 2103 /* No mute */
2095 val = 0; 2104 shadow_7f9 = 0;
2096 mas_writemem(MAS_BANK_D0, 0x7f9, &val, 1); 2105 mas_writemem(MAS_BANK_D0, 0x7f9, &shadow_7f9, 1);
2097 2106
2098 /* Set Demand mode, no monitoring and validate all settings */ 2107 /* Set Demand mode, monitoring OFF and validate all settings */
2099 val = 0x125; 2108 shadow_7f1 = 0x125;
2100 mas_writemem(MAS_BANK_D0, 0x7f1, &val, 1); 2109 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1, 1);
2101 2110
2102 /* Start the encoder application */ 2111 /* Start the encoder application */
2103 val = 0x40; 2112 val = 0x40;
@@ -2107,6 +2116,7 @@ static void init_recording(void)
2107 mas_readmem(MAS_BANK_D0, 0x7f7, &val, 1); 2116 mas_readmem(MAS_BANK_D0, 0x7f7, &val, 1);
2108 } while(!(val & 0x40)); 2117 } while(!(val & 0x40));
2109 2118
2119#if 1
2110 /* We have started the recording application with monitoring OFF. 2120 /* We have started the recording application with monitoring OFF.
2111 This is because we want to record at least one frame to fill the DMA 2121 This is because we want to record at least one frame to fill the DMA
2112 buffer, because the silly MAS will not negate EOD until at least one 2122 buffer, because the silly MAS will not negate EOD until at least one
@@ -2115,9 +2125,11 @@ static void init_recording(void)
2115 sleep(20); 2125 sleep(20);
2116 2126
2117 /* Now set it to Monitoring mode as default, saves power */ 2127 /* Now set it to Monitoring mode as default, saves power */
2118 val = 0x525; 2128 shadow_7f1 = 0x525;
2119 mas_writemem(MAS_BANK_D0, 0x7f1, &val, 1); 2129 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1, 1);
2120 2130
2131 drain_dma_buffer();
2132#endif
2121 mpeg_mode = MPEG_ENCODER; 2133 mpeg_mode = MPEG_ENCODER;
2122 2134
2123 DEBUGF("MAS Recording application started\n"); 2135 DEBUGF("MAS Recording application started\n");
@@ -2152,11 +2164,9 @@ static void start_prerecording(void)
2152 is_prerecording = true; 2164 is_prerecording = true;
2153 2165
2154 /* Stop monitoring and start the encoder */ 2166 /* Stop monitoring and start the encoder */
2155 mas_readmem(MAS_BANK_D0, 0x7f1, &val, 1); 2167 shadow_7f1 &= ~(1 << 10);
2156 val &= ~(1 << 10); 2168 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1, 1);
2157 val |= 1; 2169 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", shadow_7f1);
2158 mas_writemem(MAS_BANK_D0, 0x7f1, &val, 1);
2159 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", val);
2160 2170
2161 /* Wait until the DSP has accepted the settings */ 2171 /* Wait until the DSP has accepted the settings */
2162 do 2172 do
@@ -2164,8 +2174,6 @@ static void start_prerecording(void)
2164 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1); 2174 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1);
2165 } while(val & 1); 2175 } while(val & 1);
2166 2176
2167 sleep(HZ/100);
2168
2169 is_recording = true; 2177 is_recording = true;
2170 stop_pending = false; 2178 stop_pending = false;
2171 saving = false; 2179 saving = false;
@@ -2190,19 +2198,15 @@ static void start_recording(void)
2190 { 2198 {
2191 /* If prerecording is off, we need to stop the monitoring 2199 /* If prerecording is off, we need to stop the monitoring
2192 and start the encoder */ 2200 and start the encoder */
2193 mas_readmem(MAS_BANK_D0, 0x7f1, &val, 1); 2201 shadow_7f1 &= ~(1 << 10);
2194 val &= ~(1 << 10); 2202 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1, 1);
2195 val |= 1; 2203 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", shadow_7f1);
2196 mas_writemem(MAS_BANK_D0, 0x7f1, &val, 1);
2197 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", val);
2198 2204
2199 /* Wait until the DSP has accepted the settings */ 2205 /* Wait until the DSP has accepted the settings */
2200 do 2206 do
2201 { 2207 {
2202 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1); 2208 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1);
2203 } while(val & 1); 2209 } while(val & 1);
2204
2205 sleep(HZ/100);
2206 } 2210 }
2207 2211
2208 is_recording = true; 2212 is_recording = true;
@@ -2218,10 +2222,52 @@ static void start_recording(void)
2218 demand_irq_enable(true); 2222 demand_irq_enable(true);
2219} 2223}
2220 2224
2225static void pause_recording(void)
2226{
2227 unsigned long val;
2228
2229 /* Set the pause bit */
2230 shadow_7f9 |= 2;
2231 mas_writemem(MAS_BANK_D0, 0x7f9, &shadow_7f9, 1);
2232
2233 /* Tell the MAS that something has changed */
2234 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1, 1);
2235 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", shadow_7f1);
2236
2237 /* Wait until the DSP has accepted the settings */
2238 do
2239 {
2240 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1);
2241 } while(val & 1);
2242}
2243
2244static void resume_recording(void)
2245{
2246 unsigned long val;
2247
2248 /* Clear the pause bit */
2249 shadow_7f9 &= ~2;
2250 mas_writemem(MAS_BANK_D0, 0x7f9, &shadow_7f9, 1);
2251
2252 /* Tell the MAS that something has changed */
2253 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1, 1);
2254 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", shadow_7f1);
2255
2256 /* Wait until the DSP has accepted the settings */
2257 do
2258 {
2259 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1);
2260 } while(val & 1);
2261}
2262
2221static void stop_recording(void) 2263static void stop_recording(void)
2222{ 2264{
2223 unsigned long val; 2265 unsigned long val;
2224 2266
2267 /* Let it finish the last frame */
2268 pause_recording();
2269 sleep(HZ/5);
2270
2225 demand_irq_enable(false); 2271 demand_irq_enable(false);
2226 2272
2227 is_recording = false; 2273 is_recording = false;
@@ -2231,18 +2277,17 @@ static void stop_recording(void)
2231 mas_readmem(MAS_BANK_D0, 0xfd0, &num_recorded_frames, 1); 2277 mas_readmem(MAS_BANK_D0, 0xfd0, &num_recorded_frames, 1);
2232 2278
2233 /* Start monitoring */ 2279 /* Start monitoring */
2234 mas_readmem(MAS_BANK_D0, 0x7f1, &val, 1); 2280 shadow_7f1 |= (1 << 10);
2235 val |= (1 << 10) | 1;
2236 mas_writemem(MAS_BANK_D0, 0x7f1, &val, 1); 2281 mas_writemem(MAS_BANK_D0, 0x7f1, &val, 1);
2237 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", val); 2282 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", shadow_7f1);
2238 2283
2239 /* Wait until the DSP has accepted the settings */ 2284 /* Wait until the DSP has accepted the settings */
2240 do 2285 do
2241 { 2286 {
2242 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1); 2287 mas_readmem(MAS_BANK_D0, 0x7f1, &val,1);
2243 } while(val & 1); 2288 } while(val & 1);
2244 2289
2245 drain_dma_buffer(); 2290 resume_recording();
2246} 2291}
2247 2292
2248void mpeg_set_recording_options(int frequency, int quality, 2293void mpeg_set_recording_options(int frequency, int quality,
@@ -2250,40 +2295,37 @@ void mpeg_set_recording_options(int frequency, int quality,
2250 bool editable, int prerecord_time) 2295 bool editable, int prerecord_time)
2251{ 2296{
2252 bool is_mpeg1; 2297 bool is_mpeg1;
2253 unsigned long val;
2254 2298
2255 is_mpeg1 = (frequency < 3)?true:false; 2299 is_mpeg1 = (frequency < 3)?true:false;
2256 2300
2257 rec_version_index = is_mpeg1?3:2; 2301 rec_version_index = is_mpeg1?3:2;
2258 rec_frequency_index = frequency % 3; 2302 rec_frequency_index = frequency % 3;
2259 2303
2260 val = (quality << 17) | 2304 shadow_7f0 = (quality << 17) |
2261 (rec_frequency_index << 10) | 2305 (rec_frequency_index << 10) |
2262 ((is_mpeg1?1:0) << 9) | 2306 ((is_mpeg1?1:0) << 9) |
2263 (1 << 8) | /* CRC on */
2264 (((channel_mode * 2 + 1) & 3) << 6) | 2307 (((channel_mode * 2 + 1) & 3) << 6) |
2265 (1 << 5) /* MS-stereo */ | 2308 (1 << 5) /* MS-stereo */ |
2266 (1 << 2) /* Is an original */; 2309 (1 << 2) /* Is an original */;
2267 mas_writemem(MAS_BANK_D0, 0x7f0, &val,1); 2310 mas_writemem(MAS_BANK_D0, 0x7f0, &shadow_7f0,1);
2268 2311
2269 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f0, %x)\n", val); 2312 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f0, %x)\n", shadow_7f0);
2270 2313
2271 val = editable?4:0; 2314 shadow_7f9 = editable?4:0;
2272 mas_writemem(MAS_BANK_D0, 0x7f9, &val,1); 2315 mas_writemem(MAS_BANK_D0, 0x7f9, &shadow_7f9,1);
2273 2316
2274 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f9, %x)\n", val); 2317 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f9, %x)\n", shadow_7f9);
2275 2318
2276 val = (((source < 2)?1:2) << 8) | /* Input select */ 2319 shadow_7f1 = ((1 << 10) | /* Monitoring ON */
2320 ((source < 2)?1:2) << 8) | /* Input select */
2277 (1 << 5) | /* SDO strobe invert */ 2321 (1 << 5) | /* SDO strobe invert */
2278 ((is_mpeg1?0:1) << 3) | 2322 ((is_mpeg1?0:1) << 3) |
2279 (1 << 2) | /* Inverted SIBC clock signal */ 2323 (1 << 2) | /* Inverted SIBC clock signal */
2280 1; /* Validate */ 2324 1; /* Validate */
2281 mas_writemem(MAS_BANK_D0, 0x7f1, &val,1); 2325 mas_writemem(MAS_BANK_D0, 0x7f1, &shadow_7f1,1);
2282 2326
2283 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", val); 2327 DEBUGF("mas_writemem(MAS_BANK_D0, 0x7f1, %x)\n", shadow_7f1);
2284 2328
2285 drain_dma_buffer();
2286
2287 if(source == 0) /* Mic */ 2329 if(source == 0) /* Mic */
2288 { 2330 {
2289 /* Copy left channel to right (mono mode) */ 2331 /* Copy left channel to right (mono mode) */