1 /*****************************************************************************
2 * info.c : CD digital audio input information routines
3 *****************************************************************************
4 * Copyright (C) 2004 VideoLAN
5 * $Id: info.c 8845 2004-09-29 09:00:41Z rocky $
7 * Authors: Rocky Bernstein <rocky@panix.com>
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
22 *****************************************************************************/
24 /*****************************************************************************
26 *****************************************************************************/
27 #include "callback.h" /* FIXME - reorganize callback.h, cdda.h better */
28 #include "cdda.h" /* private structures. Also #includes vlc things */
29 #include <vlc_playlist.h> /* Has to come *after* cdda.h */
31 #include <cdio/cdio.h>
32 #include <cdio/cdtext.h>
33 #include <cdio/logging.h>
34 #include <cdio/cd_types.h>
41 #define CDDA_MRL_PREFIX "cddax://"
45 #define free_and_dup(var, val) \
47 if (val) var=strdup(val);
50 static void GetCDDBInfo( access_t *p_access, cdda_data_t *p_cdda )
53 cddb_conn_t *conn = cddb_new();
54 const CdIo *p_cdio = p_cdda->p_cdio;
56 dbg_print( (INPUT_DBG_CALL), "" );
59 cddb_log_set_handler (uninit_log_handler);
64 msg_Warn( p_access, "Unable to initialize libcddb" );
68 cddb_set_email_address( conn,
69 config_GetPsz( p_access,
70 MODULE_STRING "-cddb-email") );
71 cddb_set_server_name( conn,
72 config_GetPsz( p_access,
73 MODULE_STRING "-cddb-server") );
74 cddb_set_server_port(conn,
75 config_GetInt( p_access,
76 MODULE_STRING "-cddb-port") );
78 /* Set the location of the local CDDB cache directory.
79 The default location of this directory is */
81 if (!config_GetInt( p_access, MODULE_STRING "-cddb-enable-cache" ))
82 cddb_cache_disable(conn);
84 cddb_cache_set_dir(conn,
85 config_GetPsz( p_access,
86 MODULE_STRING "-cddb-cachedir") );
88 cddb_set_timeout(conn,
89 config_GetInt( p_access, MODULE_STRING "-cddb-timeout") );
92 if (config_GetInt( p_access, MODULE_STRING "-cddb-httpd" ) )
94 cddb_http_enable(conn);
98 cddb_http_disable(conn);
101 p_cdda->cddb.disc = cddb_disc_new();
103 if (!p_cdda->cddb.disc)
105 msg_Err( p_access, "Unable to create CDDB disc structure." );
109 for(i = 0; i < p_cdda->i_tracks; i++)
111 track_t i_track = p_cdda->i_first_track + i;
112 cddb_track_t *t = cddb_track_new();
113 t->frame_offset = cdio_get_track_lba(p_cdio, i_track);
114 cddb_disc_add_track(p_cdda->cddb.disc, t);
117 p_cdda->cddb.disc->length =
118 cdio_get_track_lba(p_cdio, CDIO_CDROM_LEADOUT_TRACK)
119 / CDIO_CD_FRAMES_PER_SEC;
121 if (!cddb_disc_calc_discid(p_cdda->cddb.disc))
123 msg_Err( p_access, "CDDB disc ID calculation failed" );
127 i_matches = cddb_query(conn, p_cdda->cddb.disc);
132 msg_Warn( p_access, "Found %d matches in CDDB. Using first one.",
134 cddb_read(conn, p_cdda->cddb.disc);
136 if (p_cdda->i_debug & INPUT_DBG_CDDB)
137 cddb_disc_print(p_cdda->cddb.disc);
142 msg_Warn( p_access, "CDDB error: %s", cddb_error_str(errno));
150 #endif /*HAVE_LIBCDDB*/
152 #define add_meta_val(FIELD, VLC_META, VAL) \
153 if ( p_cdda->p_meta && VAL) { \
154 vlc_meta_Add( p_cdda->p_meta, VLC_META, VAL ); \
155 dbg_print( INPUT_DBG_META, "field %s: %s\n", VLC_META, VAL ); \
158 #define add_cddb_meta(FIELD, VLC_META) \
159 add_meta_val(FIELD, VLC_META, p_cdda->cddb.disc->FIELD);
161 #define add_cddb_meta_fmt(FIELD, FORMAT_SPEC, VLC_META) \
164 snprintf( psz_buf, sizeof(psz_buf)-1, FORMAT_SPEC, \
165 p_cdda->cddb.disc->FIELD ); \
166 psz_buf[sizeof(psz_buf)-1] = '\0'; \
167 add_meta_val(FIELD, VLC_META, psz_buf); \
170 /* Adds a string-valued entry to the stream and media information if
171 the string is not null or the null string.
173 #define add_info_str(CATEGORY, TITLE, FIELD) \
174 if (FIELD && strlen(FIELD)) { \
175 input_Control( p_cdda->p_input, INPUT_ADD_INFO, CATEGORY, \
176 _(TITLE), "%s", FIELD ); \
179 /* Adds a numeric-valued entry to the stream and media information
180 if the number is not zero. */
181 #define add_info_val(CATEGORY, TITLE, FMT, FIELD) \
183 input_Control( p_cdda->p_input, INPUT_ADD_INFO, CATEGORY, \
184 _(TITLE), FMT, FIELD ); \
187 /* Adds a CDDB string-valued entry to the stream and media information
188 under category "Disc" if the string is not null or the null string.
190 #define add_cddb_disc_info_str(TITLE, FIELD) \
191 add_info_str("Disc", TITLE, p_cdda->cddb.disc->FIELD)
193 /* Adds a CDDB numeric-valued entry to the stream and media information
194 under category "Disc" if the string is not null or the null string.
196 #define add_cddb_disc_info_val(TITLE, FMT, FIELD) \
197 add_info_val("Disc", TITLE, FMT, p_cdda->cddb.disc->FIELD)
199 /* Adds a CD-Text string-valued entry to the stream and media information
200 under category "Disc" if the string is not null or the null string.
202 #define add_cdtext_info_str(CATEGORY, TITLE, INDEX, FIELD) \
203 add_info_str(CATEGORY, TITLE, p_cdda->p_cdtext[INDEX]->field[FIELD])
205 /* Adds a CD-Text string-valued entry to the stream and media information
206 under category "Disc" if the string is not null or the null string.
208 #define add_cdtext_disc_info_str(TITLE, FIELD) \
209 add_cdtext_info_str("Disc", TITLE, 0, FIELD)
213 Gets and saves Meta Information about the CD-DA.
215 In the Control routine, we handle Meta Information requests and
216 basically copy what we've saved here.
218 Meta information is also used elsewhere such as in "stream and
219 media info" or in playlist info. The intialization of CD-Text or CDDB
222 void CDDAMetaInfo( access_t *p_access, int i_track )
224 cdda_data_t *p_cdda = (cdda_data_t *) p_access->p_sys;
226 if ( ! p_cdda ) return;
228 p_cdda->psz_mcn = cdio_get_mcn(p_cdda->p_cdio);
231 if ( p_cdda->b_cddb_enabled )
233 GetCDDBInfo(p_access, p_cdda);
234 if ( p_cdda->cddb.disc )
236 p_cdda->p_meta = vlc_meta_New();
239 add_cddb_meta(title, VLC_META_TITLE);
240 add_cddb_meta(artist, VLC_META_ARTIST);
241 input_Control( p_cdda->p_input, INPUT_SET_NAME,
242 p_cdda->cddb.disc->artist );
246 cddb_track_t *t=cddb_disc_get_track(p_cdda->cddb.disc,
250 if( t->title != NULL )
252 add_meta_val( NULL, VLC_META_TITLE, t->title );
254 if( t->artist != NULL )
256 add_meta_val( NULL, VLC_META_ARTIST, t->artist );
260 add_cddb_meta(genre, VLC_META_GENRE);
261 add_cddb_meta_fmt(year, "%d", VLC_META_DATE );
265 #endif /*HAVE_LIBCDDB*/
268 track_t i = p_cdda->i_tracks;
269 const int i_first_track = p_cdda->i_first_track;
270 char psz_buffer[MSTRTIME_MAX_SIZE];
272 (p_cdda->lsn[i_first_track+i] - p_cdda->lsn[i_first_track])
273 / CDIO_CD_FRAMES_PER_SEC;
275 dbg_print( INPUT_DBG_META, "Duration %ld, tracks %d",
276 (long int) i_duration, p_cdda->i_tracks );
277 input_Control( p_cdda->p_input, INPUT_ADD_INFO,
278 _("Disc"), _("Duration"), "%s",
279 secstotimestr( psz_buffer, i_duration ) );
281 input_Control( p_cdda->p_input, INPUT_ADD_INFO,
282 _("Disc"), _("Tracks"), "%d", p_cdda->i_tracks );
285 if (p_cdda->b_cddb_enabled && p_cdda->cddb.disc)
287 add_cddb_disc_info_str("Artist (CDDB)", artist);
288 add_cddb_disc_info_str("Genre (CDDB)", genre);
289 add_cddb_disc_info_str("Extended Data (CDDB)", ext_data);
290 add_cddb_disc_info_val("Year (CDDB)", "%d", year);
291 add_cddb_disc_info_val("Disc ID (CDDB)", "%x", discid);
292 add_cddb_disc_info_str("Title (CDDB)", title);
293 add_info_str("Disc", "Category (CDDB)",
294 CDDB_CATEGORY[p_cdda->cddb.disc->category]);
297 #endif /*HAVE_LIBCDDB*/
299 p_cdda->p_cdtext[0] = cdio_get_cdtext(p_cdda->p_cdio, 0);
300 if (p_cdda->p_cdtext[0])
302 add_cdtext_disc_info_str("Arranger (CD-Text)", CDTEXT_ARRANGER);
303 add_cdtext_disc_info_str("Composer (CD-Text)", CDTEXT_COMPOSER);
304 add_cdtext_disc_info_str("Disc ID (CD-Text)", CDTEXT_DISCID);
305 add_cdtext_disc_info_str("Genre (CD-Text)", CDTEXT_GENRE);
306 add_cdtext_disc_info_str("Message (CD-Text)", CDTEXT_MESSAGE);
307 add_cdtext_disc_info_str("Performer (CD-Text)", CDTEXT_PERFORMER);
308 add_cdtext_disc_info_str("Songwriter (CD-Text)", CDTEXT_SONGWRITER);
309 add_cdtext_disc_info_str("Title (CD-Text)", CDTEXT_TITLE);
312 for( i = 0 ; i < p_cdda->i_tracks ; i++ )
314 char psz_track[TITLE_MAX];
315 const track_t i_track = i_first_track + i;
316 mtime_t i_duration = (p_cdda->lsn[i_track+1] -
317 p_cdda->lsn[i_track])
318 / CDIO_CD_FRAMES_PER_SEC;
319 snprintf(psz_track, TITLE_MAX, "%s %02d", _("Track"), i_track);
321 input_Control( p_cdda->p_input, INPUT_ADD_INFO, psz_track,
323 secstotimestr( psz_buffer, i_duration ) );
325 p_cdda->p_cdtext[i_track] =
326 cdio_get_cdtext(p_cdda->p_cdio, i_track);
328 if (p_cdda->p_cdtext[i_track])
330 add_cdtext_info_str( psz_track, "Arranger (CD-Text)",
331 i_track, CDTEXT_ARRANGER);
332 add_cdtext_info_str( psz_track, "Composer (CD-Text)",
333 i_track, CDTEXT_COMPOSER);
334 add_cdtext_info_str( psz_track, "Disc ID (CD-Text)",
335 i_track, CDTEXT_DISCID);
336 add_cdtext_info_str( psz_track, "Genre (CD-Text)",
337 i_track, CDTEXT_GENRE);
338 add_cdtext_info_str( psz_track, "Message (CD-Text)",
339 i_track, CDTEXT_MESSAGE);
340 add_cdtext_info_str( psz_track, "Performer (CD-Text)",
341 i_track, CDTEXT_PERFORMER);
342 add_cdtext_info_str( psz_track, "Songwriter (CD-Text)",
343 i_track, CDTEXT_SONGWRITER);
344 add_cdtext_info_str( psz_track, "Title (CD-Text)",
345 i_track, CDTEXT_TITLE);
349 if (p_cdda->b_cddb_enabled)
351 cddb_track_t *t=cddb_disc_get_track(p_cdda->cddb.disc, i);
354 add_info_str(psz_track, "Artist (CDDB)", t->artist);
355 add_info_str(psz_track, "Title (CDDB)", t->title);
356 add_info_str(psz_track, "Extended Data (CDDB)",
360 #endif /*HAVE_LIBCDDB*/
365 #define add_format_str_info(val) \
367 const char *str = val; \
372 strncat(tp, str, TEMP_STR_LEN-(tp-temp_str)); \
375 saw_control_prefix = false; \
379 #define add_format_num_info(val, fmt) \
383 sprintf(num_str, fmt, val); \
384 len=strlen(num_str); \
386 strncat(tp, num_str, TEMP_STR_LEN-(tp-temp_str)); \
389 saw_control_prefix = false; \
394 cdda_data_t *p_cdda, char *psz_cdtext)
396 /* We either don't have CD-Text info, or we do but we prefer to get CDDB
397 which means CDDB has been enabled and we were able to retrieve the info.*/
399 return !psz_cdtext ||
400 (!p_cdda->b_cdtext_prefer && p_cdda->b_cddb_enabled && p_cdda->cddb.disc);
408 Take a format string and expand escape sequences, that is sequences that
409 begin with %, with information from the current CD.
410 The expanded string is returned. Here is a list of escape sequences:
412 %a : The album artist **
413 %A : The album information **
418 %m : The CD-DA Media Catalog Number (MCN)
419 %n : The number of tracks on the CD
420 %p : The artist/performer/composer in the track **
421 %T : The track number **
422 %s : Number of seconds in this track
424 %Y : The year 19xx or 20xx **
428 CDDAFormatStr( const access_t *p_access, cdda_data_t *p_cdda,
429 const char format_str[], const char *mrl, track_t i_track)
431 #define TEMP_STR_SIZE 256
432 #define TEMP_STR_LEN (TEMP_STR_SIZE-1)
433 static char temp_str[TEMP_STR_SIZE];
435 char * tp = temp_str;
436 vlc_bool_t saw_control_prefix = false;
437 size_t format_len = strlen(format_str);
439 memset(temp_str, 0, TEMP_STR_SIZE);
441 for (i=0; i<format_len; i++)
445 if (!saw_control_prefix && format_str[i] != '%')
447 *tp++ = format_str[i];
448 saw_control_prefix = false;
452 switch(format_str[i])
455 if (saw_control_prefix)
459 saw_control_prefix = !saw_control_prefix;
463 if (p_cdda->p_cdtext[0]
464 && p_cdda->p_cdtext[0]->field[CDTEXT_PERFORMER])
465 psz = p_cdda->p_cdtext[0]->field[CDTEXT_PERFORMER];
466 if (want_cddb_info(p_cdda, psz))
467 psz = p_cdda->cddb.disc->artist;
470 if (p_cdda->p_cdtext[0]
471 && p_cdda->p_cdtext[0]->field[CDTEXT_TITLE])
472 psz = p_cdda->p_cdtext[0]->field[CDTEXT_TITLE];
473 if (want_cddb_info(p_cdda, psz))
474 psz = p_cdda->cddb.disc->title;
477 if (!p_cdda->b_cddb_enabled) goto not_special;
478 if (p_cdda->cddb.disc)
480 CDDB_CATEGORY[p_cdda->cddb.disc->category]);
483 if (p_cdda->p_cdtext[0]
484 && p_cdda->p_cdtext[0]->field[CDTEXT_GENRE])
485 psz = p_cdda->p_cdtext[0]->field[CDTEXT_GENRE];
486 if (want_cddb_info(p_cdda, psz))
487 psz = p_cdda->cddb.disc->genre;
490 if (p_cdda->p_cdtext[0]
491 && p_cdda->p_cdtext[0]->field[CDTEXT_DISCID])
492 psz = p_cdda->p_cdtext[0]->field[CDTEXT_DISCID];
493 if (want_cddb_info(p_cdda, psz)) {
494 add_format_num_info(p_cdda->cddb.disc->discid, "%x");
496 add_format_str_info(psz);
499 if (!p_cdda->b_cddb_enabled) goto not_special;
500 if (p_cdda->cddb.disc)
501 add_format_num_info(p_cdda->cddb.disc->year, "%5d");
504 if (p_cdda && p_cdda->b_cddb_enabled && p_cdda->cddb.disc)
506 cddb_track_t *t=cddb_disc_get_track(p_cdda->cddb.disc,
508 if (t != NULL && t->title != NULL)
509 add_format_str_info(t->title);
511 else goto not_special;
514 if (p_cdda->p_cdtext[i_track]
515 && p_cdda->p_cdtext[i_track]->field[CDTEXT_PERFORMER])
516 psz = p_cdda->p_cdtext[i_track]->field[CDTEXT_PERFORMER];
517 if (want_cddb_info(p_cdda, psz))
519 cddb_track_t *t=cddb_disc_get_track(p_cdda->cddb.disc,
521 if (t != NULL && t->artist != NULL)
526 if (p_cdda->p_cdtext[i_track]
527 && p_cdda->p_cdtext[i_track]->field[CDTEXT_MESSAGE])
528 psz = p_cdda->p_cdtext[i_track]->field[CDTEXT_MESSAGE];
529 if (want_cddb_info(p_cdda, psz))
531 cddb_track_t *t=cddb_disc_get_track(p_cdda->cddb.disc,
533 if (t != NULL && t->ext_data != NULL)
539 if (p_cdda->b_cddb_enabled)
541 char psz_buffer[MSTRTIME_MAX_SIZE];
542 mtime_t i_duration = (p_cdda->lsn[i_track+1] -
543 p_cdda->lsn[i_track])
544 / CDIO_CD_FRAMES_PER_SEC;
545 add_format_str_info(secstotimestr( psz_buffer,
547 } else goto not_special;
551 if (p_cdda->p_cdtext[0]
552 && p_cdda->p_cdtext[0]->field[CDTEXT_PERFORMER])
553 psz = p_cdda->p_cdtext[0]->field[CDTEXT_PERFORMER];
556 if (p_cdda->p_cdtext[0]
557 && p_cdda->p_cdtext[0]->field[CDTEXT_TITLE])
558 psz = p_cdda->p_cdtext[0]->field[CDTEXT_TITLE];
561 if (p_cdda->p_cdtext[0]
562 && p_cdda->p_cdtext[0]->field[CDTEXT_GENRE])
563 psz = p_cdda->p_cdtext[0]->field[CDTEXT_GENRE];
566 if (p_cdda->p_cdtext[0]
567 && p_cdda->p_cdtext[0]->field[CDTEXT_DISCID])
568 add_format_str_info(p_cdda->p_cdtext[0]->field[CDTEXT_DISCID]);
571 if (p_cdda->p_cdtext[i_track]
572 && p_cdda->p_cdtext[i_track]->field[CDTEXT_PERFORMER])
573 psz = p_cdda->p_cdtext[i_track]->field[CDTEXT_PERFORMER];
576 if (p_cdda->p_cdtext[i_track]
577 && p_cdda->p_cdtext[i_track]->field[CDTEXT_MESSAGE])
578 psz = p_cdda->p_cdtext[i_track]->field[CDTEXT_MESSAGE];
581 #endif /*HAVE_LIBCDDB*/
584 add_format_str_info(mrl);
588 add_format_str_info(p_cdda->psz_mcn);
592 add_format_num_info(p_cdda->i_tracks, "%d");
596 add_format_num_info(i_track, "%02d");
600 add_format_str_info(psz);
607 *tp++ = format_str[i];
608 saw_control_prefix = false;
611 return strdup(temp_str);
614 /* Adds a string-valued entry to the playlist information under "Track"
615 if the string is not null or the null string.
617 #define add_playlist_track_info_str(TITLE, FIELD) \
618 if (FIELD && strlen(FIELD)) \
620 playlist_ItemAddInfo( p_item, _("Track"), _(TITLE), \
625 CDDACreatePlaylistItem( const access_t *p_access, cdda_data_t *p_cdda,
626 playlist_t *p_playlist, playlist_item_t *p_item,
627 track_t i_track, char *psz_mrl, int psz_mrl_max,
628 const char *psz_source )
630 mtime_t i_duration = (p_cdda->lsn[i_track+1] - p_cdda->lsn[i_track])
631 * (1000000 / CDIO_CD_FRAMES_PER_SEC) ;
633 char *config_varname = MODULE_STRING "-title-format";
635 playlist_item_t *p_child = NULL;
643 if (p_cdda->b_cddb_enabled)
645 config_varname = MODULE_STRING "-cddb-title-format";
647 #endif /*HAVE_LIBCDDB*/
650 psz_title = CDDAFormatStr( p_access, p_cdda,
651 config_GetPsz( p_access, config_varname ),
654 snprintf(psz_mrl, psz_mrl_max, "%s%s@T%u",
655 CDDA_MRL_PREFIX, psz_source, i_track);
657 dbg_print( INPUT_DBG_META, "mrl: %s, title: %s, duration, %ld",
658 psz_mrl, psz_title, (long int) i_duration / 1000000 );
660 p_child = playlist_ItemNew( p_playlist, psz_mrl, psz_title );
661 p_child->input.b_fixed_name = VLC_TRUE;
663 if( !p_child ) return NULL;
665 playlist_NodeAddItem( p_playlist, p_child,
666 p_item->pp_parents[0]->i_view,
667 p_item, PLAYLIST_APPEND, PLAYLIST_END );
668 playlist_CopyParents( p_item, p_child );
673 int CDDAAddMetaToItem( access_t *p_access, cdda_data_t *p_cdda,
674 playlist_item_t *p_item, const char *psz_source,
675 int i_track, vlc_bool_t b_single )
677 vlc_mutex_lock( &p_item->input.lock );
679 add_playlist_track_info_str("Source", psz_source);
680 playlist_ItemAddInfo( p_item, _("Track"), _("Track Number"),
683 if (p_cdda->p_cdtext[0])
685 const cdtext_t *p = p_cdda->p_cdtext[0];
686 add_playlist_track_info_str("Disc Arranger (CD-Text)",
687 p->field[CDTEXT_ARRANGER]);
688 add_playlist_track_info_str("Disc Composer (CD-Text)",
689 p->field[CDTEXT_COMPOSER]);
690 add_playlist_track_info_str("Disc ID (CD-Text)",
691 p->field[CDTEXT_DISCID]);
692 add_playlist_track_info_str("Disc Genre (CD-Text)",
693 p->field[CDTEXT_GENRE]);
694 add_playlist_track_info_str("Disc Message (CD-Text)",
695 p->field[CDTEXT_MESSAGE]);
696 add_playlist_track_info_str("Disc Performer (CD-Text)",
697 p->field[CDTEXT_PERFORMER]);
698 add_playlist_track_info_str("Disc Songwriter (CD-Text)",
699 p->field[CDTEXT_SONGWRITER]);
700 add_playlist_track_info_str("Disc Title (CD-Text)",
701 p->field[CDTEXT_TITLE]);
704 if (p_cdda->p_cdtext[i_track])
706 const cdtext_t *p = p_cdda->p_cdtext[i_track];
707 add_playlist_track_info_str("Arranger (CD-Text)",
708 p->field[CDTEXT_ARRANGER]);
709 add_playlist_track_info_str("Composer (CD-Text)",
710 p->field[CDTEXT_COMPOSER]);
711 add_playlist_track_info_str("Genre (CD-Text)",
712 p->field[CDTEXT_GENRE]);
713 add_playlist_track_info_str("Message (CD-Text)",
714 p->field[CDTEXT_MESSAGE]);
715 add_playlist_track_info_str("Performer (CD-Text)",
716 p->field[CDTEXT_PERFORMER]);
717 add_playlist_track_info_str("Songwriter (CD-Text)",
718 p->field[CDTEXT_SONGWRITER]);
719 add_playlist_track_info_str("Title (CD-Text)",
720 p->field[CDTEXT_TITLE]);
724 if (p_cdda->b_cddb_enabled)
726 cddb_track_t *t=cddb_disc_get_track(p_cdda->cddb.disc,
727 i_track-p_cdda->i_first_track);
729 add_playlist_track_info_str("Disc Album (CDDB)",
730 p_cdda->cddb.disc->title);
731 add_playlist_track_info_str("Disc Artist(s) (CDDB)",
732 p_cdda->cddb.disc->artist);
733 add_playlist_track_info_str("Disc Category (CDDB)",
734 CDDB_CATEGORY[p_cdda->cddb.disc->category]);
735 add_playlist_track_info_str("Disc Genre (CDDB)",
736 p_cdda->cddb.disc->genre);
738 if ( p_cdda->cddb.disc->discid )
740 playlist_ItemAddInfo( p_item, _("Track"), _("Disc ID (CDDB)"),
741 "%x", p_cdda->cddb.disc->discid );
743 if (p_cdda->cddb.disc->year != 0)
745 playlist_ItemAddInfo( p_item, _("Track"), _("Year (CDDB)"),
746 "%5d", p_cdda->cddb.disc->year );
752 add_playlist_track_info_str("Track Artist (CDDB)",
755 add_playlist_track_info_str("Track Title (CDDB)",
759 #endif /*HAVE_LIBCDDB*/
761 vlc_mutex_unlock( &p_item->input.lock );
767 CDDAFixupPlaylist( access_t *p_access, cdda_data_t *p_cdda,
768 const char *psz_source, vlc_bool_t b_single_track )
771 playlist_t * p_playlist;
773 unsigned int psz_mrl_max = strlen(CDDA_MRL_PREFIX) + strlen(psz_source) +
774 strlen("@T") + strlen("100") + 1;
775 const track_t i_first_track = p_cdda->i_first_track;
776 playlist_item_t *p_item;
777 vlc_bool_t b_play = VLC_FALSE;
780 p_cdda->b_cddb_enabled =
781 config_GetInt( p_access, MODULE_STRING "-cddb-enabled" );
782 if( b_single_track && !p_cdda->b_cddb_enabled )
789 psz_mrl = malloc( psz_mrl_max );
791 if( psz_mrl == NULL )
793 msg_Warn( p_access, "out of memory" );
797 p_playlist = (playlist_t *) vlc_object_find( p_access, VLC_OBJECT_PLAYLIST,
801 msg_Warn( p_access, "can't find playlist" );
808 CDDAMetaInfo( p_access, p_cdda->i_track );
812 CDDAMetaInfo( p_access, -1 );
815 p_item = playlist_ItemGetByInput( p_playlist,
816 ((input_thread_t *)p_access->p_parent)->input.p_item );
818 if( p_item == p_playlist->status.p_item && !b_single_track )
829 /*May fill out more information when the playlist user interface becomes
832 track_t i_track = p_cdda->i_track;
834 input_title_t *t = p_cdda->p_title[0] = //i_track-i_first_track] =
835 vlc_input_title_New();
837 asprintf( &t->psz_name, _("Track %i"), i_track );
838 t->i_size = p_access->info.i_size =
839 ( p_cdda->lsn[i_track+1] - p_cdda->lsn[i_track] ) *
840 (int64_t) CDIO_CD_FRAMESIZE_RAW;
842 t->i_length = I64C(1000000) * t->i_size / CDDA_FREQUENCY_SAMPLE / 4;
845 CDDAAddMetaToItem( p_access, p_cdda, p_item, psz_source, i_track,
848 p_cdda->i_titles = 1;
852 playlist_ItemToNode( p_playlist, p_item );
853 for( i = 0 ; i < p_cdda->i_tracks ; i++ )
855 playlist_item_t *p_child;
856 const track_t i_track = i_first_track + i;
857 input_title_t *t = p_cdda->p_title[i] = vlc_input_title_New();
859 asprintf( &t->psz_name, _("Track %i"), i_track );
860 t->i_size = ( p_cdda->lsn[i_track+1] - p_cdda->lsn[i_track] ) *
861 (int64_t) CDIO_CD_FRAMESIZE_RAW;
863 t->i_length = I64C(1000000) * t->i_size / CDDA_FREQUENCY_SAMPLE / 4;
865 p_child = CDDACreatePlaylistItem( p_access, p_cdda, p_playlist,
868 psz_mrl_max, psz_source );
869 CDDAAddMetaToItem( p_access, p_cdda, p_child, psz_source,
872 p_cdda->i_titles = p_cdda->i_tracks; /* should be +1 */
873 p_access->info.i_size =
874 (p_cdda->lsn[i_first_track + p_cdda->i_tracks]
875 - p_cdda->lsn[i_first_track]) * (int64_t) CDIO_CD_FRAMESIZE_RAW;
880 playlist_Control( p_playlist, PLAYLIST_VIEWPLAY,
881 p_playlist->status.i_view,
882 p_playlist->status.p_item, NULL );
885 vlc_object_release( p_playlist );