CTDB: send drivename separately from userAgent

CTDB: include OS version in userAgent
CTDB: send rip quality
LAME: fix VBR options
CTDB: optimize chienSearch
This commit is contained in:
chudov
2011-05-06 20:22:21 +00:00
parent 1cc474e170
commit a6941bc51b
12 changed files with 167 additions and 140 deletions

View File

@@ -376,24 +376,12 @@ namespace CUERipper
try
{
cueSheet.Go();
if ((cueSheet.CTDB.AccResult == HttpStatusCode.NotFound || cueSheet.CTDB.AccResult == HttpStatusCode.OK)
&& audioSource.CorrectionQuality > 0 && audioSource.ErrorsCount == 0)
{
DBEntry confirm = null;
foreach (DBEntry entry in cueSheet.CTDB.Entries)
if (entry.toc.TrackOffsets == selectedDriveInfo.drive.TOC.TrackOffsets && !entry.hasErrors)
confirm = entry;
if (confirm != null)
cueSheet.CTDB.Confirm(confirm);
else
cueSheet.CTDB.Submit(
(int)cueSheet.ArVerify.WorstConfidence() + 1,
audioSource.CorrectionQuality == 0 ? 0 :
100 - (int)(7 * Math.Log(audioSource.ErrorsCount + 1)), // ErrorsCount==1 ~= 95, ErrorsCount==max ~= 5;
cueSheet.Artist,
cueSheet.Title);
}
bool canFix = false;
if (cueSheet.CTDB.AccResult == HttpStatusCode.OK && audioSource.ErrorsCount != 0)
{
@@ -628,7 +616,7 @@ namespace CUERipper
cueSheet.Action = CUEAction.Encode;
this.BeginInvoke((MethodInvoker)delegate() { toolStripStatusLabel1.Text = Properties.Resources.LookingUpVia + " CTDB..."; });
cueSheet.UseCUEToolsDB(true, "CUERipper " + CUESheet.CUEToolsVersion + ": " + selectedDriveInfo.drive.ARName);
cueSheet.UseCUEToolsDB(true, "CUERipper " + CUESheet.CUEToolsVersion, selectedDriveInfo.drive.ARName);
cueSheet.CTDB.UploadHelper.onProgress += new EventHandler<Krystalware.UploadHelper.UploadProgressEventArgs>(UploadProgress);
this.BeginInvoke((MethodInvoker)delegate() { toolStripStatusLabel1.Text = Properties.Resources.LookingUpVia + " AccurateRip..."; });
cueSheet.UseAccurateRip();

View File

@@ -308,6 +308,7 @@ namespace CUETools.AccurateRip
// find offset
fixed (byte* par2ptr = &parity2[pos])
fixed (ushort* chT = rs.chienTable)
{
ushort* par2 = (ushort*)par2ptr;
int* _sigma = stackalloc int[npar];
@@ -354,7 +355,7 @@ namespace CUETools.AccurateRip
err |= synI;
}
int err_count = err == 0 ? 0 : rs.calcSigmaMBM(_sigma, syn);
if (err_count == allowed_errors && (err_count == 0 || rs.chienSearch(_errpos, stridecount + npar, err_count, _sigma)))
if (err_count == allowed_errors && (err_count == 0 || rs.chienSearch(_errpos, stridecount + npar, err_count, _sigma, chT)))
{
actualOffset = offset;
hasErrors = err_count != 0 || ar.CTDBCRC(-offset) != expectedCRC;
@@ -386,7 +387,8 @@ namespace CUETools.AccurateRip
fix.errors = new int[stride];
fixed (byte* par = &parity2[pos])
fixed (ushort* exp = galois.ExpTbl, log = galois.LogTbl)
fixed (ushort* exp = galois.ExpTbl, log = galois.LogTbl, chT = rs.chienTable)
fixed (int* sf = fix.sigma, of = fix.omega, ef = fix.errpos)
{
int* syn = stackalloc int[npar];
int offset = fix.actualOffset;
@@ -437,12 +439,15 @@ namespace CUETools.AccurateRip
if (err != 0)
{
fixed (int* s = &fix.sigma[part, 0], o = &fix.omega[part, 0], e = &fix.errpos[part, 0])
int* s = sf + part * fix.sigma.GetLength(1);
int* o = of + part * fix.omega.GetLength(1);
int* e = ef + part * fix.errpos.GetLength(1);
//fixed (int* s = &fix.sigma[part, 0], o = &fix.omega[part, 0], e = &fix.errpos[part, 0])
{
fix.errors[part] = rs.calcSigmaMBM(s, syn);
fix.hasErrors = true;
fix.correctableErrors += fix.errors[part];
if (fix.errors[part] <= 0 || !rs.chienSearch(e, stridecount + npar, fix.errors[part], s))
if (fix.errors[part] <= 0 || !rs.chienSearch(e, stridecount + npar, fix.errors[part], s, chT))
fix.canRecover = false;
else
galois.mulPoly(o, s, syn, npar / 2 + 1, npar, npar);

View File

@@ -36,6 +36,7 @@
<Reference Include="Interop.HelperFunctionsLib, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion>
<HintPath>.\Interop.HelperFunctionsLib.dll</HintPath>
<Private>False</Private>
</Reference>
<Reference Include="System" />
<Reference Include="System.Drawing" />

View File

@@ -155,7 +155,7 @@ namespace AudioDataPlugIn
#if USEAR
ar.ContactAccurateRip(ArId);
#endif
ctdb.ContactDB("EAC" + m_data.HostVersion + " CTDB 2.1.1: " + m_drivename);
ctdb.ContactDB("EAC" + m_data.HostVersion + " CTDB 2.1.1", m_drivename);
ctdb.Init(true, ar);
this.sequence_ok = true;
this.m_start_pos = 0;
@@ -241,33 +241,20 @@ namespace AudioDataPlugIn
return "";
if (this.sequence_ok)
{
bool is_accurate = (arTest.Position == 0 && this.is_secure_mode) || arTest.CRC32(0) == ar.CRC32(0);
DBEntry confirm = null;
if (ctdb.AccResult == HttpStatusCode.OK)
ctdb.DoVerify();
if ((ctdb.AccResult == HttpStatusCode.NotFound || ctdb.AccResult == HttpStatusCode.OK)
&& is_accurate)
{
foreach (DBEntry entry in ctdb.Entries)
if (entry.toc.TrackOffsets == TOC.TrackOffsets && !entry.hasErrors)
confirm = entry;
if (confirm != null)
ctdb.Confirm(confirm);
else
ctdb.Submit(
#if USEAR
(int)ar.WorstConfidence() + 1,
#else
1,
#endif
(arTest.Position == 0 && this.is_secure_mode) || arTest.CRC32(0) == ar.CRC32(0) ? 100 : 0,
m_data.AlbumArtist,
m_data.AlbumTitle);
}
sw.WriteLine("[CTDB TOCID: {0}] {1}{2}.",
TOC.TOCID,
ctdb.DBStatus ?? "found",
(confirm != null || ctdb.SubStatus == null) ? "" : (", Submit result: " + ctdb.SubStatus));
(ctdb.SubStatus == null) ? "" : (", Submit result: " + ctdb.SubStatus));
foreach (DBEntry entry in ctdb.Entries)
{
string confFormat = (ctdb.Total < 10) ? "{0:0}/{1:0}" :
@@ -284,14 +271,13 @@ namespace AudioDataPlugIn
entry.canRecover ? string.Format("Differs in {0} samples @{1}", entry.repair.CorrectableErrors, entry.repair.AffectedSectors) :
(entry.httpStatus == 0 || entry.httpStatus == HttpStatusCode.OK) ? "No match" :
entry.httpStatus.ToString());
sw.WriteLine("[{0:x8}] ({1}) {2}{3}",
sw.WriteLine("[{0:x8}] ({1}) {2}",
entry.crc,
conf,
status,
(confirm != entry || ctdb.SubStatus == null) ? "" : (", Submit result: " + ctdb.SubStatus));
status);
}
bool canFix = false;
if (ctdb.AccResult == HttpStatusCode.OK && !is_accurate)
if (ctdb.AccResult == HttpStatusCode.OK)
{
foreach (DBEntry entry in ctdb.Entries)
if (entry.hasErrors && entry.canRecover)

View File

@@ -18,6 +18,7 @@ namespace CUETools.CTDB
{
const string urlbase = "http://db.cuetools.net";
string userAgent;
string driveName;
private CDRepairEncode verify;
private CDImageLayout toc;
@@ -38,9 +39,10 @@ namespace CUETools.CTDB
this.uploadHelper = new HttpUploadHelper();
}
public void ContactDB(string userAgent)
public void ContactDB(string userAgent, string driveName)
{
this.userAgent = userAgent;
this.driveName = driveName;
this.userAgent = userAgent + " (" + Environment.OSVersion.VersionString + ")" + (driveName != null ? " (" + driveName + ")" : "");
this.total = 0;
HttpWebRequest req = (HttpWebRequest)WebRequest.Create(urlbase + "/lookup.php?tocid=" + toc.TOCID);
@@ -184,17 +186,22 @@ namespace CUETools.CTDB
return uuidInfo;
}
public string Confirm(DBEntry entry)
public string Submit(int confidence, int quality, string artist, string title)
{
return Submit(1, null, null, !entry.hasParity /*&& entry.conf > 100*/, true, entry.id);
if (this.AccResult != HttpStatusCode.NotFound && this.AccResult != HttpStatusCode.OK)
return this.DBStatus;
DBEntry confirm = null;
foreach (DBEntry entry in this.Entries)
if (entry.toc.TrackOffsets == this.toc.TrackOffsets && !entry.hasErrors)
confirm = entry;
if (confirm != null) confidence = 1;
DoSubmit(confidence, quality, artist, title, false, confirm);
if (subResult == "parity needed")
DoSubmit(confidence, quality, artist, title, true, confirm);
return subResult;
}
public string Submit(int confidence, string artist, string title)
{
return Submit(confidence, artist, title, confidence > 1, false, null);
}
public string Submit(int confidence, string artist, string title, bool upload, bool confirm, string confirmid)
protected string DoSubmit(int confidence, int quality, string artist, string title, bool upload, DBEntry confirm)
{
UploadFile[] files;
if (upload)
@@ -229,8 +236,8 @@ namespace CUETools.CTDB
NameValueCollection form = new NameValueCollection();
if (upload)
form.Add("parityfile", "1");
if (confirm)
form.Add("confirmid", confirmid);
if (confirm != null)
form.Add("confirmid", confirm.id);
form.Add("tocid", toc.TOCID);
form.Add("crc32", ((int)verify.CRC).ToString());
form.Add("trackcrcs", verify.TrackCRCs);
@@ -241,6 +248,9 @@ namespace CUETools.CTDB
form.Add("audiotracks", toc.AudioTracks.ToString());
form.Add("trackoffsets", toc.TrackOffsets);
form.Add("userid", GetUUID());
form.Add("quality", quality.ToString());
if (driveName != null)
form.Add("drivename", driveName);
if (artist != null && artist != "") form.Add("artist", artist);
if (title != null && title != "") form.Add("title", title);
@@ -340,6 +350,8 @@ namespace CUETools.CTDB
public void DoVerify()
{
if (this.AccResult != HttpStatusCode.OK)
return;
foreach (DBEntry entry in entries)
{
if (entry.toc.Pregap != toc.Pregap || entry.toc.AudioLength != toc.AudioLength || entry.stride != verify.Stride / 2)

View File

@@ -29,6 +29,7 @@
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
</PropertyGroup>
<ItemGroup>
<Reference Include="System" />

View File

@@ -105,7 +105,7 @@ namespace CUETools.Codecs.LAME
protected virtual BE_CONFIG MakeConfig()
{
return new BE_CONFIG(_pcm, 128);
return new BE_CONFIG(_pcm);
}
private bool inited = false;
@@ -121,7 +121,7 @@ namespace CUETools.Codecs.LAME
throw new ApplicationException(string.Format("Lame_encDll.beInitStream failed with the error code {0}", LameResult));
m_InBuffer = new byte[m_InputSamples * 2]; //Input buffer is expected as short[]
m_OutBuffer = new byte[m_OutBufferSize];
m_OutBuffer = new byte[Math.Max(65536, m_OutBufferSize)];
if (_IO == null)
_IO = new FileStream(_path, FileMode.Create, FileAccess.Write, FileShare.Read);
@@ -129,7 +129,7 @@ namespace CUETools.Codecs.LAME
inited = true;
}
public void Write(AudioBuffer buff)
public unsafe void Write(AudioBuffer buff)
{
buff.Prepare(this);
@@ -142,6 +142,9 @@ namespace CUETools.Codecs.LAME
int ToCopy = 0;
uint EncodedSize = 0;
uint LameResult;
uint outBufferIndex = 0;
fixed (byte* pBuffer = buffer, pOutBuffer = m_OutBuffer)
{
while (count > 0)
{
if (m_InBufferPos > 0)
@@ -154,13 +157,16 @@ namespace CUETools.Codecs.LAME
if (m_InBufferPos >= m_InBuffer.Length)
{
m_InBufferPos = 0;
if (outBufferIndex > 0)
{
_IO.Write(m_OutBuffer, 0, (int)outBufferIndex);
bytesWritten += outBufferIndex;
outBufferIndex = 0;
}
if ((LameResult = Lame_encDll.EncodeChunk(m_hLameStream, m_InBuffer, m_OutBuffer, ref EncodedSize)) == Lame_encDll.BE_ERR_SUCCESSFUL)
{
if (EncodedSize > 0)
{
_IO.Write(m_OutBuffer, 0, (int)EncodedSize);
bytesWritten += EncodedSize;
}
outBufferIndex += EncodedSize;
}
else
{
@@ -172,13 +178,16 @@ namespace CUETools.Codecs.LAME
{
if (count >= m_InBuffer.Length)
{
if ((LameResult = Lame_encDll.EncodeChunk(m_hLameStream, buffer, index, (uint)m_InBuffer.Length, m_OutBuffer, ref EncodedSize)) == Lame_encDll.BE_ERR_SUCCESSFUL)
if (outBufferIndex + m_OutBufferSize > m_OutBuffer.Length)
{
if (EncodedSize > 0)
{
_IO.Write(m_OutBuffer, 0, (int)EncodedSize);
bytesWritten += EncodedSize;
_IO.Write(m_OutBuffer, 0, (int)outBufferIndex);
bytesWritten += outBufferIndex;
outBufferIndex = 0;
}
if ((LameResult = Lame_encDll.EncodeChunk(m_hLameStream, pBuffer + index, (uint)m_InBuffer.Length, pOutBuffer + outBufferIndex, ref EncodedSize)) == Lame_encDll.BE_ERR_SUCCESSFUL)
{
outBufferIndex += EncodedSize;
}
else
{
@@ -198,6 +207,13 @@ namespace CUETools.Codecs.LAME
}
}
if (outBufferIndex > 0)
{
_IO.Write(m_OutBuffer, 0, (int)outBufferIndex);
bytesWritten += outBufferIndex;
}
}
public virtual int CompressionLevel
{
get
@@ -264,10 +280,23 @@ namespace CUETools.Codecs.LAME
}
}
public enum LAMEEncoderVBRProcessingQuality : uint
{
Best = 0,
Normal = 5,
}
public class LAMEEncoderVBRSettings
{
public LAMEEncoderVBRSettings() { }
public LAMEEncoderVBRSettings()
{
// Iterate through each property and call ResetValue()
foreach (PropertyDescriptor property in TypeDescriptor.GetProperties(this))
property.ResetValue(this);
}
[DefaultValue(LAMEEncoderVBRProcessingQuality.Normal)]
public LAMEEncoderVBRProcessingQuality Quality { get; set; }
}
[AudioEncoderClass("lame VBR", "mp3", false, "V9 V8 V7 V6 V5 V4 V3 V2 V1 V0", "V2", 2, typeof(LAMEEncoderVBRSettings))]
@@ -287,7 +316,7 @@ namespace CUETools.Codecs.LAME
protected override BE_CONFIG MakeConfig()
{
BE_CONFIG Mp3Config = new BE_CONFIG(PCM, 128);
BE_CONFIG Mp3Config = new BE_CONFIG(PCM, 0, (uint)_settings.Quality);
Mp3Config.format.lhv1.bWriteVBRHeader = 1;
Mp3Config.format.lhv1.nMode = MpegMode.JOINT_STEREO;
Mp3Config.format.lhv1.bEnableVBR = 1;
@@ -391,7 +420,7 @@ namespace CUETools.Codecs.LAME
protected override BE_CONFIG MakeConfig()
{
BE_CONFIG Mp3Config = new BE_CONFIG(PCM, _settings.CustomBitrate > 0 ? (uint)_settings.CustomBitrate : bps);
BE_CONFIG Mp3Config = new BE_CONFIG(PCM, _settings.CustomBitrate > 0 ? (uint)_settings.CustomBitrate : bps, 5);
Mp3Config.format.lhv1.bWriteVBRHeader = 1;
Mp3Config.format.lhv1.nMode = _settings.StereoMode;
//Mp3Config.format.lhv1.nVbrMethod = VBRMETHOD.VBR_METHOD_NONE; // --cbr

View File

@@ -137,7 +137,7 @@ namespace CUETools.Codecs.LAME
//[ MarshalAs( UnmanagedType.ByValArray, SizeConst=255-4*4-2 )]
//public byte[] btReserved;//[255-4*sizeof(DWORD) - sizeof( WORD )];
public LHV1(AudioPCMConfig format, uint MpeBitRate)
public LHV1(AudioPCMConfig format, uint MpeBitRate, uint quality)
{
dwStructVersion = 1;
dwStructSize = (uint)Marshal.SizeOf(typeof(BE_CONFIG));
@@ -171,6 +171,7 @@ namespace CUETools.Codecs.LAME
}
switch (MpeBitRate)
{
case 0 :
case 32 :
case 40 :
case 48 :
@@ -217,7 +218,7 @@ namespace CUETools.Codecs.LAME
bStrictIso = 0;
dwMaxBitrate = 0;
dwVbrAbr_bps = 0;
nQuality = 0;
nQuality = (ushort)(quality | ((~quality) << 8));
nVbrMethod = VBRMETHOD.VBR_METHOD_NONE;
nVBRQuality = 0;
}
@@ -243,9 +244,9 @@ namespace CUETools.Codecs.LAME
[FieldOffset(0)]
public ACC acc;
public Format(AudioPCMConfig format, uint MpeBitRate)
public Format(AudioPCMConfig format, uint MpeBitRate, uint quality)
{
lhv1 = new LHV1(format, MpeBitRate);
lhv1 = new LHV1(format, MpeBitRate, quality);
}
}
@@ -259,13 +260,13 @@ namespace CUETools.Codecs.LAME
public uint dwConfig;
public Format format;
public BE_CONFIG(AudioPCMConfig format, uint MpeBitRate)
public BE_CONFIG(AudioPCMConfig format, uint MpeBitRate, uint quality)
{
this.dwConfig = BE_CONFIG_LAME;
this.format = new Format(format, MpeBitRate);
this.format = new Format(format, MpeBitRate, quality);
}
public BE_CONFIG(AudioPCMConfig format)
: this(format, 128)
: this(format, 0, 5)
{
}
}
@@ -356,7 +357,7 @@ namespace CUETools.Codecs.LAME
/// The amount of data written might vary from chunk to chunk</param>
/// <returns>On success: BE_ERR_SUCCESSFUL</returns>
[DllImport("Lame_enc.dll")]
protected static extern uint beEncodeChunk(uint hbeStream, uint nSamples, IntPtr pSamples, [In, Out] byte[] pOutput, ref uint pdwOutput);
protected static extern uint beEncodeChunk(uint hbeStream, uint nSamples, IntPtr pSamples, IntPtr pOutput, ref uint pdwOutput);
/// <summary>
/// Encodes a chunk of samples. Samples are contained in a byte array
@@ -370,20 +371,27 @@ namespace CUETools.Codecs.LAME
/// <param name="pdwOutput">Returns the number of bytes of encoded data written.
/// The amount of data written might vary from chunk to chunk</param>
/// <returns>On success: BE_ERR_SUCCESSFUL</returns>
public static uint EncodeChunk(uint hbeStream, byte[] buffer, int index, uint nBytes, byte[] pOutput, ref uint pdwOutput)
public static unsafe uint EncodeChunk(uint hbeStream, byte *pSamples, uint nBytes, byte* pOutput, ref uint pdwOutput)
{
uint res;
GCHandle handle = GCHandle.Alloc(buffer, GCHandleType.Pinned);
try
{
IntPtr ptr = (IntPtr)(handle.AddrOfPinnedObject().ToInt32()+index);
res = beEncodeChunk(hbeStream, nBytes/2/*Samples*/, ptr, pOutput, ref pdwOutput);
return beEncodeChunk(hbeStream, nBytes / 2/*Samples*/, (IntPtr)pSamples, (IntPtr)pOutput, ref pdwOutput);
}
finally
/// <summary>
/// Encodes a chunk of samples. Samples are contained in a byte array
/// </summary>
/// <param name="hbeStream">Handle of the stream.</param>
/// <param name="buffer">Bytes to encode</param>
/// <param name="index">Position of the first byte to encode</param>
/// <param name="nBytes">Number of bytes to encode (not samples, samples are two byte lenght)</param>
/// <param name="pOutput">Buffer where to write the encoded data.
/// This buffer should be at least of the minimum size returned by beInitStream().</param>
/// <param name="pdwOutput">Returns the number of bytes of encoded data written.
/// The amount of data written might vary from chunk to chunk</param>
/// <returns>On success: BE_ERR_SUCCESSFUL</returns>
public static unsafe uint EncodeChunk(uint hbeStream, byte[] Samples, int index, uint nBytes, byte[] Output, ref uint pdwOutput)
{
handle.Free();
}
return res;
fixed(byte *pSamples = &Samples[index], pOutput = Output)
return beEncodeChunk(hbeStream, nBytes / 2/*Samples*/, (IntPtr)pSamples, (IntPtr)pOutput, ref pdwOutput);
}
/// <summary>

Binary file not shown.

Binary file not shown.

View File

@@ -3191,13 +3191,13 @@ string status = processor.Go();
_padding += _eacLog.Length;
}
public void UseCUEToolsDB(bool submit, string userAgent)
public void UseCUEToolsDB(bool submit, string userAgent, string driveName)
{
ShowProgress((string)"Contacting CUETools database...", 0, null, null);
_CUEToolsDB = new CUEToolsDB(_toc, proxy);
_CUEToolsDB.UploadHelper.onProgress += new EventHandler<Krystalware.UploadHelper.UploadProgressEventArgs>(UploadProgress);
_CUEToolsDB.ContactDB(userAgent);
_CUEToolsDB.ContactDB(userAgent, driveName);
if (!_toc[_toc.TrackCount].IsAudio && DataTrackLength == 0)
foreach (DBEntry e in _CUEToolsDB.Entries)
@@ -4325,11 +4325,8 @@ string status = processor.Go();
else if (_audioEncoderType != AudioEncoderType.NoAudio)
WriteAudioFilesPass(OutputDir, OutputStyle, destLengths, htoaToFile, _action == CUEAction.Verify);
if (_useCUEToolsDB && _CUEToolsDB.AccResult == HttpStatusCode.OK)
{
if (!_useCUEToolsDBFix)
if (_useCUEToolsDB && !_useCUEToolsDBFix)
_CUEToolsDB.DoVerify();
}
_processed = true;
@@ -6311,17 +6308,17 @@ string status = processor.Go();
foreach (DBEntry entry in CTDB.Entries)
if (entry.toc.TrackOffsets == _toc.TrackOffsets && !entry.hasErrors)
return "CUEToolsDB: " + CTDB.Status;
if (ArVerify.WorstConfidence() < 2)
if (ArVerify.WorstConfidence() < 1)
{
CTDB.SubStatus = "will not submit";
return GenerateAccurateRipStatus();
}
CTDB.Submit((int)ArVerify.WorstConfidence(), Artist, Title);
CTDB.Submit((int)ArVerify.WorstConfidence(), 100, Artist, Title);
return GenerateAccurateRipStatus();
}
case "repair":
{
UseCUEToolsDB(false, "CUETools " + CUEToolsVersion);
UseCUEToolsDB(false, "CUETools " + CUEToolsVersion, null);
Action = CUEAction.Verify;
if (CTDB.DBStatus != null)
return CTDB.DBStatus;

View File

@@ -873,7 +873,7 @@ namespace JDP {
if (useLocalDB)
cueSheet.UseLocalDB(_localDB);
if (useCUEToolsDB)
cueSheet.UseCUEToolsDB(false, "CUETools " + CUESheet.CUEToolsVersion);
cueSheet.UseCUEToolsDB(false, "CUETools " + CUESheet.CUEToolsVersion, null);
if (useAR)
cueSheet.UseAccurateRip();