Exemple #1
0
static MediaInfo* media_from_file(gchar *path, GFileInfo *file_info, const gchar *file_mime)
{
        MediaInfo* media;
        ID3Tag *tag = NULL;

        media = malloc(sizeof(MediaInfo));
        memset(media, 0, sizeof(MediaInfo));

        tag = ID3Tag_New();
        ID3Tag_Link(tag, path);
        if (tag) {
                set_field(&(media->title), tag, ID3FN_TEXT, ID3FID_TITLE);

                set_field(&(media->artist), tag, ID3FN_TEXT, ID3FID_LEADARTIST);

                set_field(&(media->album), tag, ID3FN_TEXT, ID3FID_ALBUM);

                set_field(&(media->genre), tag, ID3FN_TEXT, ID3FID_CONTENTTYPE);
        }
        if (!media->title)
                media->title = g_strdup(g_file_info_get_display_name(file_info));
        media->path = g_strdup(path);
        media->mime = g_strdup(file_mime);

        if (tag)
                ID3Tag_Delete(tag);
        return media;
}
Exemple #2
0
// Reads ID3v2.x tag
// idea of this come from "tag" by Case <*****@*****.**>
int readtag_id3v2 ( apetag *mem_cnt, char* fileName )
{
    ID3Tag*             tag;
    ID3Frame*           frame;
    ID3TagIterator*     iter;
    char*               item = NULL;
    int                 itemSize;
    char*               value = NULL;
    int                 valueSize;
    unsigned long       flags;

    // first - check of id3tag v2 and init 
    if ( (tag = ID3Tag_New ()) == NULL )
    return 1;
    // on some casses its weerrryyy slooowwwwlyyy 65k file take 2-5 sec 
    ID3Tag_LinkWithFlags ( tag, fileName, ID3TT_ID3V2 );
    
    if ( tag == NULL ) {
    ID3Tag_Delete (tag);
    return 0;
    }

    if ( !ID3Tag_HasTagType ( tag, ID3TT_ID3V2 ) ) {
    ID3Tag_Delete (tag);
    return 0;
    }

    if ( (iter = ID3Tag_CreateIterator (tag)) == NULL ) {
    ID3Tag_Delete (tag);
    return 0;
    }

    while ( (frame = ID3TagIterator_GetNext (iter)) != NULL ) {

    libapetag_convertID3v2toAPE ( frame, &item, &itemSize, &value, &valueSize, &flags);

    if ( !item || !value || item[0] == '\0' || value[0] == '\0' )
        continue;
    
    if ( !value || value[0] != '\0' ) {
        PRINT_D4(">id3v2_read>[i%i]%s: [v%i]'%s'\n",itemSize,item,valueSize,value);
        if ( apefrm_getstr (mem_cnt, item) == NULL ) /* noreplece !!! */
            apefrm_add_bin (mem_cnt, flags, itemSize, item, valueSize ,value);
    }
    free ( value );
    free ( item );
    }

    ID3TagIterator_Delete (iter);
    ID3Tag_Delete (tag);

    return 0;
}
Exemple #3
0
static int _id3_set(const gchar *filename, int clear, const gchar *lead_artist,
                    const gchar *content_group, const gchar *title, const gchar *album,
                    const gchar *content_type, const gchar *year, const gchar *comment)
{
  int errors = 0;
  ID3Tag *tag;

  tag = ID3Tag_New();

  if (!tag)
    return 1;

  ID3Tag_Link(tag, filename);

  if (clear)
    ID3Tag_Clear(tag); // TODO

  if (lead_artist) {
    errors += _id3_find_and_set_frame(tag, ID3FID_LEADARTIST, lead_artist);

    if (verbose)
      printf(" * Set ID3 tag lead artist to %s.\n", lead_artist);
  }

  if (content_group) {
    errors += _id3_find_and_set_frame(tag, ID3FID_CONTENTGROUP, content_group);

    if (verbose)
      printf(" * Set ID3 tag content group to %s.\n", content_group);
  }

  if (title) {
    errors += _id3_find_and_set_frame(tag, ID3FID_TITLE, title);

    if (verbose)
      printf(" * Set ID3 tag title to %s.\n", title);
  }

  if (album) {
    errors += _id3_find_and_set_frame(tag, ID3FID_ALBUM, album);

    if (verbose)
      printf(" * Set ID3 tag album to %s.\n", album);
  }

  if (content_type) {
    errors += _id3_find_and_set_frame(tag, ID3FID_CONTENTTYPE, content_type);

    if (verbose)
      printf(" * Set ID3 tag content type to %s.\n", content_type);
  }

  if (year) {
    errors += _id3_find_and_set_frame(tag, ID3FID_YEAR, year);

    if (verbose)
      printf(" * Set ID3 title year to %s.\n", year);
  }

  if (comment) {
    errors += _id3_find_and_set_frame(tag, ID3FID_COMMENT, comment);

    if (verbose)
      printf(" * Set ID3 tag comment to %s.\n", comment);
  }

  if (!errors)
    ID3Tag_Update(tag);

  ID3Tag_Delete(tag);

  return errors;
}
Exemple #4
0
/*
 * Read id3v1.x / id3v2 tag and load data into the File_Tag structure using id3lib functions.
 * Returns true on success, else false.
 * If a tag entry exists (ex: title), we allocate memory, else value stays to NULL
 */
