Issue with writing files to an ISO file

Jan 3, 2009 at 3:43 PM

Festive Ken,

 

First of all I want to say “Thank You” for making the .net DiscUtils code available. I’ve been looking for a way to create ISO files without using a third party application. I downloaded the released version of the dll file from the CodeProject web site

(Serve Customized .ISO files from ASP.NET). I used this dll with code I wrote in C# to write an iso image from a directory on my hard drive. The code is listed below. I am able to create the iso image and when I open it with the Ultra ISO program, I am able to view and even extract all files to a temporary folder. The issue I’m having is that when I burn the image to a cd, some files are not written to the cd. I used two test cases: one with 154 files and 17 folders (which worked just fine) and another test of 3910 files and 9 folders (which failed). When I used the ImgBurn program to create the image with the second test case, I get an iso file that is 154 MB in size and I was able to burn this image successfully. When I use the code below against the same folder, I get an image at 147MB in size and was missing files (only 57 files made it to the cd) when I burned it to a cd. I am really dumbfounded because the image with your code/dll file seems to work except when writing the image to an optical disc. I tried to trace the code of the dll (DiscUtils) but cannot find where this possible bug may be. Please advise. Thanks,  Rich

 

using System;

using System.Collections.Generic;

using System.ComponentModel;

using System.Data;

using System.Drawing;

using System.Text;

using System.Windows.Forms;

using System.IO;

using DiscUtils.Iso9660;

 

 

namespace CreateISO

{     

    public partial class Form1 : Form

    {

        int rnc = 0;

 

        public Form1()

        {

            InitializeComponent();

        }

 

        private void Form1_Load(object sender, EventArgs e)

        {

 

        }

 

        public static void PopulateFromFolder(CDBuilder builder, DirectoryInfo di, string basePath)

        {

            int lfc = 0;

 

            foreach (FileInfo file in di.GetFiles())

            {

                builder.AddFile(file.FullName.Substring(basePath.Length), file.FullName);

                //builder.AddFile(file.FullName.Substring(basePath.Length), Encoding.Default.GetBytes(file.FullName));

                lfc++;

            }

           

            foreach (DirectoryInfo dir in di.GetDirectories())

            {

                PopulateFromFolder(builder, dir, basePath);

            }

 

            rnc += lfc;

        }

 

        private void button1_Click(object sender, EventArgs e)

        {

            CDBuilder builder = new CDBuilder();

            builder.UseJoliet = true;

            builder.VolumeIdentifier = "RICHS_DBS";

 

            DirectoryInfo di = new DirectoryInfo("C:\\Temp");

 

            PopulateFromFolder(builder, di, di.FullName);

            MessageBox.Show(rnc.ToString());

 

            FileStream bw = new FileStream("C:\\sample1.iso", FileMode.Create);

 

            Stream cdStream = builder.Build();

            MessageBox.Show(cdStream.Length.ToString());

 

            byte[] buffer = new byte[64 * 1024];

            int numBytes = buffer.Length; // cdStream.Read(buffer, 0, buffer.Length);

 

            while (numBytes != 0)

            {

                numBytes = cdStream.Read(buffer, 0, buffer.Length);

                bw.Write(buffer, 0, numBytes);

            }

 

            cdStream.Close();

            bw.Close();

            //builder.Build(@"C:\sample.iso");

 

            MessageBox.Show("Done");

        }

 

    }

}

Coordinator
Jan 3, 2009 at 10:11 PM
Hi Rich,

Thanks for your feedback.  I've taken a bit of a look, and I've found some bugs around handling for directories with (relatively) large numbers of entries which results in corrupt directory info.  This code illustrates the bug:
CDBuilder builder = new CDBuilder();
builder.UseJoliet = true;
for (int i = 0; i < 3000; ++i)
{
  builder.AddFile("FILE" + i + ".TXT", new byte[] { });
}
CDReader reader = new CDReader(builder.Build(), true);
Assert.AreEqual(3000, reader.Root.GetFiles().Length);

I can't be certain this bug will be the one you're seeing, but it's quite likely.  I'll start investigating.

Cheers,

Ken

 

Coordinator
Jan 3, 2009 at 10:12 PM
This discussion has been copied to a work item. Click here to go to the work item and continue the discussion.