summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWilliam Wilgus <wilgus.william@gmail.com>2022-11-25 09:49:12 -0500
committerWilliam Wilgus <wilgus.william@gmail.com>2022-11-25 23:39:47 -0500
commit88ecaf2b8cbee654d66ef3f559679d8d1c390949 (patch)
tree9cc3493916229ca4783a7a86bce5771e5af7b206
parent853d70e938f6b32dc965e92f9d34905fbe7ff0a8 (diff)
downloadrockbox-88ecaf2b8cbee654d66ef3f559679d8d1c390949.tar.gz
rockbox-88ecaf2b8cbee654d66ef3f559679d8d1c390949.zip
bookmark.c remove static bookmark buffer
Change-Id: Ie23760890e76177acf3700fb8eb73ca7f81f112e
-rw-r--r--apps/bookmark.c379
1 files changed, 210 insertions, 169 deletions
diff --git a/apps/bookmark.c b/apps/bookmark.c
index 16bfe1cd2b..f3c712240a 100644
--- a/apps/bookmark.c
+++ b/apps/bookmark.c
@@ -43,6 +43,9 @@
43#include "file.h" 43#include "file.h"
44#include "pathfuncs.h" 44#include "pathfuncs.h"
45 45
46/*#define LOGF_ENABLE*/
47#include "logf.h"
48
46#define MAX_BOOKMARKS 10 49#define MAX_BOOKMARKS 10
47#define MAX_BOOKMARK_SIZE 350 50#define MAX_BOOKMARK_SIZE 350
48#define RECENT_BOOKMARK_FILE ROCKBOX_DIR "/most-recent.bmark" 51#define RECENT_BOOKMARK_FILE ROCKBOX_DIR "/most-recent.bmark"
@@ -66,7 +69,8 @@ struct bookmark_list
66#define BM_SPEED 0x02 69#define BM_SPEED 0x02
67 70
68/* bookmark values */ 71/* bookmark values */
69static struct { 72static struct resume_info{
73 const struct mp3entry *id3;
70 int resume_index; 74 int resume_index;
71 unsigned long resume_offset; 75 unsigned long resume_offset;
72 int resume_seed; 76 int resume_seed;
@@ -76,15 +80,12 @@ static struct {
76 /* optional values */ 80 /* optional values */
77 int pitch; 81 int pitch;
78 int speed; 82 int speed;
79} bm; 83} resume_info;
80 84
81/* Temp buffer used for reading and filename creation */ 85/* Temp buffer used for reading, create_bookmark and filename creation */
82#define TEMP_BUF_SIZE (MAX(MAX_BOOKMARK_SIZE, MAX_PATH + 1)) 86#define TEMP_BUF_SIZE (MAX(MAX_BOOKMARK_SIZE, MAX_PATH + 1))
83static char global_temp_buffer[TEMP_BUF_SIZE]; 87static char global_temp_buffer[TEMP_BUF_SIZE];
84 88
85/* Bookmark created by create_bookmark*/
86static char global_bookmark[MAX_BOOKMARK_SIZE];
87
88static const char* skip_token(const char* s) 89static const char* skip_token(const char* s)
89{ 90{
90 while (*s && *s != ';') 91 while (*s && *s != ';')
@@ -116,10 +117,10 @@ static const char* long_token(const char* s, long* dest)
116/* Get the name of the playlist and the name of the track from a bookmark. */ 117/* Get the name of the playlist and the name of the track from a bookmark. */
117/* Returns true iff both were extracted. */ 118/* Returns true iff both were extracted. */
118/*-------------------------------------------------------------------------*/ 119/*-------------------------------------------------------------------------*/
119static bool get_playlist_and_track(const char *bookmark, 120static bool bookmark_get_playlist_and_track(const char *bookmark,
120 char **pl_start, 121 char **pl_start,
121 char **pl_end, 122 char **pl_end,
122 char **track) 123 char **track)
123{ 124{
124 *pl_start = strchr(bookmark,'/'); 125 *pl_start = strchr(bookmark,'/');
125 if (!(*pl_start)) 126 if (!(*pl_start))
@@ -158,20 +159,20 @@ static bool parse_bookmark(char *filenamebuf,
158 } 159 }
159 160
160 /* extract all original bookmark tokens */ 161 /* extract all original bookmark tokens */
161 GET_INT_TOKEN(bm.resume_index); 162 GET_INT_TOKEN(resume_info.resume_index);
162 GET_LONG_TOKEN(bm.resume_offset); 163 GET_LONG_TOKEN(resume_info.resume_offset);
163 GET_INT_TOKEN(bm.resume_seed); 164 GET_INT_TOKEN(resume_info.resume_seed);
164 if (!new_format) /* skip deprecated token */ 165 if (!new_format) /* skip deprecated token */
165 s = skip_token(s); 166 s = skip_token(s);
166 GET_LONG_TOKEN(bm.resume_time); 167 GET_LONG_TOKEN(resume_info.resume_time);
167 GET_INT_TOKEN(bm.repeat_mode); 168 GET_INT_TOKEN(resume_info.repeat_mode);
168 GET_BOOL_TOKEN(bm.shuffle); 169 GET_BOOL_TOKEN(resume_info.shuffle);
169 170
170 /* extract all optional bookmark tokens */ 171 /* extract all optional bookmark tokens */
171 if (opt_flags & BM_PITCH) 172 if (opt_flags & BM_PITCH)
172 GET_INT_TOKEN(bm.pitch); 173 GET_INT_TOKEN(resume_info.pitch);
173 if (opt_flags & BM_SPEED) 174 if (opt_flags & BM_SPEED)
174 GET_INT_TOKEN(bm.speed); 175 GET_INT_TOKEN(resume_info.speed);
175 176
176 if (*s == 0) 177 if (*s == 0)
177 { 178 {
@@ -217,7 +218,15 @@ static int open_temp_bookmark(char *buf,
217 const char* filename) 218 const char* filename)
218{ 219{
219 /* Opening up a temp bookmark file */ 220 /* Opening up a temp bookmark file */
220 return open_pathfmt(buf, bufsz, oflags, "%s.tmp", filename); 221 int fd = open_pathfmt(buf, bufsz, oflags, "/%s.tmp", filename);
222#ifdef LOGF_ENABLE
223 if (oflags & O_PATH)
224 logf("tempfile path %s", buf);
225 else
226 logf("opening tempfile %s", buf);
227#endif
228 return fd;
229
221} 230}
222 231
223/* ----------------------------------------------------------------------- */ 232/* ----------------------------------------------------------------------- */
@@ -228,30 +237,31 @@ static bool add_bookmark(const char* bookmark_file_name,
228 const char* bookmark, 237 const char* bookmark,
229 bool most_recent) 238 bool most_recent)
230{ 239{
231 int temp_bookmark_file = 0; 240 char fnamebuf[MAX_PATH];
232 int bookmark_file = 0; 241 int temp_bookmark_file = 0;
233 int bookmark_count = 0; 242 int bookmark_file = 0;
234 char *pl_start = NULL, *bm_pl_start; 243 int bookmark_count = 0;
235 char *pl_end = NULL, *bm_pl_end; 244 char *pl_start = NULL, *bm_pl_start;
236 int pl_len = 0, bm_pl_len; 245 char *pl_end = NULL, *bm_pl_end;
237 char *track = NULL, *bm_track; 246 int pl_len = 0, bm_pl_len;
238 bool comp_playlist = false; 247 char *track = NULL, *bm_track;
239 bool comp_track = false; 248 bool comp_playlist = false;
240 bool equal; 249 bool comp_track = false;
250 bool equal;
241 251
242 /* Opening up a temp bookmark file */ 252 /* Opening up a temp bookmark file */
243 temp_bookmark_file = open_temp_bookmark(global_temp_buffer, 253 temp_bookmark_file = open_temp_bookmark(fnamebuf,
244 sizeof(global_temp_buffer), 254 sizeof(fnamebuf),
245 O_WRONLY | O_CREAT | O_TRUNC, 255 O_WRONLY | O_CREAT | O_TRUNC,
246 bookmark_file_name); 256 bookmark_file_name);
247 257
248 if (temp_bookmark_file < 0) 258 if (temp_bookmark_file < 0 || !bookmark)
249 return false; /* can't open the temp file */ 259 return false; /* can't open the temp file or no bookmark */
250 260
251 if (most_recent && ((global_settings.usemrb == BOOKMARK_ONE_PER_PLAYLIST) 261 if (most_recent && ((global_settings.usemrb == BOOKMARK_ONE_PER_PLAYLIST)
252 || (global_settings.usemrb == BOOKMARK_ONE_PER_TRACK))) 262 || (global_settings.usemrb == BOOKMARK_ONE_PER_TRACK)))
253 { 263 {
254 if (get_playlist_and_track(bookmark, &pl_start, &pl_end, &track)) 264 if (bookmark_get_playlist_and_track(bookmark, &pl_start, &pl_end, &track))
255 { 265 {
256 comp_playlist = true; 266 comp_playlist = true;
257 pl_len = pl_end - pl_start; 267 pl_len = pl_end - pl_start;
@@ -259,13 +269,14 @@ static bool add_bookmark(const char* bookmark_file_name,
259 comp_track = true; 269 comp_track = true;
260 } 270 }
261 } 271 }
262 272 logf("adding bookmark to %s [%s]", fnamebuf, bookmark);
263 /* Writing the new bookmark to the begining of the temp file */ 273 /* Writing the new bookmark to the begining of the temp file */
264 write(temp_bookmark_file, bookmark, strlen(bookmark)); 274 write(temp_bookmark_file, bookmark, strlen(bookmark));
265 write(temp_bookmark_file, "\n", 1); 275 write(temp_bookmark_file, "\n", 1);
266 bookmark_count++; 276 bookmark_count++;
267 277
268 /* Reading in the previous bookmarks and writing them to the temp file */ 278 /* Reading in the previous bookmarks and writing them to the temp file */
279 logf("opening old bookmark %s", bookmark_file_name);
269 bookmark_file = open(bookmark_file_name, O_RDONLY); 280 bookmark_file = open(bookmark_file_name, O_RDONLY);
270 if (bookmark_file >= 0) 281 if (bookmark_file >= 0)
271 { 282 {
@@ -283,8 +294,8 @@ static bool add_bookmark(const char* bookmark_file_name,
283 equal = false; 294 equal = false;
284 if (comp_playlist) 295 if (comp_playlist)
285 { 296 {
286 if (get_playlist_and_track(global_temp_buffer, &bm_pl_start, 297 if (bookmark_get_playlist_and_track(global_temp_buffer,
287 &bm_pl_end, &bm_track)) 298 &bm_pl_start, &bm_pl_end, &bm_track))
288 { 299 {
289 bm_pl_len = bm_pl_end - bm_pl_start; 300 bm_pl_len = bm_pl_end - bm_pl_start;
290 equal = (pl_len == bm_pl_len) && 301 equal = (pl_len == bm_pl_len) &&
@@ -297,6 +308,7 @@ static bool add_bookmark(const char* bookmark_file_name,
297 if (!equal) 308 if (!equal)
298 { 309 {
299 bookmark_count++; 310 bookmark_count++;
311 /*logf("copying old bookmark [%s]", global_temp_buffer);*/
300 write(temp_bookmark_file, global_temp_buffer, 312 write(temp_bookmark_file, global_temp_buffer,
301 strlen(global_temp_buffer)); 313 strlen(global_temp_buffer));
302 write(temp_bookmark_file, "\n", 1); 314 write(temp_bookmark_file, "\n", 1);
@@ -307,12 +319,12 @@ static bool add_bookmark(const char* bookmark_file_name,
307 close(temp_bookmark_file); 319 close(temp_bookmark_file);
308 320
309 /* only retrieve the path*/ 321 /* only retrieve the path*/
310 open_temp_bookmark(global_temp_buffer, 322 open_temp_bookmark(fnamebuf,
311 sizeof(global_temp_buffer), 323 sizeof(fnamebuf),
312 O_PATH, 324 O_PATH,
313 bookmark_file_name); 325 bookmark_file_name);
314 remove(bookmark_file_name); 326 remove(bookmark_file_name);
315 rename(global_temp_buffer, bookmark_file_name); 327 rename(fnamebuf, bookmark_file_name);
316 328
317 return true; 329 return true;
318} 330}
@@ -327,7 +339,8 @@ static bool add_bookmark(const char* bookmark_file_name,
327/* ----------------------------------------------------------------------- */ 339/* ----------------------------------------------------------------------- */
328static bool generate_bookmark_file_name(char *filenamebuf, 340static bool generate_bookmark_file_name(char *filenamebuf,
329 size_t filenamebufsz, 341 size_t filenamebufsz,
330 const char *bmarknamein) 342 const char *bmarknamein,
343 size_t bmarknamelen)
331{ 344{
332 /* if this is a root dir MP3, rename the bookmark file root_dir.bmark */ 345 /* if this is a root dir MP3, rename the bookmark file root_dir.bmark */
333 /* otherwise, name it based on the bmarknamein variable */ 346 /* otherwise, name it based on the bmarknamein variable */
@@ -335,35 +348,129 @@ static bool generate_bookmark_file_name(char *filenamebuf,
335 strmemccpy(filenamebuf, "/root_dir.bmark", filenamebufsz); 348 strmemccpy(filenamebuf, "/root_dir.bmark", filenamebufsz);
336 else 349 else
337 { 350 {
351 size_t len = strlcpy(filenamebuf, bmarknamein,
352 MIN(filenamebufsz, bmarknamelen));
353 if(len >= filenamebufsz)
354 return false;
338#ifdef HAVE_MULTIVOLUME 355#ifdef HAVE_MULTIVOLUME
339 /* The "root" of an extra volume need special handling too. */ 356 /* The "root" of an extra volume need special handling too. */
340 const char *filename; 357 const char *filename;
341 path_strip_volume(bmarknamein, &filename, true); 358 path_strip_volume(filenamebuf, &filename, true);
342 bool volume_root = *filename == '\0'; 359 bool volume_root = *filename == '\0';
343#endif 360#endif
344 size_t len = strlcpy(filenamebuf, bmarknamein, filenamebufsz);
345 if(len >= filenamebufsz)
346 return false;
347
348 if(filenamebuf[len-1] == '/') { 361 if(filenamebuf[len-1] == '/') {
349 filenamebuf[len-1] = '\0'; 362 filenamebuf[len-1] = '\0';
350 len--; 363 len--;
351 } 364 }
352 365
366 const char *name = ".bmark";
353#ifdef HAVE_MULTIVOLUME 367#ifdef HAVE_MULTIVOLUME
354 if (volume_root) 368 if (volume_root)
355 len = strlcat(filenamebuf, "/volume_dir.bmark", filenamebufsz); 369 name = "/volume_dir.bmark";
356 else
357#endif 370#endif
358 len = strlcat(filenamebuf, ".bmark", filenamebufsz); 371 len = strlcat(filenamebuf, name, filenamebufsz);
359 372
360 if(len >= filenamebufsz) 373 if(len >= filenamebufsz)
361 return false; 374 return false;
362 } 375 }
363 376 logf ("generated name '%s' from '%.*s'",
377 filenamebuf, (int)bmarknamelen, bmarknamein);
364 return true; 378 return true;
365} 379}
366 380
381/* GCC 7 and up complain about the snprintf in create_bookmark() when
382 compiled with -D_FORTIFY_SOURCE or -Wformat-truncation
383 This is a false positive, so disable it here only */
384/* SHOULD NO LONGER BE NEEDED --Bilgus 11-2022 */
385#if 0 /* __GNUC__ >= 7 */
386#pragma GCC diagnostic push
387#pragma GCC diagnostic ignored "-Wformat-truncation"
388#endif
389/* ----------------------------------------------------------------------- */
390/* This function takes the system resume data and formats it into a valid */
391/* bookmark. */
392/* playlist name and name len are passed back through the name/namelen */
393/* Return is not NULL on successful bookmark format. */
394/* ----------------------------------------------------------------------- */
395static char* create_bookmark(char **name, size_t *namelen)
396{
397 const char *file;
398 char *buf = global_temp_buffer;
399 size_t bufsz = sizeof(global_temp_buffer);
400
401 if(!resume_info.id3)
402 return NULL;
403
404 size_t bmsz = snprintf(buf, bufsz,
405 /* new optional bookmark token descriptors should
406 be inserted just after ';"' in this line... */
407#if defined(HAVE_PITCHCONTROL)
408 ">%d;%d;%ld;%d;%ld;%d;%d;%ld;%ld;",
409#else
410 ">%d;%d;%ld;%d;%ld;%d;%d;",
411#endif
412 /* ... their flags should go here ... */
413#if defined(HAVE_PITCHCONTROL)
414 BM_PITCH | BM_SPEED,
415#else
416 0,
417#endif
418 resume_info.resume_index,
419 resume_info.id3->offset,
420 resume_info.resume_seed,
421 resume_info.id3->elapsed,
422 resume_info.repeat_mode,
423 resume_info.shuffle,
424 /* ...and their values should go here */
425#if defined(HAVE_PITCHCONTROL)
426 (long)resume_info.pitch,
427 (long)resume_info.speed
428#endif
429 ); /*sprintf*/
430/* mandatory tokens */
431 if (bmsz >= bufsz) /* include NULL*/
432 return NULL;
433 buf += bmsz;
434 bufsz -= bmsz;
435
436 /* create the bookmark */
437 playlist_get_name(NULL, buf, bmsz);
438 bmsz = strlen(buf);
439
440 if (bmsz == 0 || (bmsz + 1) >= bufsz) /* include the separator & NULL*/
441 return NULL;
442
443 *name = buf; /* return the playlist name through the *pointer */
444 *namelen = bmsz; /* return the name length through the pointer */
445
446 /* Get the currently playing file minus the path */
447 /* This is used when displaying the available bookmarks */
448 file = strrchr(resume_info.id3->path,'/');
449 if(NULL == file)
450 return NULL;
451
452 if (buf[bmsz - 1] != '/')
453 file = resume_info.id3->path;
454 else file++;
455
456 buf += bmsz;
457 bufsz -= (bmsz + 1);
458 buf[0] = ';';
459 buf[1] = '\0';
460
461 strlcat(buf, file, bufsz);
462
463 logf("%s [%s]", __func__, global_temp_buffer);
464 /* checking to see if the bookmark is valid */
465 if (parse_bookmark(NULL, 0, global_temp_buffer, false))
466 return global_temp_buffer;
467 else
468 return NULL;
469}
470#if 0/* __GNUC__ >= 7*/
471#pragma GCC diagnostic pop /* -Wformat-truncation */
472#endif
473
367/* ----------------------------------------------------------------------- */ 474/* ----------------------------------------------------------------------- */
368/* This function takes the current current resume information and writes */ 475/* This function takes the current current resume information and writes */
369/* that to the beginning of the bookmark file. */ 476/* that to the beginning of the bookmark file. */
@@ -375,31 +482,43 @@ static bool generate_bookmark_file_name(char *filenamebuf,
375/* possible that a bookmark is successfully added to the most recent */ 482/* possible that a bookmark is successfully added to the most recent */
376/* bookmark list but fails to be added to the bookmark file or vice versa. */ 483/* bookmark list but fails to be added to the bookmark file or vice versa. */
377/* ------------------------------------------------------------------------*/ 484/* ------------------------------------------------------------------------*/
378static bool write_bookmark(bool create_bookmark_file, const char *bookmark) 485static bool write_bookmark(bool create_bookmark_file)
379{ 486{
380 char bm_filename[MAX_PATH]; 487 char bm_filename[MAX_PATH];
381 bool ret=true; 488 bool ret=true;
382 489
383 if (!bookmark) 490 char *name = NULL;
384 { 491 size_t namelen = 0;
385 ret = false; /* something didn't happen correctly, do nothing */ 492 char* bm;
386 } 493
387 else 494 if (bookmark_is_bookmarkable_state())
388 { 495 {
496 /* Get some basic resume information */
497 playlist_get_resume_info(&(resume_info.resume_index));
498 resume_info.resume_seed = playlist_get_seed(NULL);
499 resume_info.id3 = audio_current_track();
500 resume_info.repeat_mode = global_settings.repeat_mode;
501 resume_info.shuffle = global_settings.playlist_shuffle;
502#if defined(HAVE_PITCHCONTROL)
503 resume_info.pitch = sound_get_pitch();
504 resume_info.speed = dsp_get_timestretch();
505#endif
506 /* writing the most recent bookmark */
389 if (global_settings.usemrb) 507 if (global_settings.usemrb)
390 ret = add_bookmark(RECENT_BOOKMARK_FILE, bookmark, true); 508 {
391 509 /* since we use the same buffer bookmark needs created each time */
510 bm = create_bookmark(&name, &namelen);
511 ret = add_bookmark(RECENT_BOOKMARK_FILE, bm, true);
512 }
392 513
393 /* writing the bookmark */ 514 /* writing the directory bookmark */
394 if (create_bookmark_file) 515 if (create_bookmark_file)
395 { 516 {
396 char* name = playlist_get_name(NULL, global_temp_buffer, 517 bm = create_bookmark(&name, &namelen);
397 sizeof(global_temp_buffer));
398
399 if (generate_bookmark_file_name(bm_filename, 518 if (generate_bookmark_file_name(bm_filename,
400 sizeof(bm_filename), name)) 519 sizeof(bm_filename), name, namelen))
401 { 520 {
402 ret = ret & add_bookmark(bm_filename, bookmark, false); 521 ret &= add_bookmark(bm_filename, bm, false);
403 } 522 }
404 else 523 else
405 { 524 {
@@ -407,6 +526,8 @@ static bool write_bookmark(bool create_bookmark_file, const char *bookmark)
407 } 526 }
408 } 527 }
409 } 528 }
529 else
530 ret = false;
410 531
411 splash(HZ, ret ? ID2P(LANG_BOOKMARK_CREATE_SUCCESS) 532 splash(HZ, ret ? ID2P(LANG_BOOKMARK_CREATE_SUCCESS)
412 : ID2P(LANG_BOOKMARK_CREATE_FAILURE)); 533 : ID2P(LANG_BOOKMARK_CREATE_FAILURE));
@@ -585,9 +706,10 @@ static const char* get_bookmark_info(int list_index,
585 { 706 {
586 char time_buf[32]; 707 char time_buf[32];
587 708
588 format_time(time_buf, sizeof(time_buf), bm.resume_time); 709 format_time(time_buf, sizeof(time_buf), resume_info.resume_time);
589 snprintf(buffer, buffer_len, "%s, %d%s", time_buf, bm.resume_index + 1, 710 snprintf(buffer, buffer_len, "%s, %d%s", time_buf,
590 bm.shuffle ? (char*) str(LANG_BOOKMARK_SHUFFLE) : ""); 711 resume_info.resume_index + 1,
712 resume_info.shuffle ? (char*) str(LANG_BOOKMARK_SHUFFLE) : "");
591 return buffer; 713 return buffer;
592 } 714 }
593} 715}
@@ -623,13 +745,13 @@ static void say_bookmark(const char* bookmark,
623 TALK_IDARRAY(LANG_PLAYLIST), true); 745 TALK_IDARRAY(LANG_PLAYLIST), true);
624 } 746 }
625 747
626 if(bm.shuffle) 748 if(resume_info.shuffle)
627 talk_id(LANG_SHUFFLE, true); 749 talk_id(LANG_SHUFFLE, true);
628 750
629 talk_id(VOICE_BOOKMARK_SELECT_INDEX_TEXT, true); 751 talk_id(VOICE_BOOKMARK_SELECT_INDEX_TEXT, true);
630 talk_number(bm.resume_index + 1, true); 752 talk_number(resume_info.resume_index + 1, true);
631 talk_id(LANG_TIME, true); 753 talk_id(LANG_TIME, true);
632 talk_value(bm.resume_time / 1000, UNIT_TIME, true); 754 talk_value(resume_info.resume_time / 1000, UNIT_TIME, true);
633 755
634 /* Track filename */ 756 /* Track filename */
635 if(!is_dir) 757 if(!is_dir)
@@ -865,106 +987,28 @@ static bool play_bookmark(const char* bookmark)
865 char fnamebuf[MAX_PATH]; 987 char fnamebuf[MAX_PATH];
866#if defined(HAVE_PITCHCONTROL) 988#if defined(HAVE_PITCHCONTROL)
867 /* preset pitch and speed to 100% in case bookmark doesn't have info */ 989 /* preset pitch and speed to 100% in case bookmark doesn't have info */
868 bm.pitch = sound_get_pitch(); 990 resume_info.pitch = sound_get_pitch();
869 bm.speed = dsp_get_timestretch(); 991 resume_info.speed = dsp_get_timestretch();
870#endif 992#endif
871 993
872 if (parse_bookmark(fnamebuf, sizeof(fnamebuf), bookmark, true)) 994 if (parse_bookmark(fnamebuf, sizeof(fnamebuf), bookmark, true))
873 { 995 {
874 global_settings.repeat_mode = bm.repeat_mode; 996 global_settings.repeat_mode = resume_info.repeat_mode;
875 global_settings.playlist_shuffle = bm.shuffle; 997 global_settings.playlist_shuffle = resume_info.shuffle;
876#if defined(HAVE_PITCHCONTROL) 998#if defined(HAVE_PITCHCONTROL)
877 sound_set_pitch(bm.pitch); 999 sound_set_pitch(resume_info.pitch);
878 dsp_set_timestretch(bm.speed); 1000 dsp_set_timestretch(resume_info.speed);
879#endif 1001#endif
880 if (!warn_on_pl_erase()) 1002 if (!warn_on_pl_erase())
881 return false; 1003 return false;
882 return bookmark_play(global_temp_buffer, bm.resume_index, 1004 return bookmark_play(global_temp_buffer, resume_info.resume_index,
883 bm.resume_time, bm.resume_offset, bm.resume_seed, fnamebuf); 1005 resume_info.resume_time, resume_info.resume_offset,
1006 resume_info.resume_seed, fnamebuf);
884 } 1007 }
885 1008
886 return false; 1009 return false;
887} 1010}
888 1011
889/* GCC 7 and up complain about the snprintf in create_bookmark() when
890 compiled with -D_FORTIFY_SOURCE or -Wformat-truncation
891 This is a false positive, so disable it here only */
892#if __GNUC__ >= 7
893#pragma GCC diagnostic push
894#pragma GCC diagnostic ignored "-Wformat-truncation"
895#endif
896/* ----------------------------------------------------------------------- */
897/* This function takes the system resume data and formats it into a valid */
898/* bookmark. */
899/* Returns not NULL on successful bookmark format. */
900/* ----------------------------------------------------------------------- */
901static char* create_bookmark(void)
902{
903 int resume_index = 0;
904 char *file;
905
906 if (!bookmark_is_bookmarkable_state())
907 return NULL; /* something didn't happen correctly, do nothing */
908
909 /* grab the currently playing track */
910 struct mp3entry *id3 = audio_current_track();
911 if(!id3)
912 return NULL;
913
914 /* Get some basic resume information */
915 /* queue_resume and queue_resume_index are not used and can be ignored.*/
916 playlist_get_resume_info(&resume_index);
917
918 /* Get the currently playing file minus the path */
919 /* This is used when displaying the available bookmarks */
920 file = strrchr(id3->path,'/');
921 if(NULL == file)
922 return NULL;
923
924 /* create the bookmark */
925 playlist_get_name(NULL, global_temp_buffer, sizeof(global_temp_buffer));
926 if (global_temp_buffer[strlen(global_temp_buffer) - 1] != '/')
927 file = id3->path;
928 else file++;
929 snprintf(global_bookmark, sizeof(global_bookmark),
930 /* new optional bookmark token descriptors should be inserted
931 just before the "%s;%s" in this line... */
932#if defined(HAVE_PITCHCONTROL)
933 ">%d;%d;%ld;%d;%ld;%d;%d;%ld;%ld;%s;%s",
934#else
935 ">%d;%d;%ld;%d;%ld;%d;%d;%s;%s",
936#endif
937 /* ... their flags should go here ... */
938#if defined(HAVE_PITCHCONTROL)
939 BM_PITCH | BM_SPEED,
940#else
941 0,
942#endif
943 resume_index,
944 id3->offset,
945 playlist_get_seed(NULL),
946 id3->elapsed,
947 global_settings.repeat_mode,
948 global_settings.playlist_shuffle,
949 /* ...and their values should go here */
950#if defined(HAVE_PITCHCONTROL)
951 (long)sound_get_pitch(),
952 (long)dsp_get_timestretch(),
953#endif
954 /* more mandatory tokens */
955 global_temp_buffer,
956 file);
957
958 /* checking to see if the bookmark is valid */
959 if (parse_bookmark(NULL, 0, global_bookmark, false))
960 return global_bookmark;
961 else
962 return NULL;
963}
964#if __GNUC__ >= 7
965#pragma GCC diagnostic pop /* -Wformat-truncation */
966#endif
967
968/*-------------------------------------------------------------------------*/ 1012/*-------------------------------------------------------------------------*/
969/* PUBLIC INTERFACE -------------------------------------------------------*/ 1013/* PUBLIC INTERFACE -------------------------------------------------------*/
970/*-------------------------------------------------------------------------*/ 1014/*-------------------------------------------------------------------------*/
@@ -976,9 +1020,8 @@ static char* create_bookmark(void)
976/* ----------------------------------------------------------------------- */ 1020/* ----------------------------------------------------------------------- */
977bool bookmark_create_menu(void) 1021bool bookmark_create_menu(void)
978{ 1022{
979 return write_bookmark(true, create_bookmark()); 1023 return write_bookmark(true);
980} 1024}
981
982/* ----------------------------------------------------------------------- */ 1025/* ----------------------------------------------------------------------- */
983/* This function acts as the load interface from the context menu. */ 1026/* This function acts as the load interface from the context menu. */
984/* This function determines the bookmark file name and then loads that file*/ 1027/* This function determines the bookmark file name and then loads that file*/
@@ -998,7 +1041,7 @@ int bookmark_load_menu(void)
998 1041
999 char* name = playlist_get_name(NULL, global_temp_buffer, 1042 char* name = playlist_get_name(NULL, global_temp_buffer,
1000 sizeof(global_temp_buffer)); 1043 sizeof(global_temp_buffer));
1001 if (generate_bookmark_file_name(bm_filename, sizeof(bm_filename), name)) 1044 if (generate_bookmark_file_name(bm_filename, sizeof(bm_filename), name, -1))
1002 { 1045 {
1003 ret = select_bookmark(bm_filename, false, &bookmark); 1046 ret = select_bookmark(bm_filename, false, &bookmark);
1004 if (bookmark != NULL) 1047 if (bookmark != NULL)
@@ -1039,7 +1082,6 @@ bool bookmark_mrb_load()
1039/* ----------------------------------------------------------------------- */ 1082/* ----------------------------------------------------------------------- */
1040bool bookmark_autobookmark(bool prompt_ok) 1083bool bookmark_autobookmark(bool prompt_ok)
1041{ 1084{
1042 char* bookmark;
1043 bool update; 1085 bool update;
1044 1086
1045 if (!bookmark_is_bookmarkable_state()) 1087 if (!bookmark_is_bookmarkable_state())
@@ -1047,21 +1089,20 @@ bool bookmark_autobookmark(bool prompt_ok)
1047 1089
1048 audio_pause(); /* first pause playback */ 1090 audio_pause(); /* first pause playback */
1049 update = (global_settings.autoupdatebookmark && bookmark_exists()); 1091 update = (global_settings.autoupdatebookmark && bookmark_exists());
1050 bookmark = create_bookmark();
1051 1092
1052 if (update) 1093 if (update)
1053 return write_bookmark(true, bookmark); 1094 return write_bookmark(true);
1054 1095
1055 switch (global_settings.autocreatebookmark) 1096 switch (global_settings.autocreatebookmark)
1056 { 1097 {
1057 case BOOKMARK_YES: 1098 case BOOKMARK_YES:
1058 return write_bookmark(true, bookmark); 1099 return write_bookmark(true);
1059 1100
1060 case BOOKMARK_NO: 1101 case BOOKMARK_NO:
1061 return false; 1102 return false;
1062 1103
1063 case BOOKMARK_RECENT_ONLY_YES: 1104 case BOOKMARK_RECENT_ONLY_YES:
1064 return write_bookmark(false, bookmark); 1105 return write_bookmark(false);
1065 } 1106 }
1066 const char *lines[]={ID2P(LANG_AUTO_BOOKMARK_QUERY)}; 1107 const char *lines[]={ID2P(LANG_AUTO_BOOKMARK_QUERY)};
1067 const struct text_message message={lines, 1}; 1108 const struct text_message message={lines, 1};
@@ -1069,9 +1110,9 @@ bool bookmark_autobookmark(bool prompt_ok)
1069 if(prompt_ok && gui_syncyesno_run(&message, NULL, NULL)==YESNO_YES) 1110 if(prompt_ok && gui_syncyesno_run(&message, NULL, NULL)==YESNO_YES)
1070 { 1111 {
1071 if (global_settings.autocreatebookmark == BOOKMARK_RECENT_ONLY_ASK) 1112 if (global_settings.autocreatebookmark == BOOKMARK_RECENT_ONLY_ASK)
1072 return write_bookmark(false, bookmark); 1113 return write_bookmark(false);
1073 else 1114 else
1074 return write_bookmark(true, bookmark); 1115 return write_bookmark(true);
1075 } 1116 }
1076 return false; 1117 return false;
1077} 1118}
@@ -1093,7 +1134,7 @@ int bookmark_autoload(const char* file)
1093 return BOOKMARK_DONT_RESUME; 1134 return BOOKMARK_DONT_RESUME;
1094 1135
1095 /*Checking to see if a bookmark file exists.*/ 1136 /*Checking to see if a bookmark file exists.*/
1096 if(!generate_bookmark_file_name(bm_filename, sizeof(bm_filename), file)) 1137 if(!generate_bookmark_file_name(bm_filename, sizeof(bm_filename), file, -1))
1097 { 1138 {
1098 return BOOKMARK_DONT_RESUME; 1139 return BOOKMARK_DONT_RESUME;
1099 } 1140 }
@@ -1182,7 +1223,7 @@ bool bookmark_exists(void)
1182 1223
1183 char* name = playlist_get_name(NULL, global_temp_buffer, 1224 char* name = playlist_get_name(NULL, global_temp_buffer,
1184 sizeof(global_temp_buffer)); 1225 sizeof(global_temp_buffer));
1185 if (generate_bookmark_file_name(bm_filename, sizeof(bm_filename), name)) 1226 if (generate_bookmark_file_name(bm_filename, sizeof(bm_filename), name, -1))
1186 { 1227 {
1187 exist = file_exists(bm_filename); 1228 exist = file_exists(bm_filename);
1188 } 1229 }