static FLAC__bool local__get_tag(const char *filename, FLAC_Plugin__CanonicalTag *tag)
{
	FILE *file;
	ID3Tag *id3_tag = 0; /* Tag defined by id3lib */
	char *string, *string1;

	FLAC__ASSERT(0 != filename);
	FLAC__ASSERT(0 != tag);

	if(0 == (file = fopen(filename, "r"))) {
#ifdef DEBUG
		fprintf(stderr, _("ERROR while opening file: '%s' (%s).\n\a"), filename, strerror(errno));
#endif
		return false;
	}
	fclose(file); /* We close it cause id3lib opens/closes file itself */


	/* Get data from tag */
	if(0 != (id3_tag = ID3Tag_New())) {
		ID3Frame *id3_frame;
		ID3Field *id3_field;
		luint frm_size;
		luint num_chars;
		size_t field_num = 0; /* First field */

		/* Link the file to the tag */
		frm_size = local__ID3Tag_Link_wrapper(id3_tag, filename);

		string = malloc(ID3V2_MAX_STRING_LEN+1);

		/*********
		 * Title *
		 *********/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_TITLE))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				/* Note: if 'num_chars' is equal to 0, then the field is empty or corrupted! */
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					local__strip(string);
					tag->title = strdup(string);
				}
			}
		}


		/************
		 * Composer *
		 ************/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_COMPOSER))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					local__strip(string);
					tag->composer = strdup(string);
				}
			}
		}


		/**********
		 * Artist *
		 **********/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_LEADARTIST))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					local__strip(string);
					tag->performer = strdup(string);
				}
			}
		}


		/*********
		 * Album *
		 *********/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_ALBUM))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					local__strip(string);
					tag->album = strdup(string);
				}
			}
		}


		/********
		 * Year *
		 ********/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_YEAR))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					char *tmp_str;

					local__strip(string);

					/* Fix for id3lib 3.7.x: if the id3v1.x tag was filled with spaces
					 * instead of zeroes, then the year field contains garbages! */
					tmp_str = string;
					while (isdigit(*tmp_str)) tmp_str++;
					*tmp_str = 0;
					/* End of fix for id3lib 3.7.x */

					local__strip(string);
					tag->year_recorded = strdup(string);
					tag->year_performed = strdup(string);
				}
			}
		}


		/*************************
		 * Track and Total Track *
		 *************************/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_TRACKNUM))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					local__strip(string);

					string1 = strchr(string, '/');
					if (NUMBER_TRACK_FORMATED) {
						if (string1) {
							/* Just to have numbers like this : '01', '05', '12', ... */
							tag->tracks_in_album = malloc(64);
							sprintf(tag->tracks_in_album, "%.2d", atoi(string1+1));
							*string1 = '\0';
						}
						/* Just to have numbers like this : '01', '05', '12', ... */
						tag->track_number = malloc(64);
						sprintf(tag->track_number, "%.2d", atoi(string));
					}
					else {
						if (string1) {
							tag->tracks_in_album = strdup(string1+1);
							*string1 = '\0';
						}
						tag->track_number = strdup(string);
					}
				}
			}
		}


		/*********
		 * Genre *
		 *********/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_CONTENTTYPE))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				/*
				 * We manipulate only the name of the genre
				 */
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					char *tmp;

					local__strip(string);

					if((string[0]=='(') && (tmp=strchr(string, ')')) && (strlen((tmp+1))>0)) {
						/* Convert a genre written as '(3)Dance' into 'Dance' */
						tag->genre = strdup(tmp+1);

					}
					else if((string[0]=='(') && (tmp=strchr(string, ')'))) {
						/* Convert a genre written as '(3)' into 'Dance' */
						*tmp = 0;
						tag->genre = strdup(local__genre_to_string((unsigned)atoi(string+1)));

					}
					else {
						/* Genre is already written as 'Dance' */
						tag->genre = strdup(string);
					}
				}
			}
		}


		/***********
		 * Comment *
		 ***********/
		if(0 != (id3_frame = ID3Tag_FindFrameWithID(id3_tag, ID3FID_COMMENT))) {
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_TEXT))) {
				if((num_chars = local__ID3Field_GetASCII_wrapper(id3_field, string, ID3V2_MAX_STRING_LEN, field_num)) > 0 && string != NULL) {
					local__strip(string);
					tag->comment = strdup(string);
				}
			}
#if 0
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_DESCRIPTION))) {
				char *comment1 = calloc(MAX_STRING_LEN+1);
				num_chars = ID3Field_GetASCII(id3_field, comment1, MAX_STRING_LEN, Item_Num);
				free(comment1);
			}
			if(0 != (id3_field = ID3Frame_GetField(id3_frame, ID3FN_LANGUAGE))) {
				char *comment2 = calloc(MAX_STRING_LEN+1);
				num_chars = ID3Field_GetASCII(id3_field, comment2, MAX_STRING_LEN, Item_Num);
				free(comment2);
			}
