0
0

Hi, I’ve got a project that allows me to populate a listview with music information (length, artist, track id etc) by parsing a M3U file. Every music file in the M3U is loaded via FMOD, its tag information is extracted and the details are placed in the listview. This is fine for small M3U files, but for larger files (I.e. ones that contain several thousand songs) I get memory read/write errors and memory protection errors anywhere after reading a few songs details to reading several hundred songs details. The error(s) appear at different times and appear to be random.

These sort of memory errors from past experience usually indicate that I am not looking after my pointers correctly but I can not see anywhere in the code that I have done something wrong and if I comment out the getTag code (Between the //TAG START and //TAG END comments in the code below) the M3U file is parsed fine without any memory errors. I have tried this code with the latest FMOD and FMOD beta DLL’s.

I have modified the readtags C# example so that it operates in the same way as my code. (I.e. it parses a M3U file and loads each sound, tries to extract the tag information and then unloads the sound.)

Can someone take a look at the code below please and see if I have made any stupid mistakes?

Thanks

[code:142kqq91]/*===============================================================================================
ReadTags Example
Copyright (c), Firelight Technologies Pty, Ltd 2004.

This example shows how to read tags from sound files
===============================================================================================*/

using System;
using System.Drawing;
using System.Collections;
using System.ComponentModel;
using System.Windows.Forms;
using System.Data;
using System.Runtime.InteropServices;

using System.IO;
using System.Threading;
using System.Collections.Generic;

namespace readtags
{
public class ReadTags : System.Windows.Forms.Form
{
private FMOD.System system = null;
private FMOD.Sound sound = null;

    private System.Windows.Forms.Label label;
    private System.Windows.Forms.Button exit_button;
    private System.Windows.Forms.ListBox listBox;
    private OpenFileDialog openFileDialog1;

    private System.ComponentModel.Container components = null;

    public ReadTags()
    {
        InitializeComponent();
    }

    protected override void Dispose( bool disposing )
    {
        if( disposing )
        {
            FMOD.RESULT     result;

            /*
                Shut down
            */
            if (sound != null)
            {
                result = sound.release();
                ERRCHECK(result);
            }
            if (system != null)
            {
                result = system.close();
                ERRCHECK(result);
                result = system.release();
                ERRCHECK(result);
            }

            if (components != null) 
            {
                components.Dispose();
            }
        }
        base.Dispose( disposing );
    }

    #region Windows Form Designer generated code
    /// <summary>
    /// Required method for Designer support - do not modify
    /// the contents of this method with the code editor.
    /// </summary>
    private void InitializeComponent()
    {
        this.label = new System.Windows.Forms.Label();
        this.exit_button = new System.Windows.Forms.Button();
        this.listBox = new System.Windows.Forms.ListBox();
        this.openFileDialog1 = new System.Windows.Forms.OpenFileDialog();
        this.SuspendLayout();
        // 
        // label
        // 
        this.label.Location = new System.Drawing.Point(56, 16);
        this.label.Name = "label";
        this.label.Size = new System.Drawing.Size(264, 32);
        this.label.TabIndex = 7;
        this.label.Text = "Copyright (c) Firelight Technologies 2004-2005";
        this.label.TextAlign = System.Drawing.ContentAlignment.MiddleCenter;
        // 
        // exit_button
        // 
        this.exit_button.Location = new System.Drawing.Point(160, 240);
        this.exit_button.Name = "exit_button";
        this.exit_button.Size = new System.Drawing.Size(72, 24);
        this.exit_button.TabIndex = 14;
        this.exit_button.Text = "Exit";
        this.exit_button.Click += new System.EventHandler(this.exit_button_Click);
        // 
        // listBox
        // 
        this.listBox.Location = new System.Drawing.Point(8, 56);
        this.listBox.Name = "listBox";
        this.listBox.Size = new System.Drawing.Size(360, 173);
        this.listBox.TabIndex = 15;
        // 
        // openFileDialog1
        // 
        this.openFileDialog1.FileName = "openFileDialog1";
        // 
        // ReadTags
        // 
        this.AutoScaleBaseSize = new System.Drawing.Size(5, 13);
        this.ClientSize = new System.Drawing.Size(384, 271);
        this.Controls.Add(this.listBox);
        this.Controls.Add(this.exit_button);
        this.Controls.Add(this.label);
        this.Name = "ReadTags";
        this.Text = "Read Tags Example";
        this.Load += new System.EventHandler(this.ReadTags_Load);
        this.ResumeLayout(false);

    }
    #endregion

    [STAThread]
    static void Main() 
    {
        Application.Run(new ReadTags());
    }

    private void ReadTags_Load(object sender, System.EventArgs e)
    {
        FMOD.TAG        tag = new FMOD.TAG();
        int             numtags = 0, numtagsupdated = 0;
        uint            version = 0;
        FMOD.RESULT     result;

        /*
            Create a System object and initialize.
        */
        result = FMOD.Factory.System_Create(ref system);
        ERRCHECK(result);

        result = system.getVersion(ref version);
        ERRCHECK(result);
        if (version < FMOD.VERSION.number)
        {
            MessageBox.Show("Error!  You are using an old version of FMOD " + version.ToString("X") + ".  This program requires " + FMOD.VERSION.number.ToString("X") + ".");
            Application.Exit();
        }
        result = system.init(100, FMOD.INITFLAG.NORMAL, (IntPtr)null);
        ERRCHECK(result);

        openFileDialog1.Filter = "M3U Playlist (*.m3u)|*.m3u|M3U8 Playlist (*.m3u8)|*.m3u8";
        openFileDialog1.Multiselect = false;
        openFileDialog1.Title = "Choose a playlist to load";

        if (openFileDialog1.ShowDialog() == DialogResult.OK)
        {
            TextReader reader = new StreamReader(openFileDialog1.FileName);

            List<string> listSounds = new List<string>();

            string line;
            while ((line = reader.ReadLine()) != null)
            {
                //Ignore comments
                if (!line.StartsWith("#"))
                    listSounds.Add(line);
            }

            listSounds.TrimExcess();

            reader.Dispose();


            foreach (string strFile in listSounds)
            {
                if (sound != null)
                {
                    result = sound.release();
                    ERRCHECK(result);
                }

                tag = new FMOD.TAG();

                FileInfo fiTemp = new FileInfo(strFile);

                if (fiTemp.Exists)
                {
                    /*
                        Open the specified file. Use FMOD_CREATESTREAM and FMOD_DONTPREBUFFER so it opens quickly
                    */
                    result = system.createSound(fiTemp.FullName, (FMOD.MODE.SOFTWARE | FMOD.MODE._2D | FMOD.MODE.OPENONLY), ref sound);
                    ERRCHECK(result);

                    numtags = 0;
                    numtagsupdated = 0;
                    version = 0;
                    //listBox.Items.Add(fiTemp.FullName);


                    //TAG START

                    /*
                        Read all the tags regardless of whether they're updated or not. Also show the tag type.
                    */
                    result = sound.getNumTags(ref numtags, ref numtagsupdated);
                    ERRCHECK(result);
                    for (int count = 0; count < numtags; count++)
                    {
                        string tagtext = null;

                        result = sound.getTag(null, count, ref tag);
                        ERRCHECK(result);

                        switch (tag.type)
                        {
                            case FMOD.TAGTYPE.UNKNOWN:
                                tagtext = "FMOD_TAGTYPE_UNKNOWN  ";
                                break;

                            case FMOD.TAGTYPE.ID3V1:
                                tagtext = "FMOD_TAGTYPE_ID3V1  ";
                                break;

                            case FMOD.TAGTYPE.ID3V2:
                                tagtext = "FMOD_TAGTYPE_ID3V2  ";
                                break;

                            case FMOD.TAGTYPE.VORBISCOMMENT:
                                tagtext = "FMOD_TAGTYPE_VORBISCOMMENT  ";
                                break;

                            case FMOD.TAGTYPE.SHOUTCAST:
                                tagtext = "FMOD_TAGTYPE_SHOUTCAST  ";
                                break;

                            case FMOD.TAGTYPE.ICECAST:
                                tagtext = "FMOD_TAGTYPE_ICECAST  ";
                                break;

                            case FMOD.TAGTYPE.ASF:
                                tagtext = "FMOD_TAGTYPE_ASF  ";
                                break;

                            case FMOD.TAGTYPE.FMOD:
                                tagtext = "FMOD_TAGTYPE_FMOD  ";
                                break;

                            case FMOD.TAGTYPE.USER:
                                tagtext = "FMOD_TAGTYPE_USER  ";
                                break;
                        }

                        if (tag.datatype == FMOD.TAGDATATYPE.STRING)
                        {
                            tagtext += (tag.name + " = " + Marshal.PtrToStringAnsi(tag.data) + "(" + tag.datalen + " bytes)");
                        }
                        else
                        {
                            tagtext += (tag.name + " = ??? (" + tag.datalen + " bytes)");
                        }

                        listBox.Items.Add(tagtext);

                    }

                    //TAG END

                    listBox.Items.Add(" ");
                }
            }

            system.update();
        }
    }

    private void exit_button_Click(object sender, System.EventArgs e)
    {
        Application.Exit();
    }

    private void ERRCHECK(FMOD.RESULT result)
    {
        if (result != FMOD.RESULT.OK)
        {
            MessageBox.Show("FMOD error! " + result + " - " + FMOD.Error.String(result));
            throw new Exception();
        }
    }
}

}
[/code:142kqq91]

  • You must to post comments
0
0

No one else has this problem?

I get this problem on every computer everytime with big playlists being loaded!

  • You must to post comments
0
0

Can you check .DataLen != 0?

  • You must to post comments
0
0

[quote="Controller":rdjghqos]Can you check .DataLen != 0?[/quote:rdjghqos]

Thanks for the reply. I tried that and on the quick test I did last night the program crashed with a memory read/write error when calling the getTag function. Obviously this was 2 lines before the datalen check could take place but I did notice that the tag structure was successfully populated with data, although this could have been the data from the last run Either way explicitly wiping an data from the tag structure before calling the getTag() function does not help.

Thanks.

  • You must to post comments
0
0

The other day I added the FMOD.MODE.IGNORETAGS option to the createSound() method. So

[code:1fdzschz]result = system.createSound(fiTemp.FullName, (FMOD.MODE.SOFTWARE | FMOD.MODE._2D | FMOD.MODE.OPENONLY), ref sound); [/code:1fdzschz]

became

[code:1fdzschz]result = system.createSound(fiTemp.FullName, (FMOD.MODE.SOFTWARE | FMOD.MODE._2D | FMOD.MODE.OPENONLY) | FMOD.MODE.IGNORETAGS, ref sound); [/code:1fdzschz]

This solved the memory error, but as you can imagine it also stopped any tags from being read. That to me seams to point to the tag data being corrupt or the way getTag reads/handles the data being at fault.

Any ideas?

Thanks

  • You must to post comments
0
0

I experience the same problem hardly every time I read any tags. The files themselves appear to be ok, I wrote them manually with MP3Tag. I also checked the source files for the C# interface but nothing.
The access violation begins usually after the "normal", non-binary tags like AUTHOR, ARTIST, TITLE, etc.
For a start, I restricted it to a maximum of 5 tags to be read from the sound, which of course is not satisfying, but it stops my app crashing every time I load something :)

