diff --git a/contrib/mt-daapd.playlist b/contrib/mt-daapd.playlist index f17f5902..6064fc62 100644 --- a/contrib/mt-daapd.playlist +++ b/contrib/mt-daapd.playlist @@ -16,6 +16,10 @@ # Album (string) # Genre (string) # Path (string) -- full path to song, including filename +# Composer (string) +# Orchestra (string) +# Conductor (string) +# Grouping (string) -- I don't even know what this is... # Year (int) # # Valid operators include: @@ -46,9 +50,29 @@ # as well as those with a genre of "Techno-Industrial" or # "Trance/Techno", for example. # +# "AAC Files" { +# path includes ".m4a" || +# path includes ".m4p" +# } +# +# This would match all m4a and m4p files -- i.e. iTunes-ripped aac files +# or songs downloaded from iTMS. +# +# "Orchestral Music" { +# Orchestra !IS "" || +# Conductor !IS "" +# } +# +# This would match anything with *anything* entered as a +# orchestra or conductor... this would probably include any +# orchestral music. Kind of ugly, but works! +# # I expect that this language will grow over time. If you want # to hack on it, see src/lexer.l, src/parser.y, and src/playlist.c # +# If there is something missing you particularly want, let me +# (rpedde@users.sourceforge.net) know! +# "60's Music" { Year > 1959 && Year < 1970 diff --git a/src/daap.c b/src/daap.c index 62c1b708..88120cd7 100644 --- a/src/daap.c +++ b/src/daap.c @@ -226,6 +226,8 @@ DAAP_BLOCK *daap_response_songlist(void) { ENUMHANDLE henum; MP3FILE *current; char fdescr[50]; + char *artist; + int artist_len; DPRINTF(ERR_DEBUG,"Preparing to send db items\n"); @@ -253,8 +255,38 @@ DAAP_BLOCK *daap_response_songlist(void) { if(current->album) g = g && daap_add_string(mlit,"asal",current->album); - if(current->artist) + artist=NULL; + artist_len=0; + if(current->orchestra || current->conductor) { + if(current->orchestra) + artist_len += strlen(current->orchestra); + if(current->conductor) + artist_len += strlen(current->conductor); + + artist_len += 3; + + artist=(char*)malloc(artist_len); + if(artist) { + memset(artist,0x0,artist_len); + + if(current->orchestra) + strcat(artist,current->orchestra); + + if(current->orchestra && current->conductor) + strcat(artist," - "); + + if(current->conductor) + strcat(artist,current->conductor); + + g = g && daap_add_string(mlit,"asar",artist); + + free(artist); + artist=NULL; + } else + g=1; + } else if(current->artist) { g = g && daap_add_string(mlit,"asar",current->artist); + } // g = g && daap_add_short(mlit,"asbt",0); /* bpm */ if(current->bitrate) @@ -264,7 +296,12 @@ DAAP_BLOCK *daap_response_songlist(void) { g = g && daap_add_string(mlit,"ascm",current->comment); /* comment */ // g = g && daap_add_char(mlit,"asco",0x0); /* compilation */ - // g = g && daap_add_string(mlit,"ascp",""); /* composer */ + + if(current->composer) + g = g && daap_add_string(mlit,"ascp",current->composer); /* composer */ + + if(current->grouping) + g = g && daap_add_string(mlit,"agrp",current->grouping); /* grouping */ if(current->time_added) { g = g && daap_add_int(mlit,"asda",current->time_added); /* added */ @@ -304,8 +341,8 @@ DAAP_BLOCK *daap_response_songlist(void) { if(current->title) g = g && daap_add_string(mlit,"minm",current->title); /* descr */ - else - g = g && daap_add_string(mlit,"minm",current->fname); /* descr */ + else + g = g && daap_add_string(mlit,"minm",current->fname); // mper (long) // g = g && daap_add_char(mlit,"asdb",0); /* disabled */ diff --git a/src/db-gdbm.c b/src/db-gdbm.c index 257ffe7a..ca1c54fe 100644 --- a/src/db-gdbm.c +++ b/src/db-gdbm.c @@ -38,7 +38,7 @@ #include "playlist.h" #include "redblack.h" -#define DB_VERSION 1 +#define DB_VERSION 2 #define STRLEN(a) (a) ? strlen((a)) + 1 : 1 /* * Typedefs @@ -90,6 +90,10 @@ typedef struct tag_mp3packed { int genre_len; int comment_len; int type_len; + int composer_len; + int orchestra_len; + int conductor_len; + int grouping_len; char data[1]; } MP3PACKED; @@ -448,6 +452,10 @@ datum *db_packrecord(MP3FILE *pmp3) { len += STRLEN(pmp3->genre); len += STRLEN(pmp3->comment); len += STRLEN(pmp3->type); + len += STRLEN(pmp3->composer); + len += STRLEN(pmp3->orchestra); + len += STRLEN(pmp3->conductor); + len += STRLEN(pmp3->grouping); result = (datum*) malloc(sizeof(datum)); if(!result) @@ -489,6 +497,10 @@ datum *db_packrecord(MP3FILE *pmp3) { ppacked->genre_len=STRLEN(pmp3->genre); ppacked->comment_len=STRLEN(pmp3->comment); ppacked->type_len=STRLEN(pmp3->type); + ppacked->composer_len=STRLEN(pmp3->composer); + ppacked->orchestra_len=STRLEN(pmp3->orchestra); + ppacked->conductor_len=STRLEN(pmp3->conductor); + ppacked->grouping_len=STRLEN(pmp3->grouping); offset=0; if(pmp3->path) @@ -523,6 +535,22 @@ datum *db_packrecord(MP3FILE *pmp3) { strncpy(&ppacked->data[offset],pmp3->type,ppacked->type_len); offset+=ppacked->type_len; + if(pmp3->composer) + strncpy(&ppacked->data[offset],pmp3->composer,ppacked->composer_len); + offset+=ppacked->composer_len; + + if(pmp3->orchestra) + strncpy(&ppacked->data[offset],pmp3->orchestra,ppacked->orchestra_len); + offset+=ppacked->orchestra_len; + + if(pmp3->conductor) + strncpy(&ppacked->data[offset],pmp3->conductor,ppacked->conductor_len); + offset+=ppacked->conductor_len; + + if(pmp3->grouping) + strncpy(&ppacked->data[offset],pmp3->grouping,ppacked->grouping_len); + offset+=ppacked->grouping_len; + /* whew */ return result; } @@ -543,6 +571,10 @@ int db_unpackrecord(datum *pdatum, MP3FILE *pmp3) { /* VERSION 1 */ ppacked=(MP3PACKED*)pdatum->dptr; + + if(ppacked->version != DB_VERSION) + log_err(1,"ON-DISK DATABASE VERSION HAS CHANGED! Delete your songs.gdb and restart.\n"); + pmp3->bitrate=ppacked->bitrate; pmp3->samplerate=ppacked->samplerate; pmp3->song_length=ppacked->song_length; @@ -589,6 +621,22 @@ int db_unpackrecord(datum *pdatum, MP3FILE *pmp3) { if(ppacked->type_len > 1) pmp3->type=strdup(&ppacked->data[offset]); offset += ppacked->type_len; + + if(ppacked->composer_len > 1) + pmp3->composer=strdup(&ppacked->data[offset]); + offset += ppacked->composer_len; + + if(ppacked->orchestra_len > 1) + pmp3->orchestra=strdup(&ppacked->data[offset]); + offset += ppacked->orchestra_len; + + if(ppacked->conductor_len > 1) + pmp3->conductor=strdup(&ppacked->data[offset]); + offset += ppacked->conductor_len; + + if(ppacked->grouping_len > 1) + pmp3->grouping=strdup(&ppacked->data[offset]); + offset += ppacked->grouping_len; return 0; } @@ -670,6 +718,11 @@ void db_freefile(MP3FILE *pmp3) { MAYBEFREE(pmp3->album); MAYBEFREE(pmp3->genre); MAYBEFREE(pmp3->comment); + MAYBEFREE(pmp3->type); + MAYBEFREE(pmp3->composer); + MAYBEFREE(pmp3->orchestra); + MAYBEFREE(pmp3->conductor); + MAYBEFREE(pmp3->grouping); } /* diff --git a/src/db-memory.c b/src/db-memory.c index 9390b435..c034f291 100644 --- a/src/db-memory.c +++ b/src/db-memory.c @@ -352,6 +352,18 @@ int db_add(MP3FILE *mp3file) { if(mp3file->type) g = g && (pnew->mp3file.type=strdup(mp3file->type)); + if(mp3file->composer) + g = g && (pnew->mp3file.composer=strdup(mp3file->composer)); + + if(mp3file->orchestra) + g = g && (pnew->mp3file.orchestra=strdup(mp3file->orchestra)); + + if(mp3file->conductor) + g = g && (pnew->mp3file.conductor=strdup(mp3file->conductor)); + + if(mp3file->grouping) + g = g && (pnew->mp3file.grouping=strdup(mp3file->grouping)); + if(!g) { DPRINTF(ERR_WARN,"Malloc error in db_add\n"); db_freerecord(pnew); @@ -394,6 +406,10 @@ void db_freerecord(MP3RECORD *mp3record) { MAYBEFREE(mp3record->mp3file.genre); MAYBEFREE(mp3record->mp3file.comment); MAYBEFREE(mp3record->mp3file.type); + MAYBEFREE(mp3record->mp3file.composer); + MAYBEFREE(mp3record->mp3file.orchestra); + MAYBEFREE(mp3record->mp3file.conductor); + MAYBEFREE(mp3record->mp3file.grouping); free(mp3record); } diff --git a/src/lexer.l b/src/lexer.l index 6e6f0a25..818dc3ea 100644 --- a/src/lexer.l +++ b/src/lexer.l @@ -46,6 +46,10 @@ artist { yylval.ival=ARTIST; return(ARTIST); } album { yylval.ival=ALBUM; return(ALBUM); } genre { yylval.ival=GENRE; return(GENRE); } path { yylval.ival=PATH; return(PATH); } +composer { yylval.ival=COMPOSER; return(COMPOSER); } +orchestra { yylval.ival=ORCHESTRA; return(ORCHESTRA); } +conductor { yylval.ival=CONDUCTOR; return(CONDUCTOR); } +grouping { yylval.ival=GROUPING; return(GROUPING); } year { yylval.ival=YEAR; return(YEAR); } diff --git a/src/mp3-scanner.c b/src/mp3-scanner.c index 5529c968..37e1249c 100644 --- a/src/mp3-scanner.c +++ b/src/mp3-scanner.c @@ -701,6 +701,22 @@ int scan_get_mp3tags(char *file, MP3FILE *pmp3) { used=1; pmp3->album = utf8_text; DPRINTF(ERR_DEBUG," Album: %s\n",utf8_text); + } else if(!strcmp(pid3frame->id,"TCOM")) { + used=1; + pmp3->composer = utf8_text; + DPRINTF(ERR_DEBUG," Composer: %s\n",utf8_text); + } else if(!strcmp(pid3frame->id,"TIT1")) { + used=1; + pmp3->grouping = utf8_text; + DPRINTF(ERR_DEBUG," Grouping: %s\n",utf8_text); + } else if(!strcmp(pid3frame->id,"TPE2")) { + used=1; + pmp3->orchestra = utf8_text; + DPRINTF(ERR_DEBUG," Orchestra: %s\n",utf8_text); + } else if(!strcmp(pid3frame->id,"TPE3")) { + used=1; + pmp3->conductor = utf8_text; + DPRINTF(ERR_DEBUG," Conductor: %s\n",utf8_text); } else if(!strcmp(pid3frame->id,"TCON")) { used=1; pmp3->genre = utf8_text; @@ -776,6 +792,10 @@ int scan_freetags(MP3FILE *pmp3) { MAYBEFREE(pmp3->genre); MAYBEFREE(pmp3->comment); MAYBEFREE(pmp3->type); + MAYBEFREE(pmp3->composer); + MAYBEFREE(pmp3->orchestra); + MAYBEFREE(pmp3->conductor); + MAYBEFREE(pmp3->grouping); return 0; } diff --git a/src/mp3-scanner.h b/src/mp3-scanner.h index 2529f36e..c80725f6 100644 --- a/src/mp3-scanner.h +++ b/src/mp3-scanner.h @@ -25,23 +25,28 @@ typedef struct tag_mp3file { char *path; char *fname; - char *title; - char *artist; - char *album; - char *genre; - char *comment; + char *title; /* TIT2 */ + char *artist; /* TPE1 */ + char *album; /* TALB */ + char *genre; /* TCON */ + char *comment; /* COMM */ char *type; + char *composer; /* TCOM */ + char *orchestra; /* TPE2 */ + char *conductor; /* TPE3 */ + char *grouping; /* TIT1 */ + int bitrate; int samplerate; int song_length; int file_size; - int year; + int year; /* TDRC */ - int track; + int track; /* TRCK */ int total_tracks; - int disc; + int disc; /* TPOS */ int total_discs; int time_added; diff --git a/src/parser.y b/src/parser.y index 58b610cb..7461541f 100644 --- a/src/parser.y +++ b/src/parser.y @@ -57,6 +57,10 @@ int pl_number=2; %token ALBUM %token GENRE %token PATH +%token COMPOSER +%token ORCHESTRA +%token CONDUCTOR +%token GROUPING %token EQUALS %token LESS @@ -117,6 +121,10 @@ strtag: ARTIST | ALBUM | GENRE | PATH +| COMPOSER +| ORCHESTRA +| CONDUCTOR +| GROUPING ; strbool: IS { $$=$1; } diff --git a/src/playlist.c b/src/playlist.c index f523c182..31baa10a 100644 --- a/src/playlist.c +++ b/src/playlist.c @@ -101,6 +101,18 @@ void pl_dump_node(PL_NODE *pnode, int indent) { case PATH: printf("PATH "); break; + case COMPOSER: + printf("COMPOSER "); + break; + case ORCHESTRA: + printf("ORCHESTRA "); + break; + case CONDUCTOR: + printf("CONDUCTOR "); + break; + case GROUPING: + printf("GROUPING "); + break; case YEAR: printf("YEAR "); break; @@ -260,6 +272,18 @@ int pl_eval_node(MP3FILE *pmp3, PL_NODE *pnode) { case PATH: cval=pmp3->path; break; + case COMPOSER: + cval=pmp3->composer; + break; + case ORCHESTRA: + cval=pmp3->orchestra; + break; + case CONDUCTOR: + cval=pmp3->conductor; + break; + case GROUPING: + cval=pmp3->grouping; + break; case YEAR: ival=pmp3->year; break;