#endif
		}
		free(string);

		/* Free allocated data */
		ID3Tag_Delete(id3_tag);
	}

	return true;
}
Exemple #5
0
/* called after all jobs are finshed. Files are cleaned up and renamed */
void job_finisher(_main_data *main_data)
{
    int i;
    static char status_message[(MAX_FILE_PATH_LENGTH + MAX_FILE_NAME_LENGTH) * MAX_NUM_TRACK ];
    static char buffer[(MAX_FILE_PATH_LENGTH + MAX_FILE_NAME_LENGTH) * MAX_NUM_TRACK ];
    static char *wav_file, *enc_file;
    int madewavs = FALSE;
    int mademp3s = FALSE;
    int tracksdone = 0;
    char *s_track_num;
    char *artist;
    ID3Tag *myTag;

    FILE *fp_playlist = NULL;
    char playlist_filespec[ MAX_FILE_PATH_LENGTH + MAX_FILE_NAME_LENGTH ];

    /* Allocate space dynamically.  This is overkill, but certainly won't be a problem. */
    s_track_num = (char *) malloc((main_data->num_tracks + 2) * sizeof(char));
    buffer[0] = 0;

    /* Clean up */
    for(i = 0; i < main_data->num_tracks; i++)
    {
        create_file_names_for_track(main_data, i, &wav_file, &enc_file);

        if(main_data->track[ i ].wav_exist == FALSE)
        {
            unlink(wav_file);
        }
        else if(main_data->track[ i ].make_wav == TRUE)
        {
            madewavs = TRUE;
            sprintf(&buffer[strlen(buffer)], "%d: %s\n", ++tracksdone, file_name_without_path(wav_file));
        }

        main_data->track[ i ].make_wav = FALSE;

        if(main_data->track[ i ].mp3_exist == TRUE && main_data->track[ i ].make_mp3 == TRUE)
        {
            mademp3s = TRUE;

            /* add ID3 tag if requested */
            if(config.cddb_config.create_id3 == TRUE)
            {
                if(!(artist = main_data->track[ i ].artist))
                {
                    artist = main_data->disc_artist;
                }

                // TODO:  fix this to use something like
                //		if (main_data->encoding_type == OGG) {

                if(!strcmp(config.encoder.encoder, "oggenc"))
                {
                    /* set VORBIS tags using vorbistag - added DATE tag - R. Turnbull 1-2-2010 */
                    vorbistag(enc_file,
                              artist,
                              main_data->disc_title,
                              main_data->disc_year,
                              main_data->track[i].title,
                              id3_find_cddb_category(main_data->disc_category),
                              i + 1);
                }
                else if(!strcmp(config.encoder.encoder, "flac"))
                {
                    /* set FLAC tags using metaflac R. Turnbull 1-2-2010 */
                    flactag(enc_file,
                            artist,
                            main_data->disc_title,
                            main_data->disc_year,
                            main_data->track[i].title,
                            id3_find_cddb_category(main_data->disc_category),
                            i + 1);
                }
                else if(!strcmp(config.encoder.encoder, "mppenc"))
                {
                    /* do nothing for for musepack right now -
                        originally supported id3 now wants apev2 tags */
                }
                else
                {
                    /* assume MP3 tag is desired */
                    sprintf(s_track_num,"%d",(i+1));

                    myTag=ID3Tag_New();
                    ID3Tag_Link(myTag,enc_file);

                    set_TagField(myTag, main_data->track[ i ].title, ID3FID_TITLE);
                    set_TagField(myTag, artist, ID3FID_LEADARTIST);
                    set_TagField(myTag, main_data->disc_title, ID3FID_ALBUM);
                    set_TagField(myTag, main_data->disc_year, ID3FID_YEAR);
                    set_TagField(myTag, s_track_num, ID3FID_TRACKNUM);
                    set_TagField(myTag, main_data->disc_category, ID3FID_CONTENTTYPE);
                    ID3Tag_UpdateByTagType(myTag, ID3TT_ID3V2);
                    ID3Tag_Delete(myTag);
                }
            }

            //dc: strcat() is for sissies!
            sprintf(&buffer[strlen(buffer)], "%d: %s\n", ++tracksdone, file_name_without_path(enc_file));

            // tm: basic playlist support - thanks to Mark Tyler
            if(config.cddb_config.create_playlist == TRUE)
            {
                if(fp_playlist == NULL)
                {
                    sprintf(playlist_filespec, "%s/playlist.m3u", file_path_without_name(enc_file));
                    fp_playlist = fopen(playlist_filespec, "w");
                }

                // if we succeeded above, we can now write to this
                if(fp_playlist != NULL)
                {
                    fprintf(fp_playlist, "%s\n", file_name_without_path(enc_file));
                }
            }
        }

        main_data->track[ i ].make_mp3 = FALSE;
    } /* end loop over all tracks */

    free(s_track_num);

    if((config.cddb_config.create_playlist == TRUE) && (fp_playlist != NULL))
    {
        fclose(fp_playlist);
    }

    /* Generate status message */
    sprintf(status_message, _("Tracks Completed: %2d\n\nArtist: %s\nAlbum: %s\n\n%s"),
            tracksdone, main_data->disc_artist, main_data->disc_title, buffer);

    /* show status pop up */
    if(madewavs)
    {
        status_handler(STAT_FINISH_WAV, status_message);
    }
    else if(mademp3s)
    {
        status_handler(STAT_FINISH_MP3, status_message);
    }

    /* Clear status bar */
    main_window_handler(MW_CLEAR_STATUSBAR, NULL, NULL);

    /* Destroy status widget */
    wm_status_frame_handler(WIDGET_DESTROY, WAV, NULL, NULL);

    /* Create select frame */
    select_frame_handler(WIDGET_CREATE, 0, main_data);
    main_window_handler(MW_MODE_SELECT, NULL, NULL);
}
Exemple #6
0
/* Save the ID3 to the file */
void List_SaveID3(HWND hwndApp, HWND hwndList, char *filename)
{
    LV_ITEM lvi;
    ID3ITEM *pItem1;
    int i, items;
    ID3Tag *tag;
    ID3Frame *frame;
    ID3Field *field;
    
    /* Strip the tag first, before completely rewriting it */
    if ((tag = ID3Tag_New()) != NULL)
    {
        ID3Tag_Link(tag, filename);
        ID3Tag_Strip(tag, ID3TT_ALL);
        ID3Tag_Clear(tag);

        if (SendMessage(GetDlgItem(hwndApp, IDC_ID3V2TAG), BM_GETCHECK, 0, 0) == BST_UNCHECKED)
        {
            /* No frames saved */
            ID3Tag_Delete(tag);
            EnableWindow(GetDlgItem(hwndApp, IDC_ID3V2TAG), FALSE);
            ListView_DeleteAllItems(hwndList);
            return;
        }

        /* First get the number of items */
        items = ListView_GetItemCount(hwndList);

        if (items > 0)
        {
            for (i = 0; i < items; i++)
            {
                lvi.mask = LVIF_PARAM;
                lvi.iItem = i;
                lvi.iSubItem = 0;

                if (ListView_GetItem(hwndList, &lvi) == TRUE)
                {
                    pItem1 = (ID3ITEM*)lvi.lParam;

                    frame = ID3Frame_NewID(pItem1->frameId);

                    switch (pItem1->frameId)
                    {
                    case ID3FID_ALBUM:            case ID3FID_BPM:
                    case ID3FID_COMPOSER:         case ID3FID_CONTENTTYPE:
                    case ID3FID_COPYRIGHT:        case ID3FID_DATE:
                    case ID3FID_PLAYLISTDELAY:    case ID3FID_ENCODEDBY:
                    case ID3FID_LYRICIST:         case ID3FID_FILETYPE:
                    case ID3FID_TIME:             case ID3FID_CONTENTGROUP:
                    case ID3FID_TITLE:            case ID3FID_SUBTITLE:
                    case ID3FID_INITIALKEY:       case ID3FID_LANGUAGE:
                    case ID3FID_SONGLEN:          case ID3FID_MEDIATYPE:
                    case ID3FID_ORIGALBUM:        case ID3FID_ORIGFILENAME:
                    case ID3FID_ORIGLYRICIST:     case ID3FID_ORIGARTIST:
                    case ID3FID_ORIGYEAR:         case ID3FID_FILEOWNER:
                    case ID3FID_LEADARTIST:       case ID3FID_BAND:
                    case ID3FID_CONDUCTOR:        case ID3FID_MIXARTIST:
                    case ID3FID_PARTINSET:        case ID3FID_PUBLISHER:
                    case ID3FID_TRACKNUM:         case ID3FID_RECORDINGDATES:
                    case ID3FID_NETRADIOSTATION:  case ID3FID_NETRADIOOWNER:
                    case ID3FID_SIZE:             case ID3FID_ISRC:
                    case ID3FID_ENCODERSETTINGS:  case ID3FID_YEAR:
                    {
                        field = ID3Frame_GetField(frame, ID3FN_TEXT);
                        ID3Field_SetASCII(field, pItem1->aCols[1]);
                        ID3Tag_AddFrame(tag, frame);
                        break;
                    }
                    case ID3FID_USERTEXT:
                    case ID3FID_COMMENT: /* Can also contain an extra language field (but not used now) */
                    case ID3FID_UNSYNCEDLYRICS: /* Can also contain an extra language field (but not used now) */
                    {
                        field = ID3Frame_GetField(frame, ID3FN_DESCRIPTION);
                        ID3Field_SetASCII(field, pItem1->aCols[0]);
                        field = ID3Frame_GetField(frame, ID3FN_TEXT);
                        ID3Field_SetASCII(field, pItem1->aCols[1]);
                        ID3Tag_AddFrame(tag, frame);
                        break;
                    }
                    case ID3FID_WWWAUDIOFILE:     case ID3FID_WWWARTIST:
                    case ID3FID_WWWAUDIOSOURCE:   case ID3FID_WWWCOMMERCIALINFO:
                    case ID3FID_WWWCOPYRIGHT:     case ID3FID_WWWPUBLISHER:
                    case ID3FID_WWWPAYMENT:       case ID3FID_WWWRADIOPAGE:
                    {
                        field = ID3Frame_GetField(frame, ID3FN_URL);
                        ID3Field_SetASCII(field, pItem1->aCols[1]);
                        ID3Tag_AddFrame(tag, frame);
                        break;
                    }
                    case ID3FID_WWWUSER:
                    {
                        field = ID3Frame_GetField(frame, ID3FN_DESCRIPTION);
                        ID3Field_SetASCII(field, pItem1->aCols[0]);
                        field = ID3Frame_GetField(frame, ID3FN_URL);
                        ID3Field_SetASCII(field, pItem1->aCols[1]);
                        ID3Tag_AddFrame(tag, frame);
                        break;
                    }
                    default:
                        break;
                    }
                }
            }
            ID3Tag_UpdateByTagType(tag, ID3TT_ID3V2);
        }

        ID3Tag_Delete(tag);
    }
}
Exemple #7
0
void FillID3List(HWND hwndDlg, HWND hwndList, char *filename)
{
    ID3Tag *tag;
    ID3Frame *frame;
    ID3Field *field;
    ID3_FrameID eFrameID;
    char info[1024];
    int numFrames;
    int i;
    int iItem = 0;


    if ((tag = ID3Tag_New()) != NULL)
    {
        ID3Tag_Link(tag, filename);

        numFrames = ID3Tag_NumFrames(tag);

        for (i = 0; i < numFrames; i++)
        {
            iItem++;

            frame = ID3Tag_GetFrameNum(tag, i);
            eFrameID = ID3Frame_GetID(frame);

            switch (eFrameID)
            {
            case ID3FID_ALBUM:            case ID3FID_BPM:
            case ID3FID_COMPOSER:         case ID3FID_CONTENTTYPE:
            case ID3FID_COPYRIGHT:        case ID3FID_DATE:
            case ID3FID_PLAYLISTDELAY:    case ID3FID_ENCODEDBY:
            case ID3FID_LYRICIST:         case ID3FID_FILETYPE:
            case ID3FID_TIME:             case ID3FID_CONTENTGROUP:
            case ID3FID_TITLE:            case ID3FID_SUBTITLE:
            case ID3FID_INITIALKEY:       case ID3FID_LANGUAGE:
            case ID3FID_SONGLEN:          case ID3FID_MEDIATYPE:
            case ID3FID_ORIGALBUM:        case ID3FID_ORIGFILENAME:
            case ID3FID_ORIGLYRICIST:     case ID3FID_ORIGARTIST:
            case ID3FID_ORIGYEAR:         case ID3FID_FILEOWNER:
            case ID3FID_LEADARTIST:       case ID3FID_BAND:
            case ID3FID_CONDUCTOR:        case ID3FID_MIXARTIST:
            case ID3FID_PARTINSET:        case ID3FID_PUBLISHER:
            case ID3FID_TRACKNUM:         case ID3FID_RECORDINGDATES:
            case ID3FID_NETRADIOSTATION:  case ID3FID_NETRADIOOWNER:
            case ID3FID_SIZE:             case ID3FID_ISRC:
            case ID3FID_ENCODERSETTINGS:  case ID3FID_YEAR:
            {
                LV_ITEM lvi;
                ID3ITEM *pItem = LocalAlloc(LPTR, sizeof(ID3ITEM));

                /* Initialize LV_ITEM members that are common to all items. */
                lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM | LVIF_STATE;
                lvi.state = 0;
                lvi.stateMask = 0;
                lvi.pszText = LPSTR_TEXTCALLBACK;   /* app. maintains text */
                lvi.iImage = 0;
                lvi.iItem = iItem;
                lvi.iSubItem = 0;

                pItem->frameId = eFrameID;
                pItem->aCols[0] = GetFrameDesc(eFrameID);

                field = ID3Frame_GetField(frame, ID3FN_TEXT);
                ID3Field_GetASCII(field, info, 1024, 1);
                if (eFrameID == ID3FID_CONTENTTYPE)
                    pItem->aCols[1] = GetGenre(info);
                else
                    pItem->aCols[1] = DupString(info);

                lvi.lParam = (LPARAM)pItem;    /* item data */

                /* Add the item. */
                ListView_InsertItem(hwndList, &lvi);

                break;
            }
            case ID3FID_USERTEXT:
            case ID3FID_COMMENT: /* Can also contain an extra language field (but not used now) */
            case ID3FID_UNSYNCEDLYRICS: /* Can also contain an extra language field (but not used now) */
            {
                LV_ITEM lvi;
                ID3ITEM *pItem = LocalAlloc(LPTR, sizeof(ID3ITEM));

                /* Initialize LV_ITEM members that are common to all items. */
                lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM | LVIF_STATE;
                lvi.state = 0;
                lvi.stateMask = 0;
                lvi.pszText = LPSTR_TEXTCALLBACK;   /* app. maintains text */
                lvi.iImage = 0;
                lvi.iItem = iItem;
                lvi.iSubItem = 0;

                pItem->frameId = eFrameID;

                field = ID3Frame_GetField(frame, ID3FN_DESCRIPTION);
                ID3Field_GetASCII(field, info, 1024, 1);
                pItem->aCols[0] = DupString(info);

                field = ID3Frame_GetField(frame, ID3FN_TEXT);
                ID3Field_GetASCII(field, info, 1024, 1);
                pItem->aCols[1] = DupString(info);

                lvi.lParam = (LPARAM)pItem;    /* item data */

                /* Add the item. */
                ListView_InsertItem(hwndList, &lvi);

                break;
            }
            case ID3FID_WWWAUDIOFILE:       case ID3FID_WWWARTIST:
            case ID3FID_WWWAUDIOSOURCE:     case ID3FID_WWWCOMMERCIALINFO:
            case ID3FID_WWWCOPYRIGHT:       case ID3FID_WWWPUBLISHER:
            case ID3FID_WWWPAYMENT:         case ID3FID_WWWRADIOPAGE:
            {
                LV_ITEM lvi;
                ID3ITEM *pItem = LocalAlloc(LPTR, sizeof(ID3ITEM));

                /* Initialize LV_ITEM members that are common to all items. */
                lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM | LVIF_STATE;
                lvi.state = 0;
                lvi.stateMask = 0;
                lvi.pszText = LPSTR_TEXTCALLBACK;   /* app. maintains text */
                lvi.iImage = 0;
                lvi.iItem = iItem;
                lvi.iSubItem = 0;

                pItem->frameId = eFrameID;

                pItem->aCols[0] = GetFrameDesc(eFrameID);

                field = ID3Frame_GetField(frame, ID3FN_URL);
                ID3Field_GetASCII(field, info, 1024, 1);
                pItem->aCols[1] = DupString(info);

                lvi.lParam = (LPARAM)pItem;    /* item data */

                /* Add the item. */
                ListView_InsertItem(hwndList, &lvi);

                break;
            }
            case ID3FID_WWWUSER:
            {
                LV_ITEM lvi;
                ID3ITEM *pItem = LocalAlloc(LPTR, sizeof(ID3ITEM));

                /* Initialize LV_ITEM members that are common to all items. */
                lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM | LVIF_STATE;
                lvi.state = 0;
                lvi.stateMask = 0;
                lvi.pszText = LPSTR_TEXTCALLBACK;   /* app. maintains text */
                lvi.iImage = 0;
                lvi.iItem = iItem;
                lvi.iSubItem = 0;

                pItem->frameId = eFrameID;

                field = ID3Frame_GetField(frame, ID3FN_DESCRIPTION);
                ID3Field_GetASCII(field, info, 1024, 1);
                pItem->aCols[0] = DupString(info);

                field = ID3Frame_GetField(frame, ID3FN_URL);
                ID3Field_GetASCII(field, info, 1024, 1);
                pItem->aCols[1] = DupString(info);

                lvi.lParam = (LPARAM)pItem;    /* item data */

                /* Add the item. */
                ListView_InsertItem(hwndList, &lvi);

                break;
            }
            default:
                break;
            }
        }
        ID3Tag_Delete(tag);
    }
}
Exemple #8
0
/* Get the title from the file */
void GetID3FileTitle(char *filename, char *title, char *format)
{
    ID3Tag *tag;
    ID3Frame *frame;
    ID3Field *field;
    char buffer[255];
    int some_info = 0;
    char *in = format;
    char *out = title;
    char *bound = out + (MAX_PATH - 10 - 1);


    if ((tag = ID3Tag_New()) != NULL)
    {
        ID3Tag_Link(tag, filename);

        while (*in && out < bound)
        {
            switch (*in) {
            case '%':
                ++in;
                break;

            default:
                *out++ = *in++;
                continue;
            }

            /* handle % escape sequence */
            switch (*in++) {
            case '0':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_TRACKNUM)) != NULL) {
                    int size;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    lstrcpy(out, buffer); out += size;
                    some_info = 1;
                }
                break;
            case '1':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_LEADARTIST)) != NULL) {
                    int size;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    lstrcpy(out, buffer); out += size;
                    some_info = 1;
                }
                break;
            case '2':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_TITLE)) != NULL) {
                    int size;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    lstrcpy(out, buffer); out += size;
                    some_info = 1;
                }
                break;
            case '3':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_ALBUM)) != NULL) {
                    int size;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    lstrcpy(out, buffer); out += size;
                    some_info = 1;
                }
                break;
            case '4':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_YEAR)) != NULL) {
                    int size;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    lstrcpy(out, buffer); out += size;
                    some_info = 1;
                }
                break;
            case '5':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_COMMENT)) != NULL) {
                    int size;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    lstrcpy(out, buffer); out += size;
                    some_info = 1;
                }
                break;
            case '6':
                if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_CONTENTTYPE)) != NULL) {
                    int size; char *tmp;
                    field = ID3Frame_GetField(frame, ID3FN_TEXT);
                    size = ID3Field_GetASCII(field, buffer, 255, 1);
                    tmp = GetGenre(buffer);
                    lstrcpy(out, tmp); out += size;
                    some_info = 1;
                }
                break;
            case '7':
            {
                char *p=filename+lstrlen(filename);
                int len = 0;
                while (*p != '\\' && p >= filename) { p--; len++; }
                lstrcpy(out, ++p); out += len;
                some_info = 1;
                break;
            }
            }
        }

        ID3Tag_Delete(tag);
    }

    if (!some_info)
    {
        char *p=filename+lstrlen(filename);
        while (*p != '\\' && p >= filename) p--;
        lstrcpy(title,++p);
    }
}
Exemple #9
0
/*
 * Read infos into header of first frame
 */
