summaryrefslogtreecommitdiff
path: root/apps/mpeg.c
diff options
context:
space:
mode:
Diffstat (limited to 'apps/mpeg.c')
-rw-r--r--apps/mpeg.c60
1 files changed, 49 insertions, 11 deletions
diff --git a/apps/mpeg.c b/apps/mpeg.c
index c0b2ae0c0e..d3e0e5c137 100644
--- a/apps/mpeg.c
+++ b/apps/mpeg.c
@@ -177,6 +177,13 @@ static long low_watermark; /* Dynamic low watermark level */
177static long low_watermark_margin = 0; /* Extra time in seconds for watermark */ 177static long low_watermark_margin = 0; /* Extra time in seconds for watermark */
178static long lowest_watermark_level; /* Debug value to observe the buffer 178static long lowest_watermark_level; /* Debug value to observe the buffer
179 usage */ 179 usage */
180
181struct audio_resume_info
182{
183 unsigned long elapsed;
184 unsigned long offset;
185};
186
180#if CONFIG_CODEC == MAS3587F 187#if CONFIG_CODEC == MAS3587F
181static char recording_filename[MAX_PATH]; /* argument to thread */ 188static char recording_filename[MAX_PATH]; /* argument to thread */
182static char delayed_filename[MAX_PATH]; /* internal copy of above */ 189static char delayed_filename[MAX_PATH]; /* internal copy of above */
@@ -430,10 +437,9 @@ static void set_elapsed(struct mp3entry* id3)
430 id3->elapsed = id3->offset / (id3->bitrate / 8); 437 id3->elapsed = id3->offset / (id3->bitrate / 8);
431} 438}
432 439
433int audio_get_file_pos(void) 440static int audio_get_file_pos_int(struct mp3entry *id3)
434{ 441{
435 int pos = -1; 442 int pos = -1;
436 struct mp3entry *id3 = audio_current_track();
437 443
438 if (id3->vbr) 444 if (id3->vbr)
439 { 445 {
@@ -490,6 +496,12 @@ int audio_get_file_pos(void)
490 return pos; 496 return pos;
491} 497}
492 498
499int audio_get_file_pos(void)
500{
501 struct mp3entry *id3 = audio_current_track();
502 return id3 ? audio_get_file_pos_int(id3) : 0;
503}
504
493unsigned long mpeg_get_last_header(void) 505unsigned long mpeg_get_last_header(void)
494{ 506{
495#ifdef SIMULATOR 507#ifdef SIMULATOR
@@ -545,7 +557,13 @@ static int shrink_callback(int handle, unsigned hints, void* start, size_t old_s
545 } 557 }
546 /* TODO: Do it without stopping playback, if possible */ 558 /* TODO: Do it without stopping playback, if possible */
547 bool playing = (audio_status() & AUDIO_STATUS_PLAY) == AUDIO_STATUS_PLAY; 559 bool playing = (audio_status() & AUDIO_STATUS_PLAY) == AUDIO_STATUS_PLAY;
548 long offset = audio_current_track()->offset; 560 struct mp3entry *id3 = audio_current_track();
561 unsigned long elapsed = 0, offset = 0;
562 if (id3)
563 {
564 elapsed = id3->elapsed;
565 offset = id3->offset;
566 }
549 /* don't call audio_hard_stop() as it frees this handle */ 567 /* don't call audio_hard_stop() as it frees this handle */
550 if (thread_self() == audio_thread_id) 568 if (thread_self() == audio_thread_id)
551 { /* inline case MPEG_STOP (audio_stop()) response 569 { /* inline case MPEG_STOP (audio_stop()) response
@@ -574,7 +592,7 @@ static int shrink_callback(int handle, unsigned hints, void* start, size_t old_s
574 } 592 }
575 if (playing) 593 if (playing)
576 { /* safe to call even from the audio thread (due to queue_post()) */ 594 { /* safe to call even from the audio thread (due to queue_post()) */
577 audio_play(offset); 595 audio_play(elapsed, offset);
578 } 596 }
579 597
580 return BUFLIB_CB_OK; 598 return BUFLIB_CB_OK;
@@ -1274,7 +1292,7 @@ static void mpeg_thread(void)
1274 int unplayed_space_left; 1292 int unplayed_space_left;
1275 int amount_to_read; 1293 int amount_to_read;
1276 int t1, t2; 1294 int t1, t2;
1277 int start_offset; 1295 unsigned long start_elapsed, start_offset;
1278#if CONFIG_CODEC == MAS3587F 1296#if CONFIG_CODEC == MAS3587F
1279 int amount_to_save; 1297 int amount_to_save;
1280 int save_endpos = 0; 1298 int save_endpos = 0;
@@ -1337,9 +1355,16 @@ static void mpeg_thread(void)
1337 break; 1355 break;
1338 } 1356 }
1339 1357
1340 start_offset = (int)ev.data; 1358 start_elapsed = ((struct audio_resume_info *)ev.data)->elapsed;
1359 start_offset = ((struct audio_resume_info *)ev.data)->offset;
1341 1360
1342 /* mid-song resume? */ 1361 /* mid-song resume? */
1362 if (!start_offset && start_elapsed) {
1363 struct mp3entry *id3 = &get_trackdata(0)->id3;
1364 id3->elapsed = start_elapsed;
1365 start_offset = audio_get_file_pos_int(id3);
1366 }
1367
1343 if (start_offset) { 1368 if (start_offset) {
1344 struct mp3entry* id3 = &get_trackdata(0)->id3; 1369 struct mp3entry* id3 = &get_trackdata(0)->id3;
1345 lseek(mpeg_file, start_offset, SEEK_SET); 1370 lseek(mpeg_file, start_offset, SEEK_SET);
@@ -1506,7 +1531,7 @@ static void mpeg_thread(void)
1506 1531
1507 id3->elapsed = newtime; 1532 id3->elapsed = newtime;
1508 1533
1509 newpos = audio_get_file_pos(); 1534 newpos = audio_get_file_pos_int(id3);
1510 if(newpos < 0) 1535 if(newpos < 0)
1511 { 1536 {
1512 id3->elapsed = oldtime; 1537 id3->elapsed = oldtime;
@@ -2765,7 +2790,7 @@ static void audio_reset_buffer(void)
2765 audio_reset_buffer_noalloc(core_get_data(audiobuf_handle), bufsize); 2790 audio_reset_buffer_noalloc(core_get_data(audiobuf_handle), bufsize);
2766} 2791}
2767 2792
2768void audio_play(long offset) 2793void audio_play(unsigned long elapsed, unsigned long offset)
2769{ 2794{
2770 audio_reset_buffer(); 2795 audio_reset_buffer();
2771#ifdef SIMULATOR 2796#ifdef SIMULATOR
@@ -2789,15 +2814,28 @@ void audio_play(long offset)
2789 real_mpeg_play(trackname); 2814 real_mpeg_play(trackname);
2790#endif 2815#endif
2791 playlist_next(steps); 2816 playlist_next(steps);
2792 taginfo.offset = offset; 2817 if (!offset && elapsed)
2793 set_elapsed(&taginfo); 2818 {
2819 /* has an elapsed time but no offset; elapsed may take
2820 precedence in this case */
2821 taginfo.elapsed = elapsed;
2822 taginfo.offset = audio_get_file_pos_int(&taginfo);
2823 }
2824 else
2825 {
2826 taginfo.offset = offset;
2827 set_elapsed(&taginfo);
2828 }
2794 is_playing = true; 2829 is_playing = true;
2795 playing = true; 2830 playing = true;
2796 break; 2831 break;
2797 } while(1); 2832 } while(1);
2798#else /* !SIMULATOR */ 2833#else /* !SIMULATOR */
2834 static struct audio_resume_info resume;
2799 is_playing = true; 2835 is_playing = true;
2800 queue_post(&mpeg_queue, MPEG_PLAY, offset); 2836 resume.elapsed = elapsed;
2837 resume.offset = offset;
2838 queue_post(&mpeg_queue, MPEG_PLAY, (intptr_t)&resume);
2801#endif /* !SIMULATOR */ 2839#endif /* !SIMULATOR */
2802 2840
2803 mpeg_errno = 0; 2841 mpeg_errno = 0;