diff options
author | Warren Dukes <warren.dukes@gmail.com> | 2004-11-10 02:38:55 +0000 |
---|---|---|
committer | Warren Dukes <warren.dukes@gmail.com> | 2004-11-10 02:38:55 +0000 |
commit | 2d87ffa863b5eaa24862e925e767eb9a36bd58fe (patch) | |
tree | 98028112defc0aedfe282b88c8ba81b15ffdd53b | |
parent | 92a75471505391edd2f8f9af23188b4f7b17bbcb (diff) | |
download | mpd-2d87ffa863b5eaa24862e925e767eb9a36bd58fe.tar.gz mpd-2d87ffa863b5eaa24862e925e767eb9a36bd58fe.tar.xz mpd-2d87ffa863b5eaa24862e925e767eb9a36bd58fe.zip |
now we only allocate unique metadata items
git-svn-id: https://svn.musicpd.org/mpd/branches/r2562-metadata-handling-rewrite@2568 09075e82-0dd4-0310-85a5-a0d7c8717e4f
-rw-r--r-- | src/Makefile.am | 2 | ||||
-rw-r--r-- | src/list.c | 32 | ||||
-rw-r--r-- | src/list.h | 4 | ||||
-rw-r--r-- | src/player.c | 1 | ||||
-rw-r--r-- | src/song.c | 2 | ||||
-rw-r--r-- | src/tag.c | 47 | ||||
-rw-r--r-- | src/tag.h | 2 | ||||
-rw-r--r-- | src/tagTracker.c | 50 | ||||
-rw-r--r-- | src/tagTracker.h | 10 |
9 files changed, 106 insertions, 44 deletions
diff --git a/src/Makefile.am b/src/Makefile.am index 98a5412fe..8b1f3d1f6 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -51,6 +51,7 @@ mpd_headers = \ song.h \ stats.h \ tag.h \ + tagTracker.h \ utf8.h \ utils.h \ volume.h @@ -93,6 +94,7 @@ mpd_SOURCES = \ song.c \ stats.c \ tag.c \ + tagTracker.c \ utils.c \ volume.c \ utf8.c diff --git a/src/list.c b/src/list.c index c7d49397a..dad4093e6 100644 --- a/src/list.c +++ b/src/list.c @@ -104,7 +104,7 @@ int insertInListBeforeNode(List * list, ListNode * beforeNode, char * key, return 1; } -int insertInList(List * list,char * key,void * data) { +ListNode * insertInList(List * list,char * key,void * data) { ListNode * node; assert(list!=NULL); @@ -137,7 +137,7 @@ int insertInList(List * list,char * key,void * data) { list->numberOfNodes++; - return 1; + return node; } int insertInListWithoutKey(List * list, void * data) { @@ -173,7 +173,7 @@ int insertInListWithoutKey(List * list, void * data) { return 1; } -int findInList(List * list,char * key,void ** data) { +ListNode * findNodeInList(List * list, char * key) { static long high; static long low; static long cur; @@ -191,10 +191,7 @@ int findInList(List * list,char * key,void ** data) { cur = (high+low)/2; tmpNode = list->nodesArray[cur]; cmp = strcmp(tmpNode->key,key); - if(cmp==0) { - if(data) *data = tmpNode->data; - return 1; - } + if(cmp==0) return tmpNode; else if(cmp>0) high = cur; else { if(low==cur) break; @@ -205,10 +202,7 @@ int findInList(List * list,char * key,void ** data) { cur = high; if(cur>=0) { tmpNode = list->nodesArray[cur]; - if(strcmp(tmpNode->key,key)==0) { - (*data) = tmpNode->data; - return 1; - } + if(strcmp(tmpNode->key,key)==0) return tmpNode; } } else { @@ -218,10 +212,18 @@ int findInList(List * list,char * key,void ** data) { tmpNode = tmpNode->nextNode; } - if(tmpNode!=NULL) { - (*data) = tmpNode->data; - return 1; - } + if(tmpNode!=NULL) return tmpNode; + } + + return NULL; +} + +int findInList(List * list, char * key, void ** data) { + ListNode * node = findNodeInList(list, key); + + if(node) { + if(data) *data = node->data; + return 1; } return 0; diff --git a/src/list.h b/src/list.h index 4653237f0..86f4a239a 100644 --- a/src/list.h +++ b/src/list.h @@ -67,7 +67,7 @@ List * makeList(ListFreeDataFunc * freeDataFunc); * _data_ -> data to be inserted in list * returns 1 if successful, 0 otherwise */ -int insertInList(List * list,char * key,void * data); +ListNode * insertInList(List * list,char * key,void * data); int insertInListBeforeNode(List * list, ListNode * beforeNode, char * key, void * data); @@ -93,6 +93,8 @@ void deleteNodeFromList(List * list,ListNode * node); */ int findInList(List * list, char * key, void ** data); +ListNode * findNodeInList(List * list, char * key); + /* frees memory malloc'd for list and its nodes * _list_ -> List to be free'd */ diff --git a/src/player.c b/src/player.c index 8f217b091..5b8298970 100644 --- a/src/player.c +++ b/src/player.c @@ -478,7 +478,6 @@ Song * playerCurrentDecodeSong() { song = newNullSong(); song->utf8url = strdup(pc->currentUrl); song->tag = metadataChunkToMpdTagDup(prev); - validateUtf8Tag(song->tag); ret = song; resetPlayerMetadata(); } diff --git a/src/song.c b/src/song.c index 85a49ecbb..462a434cc 100644 --- a/src/song.c +++ b/src/song.c @@ -59,7 +59,6 @@ Song * newSong(char * utf8url, SONG_TYPE type) { if((plugin = isMusic(utf8url,&(song->mtime)))) { song->tag = plugin->tagDupFunc( rmp2amp(utf8ToFsCharset(utf8url))); - if(song->tag) validateUtf8Tag(song->tag); } if(!song->tag || song->tag->time<0) { freeSong(song); @@ -267,7 +266,6 @@ int updateSongInfo(Song * song) { if((plugin = isMusic(utf8url,&(song->mtime)))) { song->tag = plugin->tagDupFunc( rmp2amp(utf8ToFsCharset(utf8url))); - if(song->tag) validateUtf8Tag(song->tag); } if(!song->tag || song->tag->time<0) return -1; } @@ -25,6 +25,7 @@ #include "inputStream.h" #include "conf.h" #include "charConv.h" +#include "tagTracker.h" #include <sys/stat.h> #include <stdlib.h> @@ -62,25 +63,6 @@ void printMpdTag(FILE * fp, MpdTag * tag) { } } -#define fixUtf8(str) { \ - if(str && !validUtf8String(str)) { \ - char * temp; \ - DEBUG("not valid utf8 in tag: %s\n",str); \ - temp = latin1StrToUtf8Dup(str); \ - free(str); \ - str = temp; \ - } \ -} - -void validateUtf8Tag(MpdTag * tag) { - int i; - - for(i = 0; i < tag->numOfItems; i++) { - fixUtf8(tag->items[i].value); - stripReturnChar(tag->items[i].value); - } -} - #ifdef HAVE_ID3TAG MpdTag * getID3Info(struct id3_tag * tag, char * id, int type, MpdTag * mpdTag) { @@ -172,6 +154,8 @@ MpdTag * newMpdTag() { static void deleteItem(MpdTag * tag, int index) { tag->numOfItems--; + removeTagItemString(tag->items[index].type, tag->items[index].value); + if(tag->numOfItems-index > 0) { memmove(tag->items+index, tag->items+index+1, tag->numOfItems-index); @@ -203,7 +187,7 @@ void clearMpdTag(MpdTag * tag) { int i; for(i = 0; i < tag->numOfItems; i++) { - free(tag->items[i].value); + removeTagItemString(tag->items[i].type, tag->items[i].value); } if(tag->items) free(tag->items); @@ -255,18 +239,35 @@ int mpdTagsAreEqual(MpdTag * tag1, MpdTag * tag2) { return 1; } +#define fixUtf8(str) { \ + if(str && !validUtf8String(str)) { \ + char * temp; \ + DEBUG("not valid utf8 in tag: %s\n",str); \ + temp = latin1StrToUtf8Dup(str); \ + free(str); \ + str = temp; \ + } \ +} + inline static void appendToTagItems(MpdTag * tag, int type, char * value, int len) { int i = tag->numOfItems; + char * temp; + temp = malloc(len+1); + strncpy(temp, value, len); + temp[len] = '\0'; + + fixUtf8(temp); + tag->numOfItems++; tag->items = realloc(tag->items, tag->numOfItems*sizeof(MpdTagItem)); tag->items[i].type = type; - tag->items[i].value = malloc(len+1); - strncpy(tag->items[i].value, value, len); - tag->items[i].value[len] = '\0'; + tag->items[i].value = getTagItemString(type, value); + + free(temp); } void addItemToMpdTagWithLen(MpdTag * tag, int itemType, char * value, int len) { @@ -80,8 +80,6 @@ void printMpdTag(FILE * fp, MpdTag * tag); MpdTag * mpdTagDup(MpdTag * tag); -void validateUtf8Tag(MpdTag * tag); - int mpdTagsAreEqual(MpdTag * tag1, MpdTag * tag2); /* *last shoudl be initialzed to -1 before calling this function */ diff --git a/src/tagTracker.c b/src/tagTracker.c new file mode 100644 index 000000000..fec96550a --- /dev/null +++ b/src/tagTracker.c @@ -0,0 +1,50 @@ +#include "tagTracker.h" + +#include "list.h" + +static List * tagLists[TAG_NUM_OF_ITEM_TYPES] = +{ + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL +}; + +char * getTagItemString(int type, char * string) { + ListNode * node; + + if(tagLists[type] == NULL) { + tagLists[type] = makeList(NULL); + } + + if((node = findNodeInList(tagLists[type], string))) { + (*((int *)node->data))++; + } + else { + int * intPtr = malloc(sizeof(int)); + *intPtr = 1; + node = insertInList(tagLists[type], string, intPtr); + } + + return node->key; +} + +void removeTagItemString(int type, char * string) { + ListNode * node; + + if(tagLists[type] == NULL) return; + + if((node = findNodeInList(tagLists[type], string))) { + int * countPtr = node->data; + *countPtr--; + if(*countPtr <= 0) deleteNodeFromList(tagLists[type], node); + } + + if(tagLists[type]->numberOfNodes == 0) { + freeList(tagLists[type]); + tagLists[type] = NULL; + } +} diff --git a/src/tagTracker.h b/src/tagTracker.h new file mode 100644 index 000000000..c30185e2b --- /dev/null +++ b/src/tagTracker.h @@ -0,0 +1,10 @@ +#ifndef TAG_TRACKER_H +#define TAG_TRACKER_H + +#include "tag.h" + +char * getTagItemString(int type, char * string); + +void removeTagItemString(int type, char * string); + +#endif |