gboolean
Mpeg_Header_Read_File_Info (gchar *filename, ET_File_Info *ETFileInfo)
{
    /*
     * With id3lib, the header frame couldn't be read if the file contains an ID3v2 tag with an APIC frame
     */
    ID3Tag *id3_tag = NULL;    /* Tag defined by the id3lib */
    const Mp3_Headerinfo* headerInfo = NULL;

    g_return_val_if_fail (filename != NULL || ETFileInfo != NULL, FALSE);

    /* Get size of file */
    ETFileInfo->size = Get_File_Size (filename);

    /* Get data from tag */
    if ( (id3_tag = ID3Tag_New()) == NULL )
        return FALSE;

    /* Link the file to the tag (uses ID3TT_ID3V2 to get header if APIC is present in Tag) */
    ID3Tag_LinkWithFlags(id3_tag,filename,ID3TT_ID3V2);

    if ( (headerInfo = ID3Tag_GetMp3HeaderInfo(id3_tag)) )
    {
        switch (headerInfo->version)
        {
            case MPEGVERSION_1:
                ETFileInfo->version = 1;
                ETFileInfo->mpeg25 = FALSE;
                break;
            case MPEGVERSION_2:
                ETFileInfo->version = 2;
                ETFileInfo->mpeg25 = FALSE;
                break;
            case MPEGVERSION_2_5:
                ETFileInfo->mpeg25 = TRUE;
                ETFileInfo->mpeg25 = FALSE;
                break;
            default:
                break;
        }

        switch (headerInfo->layer)
        {
            case MPEGLAYER_I:
                ETFileInfo->layer = 1;
                break;
            case MPEGLAYER_II:
                ETFileInfo->layer = 2;
                break;
            case MPEGLAYER_III:
                ETFileInfo->layer = 3;
                break;
            default:
                break;
        }

        // Samplerate
        ETFileInfo->samplerate = headerInfo->frequency;

        // Mode -> Seems to be detected but incorrect?!
        switch (headerInfo->modeext)
        {
            case MP3CHANNELMODE_STEREO:
                ETFileInfo->mode = 0;
                break;
            case MP3CHANNELMODE_JOINT_STEREO:
                ETFileInfo->mode = 1;
                break;
            case MP3CHANNELMODE_DUAL_CHANNEL:
                ETFileInfo->mode = 2;
                break;
            case MP3CHANNELMODE_SINGLE_CHANNEL:
                ETFileInfo->mode = 3;
                break;
            default:
                break;
        }

        // Bitrate
        if (headerInfo->vbr_bitrate <= 0)
        {
            ETFileInfo->variable_bitrate = FALSE;
            ETFileInfo->bitrate = headerInfo->bitrate/1000;
        }else
        {
            ETFileInfo->variable_bitrate = TRUE;
            ETFileInfo->bitrate = headerInfo->vbr_bitrate/1000;
        }

        // Duration
        ETFileInfo->duration = headerInfo->time;
    }

    /* Free allocated data */
    ID3Tag_Delete(id3_tag);

    return TRUE;
}
Exemple #10
0
/*
 * Read infos into header of first frame
 */