[code:nxkh0qhn]
if (numTags > 5)
numTags = 10;
for (int count = 0; count < numTags; count++)
{
...
[/code:nxkh0qhn]

  • You must to post comments
0
0

[quote="hallo":fhgdmgqj]I experience the same problem hardly every time I read any tags. The files themselves appear to be ok, I wrote them manually with MP3Tag. I also checked the source files for the C# interface but nothing.
The access violation begins usually after the "normal", non-binary tags like AUTHOR, ARTIST, TITLE, etc.
For a start, I restricted it to a maximum of 5 tags to be read from the sound, which of course is not satisfying, but it stops my app crashing every time I load something :)

[code:fhgdmgqj]
if (numTags > 5)
numTags = 10;
for (int count = 0; count < numTags; count++)
{
...
[/code:fhgdmgqj][/quote:fhgdmgqj]

I tried what you suggested and it didn’t work with my project. It crashed when reading a ‘TITLE’ tag.

  • You must to post comments
0
0

Hi,

I have a similar problem. When trying to get tags from mp3s, I receive the following exception: "AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt."

Would it be possible to have a debug fmodex.dll, so that I can try to have the stack where there is the problem ? This way, maybe I could be a little help…

Thanks a lot

EDIT: The code is in C#, and I’m using VS 2005

  • You must to post comments
Showing 7 results
Your Answer

Please first to submit.