diff --git a/apps/main.c b/apps/main.c index 20cec9b..3f50f54 100644 --- a/apps/main.c +++ b/apps/main.c @@ -525,7 +525,7 @@ static void init(void) if (init_dircache(true) < 0) { #ifdef HAVE_TAGCACHE - remove(TAGCACHE_STATEFILE); + tagcache_remove_statefile(); #endif } diff --git a/apps/metadata.c b/apps/metadata.c index 0892fc6..821006e 100644 --- a/apps/metadata.c +++ b/apps/metadata.c @@ -27,15 +27,19 @@ #include "playback.h" #include "debug.h" #include "logf.h" +#ifndef __PCTOOL__ #include "cuesheet.h" +#endif #include "metadata.h" #include "metadata/metadata_parsers.h" #if CONFIG_CODEC == SWCODEC +#ifndef __PCTOOL__ /* For trailing tag stripping */ #include "buffering.h" +#endif #include "metadata/metadata_common.h" diff --git a/apps/metadata/asf.c b/apps/metadata/asf.c index 611cc2a..0c3b18c 100644 --- a/apps/metadata/asf.c +++ b/apps/metadata/asf.c @@ -32,7 +32,7 @@ #include "metadata_common.h" #include "metadata_parsers.h" #include "system.h" -#include +#include "codecs/libwma/asf.h" /* TODO: Just read the GUIDs into a 16-byte array, and use memcmp to compare */ struct guid_s { diff --git a/apps/metadata/metadata_common.c b/apps/metadata/metadata_common.c index 09f0f94..87b3e47 100644 --- a/apps/metadata/metadata_common.c +++ b/apps/metadata/metadata_common.c @@ -184,7 +184,7 @@ unsigned long get_itunes_int32(char* value, int count) { value = skip_whitespace(value); - while (*value && !isspace(*value)) + while (*value && !isspace((unsigned char)*value)) { value++; } diff --git a/apps/metadata/mp3.c b/apps/metadata/mp3.c index 86a6f63..f102ebb 100644 --- a/apps/metadata/mp3.c +++ b/apps/metadata/mp3.c @@ -926,7 +926,7 @@ static void setid3v2title(int fd, struct mp3entry *entry) tag[j] = utf8buf[j]; /* remove trailing spaces */ - while ( bytesread > 0 && isspace(tag[bytesread-1])) + while ( bytesread > 0 && isspace((unsigned char)tag[bytesread-1])) bytesread--; } diff --git a/apps/misc.c b/apps/misc.c index d7a64b3..481dc2a 100644 --- a/apps/misc.c +++ b/apps/misc.c @@ -27,9 +27,7 @@ #ifdef __PCTOOL__ #include #include -#ifdef WPSEDITOR -#include "string.h" -#endif +#include #else #include "sprintf.h" #include "appevents.h" @@ -765,26 +763,6 @@ char* strrsplt(char* str, int c) return s; } -/* Test file existence, using dircache of possible */ -bool file_exists(const char *file) -{ - int fd; - - if (!file || strlen(file) <= 0) - return false; - -#ifdef HAVE_DIRCACHE - if (dircache_is_enabled()) - return (dircache_get_entry_ptr(file) != NULL); -#endif - - fd = open(file, O_RDONLY); - if (fd < 0) - return false; - close(fd); - return true; -} - bool dir_exists(const char *path) { DIR* d = opendir(path); @@ -838,6 +816,26 @@ char* skip_whitespace(char* const str) return s; } +/* Test file existence, using dircache of possible */ +bool file_exists(const char *file) +{ + int fd; + + if (!file || strlen(file) <= 0) + return false; + +#ifdef HAVE_DIRCACHE + if (dircache_is_enabled()) + return (dircache_get_entry_ptr(file) != NULL); +#endif + + fd = open(file, O_RDONLY); + if (fd < 0) + return false; + close(fd); + return true; +} + /* Format time into buf. * * buf - buffer to format to. diff --git a/apps/replaygain.c b/apps/replaygain.c index 8f6fe4c..3b5d8a0 100644 --- a/apps/replaygain.c +++ b/apps/replaygain.c @@ -26,7 +26,7 @@ #include #include #include -#include +#include "system.h" #include "metadata.h" #include "debug.h" #include "replaygain.h" @@ -224,9 +224,9 @@ static long fp_atof(const char* s, int precision) long sign = 1; bool point = false; - while ((*s != '\0') && isspace(*s)) - { - s++; + while ((*s != '\0') && isspace((unsigned char)*s)) + { + s++; } if (*s == '-') diff --git a/apps/settings.h b/apps/settings.h old mode 100644 new mode 100755 index 17d5acb..9093088 --- a/apps/settings.h +++ b/apps/settings.h @@ -24,7 +24,7 @@ #include #include -#include "inttypes.h" +#include #include "config.h" #if CONFIG_CODEC == SWCODEC #include "audio.h" diff --git a/apps/tagcache.c b/apps/tagcache.c index 2b2881a..3c0f03d 100644 --- a/apps/tagcache.c +++ b/apps/tagcache.c @@ -60,13 +60,13 @@ #include #include #include +#include #include "config.h" #include "ata_idle_notify.h" #include "thread.h" #include "kernel.h" #include "system.h" #include "logf.h" -#include "string.h" #include "usb.h" #include "metadata.h" #include "metadata.h" @@ -86,7 +86,7 @@ #ifdef __PCTOOL__ #define yield() do { } while(0) -#define sim_sleep(timeout) do { } while(0) +#define sleep(timeout) do { } while(0) #define do_timed_yield() do { } while(0) #endif @@ -262,6 +262,38 @@ static volatile int read_lock; static bool delete_entry(long idx_id); +/* Tag database files. (without Rockbox directory) */ + +/* Temporary database containing new tags to be committed to the main db. */ +#define TAGCACHE_FILE_TEMP "/database_tmp.tcd" + +/* The main database master index and numeric data. */ +#define TAGCACHE_FILE_MASTER "/database_idx.tcd" + +/* The main database string data. */ +#define TAGCACHE_FILE_INDEX "/database_%d.tcd" + +/* ASCII dumpfile of the DB contents. */ +#define TAGCACHE_FILE_CHANGELOG "/database_changelog.txt" + +/* Serialized DB. */ +#define TAGCACHE_STATEFILE "/database_state.tcd" + +/* Tag database files. (with rockbox directory) */ +#ifdef __PCTOOL__ +static char TAGCACHE_PATH_TEMP[MAX_PATH]; +static char TAGCACHE_PATH_MASTER[MAX_PATH]; +static char TAGCACHE_PATH_INDEX[MAX_PATH]; +static char TAGCACHE_PATH_CHANGELOG[MAX_PATH]; +static char TAGCACHE_PATH_STATEFILE[MAX_PATH]; +#else +#define TAGCACHE_PATH_TEMP ROCKBOX_DIR TAGCACHE_FILE_TEMP +#define TAGCACHE_PATH_MASTER ROCKBOX_DIR TAGCACHE_FILE_MASTER +#define TAGCACHE_PATH_INDEX ROCKBOX_DIR TAGCACHE_FILE_INDEX +#define TAGCACHE_PATH_CHANGELOG ROCKBOX_DIR TAGCACHE_FILE_CHANGELOG +#define TAGCACHE_PATH_STATEFILE ROCKBOX_DIR TAGCACHE_STATEFILE +#endif + const char* tagcache_tag_to_str(int tag) { return tags_str[tag]; @@ -326,7 +358,7 @@ static int open_tag_fd(struct tagcache_header *hdr, int tag, bool write) if (tagcache_is_numeric_tag(tag) || tag < 0 || tag >= TAG_COUNT) return -1; - snprintf(buf, sizeof buf, TAGCACHE_FILE_INDEX, tag); + snprintf(buf, sizeof buf, TAGCACHE_PATH_INDEX, tag); fd = open(buf, write ? O_RDWR : O_RDONLY); if (fd < 0) @@ -353,8 +385,8 @@ static int open_master_fd(struct master_header *hdr, bool write) { int fd; int rc; - - fd = open(TAGCACHE_FILE_MASTER, write ? O_RDWR : O_RDONLY); + + fd = open(TAGCACHE_PATH_MASTER, write ? O_RDWR : O_RDONLY); if (fd < 0) { logf("master file open failed for R/W"); @@ -635,7 +667,6 @@ static bool get_index(int masterfd, int idxid, } #ifndef __PCTOOL__ - static bool write_index(int masterfd, int idxid, struct index_entry *idx) { /* We need to exclude all memory only flags & tags when writing to disk. */ @@ -680,16 +711,14 @@ static bool write_index(int masterfd, int idxid, struct index_entry *idx) return true; } - #endif /* !__PCTOOL__ */ - static bool open_files(struct tagcache_search *tcs, int tag) { if (tcs->idxfd[tag] < 0) { char fn[MAX_PATH]; - snprintf(fn, sizeof fn, TAGCACHE_FILE_INDEX, tag); + snprintf(fn, sizeof fn, TAGCACHE_PATH_INDEX, tag); tcs->idxfd[tag] = open(fn, O_RDONLY); } @@ -1153,17 +1182,25 @@ static void remove_files(void) tc_stat.ready = false; tc_stat.ramcache = false; tc_stat.econ = false; - remove(TAGCACHE_FILE_MASTER); + remove(TAGCACHE_PATH_MASTER); for (i = 0; i < TAG_COUNT; i++) { if (tagcache_is_numeric_tag(i)) continue; - snprintf(buf, sizeof buf, TAGCACHE_FILE_INDEX, i); + snprintf(buf, sizeof buf, TAGCACHE_PATH_INDEX, i); remove(buf); } } +#ifdef __PCTOOL__ +void tagcache_remove_database(void) +{ + remove_files(); + remove(TAGCACHE_PATH_TEMP); + +} +#endif static bool check_all_headers(void) { @@ -1305,7 +1342,7 @@ bool tagcache_search_add_clause(struct tagcache_search *tcs, { char buf[MAX_PATH]; - snprintf(buf, sizeof buf, TAGCACHE_FILE_INDEX, clause->tag); + snprintf(buf, sizeof buf, TAGCACHE_PATH_INDEX, clause->tag); tcs->idxfd[clause->tag] = open(buf, O_RDONLY); } @@ -1315,6 +1352,11 @@ bool tagcache_search_add_clause(struct tagcache_search *tcs, return true; } +void tagcache_remove_statefile(void) +{ + remove(TAGCACHE_PATH_STATEFILE); +} + /* TODO: Remove this mess. */ #ifdef HAVE_DIRCACHE #define TAG_FILENAME_RAM(tcs) ((tcs->type == tag_filename) \ @@ -2456,7 +2498,7 @@ static int build_index(int index_type, struct tagcache_header *h, int tmpfd) * Creating new index file to store the tags. No need to preload * anything whether the index type is sorted or not. */ - snprintf(buf, sizeof buf, TAGCACHE_FILE_INDEX, index_type); + snprintf(buf, sizeof buf, TAGCACHE_PATH_INDEX, index_type); fd = open(buf, O_WRONLY | O_CREAT | O_TRUNC); if (fd < 0) { @@ -2479,16 +2521,16 @@ static int build_index(int index_type, struct tagcache_header *h, int tmpfd) /* Loading the tag lookup file as "master file". */ logf("Loading index file"); - masterfd = open(TAGCACHE_FILE_MASTER, O_RDWR); + masterfd = open(TAGCACHE_PATH_MASTER, O_RDWR); if (masterfd < 0) { logf("Creating new DB"); - masterfd = open(TAGCACHE_FILE_MASTER, O_WRONLY | O_CREAT | O_TRUNC); + masterfd = open(TAGCACHE_PATH_MASTER, O_WRONLY | O_CREAT | O_TRUNC); if (masterfd < 0) { - logf("Failure to create index file (%s)", TAGCACHE_FILE_MASTER); + logf("Failure to create index file (%s)", TAGCACHE_PATH_MASTER); close(fd); return -2; } @@ -2802,7 +2844,7 @@ static bool commit(void) while (write_lock) sleep(1); - tmpfd = open(TAGCACHE_FILE_TEMP, O_RDONLY); + tmpfd = open(TAGCACHE_PATH_TEMP, O_RDONLY); if (tmpfd < 0) { logf("nothing to commit"); @@ -2818,7 +2860,7 @@ static bool commit(void) { logf("incorrect header"); close(tmpfd); - remove(TAGCACHE_FILE_TEMP); + remove(TAGCACHE_PATH_TEMP); return false; } @@ -2826,12 +2868,12 @@ static bool commit(void) { logf("nothing to commit"); close(tmpfd); - remove(TAGCACHE_FILE_TEMP); + remove(TAGCACHE_PATH_TEMP); return true; } #ifdef HAVE_EEPROM_SETTINGS - remove(TAGCACHE_STATEFILE); + tagcache_remove_statefile(); #endif /* At first be sure to unload the ramcache! */ @@ -2944,7 +2986,7 @@ static bool commit(void) close(masterfd); logf("tagcache committed"); - remove(TAGCACHE_FILE_TEMP); + remove(TAGCACHE_PATH_TEMP); tc_stat.ready = check_all_headers(); tc_stat.readyvalid = true; @@ -2999,7 +3041,6 @@ static void free_tempbuf(void) } #ifndef __PCTOOL__ - static bool modify_numeric_entry(int masterfd, int idx_id, int tag, long data) { struct index_entry idx; @@ -3018,6 +3059,7 @@ static bool modify_numeric_entry(int masterfd, int idx_id, int tag, long data) return write_index(masterfd, idx_id, &idx); } +#endif #if 0 bool tagcache_modify_numeric_entry(struct tagcache_search *tcs, @@ -3035,6 +3077,7 @@ bool tagcache_modify_numeric_entry(struct tagcache_search *tcs, } #endif +#ifndef __PCTOOL__ #define COMMAND_QUEUE_IS_EMPTY (command_queue_ridx == command_queue_widx) static bool command_queue_is_full(void) @@ -3160,7 +3203,6 @@ void tagcache_update_numeric(int idx_id, int tag, long data) { queue_command(CMD_UPDATE_NUMERIC, idx_id, tag, data); } -#endif /* !__PCTOOL__ */ long tagcache_get_serial(void) { @@ -3171,6 +3213,7 @@ long tagcache_get_commitid(void) { return current_tcmh.commitid; } +#endif /* !__PCTOOL__ */ static bool write_tag(int fd, const char *tagstr, const char *datastr) { @@ -3197,7 +3240,6 @@ static bool write_tag(int fd, const char *tagstr, const char *datastr) } #ifndef __PCTOOL__ - static bool read_tag(char *dest, long size, const char *src, const char *tagstr) { @@ -3351,7 +3393,7 @@ bool tagcache_import_changelog(void) while (read_lock) sleep(1); - clfd = open(TAGCACHE_FILE_CHANGELOG, O_RDONLY); + clfd = open(TAGCACHE_PATH_CHANGELOG, O_RDONLY); if (clfd < 0) { logf("failure to open changelog"); @@ -3383,7 +3425,6 @@ bool tagcache_import_changelog(void) return true; } - #endif /* !__PCTOOL__ */ bool tagcache_create_changelog(struct tagcache_search *tcs) @@ -3402,7 +3443,7 @@ bool tagcache_create_changelog(struct tagcache_search *tcs) return false; /* Initialize the changelog */ - clfd = open(TAGCACHE_FILE_CHANGELOG, O_WRONLY | O_CREAT | O_TRUNC); + clfd = open(TAGCACHE_PATH_CHANGELOG, O_WRONLY | O_CREAT | O_TRUNC); if (clfd < 0) { logf("failure to open changelog"); @@ -3730,7 +3771,7 @@ static bool tagcache_dumpload(void) long offpos; int i; - fd = open(TAGCACHE_STATEFILE, O_RDONLY); + fd = open(TAGCACHE_PATH_STATEFILE, O_RDONLY); if (fd < 0) { logf("no tagcache statedump"); @@ -3781,7 +3822,7 @@ static bool tagcache_dumpsave(void) if (!tc_stat.ramcache) return false; - fd = open(TAGCACHE_STATEFILE, O_WRONLY | O_CREAT | O_TRUNC); + fd = open(TAGCACHE_PATH_STATEFILE, O_WRONLY | O_CREAT | O_TRUNC); if (fd < 0) { logf("failed to create a statedump"); @@ -3819,7 +3860,7 @@ static bool load_tagcache(void) logf("loading tagcache to ram..."); - fd = open(TAGCACHE_FILE_MASTER, O_RDONLY); + fd = open(TAGCACHE_PATH_MASTER, O_RDONLY); if (fd < 0) { logf("tagcache open failed"); @@ -4033,7 +4074,7 @@ static bool check_deleted_files(void) struct tagfile_entry tfe; logf("reverse scan..."); - snprintf(buf, sizeof buf, TAGCACHE_FILE_INDEX, tag_filename); + snprintf(buf, sizeof buf, TAGCACHE_PATH_INDEX, tag_filename); fd = open(buf, O_RDONLY); if (fd < 0) @@ -4193,7 +4234,7 @@ void tagcache_build(const char *path) logf("updating tagcache"); - cachefd = open(TAGCACHE_FILE_TEMP, O_RDONLY); + cachefd = open(TAGCACHE_PATH_TEMP, O_RDONLY); if (cachefd >= 0) { logf("skipping, cache already waiting for commit"); @@ -4201,16 +4242,18 @@ void tagcache_build(const char *path) return ; } - cachefd = open(TAGCACHE_FILE_TEMP, O_RDWR | O_CREAT | O_TRUNC); + cachefd = open(TAGCACHE_PATH_TEMP, O_RDWR | O_CREAT | O_TRUNC); if (cachefd < 0) { - logf("master file open failed: %s", TAGCACHE_FILE_TEMP); + logf("master file open failed: %s", TAGCACHE_PATH_TEMP); return ; } filenametag_fd = open_tag_fd(&header, tag_filename, false); +#ifndef __PCTOOL__ cpu_boost(true); +#endif logf("Scanning files..."); /* Scan for new files. */ @@ -4238,7 +4281,9 @@ void tagcache_build(const char *path) if (!ret) { logf("Aborted."); +#ifndef __PCTOOL__ cpu_boost(false); +#endif return ; } @@ -4248,7 +4293,7 @@ void tagcache_build(const char *path) #endif if (commit()) { - remove(TAGCACHE_FILE_TEMP); + remove(TAGCACHE_PATH_TEMP); logf("tagcache built!"); } #ifdef __PCTOOL__ @@ -4264,7 +4309,9 @@ void tagcache_build(const char *path) } #endif +#ifndef __PCTOOL__ cpu_boost(false); +#endif } #ifdef HAVE_TC_RAMCACHE @@ -4273,7 +4320,9 @@ static void load_ramcache(void) if (!hdr) return ; +#ifndef __PCTOOL__ cpu_boost(true); +#endif /* At first we should load the cache (if exists). */ tc_stat.ramcache = load_tagcache(); @@ -4286,7 +4335,9 @@ static void load_ramcache(void) hdr = NULL; } +#ifndef __PCTOOL__ cpu_boost(false); +#endif } void tagcache_unload_ramcache(void) @@ -4315,7 +4366,7 @@ static void tagcache_thread(void) if (firmware_settings.initialized && firmware_settings.disk_clean) check_done = tagcache_dumpload(); - remove(TAGCACHE_STATEFILE); + tagcache_remove_statefile(); # endif /* Allocate space for the tagcache if found on disk. */ @@ -4345,7 +4396,7 @@ static void tagcache_thread(void) case Q_REBUILD: remove_files(); - remove(TAGCACHE_FILE_TEMP); + remove(TAGCACHE_PATH_TEMP); tagcache_build("/"); break; @@ -4507,8 +4558,14 @@ void tagcache_init(void) create_thread(tagcache_thread, tagcache_stack, sizeof(tagcache_stack), 0, tagcache_thread_name IF_PRIO(, PRIORITY_BACKGROUND) - IF_COP(, CPU)); + IF_COP(, CPU)); #else + get_rockbox_path(TAGCACHE_FILE_TEMP, TAGCACHE_PATH_TEMP); + get_rockbox_path(TAGCACHE_FILE_MASTER, TAGCACHE_PATH_MASTER); + get_rockbox_path(TAGCACHE_FILE_INDEX, TAGCACHE_PATH_INDEX); + get_rockbox_path(TAGCACHE_FILE_CHANGELOG, TAGCACHE_PATH_CHANGELOG); + get_rockbox_path(TAGCACHE_STATEFILE, TAGCACHE_PATH_STATEFILE); + tc_stat.initialized = true; allocate_tempbuf(); commit(); diff --git a/apps/tagcache.h b/apps/tagcache.h index e995784..456485a 100644 --- a/apps/tagcache.h +++ b/apps/tagcache.h @@ -77,23 +77,6 @@ enum tag_type { tag_artist = 0, tag_album, tag_genre, tag_title, #define TAGCACHE_MAX_FILTERS 4 #define TAGCACHE_MAX_CLAUSES 32 -/* Tag database files. */ - -/* Temporary database containing new tags to be committed to the main db. */ -#define TAGCACHE_FILE_TEMP ROCKBOX_DIR "/database_tmp.tcd" - -/* The main database master index and numeric data. */ -#define TAGCACHE_FILE_MASTER ROCKBOX_DIR "/database_idx.tcd" - -/* The main database string data. */ -#define TAGCACHE_FILE_INDEX ROCKBOX_DIR "/database_%d.tcd" - -/* ASCII dumpfile of the DB contents. */ -#define TAGCACHE_FILE_CHANGELOG ROCKBOX_DIR "/database_changelog.txt" - -/* Serialized DB. */ -#define TAGCACHE_STATEFILE ROCKBOX_DIR "/database_state.tcd" - /* Flags */ #define FLAG_DELETED 0x0001 /* Entry has been removed from db */ #define FLAG_DIRCACHE 0x0002 /* Filename is a dircache pointer */ @@ -179,6 +162,7 @@ void tagcache_build(const char *path); #ifdef __PCTOOL__ void tagcache_reverse_scan(void); +void tagcache_remove_database(void); #endif const char* tagcache_tag_to_str(int tag); @@ -230,5 +214,6 @@ void tagcache_stop_scan(void); bool tagcache_update(void); bool tagcache_rebuild(void); int tagcache_get_max_commit_step(void); +void tagcache_remove_statefile(void); #endif #endif diff --git a/apps/tree.c b/apps/tree.c index 66979ea..9ad1919 100644 --- a/apps/tree.c +++ b/apps/tree.c @@ -1124,7 +1124,7 @@ void tree_restore(void) #endif #ifdef HAVE_TC_RAMCACHE - remove(TAGCACHE_STATEFILE); + tagcache_remove_statefile(); #endif #ifdef HAVE_DIRCACHE diff --git a/firmware/common/unicode.c b/firmware/common/unicode.c index 61989e5..7e96ce2 100644 --- a/firmware/common/unicode.c +++ b/firmware/common/unicode.c @@ -36,11 +36,12 @@ #define O_BINARY 0 #endif -#define CODEPAGE_DIR ROCKBOX_DIR"/codepages" +/* codepage file into /CODEPAGE_DIR */ +#define CODEPAGE_DIR "/codepages" static int default_codepage = 0; static int loaded_cp_table = 0; -#ifdef HAVE_LCD_BITMAP +#if defined(HAVE_LCD_BITMAP) || defined(__PCTOOL__) #define MAX_CP_TABLE_SIZE 32768 #define NUM_TABLES 5 @@ -120,29 +121,29 @@ static int load_cp_table(int cp) int table = cp_2_table[cp]; int file, tablesize; unsigned char tmp[2]; + char path[MAX_PATH]; if (table == 0 || table == loaded_cp_table) return 1; - file = open(filename[table-1], O_RDONLY|O_BINARY); - + get_rockbox_path(filename[table-1], path); + file = open(path, O_RDONLY|O_BINARY); if (file < 0) { - DEBUGF("Can't open codepage file: %s.cp\n", filename[table-1]); + DEBUGF("Can't open codepage file: %s.cp\n", path); return 0; } tablesize = filesize(file) / 2; if (tablesize > MAX_CP_TABLE_SIZE) { - DEBUGF("Invalid codepage file: %s.cp\n", filename[table-1]); + DEBUGF("Invalid codepage file: %s.cp\n", path); close(file); return 0; } while (i < tablesize) { if (!read(file, tmp, 2)) { - DEBUGF("Can't read from codepage file: %s.cp\n", - filename[table-1]); + DEBUGF("Can't read from codepage file: %s.cp\n", path); loaded_cp_table = 0; return 0; } @@ -194,7 +195,7 @@ unsigned char* iso_decode(const unsigned char *iso, unsigned char *utf8, case ISO_8859_9: /* Turkish */ case ISO_8859_2: /* Latin Extended */ case WIN_1250: /* Central European */ -#ifdef HAVE_LCD_BITMAP +#if defined(HAVE_LCD_BITMAP) || defined(__PCTOOL__) case ISO_8859_8: /* Hebrew */ case ISO_8859_11: /* Thai */ case WIN_1256: /* Arabic */ @@ -203,7 +204,7 @@ unsigned char* iso_decode(const unsigned char *iso, unsigned char *utf8, ucs = codepage_table[tmp]; break; -#ifdef HAVE_LCD_BITMAP +#if defined(HAVE_LCD_BITMAP) || defined(__PCTOOL__) case SJIS: /* Japanese */ if (*iso > 0xA0 && *iso < 0xE0) { tmp = *iso++ | (0xA100 - 0x8000); diff --git a/firmware/export/logf.h b/firmware/export/logf.h index 4926fe5..a0e5612 100644 --- a/firmware/export/logf.h +++ b/firmware/export/logf.h @@ -20,8 +20,8 @@ ****************************************************************************/ #ifndef LOGF_H #define LOGF_H -#include #include +#include "config.h" #include "../include/_ansi.h" #include "debug.h" diff --git a/firmware/export/system.h b/firmware/export/system.h index b44600d..af1dcf2 100644 --- a/firmware/export/system.h +++ b/firmware/export/system.h @@ -228,9 +228,9 @@ enum { MAXMEMGUARD }; -#ifndef SIMULATOR +#if !defined(SIMULATOR) && !defined(__PCTOOL__) #include "system-target.h" -#else /* SIMULATOR */ +#else /* SIMULATOR and __PCTOOL__ */ static inline uint16_t swap16(uint16_t value) /* @@ -264,7 +264,7 @@ static inline uint32_t swap_odd_even32(uint32_t value) return (t >> 8) | ((t ^ value) << 8); } -#endif /* !SIMULATOR */ +#endif /* !SIMULATOR and __PCTOOL__ */ /* Declare this as HIGHEST_IRQ_LEVEL if they don't differ */ #ifndef DISABLE_INTERRUPTS diff --git a/firmware/export/thread.h b/firmware/export/thread.h index 7fe128d..bd8f4ae 100644 --- a/firmware/export/thread.h +++ b/firmware/export/thread.h @@ -78,7 +78,7 @@ #define DEFAULT_STACK_SIZE 0x400 /* Bytes */ -#ifndef SIMULATOR +#if !defined(SIMULATOR) && !defined(__PCTOOL__) /* Need to keep structures inside the header file because debug_menu * needs them. */ #ifdef CPU_COLDFIRE @@ -122,7 +122,7 @@ struct regs void *s; /* Semaphore for blocking and wakeup */ void (*start)(void); /* Start function */ }; -#endif /* !SIMULATOR */ +#endif /* !SIMULATOR and __PCTOOL__ */ /* NOTE: The use of the word "queue" may also refer to a linked list of threads being maintained that are normally dealt with in FIFO order diff --git a/firmware/include/dir_uncached.h b/firmware/include/dir_uncached.h index e198833..9c5302f 100644 --- a/firmware/include/dir_uncached.h +++ b/firmware/include/dir_uncached.h @@ -32,7 +32,7 @@ #define ATTR_ARCHIVE 0x20 #define ATTR_VOLUME 0x40 /* this is a volume, not a real directory */ -#ifdef SIMULATOR +#if defined(SIMULATOR) || defined(__PCTOOL__) #define dirent_uncached sim_dirent #define DIR_UNCACHED SIM_DIR #define opendir_uncached sim_opendir @@ -57,7 +57,7 @@ struct dirent_uncached { #include "fat.h" typedef struct { -#ifndef SIMULATOR +#if !defined(SIMULATOR) && !defined(__PCTOOL__) bool busy; long startcluster; struct fat_dir fatdir; diff --git a/firmware/include/file.h b/firmware/include/file.h index 9a9548f..00e1d4c 100644 --- a/firmware/include/file.h +++ b/firmware/include/file.h @@ -22,7 +22,13 @@ #ifndef _FILE_H_ #define _FILE_H_ +#ifdef __PCTOOL__ +#include +#include +#else #include +#include +#endif #undef MAX_PATH /* this avoids problems when building simulator */ #define MAX_PATH 260 @@ -48,7 +54,7 @@ #define O_TRUNC 0x10 #endif -#if defined(SIMULATOR) && !defined(PLUGIN) && !defined(CODEC) +#if (defined(SIMULATOR) && !defined(PLUGIN) && !defined(CODEC)) || defined(__PCTOOL__) #define open(x,y) sim_open(x,y) #define creat(x) sim_creat(x) #define remove(x) sim_remove(x) @@ -60,6 +66,13 @@ #define read(x,y,z) sim_read(x,y,z) #define write(x,y,z) sim_write(x,y,z) #define close(x) sim_close(x) +#define get_rockbox_pathname(x) get_sim_rockbox_pathname(x) +#endif + +#ifdef __PCTOOL__ +#define get_rockbox_path(dir, path) snprintf(path, MAX_PATH, "%s", get_rockbox_pathname(dir)) +#else +#define get_rockbox_path(dir, path) snprintf(path, MAX_PATH, "%s%s", ROCKBOX_DIR, dir) #endif typedef int (*open_func)(const char* pathname, int flags); @@ -73,13 +86,23 @@ extern int open(const char* pathname, int flags); extern int close(int fd); extern int fsync(int fd); extern ssize_t read(int fd, void *buf, size_t count); -extern off_t lseek(int fildes, off_t offset, int whence); extern int creat(const char *pathname); extern ssize_t write(int fd, const void *buf, size_t count); extern int remove(const char* pathname); extern int rename(const char* path, const char* newname); extern int ftruncate(int fd, off_t length); +#if !defined(__PCTOOL__) && !defined(SIMULATOR) +extern off_t lseek(int fildes, off_t offset, int whence); extern off_t filesize(int fd); +#else +extern long lseek(int fildes, long offset, int whence); +extern long filesize(int fd); +#endif +#ifdef HAVE_HOTSWAP extern int release_files(int volume); +#endif +#if defined(__PCTOOL__) +extern const char* get_rockbox_pathname(const char *name); +#endif #endif diff --git a/firmware/include/rbunicode.h b/firmware/include/rbunicode.h index 39fe253..6322816 100644 --- a/firmware/include/rbunicode.h +++ b/firmware/include/rbunicode.h @@ -35,7 +35,7 @@ #define MASK 0xC0 /* 11000000 */ #define COMP 0x80 /* 10x */ -#ifdef HAVE_LCD_BITMAP +#if defined(HAVE_LCD_BITMAP) || defined(__PCTOOL__) enum codepages { ISO_8859_1 = 0, ISO_8859_7, ISO_8859_8, WIN_1251, diff --git a/uisimulator/common/io.c b/uisimulator/common/io.c index d87e331..df6680d 100644 --- a/uisimulator/common/io.c +++ b/uisimulator/common/io.c @@ -31,11 +31,11 @@ #elif defined(__APPLE__) #include #include -#elif !defined(WIN32) +#elif !defined(_WIN32) #include #endif -#ifdef WIN32 +#ifdef _WIN32 #include #endif @@ -50,14 +50,16 @@ #define MAX_OPEN_FILES 11 #include +#ifndef __PCTOOL__ #include #include #include "thread.h" #include "kernel.h" +#include "thread-sdl.h" +#endif #include "debug.h" #include "config.h" #include "ata.h" /* for IF_MV2 et al. */ -#include "thread-sdl.h" /* Windows (and potentially other OSes) distinguish binary and text files. @@ -99,8 +101,8 @@ static unsigned char *ucs2_to_utf8(const wchar_t *ucs, unsigned char *buffer) return buffer; } -#define UTF8_TO_OS(a) utf8_to_ucs2(a,convbuf1) -#define OS_TO_UTF8(a) ucs2_to_utf8(a,convbuf1) +#define UTF8_TO_OS(a) utf8_to_ucs2((const unsigned char *)(a),convbuf1) +#define OS_TO_UTF8(a) ucs2_to_utf8((const wchar_t *)(a),convbuf1) #define DIR_T _WDIR #define DIRENT_T struct _wdirent #define STAT_T struct _stat @@ -115,7 +117,7 @@ extern int _wrmdir(const wchar_t*); #define OPEN(a,b,c) (_wopen)(UTF8_TO_OS(a),b,c) #define CLOSE(a) (close)(a) #define REMOVE(a) (_wremove)(UTF8_TO_OS(a)) -#define RENAME(a,b) (_wrename)(UTF8_TO_OS(a),utf8_to_ucs2(b,convbuf2)) +#define RENAME(a,b) (_wrename)(UTF8_TO_OS(a),utf8_to_ucs2((const unsigned char *)(b),convbuf2)) #else /* !__MINGW32__ */ @@ -143,10 +145,19 @@ void dircache_remove(const char *name); void dircache_rename(const char *oldname, const char *newname); #endif +#ifdef __PCTOOL__ +#define get_rockbox_pathname get_sim_rockbox_pathname +#endif #define SIMULATOR_DEFAULT_ROOT "simdisk" extern const char *sim_root_dir; +#ifdef __PCTOOL__ +#define PCTOOL_DEFAULT_ROOT "./" +#define PCTOOL_DEFAULT_ROCKBOX_DIR "/.rockbox" +extern const char *sim_rockbox_dir; +#endif + static int num_openfiles = 0; struct sim_dirent { @@ -170,7 +181,7 @@ struct mydir { typedef struct mydir MYDIR; -#if 1 /* maybe this needs disabling for MSVC... */ +#ifndef __PCTOOL__ /* maybe this needs disabling for MSVC... */ static unsigned int rockbox2sim(int opt) { int newopt = O_BINARY; @@ -201,7 +212,9 @@ enum struct sim_io { +#ifndef __PCTOOL__ struct mutex sim_mutex; /* Rockbox mutex */ +#endif int cmd; /* The command to perform */ int ready; /* I/O ready flag - 1= ready */ int fd; /* The file to read/write */ @@ -214,22 +227,29 @@ static struct sim_io io; int ata_init(void) { +#ifndef __PCTOOL__ /* Initialize the rockbox kernel objects on a rockbox thread */ mutex_init(&io.sim_mutex); +#endif io.accum = 0; return 1; } +#ifndef __PCTOOL__ int ata_spinup_time(void) { return HZ; } +#endif static ssize_t io_trigger_and_wait(int cmd) { +#ifndef __PCTOOL__ void *mythread = NULL; - ssize_t result; +#endif + ssize_t result = 0; +#ifndef __PCTOOL__ if (io.count > IO_YIELD_THRESHOLD || (io.accum += io.count) >= IO_YIELD_THRESHOLD) { @@ -237,6 +257,7 @@ static ssize_t io_trigger_and_wait(int cmd) io.accum = 0; mythread = thread_sdl_thread_unlock(); } +#endif switch (cmd) { @@ -247,21 +268,37 @@ static ssize_t io_trigger_and_wait(int cmd) result = write(io.fd, io.buf, io.count); break; } - +#ifndef __PCTOOL__ /* Regain our status as current */ if (mythread != NULL) { thread_sdl_thread_lock(mythread); } - +#endif return result; } -#ifndef __PCTOOL__ +#ifdef __PCTOOL__ +const char *get_sim_rockbox_pathname(const char *name) +{ + static char buffer[MAX_PATH]; /* sufficiently big */ + + if(name[0] == '/') + { + snprintf(buffer, sizeof(buffer), "%s%s", + sim_rockbox_dir != NULL ? sim_rockbox_dir : PCTOOL_DEFAULT_ROCKBOX_DIR, name); + } + else + snprintf(buffer, sizeof(buffer), "%s", name); + return buffer; +} +#endif + static const char *get_sim_pathname(const char *name) { static char buffer[MAX_PATH]; /* sufficiently big */ +#ifndef __PCTOOL__ if(name[0] == '/') { snprintf(buffer, sizeof(buffer), "%s%s", @@ -270,10 +307,17 @@ static const char *get_sim_pathname(const char *name) } fprintf(stderr, "WARNING, bad file name lacks slash: %s\n", name); return name; -} #else -#define get_sim_pathname(name) name + if(name[0] == '/') + { + snprintf(buffer, sizeof(buffer), "%s%s", + sim_root_dir != NULL ? sim_root_dir : PCTOOL_DEFAULT_ROOT, name); + } + else + snprintf(buffer, sizeof(buffer), "%s", name); + return buffer; #endif +} MYDIR *sim_opendir(const char *name) { @@ -305,7 +349,7 @@ struct sim_dirent *sim_readdir(MYDIR *dir) if(!x11) return (struct sim_dirent *)0; - strcpy((char *)secret.d_name, OS_TO_UTF8(x11->d_name)); + strcpy((char *)secret.d_name, (char *)OS_TO_UTF8(x11->d_name)); /* build file name */ snprintf(buffer, sizeof(buffer), "%s/%s", @@ -337,7 +381,11 @@ void sim_closedir(MYDIR *dir) int sim_open(const char *name, int o) { +#ifdef __PCTOOL__ + int opts = o | O_BINARY; +#else int opts = rockbox2sim(o); +#endif int ret; if (num_openfiles >= MAX_OPEN_FILES) @@ -366,35 +414,35 @@ int sim_creat(const char *name) ssize_t sim_read(int fd, void *buf, size_t count) { ssize_t result; - +#ifndef __PCTOOL__ mutex_lock(&io.sim_mutex); - +#endif /* Setup parameters */ io.fd = fd; io.buf = buf; io.count = count; result = io_trigger_and_wait(IO_READ); - +#ifndef __PCTOOL__ mutex_unlock(&io.sim_mutex); - +#endif return result; } ssize_t sim_write(int fd, const void *buf, size_t count) { ssize_t result; - +#ifndef __PCTOOL__ mutex_lock(&io.sim_mutex); - +#endif io.fd = fd; io.buf = (void*)buf; io.count = count; result = io_trigger_and_wait(IO_WRITE); - +#ifndef __PCTOOL__ mutex_unlock(&io.sim_mutex); - +#endif return result; } @@ -432,7 +480,7 @@ long sim_lseek(int fildes, long offset, int whence) long sim_filesize(int fd) { -#ifdef WIN32 +#ifdef _WIN32 return _filelength(fd); #else struct stat buf; @@ -456,8 +504,8 @@ void fat_size(IF_MV2(int volume,) unsigned long* size, unsigned long* free) } #endif -#ifdef WIN32 - long secperclus, bytespersec, free_clusters, num_clusters; +#ifdef _WIN32 + unsigned long secperclus, bytespersec, free_clusters, num_clusters; if (GetDiskFreeSpace(NULL, &secperclus, &bytespersec, &free_clusters, &num_clusters)) { @@ -488,31 +536,33 @@ void fat_size(IF_MV2(int volume,) unsigned long* size, unsigned long* free) int sim_fsync(int fd) { -#ifdef WIN32 +#ifdef _WIN32 return _commit(fd); #else return fsync(fd); #endif } -#ifdef WIN32 +#ifdef _WIN32 /* sim-win32 */ +typedef void (__stdcall *dlfunc)(); #define dlopen(_x_, _y_) LoadLibraryW(UTF8_TO_OS(_x_)) -#define dlsym(_x_, _y_) (void *)GetProcAddress(_x_, _y_) +#define dlsym(_x_, _y_) (dlfunc)GetProcAddress(_x_, _y_) #define dlclose(_x_) FreeLibrary(_x_) #else /* sim-x11 */ #include +#define dlfunc void* #endif -void *sim_codec_load_ram(char* codecptr, int size, void **pd) +dlfunc sim_codec_load_ram(char* codecptr, int size, void **pd) { - void *hdr; + dlfunc hdr; char name[MAX_PATH]; char path[MAX_PATH]; int fd; int codec_count; -#ifdef WIN32 +#ifdef _WIN32 char buf[MAX_PATH]; #endif @@ -548,7 +598,7 @@ void *sim_codec_load_ram(char* codecptr, int size, void **pd) if (*pd == NULL) { DEBUGF("failed to load %s\n", path); -#ifdef WIN32 +#ifdef _WIN32 FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM, NULL, GetLastError(), 0, buf, sizeof buf, NULL); DEBUGF("dlopen(%s): %s\n", path, buf); @@ -570,11 +620,11 @@ void sim_codec_close(void *pd) dlclose(pd); } -void *sim_plugin_load(char *plugin, void **pd) +dlfunc sim_plugin_load(char *plugin, void **pd) { - void *hdr; + dlfunc hdr; char path[MAX_PATH]; -#ifdef WIN32 +#ifdef _WIN32 char buf[MAX_PATH]; #endif @@ -585,7 +635,7 @@ void *sim_plugin_load(char *plugin, void **pd) *pd = dlopen(path, RTLD_NOW); if (*pd == NULL) { DEBUGF("failed to load %s\n", plugin); -#ifdef WIN32 +#ifdef _WIN32 FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM, NULL, GetLastError(), 0, buf, sizeof(buf), NULL); DEBUGF("dlopen(%s): %s\n", path, buf); @@ -607,7 +657,7 @@ void sim_plugin_close(void *pd) dlclose(pd); } -#ifdef WIN32 +#ifdef _WIN32 static unsigned old_cp; void debug_exit(void) @@ -651,7 +701,7 @@ void ldebugf(const char* file, int line, const char *fmt, ...) /* rockbox off_t may be different from system off_t */ int sim_ftruncate(int fd, long length) { -#ifdef WIN32 +#ifdef _WIN32 return _chsize(fd, length); #else return ftruncate(fd, length); diff --git a/utils/songdb/Makefile b/utils/songdb/Makefile new file mode 100644 index 0000000..8b21af0 --- /dev/null +++ b/utils/songdb/Makefile @@ -0,0 +1,101 @@ +# __________ __ ___. +# Open \______ \ ____ ____ | | _\_ |__ _______ ___ +# Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / +# Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < +# Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ +# \/ \/ \/ \/ \/ +# $Id$ +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY +# KIND, either express or implied. +# +SILENT:=@ +CC:=gcc +MAKE:=make +RM:=rm + +ifneq "$(MAKECMDGOALS)" "clean" + VERSION:=$(shell ../../tools/version.sh ../../) + BUILDDATE:=$(shell date -u +'-DYEAR=%Y -DMONTH=%m -DDAY=%d') +endif + +# -I- option check. If gcc version >= 4 then -I- option obsolete. +# gcc version >= 4 +# -iquotedir1 -iquotedir2 ... +# gcc version <= 3 +# -Idir1 -Idir2 ... -I- +ifeq "$(shell $(CC) -dumpversion | sed -e 's/\..*//')" "4" + INC_OPT := -iquote + SYS_INC_OPT := +else + INC_OPT := -I + SYS_INC_OPT := -I- +endif + +GCCOPTS := -std=c99 -O -W -Wall -Wshadow -pedantic -fno-builtin +DEBUG := -g +DEFINES := -D__PCTOOL__ -DHAVE_TAGCACHE -DCONFIG_CODEC=1 -DROCKBOX_LITTLE_ENDIAN -DAPP_VERSION=\"$(VERSION)\" $(BUILDDATE) +INCLUDES := $(INC_OPT)../../apps $(INC_OPT)../../apps/metadata $(INC_OPT)../../firmware/export $(INC_OPT)../../firmware/include $(SYS_INC_OPT) +LIBS := + +EXTRA_DEFINES := -DROCKBOX_HAS_LOGF + +ifeq ($(findstring CYGWIN,$(shell uname)),CYGWIN) + GCCOPTS += -mno-cygwin +else + ifneq ($(findstring MINGW,$(shell uname)),MINGW) + LIBS += -ldl + endif +endif + +CFLAGS = $(GCCOPTS) $(DEBUG) $(DEFINES) $(EXTRA_DEFINES) $(INCLUDES) + +.PHONY: all clean +all: songdb + +SRCS:=../../uisimulator/common/io.c \ +../../firmware/common/crc32.c \ +../../firmware/common/errno.c \ +../../firmware/common/strcasestr.c \ +../../firmware/common/structec.c \ +../../firmware/common/unicode.c \ +../../apps/metadata.c \ +../../apps/misc.c \ +../../apps/mp3data.c \ +../../apps/replaygain.c \ +../../apps/tagcache.c + +# append metadata files +SRCS += $(wildcard ../../apps/metadata/*.c) + +ifneq "$(filter -DROCKBOX_HAS_LOGF,$(EXTRA_DEFINES))" "" + SRCS += ../../firmware/logf.c +endif + +OBJS=$(patsubst %.c,%.o, $(notdir $(SRCS))) + +DEPFILE = songdb.d + +$(DEPFILE): $(SRCS) + $(SILENT)(for each in $(SRCS); do \ + obj=`echo $$each | sed -e 's/\.c/.o/' -e 's/^.*\///'`; \ + $(CC) -MG -MM -MT "$$obj" $(CFLAGS) $$each 2>/dev/null; \ + done) >> $(DEPFILE) + +songdb: songdb.c ../../firmware/include/rbunicode.h ../../apps/tagcache.h $(OBJS) + $(SILENT)$(CC) $(CFLAGS) songdb.c -o $@ $(OBJS) $(LIBS) + +$(OBJS):%.o: $(shell grep %.c $(SRCS)) + $(SILENT)$(CC) $(CFLAGS) -c $< -o $@ + +clean: + $(SILENT)$(RM) -f *.o songdb.exe songdb *.d + +ifneq "$(MAKECMDGOALS)" "clean" + -include $(DEPFILE) +endif diff --git a/utils/songdb/readme.txt b/utils/songdb/readme.txt new file mode 100644 index 0000000..a611d54 --- /dev/null +++ b/utils/songdb/readme.txt @@ -0,0 +1,123 @@ + __________ __ ___. + Open \______ \ ____ ____ | | _\_ |__ _______ ___ + Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + \/ \/ \/ \/ \/ +$Id$ + +Copyright (C) 2009 Yoshihisa Uchida + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License + as published by the Free Software Foundation; either version 2 + of the License, or (at your option) any later version. + + This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + KIND, either express or implied. + +========================================================================== +songdb + Create the song database (database_*.tcd) application. + + +================================================= +Usage +================================================= +songdb -r|--root-path + -m|--mode + [-d|--rockbox-directory ] + [-s|--song-directory ] + [-c|--codepage ] + [-h|--help] + [-V|--version] + +-r|--root-path + Rockbox root directory. + + / + and //codepages/*.cp + should exist. + + When songdb is used on Windows, the drive letter is written + Windows style (such as "C:/path/of/root"). + + Song database (database_*.tcd) is build for + / directory. + +-m|--mode + create: build database newly. + update: update database. + commit: commit database. + append: append non registered files. + It is not checked whether the file registered in the database + has been deleted. + +-d|--rockbox-directory + Rockbox directory. + If this option is not given, then Rockbox directory is ".rockbox". + +-s|--song-directory + song storage directory. + If begins with a "/", then it looks for the song file + from /. + If does not begin with a "/", then it looks for the song + file from /. + + If this option is not given, then = "/". + + When using songdb on MinGW+MSYS shell, it should be set not /hoge but //hoge. + +-c|--codepage + metadata codepage. + If this option is not given, then metadata codepage is "UTF-8". + + codepage list + option value codepage + ----------------------------------------------- + ISO-8859-1 Latin1 (ISO-8859-1) + ISO-8859-2 Latin Extended (ISO-8859-2) + ISO-8859-7 Greek (ISO-8859-7) + ISO-8859-8 Hebrew (ISO-8859-8) + ISO-8859-9 Turkish (ISO-8859-9) + ISO-8859-11 Thai (ISO-8859-11) + CP1250 Central European (CP1250) + CP1251 Cyrillic (CP1251) + CP1256 Arabic (CP1256) + SJIS Japanese (SJIS) + GB-2312 Simple Chinese (GB2312) + KSX-1001 Korean (KSX1001) + BIG-5 Traditional Chinese (BIG5) + UTF-8 Unicode (UTF-8) + +-h|--help + show help message and exit. + +-V|--version + show version information and exit. + +================================================= +Requirement +================================================= +OS + 1) Windows + - Cygwin or MinGW (with MSYS) must be installed. + + 2) Linux + + Other OS do not checked. + +When songdb does not use SDL library, SDL library +may not be installed. + +================================================= +Build +================================================= +1) edit Makefile (gcc options) +2) make + +================================================= +TODO +================================================= +1) The folder of song database can be freely set. +2) Fix build warning. diff --git a/utils/songdb/songdb.c b/utils/songdb/songdb.c new file mode 100644 index 0000000..d08cbf6 --- /dev/null +++ b/utils/songdb/songdb.c @@ -0,0 +1,234 @@ +/**************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2009 Yoshihisa Uchida + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ +#include +#include +#include +#include "rbunicode.h" +#include "tagcache.h" + +const char *sim_root_dir = NULL; +const char *sim_rockbox_dir = NULL; + +#define DEFAULT_ROCKBOX_DIRECTORY "/.rockbox" + +#define DB_MODE_CREATE_STR "create" +#define DB_MODE_UPDATE_STR "update" +#define DB_MODE_COMMIT_STR "commit" +#define DB_MODE_APPEND_STR "append" + +enum {DB_MODE_CREATE, DB_MODE_UPDATE, DB_MODE_COMMIT, DB_MODE_APPEND}; + +static void show_usage(void) +{ + fprintf(stdout, "Usage: songdb -r|--root-path -m|--mode [-d|--rockbox-directory ] [-s|--song-directory ][-c|--codepage ][-h|--help][-V|--version]\n"); + fprintf(stdout, "\n"); + fprintf(stdout, "Options\n"); + fprintf(stdout, " -r|--root-path \n"); + fprintf(stdout, " Rockbox root path.\n"); + fprintf(stdout, " -m|--mode \n"); + fprintf(stdout, " create: build database newly.\n"); + fprintf(stdout, " update: update database.\n"); + fprintf(stdout, " commit: commit database.\n"); + fprintf(stdout, " append: append non registered files.\n"); + fprintf(stdout, " -d|--rockbox-directory \n"); + fprintf(stdout, " Rockbox directory.\n"); + fprintf(stdout, " -s|--song-directory \n"); + fprintf(stdout, " song storage directory.\n"); + fprintf(stdout, " -c|--codepage \n"); + fprintf(stdout, " metadata codepage\n"); + fprintf(stdout, " -h|--help\n"); + fprintf(stdout, " show this help message and exit.\n"); + fprintf(stdout, " -V|--version\n"); + fprintf(stdout, " show version information and exit.\n"); + return; +} + +static void show_version(void) +{ + fprintf(stdout, "songdb version %s\n", APP_VERSION); + fprintf(stdout, "Copyright (C) 2009 The Rockbox Team., Yoshihisa Uchida\n"); + fprintf(stdout, "Released under the GNU General Public License v2+\n"); + return; +} + +static void show_errmsg(const char *msg) +{ + fprintf(stderr, "error: %s\n", msg); + return; +} + +static int get_codepage(const char *cp) +{ + int code; + + for (code = 0; code < NUM_CODEPAGES; code++) + { + if (strcmp(cp, get_codepage_name(code)) == 0) + return code; + } + + return -1; +} + +int main(int argc, char **argv) +{ + int idx = 0; + int mode = -1; + char rootdir[MAX_PATH] = "\0"; + char rockboxdir[MAX_PATH] = DEFAULT_ROCKBOX_DIRECTORY; + char songdir[MAX_PATH] = "/"; + int cp = UTF_8; + + for (idx = 1; idx < argc; idx++) + { + if ((strcmp(argv[idx],"-h")==0) || (strcmp(argv[idx],"--help")==0)) + { + show_usage(); + return 0; + } + else if ((strcmp(argv[idx],"-V")==0) || (strcmp(argv[idx],"--version")==0)) + { + show_version(); + return 0; + } + else if ((strcmp(argv[idx],"-r")==0) || (strcmp(argv[idx],"--root-path")==0)) + { + if ((idx == argc-1) || (argv[idx+1][0] == '-')) + { + show_usage(); + return 1; + } + idx++; + + if (strlen(argv[idx]) >= MAX_PATH) + { + show_errmsg("root path is too long."); + return 1; + } + strcpy(rootdir, argv[idx]); + } + else if ((strcmp(argv[idx],"-d")==0) || (strcmp(argv[idx],"--rockbox-directory")==0)) + { + if ((idx == argc-1) || (argv[idx+1][0] == '-')) + { + show_usage(); + return 1; + } + idx++; + + if (strlen(argv[idx]) >= MAX_PATH) + { + show_errmsg("Rockbox directory is too long."); + return 1; + } + strcpy(rockboxdir, "/"); + strcat(rockboxdir, argv[idx]); + } + else if ((strcmp(argv[idx],"-s")==0) || (strcmp(argv[idx],"--song-directory")==0)) + { + if ((idx == argc-1) || (argv[idx+1][0] == '-')) + { + show_usage(); + return 1; + } + idx++; + + if (strlen(argv[idx]) >= MAX_PATH) + { + show_errmsg("song store directory is too long."); + return 1; + } + strcpy(songdir, argv[idx]); + } + else if ((strcmp(argv[idx],"-m")==0) || (strcmp(argv[idx],"--mode")==0)) + { + if (idx == argc-1) + { + show_usage(); + return 1; + } + idx++; + if (strcmp(argv[idx],DB_MODE_CREATE_STR)==0) + mode = DB_MODE_CREATE; + else if (strcmp(argv[idx],DB_MODE_UPDATE_STR)==0) + mode = DB_MODE_UPDATE; + else if (strcmp(argv[idx],DB_MODE_COMMIT_STR)==0) + mode = DB_MODE_COMMIT; + else if (strcmp(argv[idx],DB_MODE_APPEND_STR)==0) + mode = DB_MODE_APPEND; + else + { + show_errmsg("--mode is invalid."); + return 1; + } + } + else if ((strcmp(argv[idx], "-c")==0) || (strcmp(argv[idx], "--codepage")==0)) + { + if (idx == argc-1) + { + show_usage(); + return 1; + } + idx++; + cp = get_codepage(argv[idx]); + if (cp < 0) + { + show_errmsg("codepage is invalid."); + return 1; + } + } + else + { + show_usage(); + return 1; + } + } + + if (rootdir[0] == '\0' || mode < 0) + { + show_usage(); + return 1; + } + + sim_root_dir = rootdir; + sim_rockbox_dir = rockboxdir; + + set_codepage(cp); + + tagcache_init(); + + if (mode == DB_MODE_CREATE) + { + tagcache_remove_database(); + tagcache_build(songdir); + } + else if (mode == DB_MODE_UPDATE) + { + tagcache_build(songdir); + tagcache_reverse_scan(); + } + else if (mode == DB_MODE_APPEND) + { + tagcache_build(songdir); + } + + return 0; +}