gboolean Mpeg_Header_Read_File_Info (gchar *filename, ET_File_Info *ETFileInfo)
{
#if (!USE_ID3LIB_4_HEADER)
    FILE *file;
    gulong filesize;


    if (!filename || !ETFileInfo)
        return FALSE;

    /* Get size of file */
    filesize         = Get_File_Size(filename);
    ETFileInfo->size = filesize;


    /*
     * This part was taken from XMMS
     */
    if ((file = fopen(filename, "rb")) != NULL)
    {
        guint32 head;
        unsigned char tmp[4];
        struct frame frm;
        gboolean id3_found = FALSE;

        if (fread(tmp, 1, 4, file) != 4)
        {
            fclose(file);
            return FALSE;
        }

        // Skip data of the ID3v2.x tag (It may contain data similar to mpeg frame 
        // as, for example, in the id3 APIC frame) (patch from Artur Polaczynski)
        if (tmp[0] == 'I' && tmp[1] == 'D' && tmp[2] == '3' && tmp[3] < 0xFF)
        {
            // ID3v2 tag skipeer $49 44 33 yy yy xx zz zz zz zz [zz size]
            long id3v2size;
            fseek(file, 2, SEEK_CUR); // Size is 6-9 position
            if (fread(tmp, 1, 4, file) != 4) // Read bytes of tag size
            {
                fclose(file);
                return FALSE;
            }
            id3v2size = 10 + ( (long)(tmp[3]) | ((long)(tmp[2]) << 7) | ((long)(tmp[1]) << 14) | ((long)(tmp[0]) << 21) );
            fseek(file, id3v2size, SEEK_SET);
            if (fread(tmp, 1, 4, file) != 4) // Read mpeg header
            {
                fclose(file);
                return FALSE;
            }
        }

        head = ((guint32) tmp[0] << 24) | ((guint32) tmp[1] << 16) | ((guint32) tmp[2] << 8) | (guint32) tmp[3];
        while (!mpg123_head_check(head))
        {
            head <<= 8;
            if (fread(tmp, 1, 1, file) != 1)
            {
                fclose(file);
                return FALSE;
            }
            head |= tmp[0];
        }
        if (mpg123_decode_header(&frm, head))
        {
            guchar *buf;
            gdouble tpf;
            gint pos;
            XHEADDATA xing_header;
            guint32 num_frames;

            buf = g_malloc(frm.framesize + 4);
            fseek(file, -4, SEEK_CUR);
            fread(buf, 1, frm.framesize + 4, file);
            xing_header.toc = NULL;
            tpf = mpg123_compute_tpf(&frm);
            // MPEG and Layer version
            ETFileInfo->mpeg25 = frm.mpeg25;
            if (!ETFileInfo->mpeg25)
                ETFileInfo->version = frm.lsf+1;
            ETFileInfo->layer = frm.lay;
            //if (ETFileInfo->mpeg25) g_print("mpeg_level: MPEG 2.5, layer %d\n",ETFileInfo->layer);
            //else                    g_print("mpeg_level: MPEG %d, layer %d\n",ETFileInfo->version,ETFileInfo->layer);

            pos = ftell(file);
            fseek(file, 0, SEEK_END);
            // Variable bitrate? + bitrate
            if ( (ETFileInfo->variable_bitrate=mpg123_get_xing_header(&xing_header,buf)) )
            {
                num_frames = xing_header.frames;
                ETFileInfo->bitrate = (gint) ((xing_header.bytes * 8) / (tpf * xing_header.frames * 1000));
                //g_print("Bitrate: Variable,\navg. bitrate: %d kb/s\n",ETFileInfo->bitrate);
            } else
            {
                num_frames = ((ftell(file) - pos - (id3_found ? 128 : 0)) / mpg123_compute_bpf(&frm)) + 1;
                ETFileInfo->bitrate = tabsel_123[frm.lsf][frm.lay - 1][frm.bitrate_index];
                //g_print("Bitrate: %d kb/s\n",ETFileInfo->bitrate);
            }
            // Samplerate
            ETFileInfo->samplerate = mpg123_freqs[frm.sampling_frequency];
            // Mode
            ETFileInfo->mode = frm.mode;
            //g_print("Samplerate: %ld Hz\n", mpg123_freqs[frm.sampling_frequency]);
            //g_print("%s\nError protection: %s\nCopyright: %s\nOriginal: %s\nEmphasis: %s\n", channel_mode_name(frm.mode), bool_label[frm.error_protection], bool_label[frm.copyright], bool_label[frm.original], emphasis[frm.emphasis]);
            //g_print("%d frames\nFilesize: %lu B\n", num_frames, ftell(file));
            g_free(buf);
        }

        // Duration
        ETFileInfo->duration = mpg123_get_song_time(file)/1000;
        //g_print("time %s\n",Convert_Duration(ETFileInfo->duration));

        fclose(file);
    }else
    {
        gchar *filename_utf8 = filename_to_display(filename);
        Log_Print(LOG_ERROR,_("ERROR while opening file: '%s' (%s)."),filename_utf8,g_strerror(errno));
        g_free(filename_utf8);
        return FALSE;
    }

#else
    // Needs to uncomment some #include at the beginning

    /*
     * With id3lib, the header frame couldn't be read if the file contains an ID3v2 tag with an APIC frame
     */
    gulong filesize;
    ID3Tag *id3_tag = NULL;    /* Tag defined by the id3lib */
    const Mp3_Headerinfo* headerInfo = NULL;


    if (!filename || !ETFileInfo)
        return FALSE;

    /* Get size of file */
    filesize         = Get_File_Size(filename);
    ETFileInfo->size = filesize;

    /* Get data from tag */
    if ( (id3_tag = ID3Tag_New()) == NULL )
        return FALSE;

    /* Link the file to the tag (uses ID3TT_ID3V2 to get header if APIC is present in Tag) */
    ID3Tag_LinkWithFlags(id3_tag,filename,ID3TT_ID3V2);

    /*ID3_STRUCT(Mp3_Headerinfo)
    {
      Mpeg_Layers layer;
      Mpeg_Version version;
      MP3_BitRates bitrate;
      Mp3_ChannelMode channelmode;
      Mp3_ModeExt modeext;
      Mp3_Emphasis emphasis;
      Mp3_Crc crc;
      uint32 vbr_bitrate;           // avg bitrate from xing header
      uint32 frequency;             // samplerate
      uint32 framesize;
      uint32 frames;                // nr of frames
      uint32 time;                  // nr of seconds in song
      bool privatebit;
      bool copyrighted;
      bool original;
    };*/

    if ( (headerInfo = ID3Tag_GetMp3HeaderInfo(id3_tag)) )
    {
        switch (headerInfo->version)
        {
            case MPEGVERSION_1:
                ETFileInfo->version = 1;
                ETFileInfo->mpeg25 = FALSE;
                break;
            case MPEGVERSION_2:
                ETFileInfo->version = 2;
                ETFileInfo->mpeg25 = FALSE;
                break;
            case MPEGVERSION_2_5:
                ETFileInfo->mpeg25 = TRUE;
                ETFileInfo->mpeg25 = FALSE;
                break;
            default:
                break;
        }

        switch (headerInfo->layer)
        {
            case MPEGLAYER_I:
                ETFileInfo->layer = 1;
                break;
            case MPEGLAYER_II:
                ETFileInfo->layer = 2;
                break;
            case MPEGLAYER_III:
                ETFileInfo->layer = 3;
                break;
            default:
                break;
        }

        // Samplerate
        ETFileInfo->samplerate = headerInfo->frequency;

        // Mode -> Seems to be detected but incorrect?!
        switch (headerInfo->modeext)
        {
            case MP3CHANNELMODE_STEREO:
                ETFileInfo->mode = 0;
                break;
            case MP3CHANNELMODE_JOINT_STEREO:
                ETFileInfo->mode = 1;
                break;
            case MP3CHANNELMODE_DUAL_CHANNEL:
                ETFileInfo->mode = 2;
                break;
            case MP3CHANNELMODE_SINGLE_CHANNEL:
                ETFileInfo->mode = 3;
                break;
            default:
                break;
        }

        // Bitrate
        if (headerInfo->vbr_bitrate <= 0)
        {
            ETFileInfo->variable_bitrate = FALSE;
            ETFileInfo->bitrate = headerInfo->bitrate/1000;
        }else
        {
            ETFileInfo->variable_bitrate = TRUE;
            ETFileInfo->bitrate = headerInfo->vbr_bitrate/1000;
        }

        // Duration
        ETFileInfo->duration = headerInfo->time;
    }

    /* Free allocated data */
    ID3Tag_Delete(id3_tag);

#endif

    return TRUE;
}
Exemple #11
0
/* read tags from a file */
FileInfo *filetags_read_file(gchar *filename) 
{
  /* id3lib has some really weird C API. we have to manipulate this
     carefully. also there seems to be code for unicode and stuff liek
     that (esp if you look at libmad). all that is not dealt with
     here.

     the strategy is this: for every file we try to get both v1 and
     v2. we prefer v2 frames over v1 frames (i dont think they are
     called frames in v1). if a v2 frame doesnt exist then we try to
     get it from v1.
  */

  FileInfo *filetag = NULL;
  size_t v1pos = 0, v2pos = 0;
  ID3Tag *id3v1tag = NULL, *id3v2tag = NULL;
  int len = 0;
  char buffer[MAX_STRING_LEN];
  FILE *file = NULL;
  
  /* ok, make sure the file exists first of all. */
  if (!filename) {
    return NULL;
  }

  file = fopen(filename, "r");
  if (file == NULL) {
    return NULL;
  }
  fclose(file);

  /* ok file exists. now get a new tag and link it with filename. */
  filetag = (FileInfo*)g_malloc(sizeof(FileInfo));
  bzero(filetag, sizeof(FileInfo));

  id3v1tag = ID3Tag_New();
  id3v2tag = ID3Tag_New();
  
  v1pos = ID3Tag_LinkWithFlags(id3v1tag, filename, ID3TT_ID3V2);
  v2pos = ID3Tag_LinkWithFlags(id3v2tag, filename, ID3TT_ID3V1);
  
  /* I dont know if we really care about position though. id3lib
   * sources says something about _prepended_bytes. Did I mention I
   * hate C++? id3lib just made it worse. I wonder how libmad's
   * libid3tag would be. */

  /* lets get the following frames: Title, Artist, Album and Time
   * mainly and optionally get things like Genre, Year.
   */

  /* title */
  bzero(buffer, MAX_STRING_LEN*sizeof(char));
  
  len = get_text_field_from_tag(id3v2tag, ID3FID_TITLE, ID3FN_TEXT, buffer, 0);
  if (len == 0) {
    len = get_text_field_from_tag(id3v1tag, ID3FID_TITLE, ID3FN_TEXT, buffer, 0);
  }
  if (len != 0) {
    filetag->title = g_strdup(buffer);
  }

  /* artist: can be one of ID3FID_ORIGARTIST (TOPE), ID3FID_LEADARTIST
     (TPE1), ID3FID_BAND (TPE2), ID3FID_CONDUCTOR (TPE3),
     ID3FID_MIXARTIST (TPE4). We will get it in the order TPE1, TPE2,
     TOPE, TPE3, TPE4. */
  bzero(buffer, MAX_STRING_LEN*sizeof(char));
  len = get_text_field_from_tag(id3v2tag, ID3FID_LEADARTIST,
				ID3FN_TEXT, buffer, 0);
  if (len == 0) {
    len = get_text_field_from_tag(id3v1tag, ID3FID_LEADARTIST,
				  ID3FN_TEXT, buffer, 0);
  }
  if (len != 0) {
    filetag->artist = g_strdup(buffer);
  }
    
  /* album */
  bzero(buffer, MAX_STRING_LEN*sizeof(char));
  len = get_text_field_from_tag(id3v2tag, ID3FID_ALBUM, ID3FN_TEXT, buffer, 0);
  if (len == 0) {
    len = get_text_field_from_tag(id3v1tag, ID3FID_ALBUM, ID3FN_TEXT, buffer, 0);
  }
  if (len != 0) {
    filetag->album = g_strdup(buffer);
  }

  ID3Tag_Delete(id3v1tag);
  ID3Tag_Delete(id3v2tag);
  
  return filetag;
}
int
main( int argc, char *argv[] )
{
  char *filename = NULL;
  ID3Tag *tag;
  
  if (argc != 2)
  {
    printf("*** Usage: %s file\n", argv[0]);
    exit (1);
  }
  filename = argv[1];
  printf("*** Reading %s\n", filename);
  
  if ((tag = ID3Tag_New()) != NULL)
  {
    ID3Frame *frame;

    (void) ID3Tag_Link(tag, filename);
    if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_TITLE)) != NULL)
    {
      ID3Field *field;
      if ((field = ID3Frame_GetField(frame, ID3FN_TEXT)) != NULL)
      {
        char title[1024];
        (void) ID3Field_GetASCII(field, title, 1024);
        printf("Title: %s\n", title);
      }
      else
      {
        printf("Didn't get the field\n");
      }
    }
    else
    {
      printf("Didn't get the frame\n");
    }

    if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_LEADARTIST)) != NULL)
    {
      ID3Field *field;
      if ((field = ID3Frame_GetField(frame, ID3FN_TEXT)) != NULL)
      {
        char artist[1024];
        (void) ID3Field_GetASCII(field, artist, 1024);
        printf("Artist: %s\n", artist);
      }
      else
      {
        printf("Didn't get the field\n");
      }
    }
    else
    {
      printf("Didn't get the frame\n");
    }

    if ((frame = ID3Tag_FindFrameWithID(tag, ID3FID_ALBUM)) != NULL)
    {
      ID3Field *field;
      if ((field = ID3Frame_GetField(frame, ID3FN_TEXT)) != NULL)
      {
        char album[1024];
        (void) ID3Field_GetASCII(field, album, 1024);
        printf("Album: %s\n", album);
      }
      else
      {
        printf("Didn't get the field\n");
      }
    }
    else
    {
      printf("Didn't get the frame\n");
    }
  }
  else
  {
    printf("Didn't get the tag\n");
  }
  exit (0);
}