public bool EqualLayouts(CDImageLayout layout)
 {
     return this.TrackCount == layout.TrackCount
         && this.AudioTracks == layout.AudioTracks
         && this.FirstAudio == layout.FirstAudio
         && this.TrackOffsets == layout.TrackOffsets;
 }
예제 #2
0
        public AccurateRipVerify(CDImageLayout toc, IWebProxy proxy)
		{
			this.proxy = proxy;
			_accDisks = new List<AccDisk>();
			_hasLogCRC = false;
			_CRCLOG = new uint[toc.AudioTracks + 1];
			ExceptionStatus = WebExceptionStatus.Pending;
			Init(toc);
		}
		public TestImageGenerator(TestImageGenerator copy)
		{
			this.toc = copy.toc;
			this.seed = copy.seed;
			this.offset = copy.offset;
			this.start = copy.start;
			this.end = copy.end;
			this.errors = copy.errors;
            this.maxStrideErrors = copy.maxStrideErrors;
		}
예제 #4
0
		public CUEToolsDB(CDImageLayout toc, IWebProxy proxy)
		{
			this.toc = toc;
			this.length = (int)toc.AudioLength * 588;
			this.proxy = proxy;
			this.uploadHelper = new HttpUploadHelper();
			this.QueryExceptionStatus = WebExceptionStatus.Pending;
			this.connectTimeout = 15000;
			this.socketTimeout = 30000;
		}
		public TestImageGenerator(CDImageLayout toc, int seed, int offset, int errors, int maxStrideErrors, int start, int end)
		{
			this.toc = toc;
			this.seed = seed;
			this.offset = offset;
			this.start = start;
			this.end = end;
			this.errors = errors;
            this.maxStrideErrors = maxStrideErrors;
		}
		public static CDRepairEncode VerifyNoise(CDImageLayout toc, int seed, int offset, int start, int end, int errors, bool do_verify, bool do_encode)
		{
			if (start < 0 || start > end || end > toc.AudioLength * 588)
				throw new ArgumentOutOfRangeException();
			var src = new NoiseAndErrorsGenerator(AudioPCMConfig.RedBook, end - start, seed, offset + start, errors);
			var buff = new AudioBuffer(src, 588 * 100);
			var ar = new AccurateRipVerify(toc, null);
			var encode = new CDRepairEncode(ar, stride, npar, do_verify, do_encode);
			var rnd = new Random(seed);
			ar.Position = start;
			while (src.Remaining > 0)
			{
				src.Read(buff, rnd.Next(1, buff.Size));
				ar.Write(buff);
			}
			ar.Close();
			return encode;
		}
예제 #7
0
		public static void MyClassInitialize(TestContext testContext)
		{
			toc = new CDImageLayout(1, 1, 1, string.Format("0 {0}", (finalSampleCount / 588).ToString()));
			ar = new AccurateRipVerify(toc, null);
			ar2 = new AccurateRipVerify(toc, null);
			ar3 = new AccurateRipVerify(toc, null);

			new Random(2423).NextBytes(wav);
			new Random(2423).NextBytes(wav2);
			Random rnd = new Random(987);
			for (int i = 0; i < stride / 4; i++ )
				wav2[(int)(rnd.NextDouble() * (wav2.Length - 1))] = (byte)(rnd.NextDouble() * 255);

			AudioBuffer buff = new AudioBuffer(AudioPCMConfig.RedBook, 0);
			CDRepairEncode encode = new CDRepairEncode(ar, stride, npar, false, true);
			buff.Prepare(wav, finalSampleCount);
			ar.Init(toc);
			ar.Write(buff);
			ar.Close(); 
			parity = encode.Parity;
			crc = encode.CRC;

			decode = new CDRepairEncode(ar2, stride, npar, true, false);
			buff.Prepare(wav2, finalSampleCount);
			ar2.Init(toc);
			ar2.Write(buff);
			ar2.Close(); 

			int actualOffset;
			bool hasErrors;
			decode.FindOffset(npar, parity, 0, crc, out actualOffset, out hasErrors);
			fix = decode.VerifyParity(parity, actualOffset);

			decode2 = new CDRepairEncode(ar3, stride, npar, true, false);
			ar3.Init(toc);
			buff.Prepare(new byte[offset * 4], offset);
			ar3.Write(buff);
			buff.Prepare(wav2, finalSampleCount - offset);
			ar3.Write(buff);
			ar3.Close();
			decode2.FindOffset(npar, parity, 0, crc, out actualOffset, out hasErrors);
			fix2 = decode2.VerifyParity(parity, actualOffset);
		}
예제 #8
0
 public DBEntry(CTDBResponseEntry ctdbRespEntry)
 {
     this.syndrome = ctdbRespEntry.syndrome == null
         ? ParityToSyndrome.Parity2Syndrome(1, 1, 8, 8, Convert.FromBase64String(ctdbRespEntry.parity))
         : ParityToSyndrome.Bytes2Syndrome(1, Math.Min(AccurateRipVerify.maxNpar, ctdbRespEntry.npar), Convert.FromBase64String(ctdbRespEntry.syndrome));
     this.conf = ctdbRespEntry.confidence;
     this.stride = ctdbRespEntry.stride * 2;
     this.crc = uint.Parse(ctdbRespEntry.crc32, NumberStyles.HexNumber);
     this.id = ctdbRespEntry.id;
     this.toc = CDImageLayout.FromString(ctdbRespEntry.toc);
     this.hasParity = ctdbRespEntry.hasparity;
     if (ctdbRespEntry.trackcrcs != null)
     {
         var crcs = ctdbRespEntry.trackcrcs.Split(' ');
         if (crcs.Length == this.toc.AudioTracks)
         {
             this.trackcrcs = new uint[crcs.Length];
             for (int i = 0; i < this.trackcrcs.Length; i++)
             {
                 this.trackcrcs[i] = uint.Parse(crcs[i], NumberStyles.HexNumber);
             }
         }
     }
 }
예제 #9
0
 public void UseAccurateRip()
 {
     ShowProgress((string)"Contacting AccurateRip database...", 0, null, null);
     if (!_toc[_toc.TrackCount].IsAudio && DataTrackLength == 0 && _minDataTrackLength.HasValue && _accurateRipId == null && _config.bruteForceDTL)
     {
         uint minDTL = _minDataTrackLength.Value;
         CDImageLayout toc2 = new CDImageLayout(_toc);
         for (uint dtl = minDTL; dtl < minDTL + 75; dtl++)
         {
             toc2[toc2.TrackCount].Length = dtl;
             _arVerify.ContactAccurateRip(AccurateRipVerify.CalculateAccurateRipId(toc2));
             if (_arVerify.ExceptionStatus == WebExceptionStatus.Success)
             {
                 DataTrackLength = dtl;
                 break;
             }
             if (_arVerify.ExceptionStatus != WebExceptionStatus.ProtocolError ||
                 _arVerify.ResponseStatus != HttpStatusCode.NotFound)
                 break;
             ShowProgress((string)"Contacting AccurateRip database...", (dtl - minDTL) / 75.0, null, null);
             CheckStop();
         }
     }
     else
     {
         _arVerify.ContactAccurateRip(_accurateRipId ?? AccurateRipVerify.CalculateAccurateRipId(_toc));
     }
     isUsingAccurateRip = true;
 }
 public bool Equals(CDImageLayout layout, List<string> fullAudioPaths)
 {
     return EqualLayouts(layout) && EqualAudioPaths(fullAudioPaths);
 }
예제 #11
0
        public bool GetCDInformation(CCDMetadata data, bool cdinfo, bool cover, bool lyrics)
        {
            if (Options.CoversSearch == CTDBCoversSearch.None)
                cover = false;

            if (!cdinfo && !cover)
                return false;

            var TOC = new CDImageLayout();
            for (int i = 0; i < data.NumberOfTracks; i++)
            {
                uint start = data.GetTrackStartPosition(i);
                uint next = data.GetTrackEndPosition(i);
                TOC.AddTrack(new CDTrack(
                    (uint)i + 1,
                    start,
                    next - start,
                    !data.GetTrackDataTrack(i),
                    data.GetTrackPreemphasis(i)));
            }
            TOC[1][0].Start = 0U;

            var ctdb = new CUEToolsDB(TOC, null);
            var form = new CUETools.CTDB.EACPlugin.FormMetadata(ctdb, "EAC" + data.HostVersion + " CTDB 2.1.4", cdinfo, cover);
            form.ShowDialog();
            var meta = form.Meta;
            if (meta == null)
                return false;

            if (cdinfo)
            {
                int year, disccount, discnumber;
                string extra = meta.extra ?? "";
                if (!string.IsNullOrEmpty(meta.discname))
                    extra += "Disc name: " + meta.discname + "\r\n";
                if (!string.IsNullOrEmpty(meta.infourl))
                    extra += "Info URL: " + meta.infourl + "\r\n";
                if (!string.IsNullOrEmpty(meta.barcode))
                    extra += "Barcode: " + meta.barcode + "\r\n";
                if (!string.IsNullOrEmpty(meta.releasedate))
                    extra += "Release date: " + meta.releasedate + "\r\n";
                if (!string.IsNullOrEmpty(meta.country))
                    extra += "Release country: " + meta.country + "\r\n";
                if (meta.label != null)
                    foreach (var label in meta.label)
                    {
                        if (!string.IsNullOrEmpty(label.name))
                            extra += "Release label: " + label.name + "\r\n";
                        if (!string.IsNullOrEmpty(label.catno))
                            extra += "Release catalog#: " + label.catno + "\r\n";
                    }
                data.Year = meta.year != null && int.TryParse(meta.year, out year) ? year : -1;
                data.TotalNumberOfCDs = meta.disccount != null && int.TryParse(meta.disccount, out disccount) ? disccount : 1;
                data.CDNumber = meta.discnumber != null && int.TryParse(meta.discnumber, out discnumber) ? discnumber : 1;
                data.FirstTrackNumber = 1;
                data.AlbumTitle = meta.album ?? "";
                data.AlbumArtist = meta.artist ?? "";
                data.MP3V2Type = meta.genre ?? "";
                data.CDDBMusicType = GetFreeDBMusicType(meta);
                data.MP3Type = GetMP3MusicType(data.CDDBMusicType);
                data.ExtendedDiscInformation = extra;
                data.Revision = -1; // TODO: meta.id? rock/ffffffff/16?
                if (meta.track != null)
                {
                    int firstAudio = meta.track.Length == TOC.AudioTracks ? TOC.FirstAudio - 1 : 0;
                    for (int track = 0; track < data.NumberOfTracks; track++)
                    {
                        if (track - firstAudio >= 0 && track - firstAudio < meta.track.Length)
                        {
                            data.SetTrackTitle(track, meta.track[track - firstAudio].name ?? "");
                            data.SetTrackArtist(track, meta.track[track - firstAudio].artist ?? meta.artist ?? "");
                            data.SetExtendedTrackInformation(track, meta.track[track - firstAudio].extra ?? "");
                        }
                        else if (!TOC[track + 1].IsAudio)
                        {
                            data.SetTrackTitle(track, "[data track]");
                            data.SetTrackArtist(track, meta.artist ?? "");
                            data.SetExtendedTrackInformation(track, "");
                        }
                        else
                        {
                            data.SetTrackTitle(track, "");
                            data.SetTrackArtist(track, meta.artist ?? "");
                            data.SetExtendedTrackInformation(track, "");
                        }
                        data.SetTrackComposer(track, "");
                    }
                }
            }

            if (cover)
            {                
                data.CoverImage = null;
                data.CoverImageURL = "";
                if (form.Image != null)
                {
                    data.CoverImage = form.Image.Data;
                    data.CoverImageURL = form.Image.URL;
                }
            }

            return true;
        }
		public static CDRepairEncode VerifyNoise(string trackoffsets, int seed, int offset, int errors, bool do_verify, bool do_encode)
		{
			var toc = new CDImageLayout(trackoffsets);
			return VerifyNoise(toc, seed, offset, 0, (int)toc.AudioLength * 588, errors, do_verify, do_encode);
		}
예제 #13
0
		public void Close()
		{
			UserData = null;
			C2Count = null;
			if (m_device != null)
				m_device.Close();
			m_device = null;
			_toc = null;
			_toc2 = null;
			gapsDetected = false;
			readCommandFound = false;
			_currentStart = -1;
			_currentEnd = -1;
		}
예제 #14
0
 public CUESheet(CUEConfig config)
 {
     _config = config;
     _progress = new CUEToolsProgressEventArgs();
     _progress.cueSheet = this;
     _attributes = new List<CUELine>();
     _tracks = new List<TrackInfo>();
     _trackFilenames = new List<string>();
     _toc = new CDImageLayout();
     _sources = new List<SourceInfo>();
     _sourcePaths = new List<string>();
     _stop = false;
     _pause = false;
     _outputPath = null;
     _paddedToFrame = false;
     _truncated4608 = false;
     _usePregapForFirstTrackInSingleFile = false;
     _action = CUEAction.Encode;
     _appliedWriteOffset = false;
     _minDataTrackLength = null;
     hdcdDecoder = null;
     _hasEmbeddedCUESheet = false;
     _isArchive = false;
     _isCD = false;
     _useLocalDB = false;
     proxy = _config.GetProxy();
 }
예제 #15
0
 public CDImageLayout TocFromCDEntry(CDEntry cdEntry)
 {
     CDImageLayout tocFromCDEntry = new CDImageLayout();
     for (int i = 0; i < cdEntry.Tracks.Count; i++)
     {
         if (i >= _toc.TrackCount)
             break;
         tocFromCDEntry.AddTrack(new CDTrack((uint)i + 1,
             (uint)cdEntry.Tracks[i].FrameOffset - 150,
             (i + 1 < cdEntry.Tracks.Count) ? (uint)(cdEntry.Tracks[i + 1].FrameOffset - cdEntry.Tracks[i].FrameOffset) : _toc[i + 1].Length,
             _toc[i + 1].IsAudio,
             false/*preEmphasis*/));
     }
     if (tocFromCDEntry.TrackCount > 0 && tocFromCDEntry[1].IsAudio)
         tocFromCDEntry[1][0].Start = 0;
     return tocFromCDEntry;
 }
예제 #16
0
		public bool Open(char Drive)
		{
			Device.CommandStatus st;

			m_inqury_result = null;

			// Open the base device
			m_device_letter = Drive;
			if (m_device != null)
				Close();

			m_device = new Device(m_logger);
			if (!m_device.Open(m_device_letter))
				throw new ReadCDException(Resource1.DeviceOpenError, Marshal.GetExceptionForHR(Marshal.GetHRForLastWin32Error()));
			//throw new ReadCDException(Resource1.DeviceOpenError + ": " + WinDev.Win32ErrorToString(m_device.LastError));

			// Get device info
			st = m_device.Inquiry(out m_inqury_result);
			if (st != Device.CommandStatus.Success)
				throw new SCSIException(Resource1.DeviceInquiryError, m_device, st);
			if (!m_inqury_result.Valid || m_inqury_result.PeripheralQualifier != 0 || m_inqury_result.PeripheralDeviceType != Device.MMCDeviceType)
				throw new ReadCDException(Resource1.DeviceNotMMC);

			m_max_sectors = Math.Min(NSECTORS, m_device.MaximumTransferLength / CB_AUDIO - 1);
			//// Open/Initialize the driver
			//Drive m_drive = new Drive(dev);
			//DiskOperationError status = m_drive.Initialize();
			//if (status != null)
			//    throw new Exception("SCSI error");

			// {
			//Drive.FeatureState readfeature = m_drive.GetFeatureState(Feature.FeatureType.CDRead);
			//if (readfeature == Drive.FeatureState.Error || readfeature == Drive.FeatureState.NotPresent)
			//    throw new Exception("SCSI error");
			// }{
			//st = m_device.GetConfiguration(Device.GetConfigType.OneFeature, 0, out flist);
			//if (st != Device.CommandStatus.Success)
			//    return CreateErrorObject(st, m_device);

			//Feature f = flist.Features[0];
			//ParseProfileList(f.Data);
			// }

			//SpeedDescriptorList speed_list;
			//st = m_device.GetSpeed(out speed_list);
			//if (st != Device.CommandStatus.Success)
			//    throw new Exception("GetSpeed failed: SCSI error");

			//m_device.SetCdSpeed(Device.RotationalControl.CLVandNonPureCav, (ushort)(0x7fff), (ushort)(0x7fff));
			//int bytesPerSec = 4 * 588 * 75 * (pass > 8 ? 4 : pass > 4 ? 8 : pass > 0 ? 16 : 32);
			//Device.CommandStatus st = m_device.SetStreaming(Device.RotationalControl.CLVandNonPureCav, start, end, bytesPerSec, 1, bytesPerSec, 1);
			//if (st != Device.CommandStatus.Success)
			//    System.Console.WriteLine("SetStreaming: ", (st == Device.CommandStatus.DeviceFailed ? Device.LookupSenseError(m_device.GetSenseAsc(), m_device.GetSenseAscq()) : st.ToString()));
			//st = m_device.SetCdSpeed(Device.RotationalControl.CLVandNonPureCav, (ushort)(bytesPerSec / 1024), (ushort)(bytesPerSec / 1024));
			//if (st != Device.CommandStatus.Success)
			//    System.Console.WriteLine("SetCdSpeed: ", (st == Device.CommandStatus.DeviceFailed ? Device.LookupSenseError(m_device.GetSenseAsc(), m_device.GetSenseAscq()) : st.ToString()));


			//st = m_device.SetCdSpeed(Device.RotationalControl.CLVandNonPureCav, 32767/*Device.OptimumSpeed*/, Device.OptimumSpeed);
			//if (st != Device.CommandStatus.Success)
			//    throw new Exception("SetCdSpeed failed: SCSI error");

			IList<TocEntry> toc;
			st = m_device.ReadToc((byte)0, false, out toc);
			if (st != Device.CommandStatus.Success)
				throw new SCSIException(Resource1.ReadTOCError, m_device, st);
				//throw new Exception("ReadTOC: " + (st == Device.CommandStatus.DeviceFailed ? Device.LookupSenseError(m_device.GetSenseAsc(), m_device.GetSenseAscq()) : st.ToString()));

			//byte[] qdata = null;
			//st = m_device.ReadPMA(out qdata);
			//if (st != Device.CommandStatus.Success)
			//    throw new SCSIException("ReadPMA", m_device, st);

			//st = m_device.ReadCDText(out cdtext, _timeout);
			// new CDTextEncoderDecoder

			_toc2 = null;
			_toc = new CDImageLayout();
			for (int iTrack = 0; iTrack < toc.Count - 1; iTrack++)
				_toc.AddTrack(new CDTrack((uint)iTrack + 1, 
					toc[iTrack].StartSector,
					toc[iTrack + 1].StartSector - toc[iTrack].StartSector - 
					    ((toc[iTrack + 1].Control < 4 || iTrack + 1 == toc.Count - 1) ? 0U : 152U * 75U), 
					toc[iTrack].Control < 4,
					(toc[iTrack].Control & 1) == 1));			
			if (_toc.AudioLength > 0)
			{
				if (_toc[1].IsAudio)
					_toc[1][0].Start = 0;
				Position = 0;
			} else
				throw new ReadCDException(Resource1.NoAudio);

            UserData = new long[MSECTORS, 2, 4 * 588];
            C2Count = new byte[MSECTORS, 294];

			return true;
		}
예제 #17
0
		public void Init(CDImageLayout toc)
		{
			_toc = toc;
			_finalSampleCount = _toc.AudioLength * 588;
			_CRCMASK = new uint[_toc.AudioTracks + 1];
			_CRCMASK[0] = 0xffffffff ^ Crc32.Combine(0xffffffff, 0, (int)_finalSampleCount * 4);
			for (int iTrack = 1; iTrack <= _toc.AudioTracks; iTrack++)
				_CRCMASK[iTrack] = 0xffffffff ^ Crc32.Combine(0xffffffff, 0, (int)_toc[iTrack + _toc.FirstAudio - 1].Length * 588 * 4);

			maxOffset = Math.Max(4096 * 2, calcParity ? stride + laststride : 0);
			if (maxOffset % 588 != 0)
				maxOffset += 588 - maxOffset % 588;
			_CRCAR = new uint[_toc.AudioTracks + 1, 3 * maxOffset];
			_CRCSM = new uint[_toc.AudioTracks + 1, 3 * maxOffset];
			_CRC32 = new uint[_toc.AudioTracks + 1, 3 * maxOffset];
			_CacheCRC32 = new uint[_toc.AudioTracks + 1, 3 * maxOffset];
			_CRCWN = new uint[_toc.AudioTracks + 1, 3 * maxOffset];
			_CacheCRCWN = new uint[_toc.AudioTracks + 1, 3 * maxOffset];
			_CRCNL = new int[_toc.AudioTracks + 1, 3 * maxOffset];
			_CRCV2 = new uint[_toc.AudioTracks + 1, 3 * maxOffset];

			_Peak = new int[_toc.AudioTracks + 1];
			parity = null;
            if (calcParity)
            {
                parity = new byte[stride * maxNpar * 2];
                encodeTable = Galois16.instance.makeEncodeTable(maxNpar);
            }

			int leadin_len = Math.Max(4096 * 4, calcParity ? stride * 2 : 0);
			int leadout_len = Math.Max(4096 * 4, calcParity ? stride + laststride : 0);
			leadin = new ushort[leadin_len];
			leadout = new ushort[leadout_len];
			_currentTrack = 0;
			Position = 0; // NOT _toc[_toc.FirstAudio][0].Start * 588;
		}
예제 #18
0
		public static string CalculateCDDBId(CDImageLayout toc)
		{
			uint cddbDiscId = 0;
			for (int iTrack = 1; iTrack <= toc.TrackCount; iTrack++)
				cddbDiscId += sumDigits(toc[iTrack].Start / 75 + 2); // !!!!!!!!!!!!!!!!! %255 !!
			return string.Format("{0:X8}", (((cddbDiscId % 255) << 24) + ((toc.Length / 75 - toc[1].Start / 75) << 8) + (uint)toc.TrackCount) & 0xFFFFFFFF);
		}
예제 #19
0
		public static string CalculateAccurateRipId(CDImageLayout toc)
		{
			// Calculate the three disc ids used by AR
			uint discId1 = 0;
			uint discId2 = 0;
			uint num = 0;

			for (int iTrack = 1; iTrack <= toc.TrackCount; iTrack++)
				if (toc[iTrack].IsAudio)
				{
					discId1 += toc[iTrack].Start;
					discId2 += Math.Max(toc[iTrack].Start, 1) * (++num);
				}
			discId1 += toc.Length;
			discId2 += Math.Max(toc.Length, 1) * (++num);
			discId1 &= 0xFFFFFFFF;
			discId2 &= 0xFFFFFFFF;
			return string.Format("{0:x8}-{1:x8}-{2}", discId1, discId2, CalculateCDDBId(toc).ToLower());
		}
예제 #20
0
		public static string CalculateCDDBQuery(CDImageLayout toc)
		{
			StringBuilder query = new StringBuilder(CalculateCDDBId(toc));
			query.AppendFormat("+{0}", toc.TrackCount);
			for (int iTrack = 1; iTrack <= toc.TrackCount; iTrack++)
				query.AppendFormat("+{0}", toc[iTrack].Start + 150);
			query.AppendFormat("+{0}", toc.Length / 75 + 2);
			return query.ToString();
		}
예제 #21
0
 public CUEMetadataEntry(CDImageLayout TOC, string key)
     : this(new CUEMetadata(TOC.TOCID, (int)TOC.AudioTracks), TOC, key)
 {
 }
		public TestImageGenerator(CDImageLayout toc, int seed, int offset, int errors = 0, int maxStrideErrors = 0)
            : this(toc, seed, offset, errors, maxStrideErrors, 0, (int)toc.AudioLength * 588)
		{
		}
예제 #23
0
        private void DetectGaps()
        {
            if (!_isCD)
                throw new Exception("not a CD");

            if (_config.detectGaps)
            {
                try { _ripper.DetectGaps(); }
                catch (Exception ex)
                {
                    if (ex is StopException)
                        throw ex;
                }
            }

            if (!_ripper.GapsDetected)
                return;

            _toc = (CDImageLayout)_ripper.TOC.Clone();
            if (_toc.Barcode != null)
                Metadata.Barcode = _toc.Barcode;
            for (int iTrack = 0; iTrack < _toc.AudioTracks; iTrack++)
            {
                if (_toc[_toc.FirstAudio + iTrack].ISRC != null)
                    Metadata.Tracks[iTrack].ISRC = _toc[_toc.FirstAudio + iTrack].ISRC;
                //General.SetCUELine(_tracks[iTrack].Attributes, "ISRC", _toc[_toc.FirstAudio + iTrack].ISRC, false);
                if (_toc[_toc.FirstAudio + iTrack].DCP || _toc[_toc.FirstAudio + iTrack].PreEmphasis)
                    _tracks[iTrack].Attributes.Add(new CUELine("FLAGS" + (_toc[_toc.FirstAudio + iTrack].PreEmphasis ? " PRE" : "") + (_toc[_toc.FirstAudio + iTrack].DCP ? " DCP" : "")));
            }
        }
예제 #24
0
		public CDImageLayout(CDImageLayout src)
		{
			_barcode = src._barcode;
			_audioTracks = src._audioTracks;
			_firstAudio = src._firstAudio;
			_tracks = new List<CDTrack>();
			for (int i = 0; i < src.TrackCount; i++)
				_tracks.Add(new CDTrack(src._tracks[i]));
		}
예제 #25
0
        public static CDImageLayout CUE2TOC(string cue, int fileTimeLengthFrames)
        {
            CDImageLayout toc = new CDImageLayout();
            bool seenFirstFileIndex = false;
            int absoluteFileStartTime = 0;
            int trackStart = -1;
            try
            {
                using (TextReader sr = new StringReader(cue))
                {
                    string lineStr;
                    while ((lineStr = sr.ReadLine()) != null)
                    {
                        CUELine line = new CUELine(lineStr);
                        if (line.Params.Count > 0)
                        {
                            string command = line.Params[0].ToUpper();

                            if (command == "TRACK")
                            {
                                if (line.Params[2].ToUpper() != "AUDIO")
                                    return null;
                            }
                            else if (command == "INDEX")
                            {
                                int index = int.Parse(line.Params[1]);
                                int timeRelativeToFileStart = CDImageLayout.TimeFromString(line.Params[2]);
                                if (!seenFirstFileIndex)
                                {
                                    if (timeRelativeToFileStart != 0)
                                        return null;
                                    seenFirstFileIndex = true;
                                }
                                else
                                {
                                    if (timeRelativeToFileStart > fileTimeLengthFrames)
                                        return null;
                                    if (Int32.TryParse(line.Params[1], out index) && index == 1 && trackStart >= 0)
                                        toc.AddTrack(new CDTrack((uint)toc.TrackCount + 1, (uint)trackStart, (uint)(absoluteFileStartTime + timeRelativeToFileStart - trackStart), true, false));
                                }
                                if (index == 1)
                                    trackStart = absoluteFileStartTime + timeRelativeToFileStart;
                            }
                            else if (command == "PREGAP")
                            {
                                if (seenFirstFileIndex)
                                    return null;
                                int pregapLength = CDImageLayout.TimeFromString(line.Params[1]);
                                absoluteFileStartTime += pregapLength;
                            }
                        }
                    }
                    sr.Close();
                }
            }
            catch
            {
                return null;
            }
            toc.AddTrack(new CDTrack((uint)toc.TrackCount + 1, (uint)trackStart, (uint)(absoluteFileStartTime + fileTimeLengthFrames - trackStart), true, false));
            toc[1][0].Start = 0;
            return toc;
        }
예제 #26
0
 public CUEMetadataEntry(CUEMetadata metadata, CDImageLayout TOC, string key)
 {
     this.metadata = new CUEMetadata(metadata);
     this.TOC = TOC;
     this.ImageKey = key;
 }
예제 #27
0
 public void OpenCD(ICDRipper ripper)
 {
     _ripper = ripper;
     _toc = (CDImageLayout)_ripper.TOC.Clone();
     for (int iTrack = 0; iTrack < _toc.AudioTracks; iTrack++)
     {
         _trackFilenames.Add(string.Format("{0:00}.wav", iTrack + 1));
         _tracks.Add(new TrackInfo());
     }
     cueMetadata = new CUEMetadata(TOC.TOCID, (int)TOC.AudioTracks);
     _arVerify = new AccurateRipVerify(_toc, proxy);
     _isCD = true;
     SourceInfo cdInfo;
     cdInfo.Path = _ripper.ARName;
     cdInfo.Offset = 0;
     cdInfo.Length = _toc.AudioLength * 588;
     _sources.Add(cdInfo);
     // Causes memory leak, so had to disable!
     //_ripper.ReadProgress += new EventHandler<ReadProgressArgs>(CDReadProgress);
     _padding += TrackCount * 200;
     _padding += _config.embedLog ? 500 + TrackCount * 200 : 0;
 }
예제 #28
0
		public unsafe bool DetectGaps()
		{
			if (!TestReadCommand())
				throw new ReadCDException(Resource1.AutodetectReadCommandFailed + ":\n" + _autodetectResult);

			if (_gapDetection == GapDetectionMethod.None)
			{
				gapsDetected = false;
				return false;
			}

			if (gapsDetected)
				return true;

			_toc2 = (CDImageLayout)_toc.Clone();

			if (_gapDetection == GapDetectionMethod.ReadSubchannel)
			{
				Device.CommandStatus st = m_device.ReadSubChannel42(2, 0, ref _subchannelBuffer, 0, _timeout);
				if (st == Device.CommandStatus.Success)
					if (_subchannelBuffer[0] == 0 && _subchannelBuffer[2] == 0 && _subchannelBuffer[3] == 20
						&& _subchannelBuffer[4] == 2 && _subchannelBuffer[8] == 0x80)
					{
						string catalog = Encoding.ASCII.GetString(_subchannelBuffer, 9, 13);
						if (catalog.ToString() != "0000000000000")
							_toc2.Barcode = catalog.ToString();
					}
			}

			int sec0 = (int)_toc2[_toc2.FirstAudio][0].Start, disc1 = (int)(_toc2[_toc2.FirstAudio][0].Start + _toc2.AudioLength) - 1;
			for (int iTrack = _toc2.FirstAudio; iTrack < _toc2.FirstAudio + _toc2.AudioTracks; iTrack++)
			{
				if (ReadProgress != null)
				{
					progressArgs.Action = Resource1.StatusDetectingGaps;
					progressArgs.Pass = -1;
					progressArgs.Position = (iTrack - _toc2.FirstAudio) * 3;
					progressArgs.PassStart = 0;
					progressArgs.PassEnd = _toc2.TrackCount * 3 - 1;
					progressArgs.ErrorsCount = 0;
					progressArgs.PassTime = DateTime.Now;
					ReadProgress(this, progressArgs);
				}
				int sec1, idx1 = 1;
				LocateLastSector(sec0, Math.Min(disc1, (int)_toc[iTrack].End + 16), iTrack, -1, ref idx1, out sec1);
				int isec0 = sec0;
				for (int idx = 0; idx <= idx1; idx++)
				{
					int isec1 = sec1, iidx1 = 1;
					if (idx < idx1)
					{
						if (ReadProgress != null)
						{
							progressArgs.Position = (iTrack - _toc2.FirstAudio) * 3 + 1;
							progressArgs.PassTime = DateTime.Now;
							ReadProgress(this, progressArgs);
						}
						LocateLastSector(isec0, sec1, iTrack, idx, ref iidx1, out isec1);
					}
					if (isec1 > isec0)
					{
						if (idx == 0 && iTrack > 1)
							_toc2[iTrack][0].Start = _toc2[iTrack].Start - (uint)(isec1 - isec0 + 1);
						if (idx > 1)
							_toc2[iTrack].AddIndex(new CDTrackIndex((uint)idx, (uint)(_toc2[iTrack][0].Start + isec0 - sec0)));
					}
					isec0 = isec1 + 1;
				}

				if (ReadProgress != null)
				{
					progressArgs.Position = (iTrack - _toc2.FirstAudio) * 3 + 2;
					progressArgs.PassTime = DateTime.Now;
					ReadProgress(this, progressArgs);
				}

				if (_gapDetection == GapDetectionMethod.ReadSubchannel)
				{
					Device.CommandStatus st = m_device.ReadSubChannel42(3, iTrack, ref _subchannelBuffer, 0, _timeout);
					if (st == Device.CommandStatus.Success)
						if (_subchannelBuffer[0] == 0 && _subchannelBuffer[2] == 0 && _subchannelBuffer[3] == 20
							&& _subchannelBuffer[4] == 3 && _subchannelBuffer[8] == 0x80) //&& _subchannelBuffer[6] == iTrack)
						{
							string isrc = Encoding.ASCII.GetString(_subchannelBuffer, 9, 12);
							if (!isrc.ToString().Contains("#") && isrc.ToString() != "000000000000")
								_toc2[iTrack].ISRC = isrc.ToString();
						}
				}
				if (_gapDetection == GapDetectionMethod.ReadCD)
				{
					Device.CommandStatus st = m_device.ReadSubChannel(2, _toc2[iTrack].Start + 16, 100, ref _subchannelBuffer, _timeout);
					if (st == Device.CommandStatus.Success)
					{
						for (int offs = 0; offs < 100 * 16; offs += 16)
						{
							int ctl = _subchannelBuffer[offs + 0] >> 4;
							int adr = _subchannelBuffer[offs + 0] & 7;
							if (adr != 2 && adr != 3)
								continue;
							ushort crc = _crc.ComputeChecksum(_subchannelBuffer, offs, 10);
							crc ^= 0xffff;
							ushort scrc = (ushort)((_subchannelBuffer[offs + 10] << 8) | _subchannelBuffer[offs + 11]);
							if (scrc != 0 && scrc != crc)
								continue;
							if (adr == 3 && _toc2[iTrack].ISRC == null)
							{
								StringBuilder isrc = new StringBuilder();
								isrc.Append(from6bit(_subchannelBuffer[offs + 1] >> 2));
								isrc.Append(from6bit(((_subchannelBuffer[offs + 1] & 0x3) << 4) + (0x0f & (_subchannelBuffer[offs + 2] >> 4))));
								isrc.Append(from6bit(((_subchannelBuffer[offs + 2] & 0xf) << 2) + (0x03 & (_subchannelBuffer[offs + 3] >> 6))));
								isrc.Append(from6bit((_subchannelBuffer[offs + 3] & 0x3f)));
								isrc.Append(from6bit(_subchannelBuffer[offs + 4] >> 2));
								isrc.Append(from6bit(((_subchannelBuffer[offs + 4] & 0x3) << 4) + (0x0f & (_subchannelBuffer[offs + 5] >> 4))));
								isrc.AppendFormat("{0:x}", _subchannelBuffer[offs + 5] & 0xf);
								isrc.AppendFormat("{0:x2}", _subchannelBuffer[offs + 6]);
								isrc.AppendFormat("{0:x2}", _subchannelBuffer[offs + 7]);
								isrc.AppendFormat("{0:x}", _subchannelBuffer[offs + 8] >> 4);
								if (!isrc.ToString().Contains("#") && isrc.ToString() != "000000000000")
									_toc2[iTrack].ISRC = isrc.ToString();
							}
							if (adr == 2 && _toc2.Barcode == null)
							{
								StringBuilder barcode = new StringBuilder();
								for (int i = 1; i < 8; i++)
									barcode.AppendFormat("{0:x2}", _subchannelBuffer[offs + i]);
								if (barcode.ToString(0, 13) != "0000000000000")
									_toc2.Barcode = barcode.ToString(0, 13);
							}
						}
					}
				}
				sec0 = sec1 + 1;
			}

			gapsDetected = true;
			return true;
		}
예제 #29
0
        // Now to the audio transfer functions, the sequence how
        // the functions are called is:
        // StartNewSession
        // StartNewTransfer
        // TransferAudio
        // ...
        // TransferAudio
        // TransferFinshed
        // Then perhaps repeating StartNewTransfer to TransferFinished
        // (e.g. when extracting several tracks), and finally
        // EndOfSession
        // This is called just before the log window will be
        // shown. You can return a log output in that stage (or
        // even display a window of your own - even though it should
        // not annoy the user)

        // StartNewSession is called once at the very beginning of an
        // extraction session. It receives the CD metadata, the
        // name of the used drive, the used read offset and whether
        // the offset was setted by AccurateRip (so having a comparable
        // offset value)

        public void StartNewSession(IMetadataLookup data, string drivename, int offset, bool aroffset, int mode)
        {
            // Copy the CD metadata to the object
            m_data = data;

#if DEBUG
            m_trace = new StringWriter();
#endif

            var parts = drivename.Split(' ');
            m_drivename = parts[0].PadRight(8, ' ') + " -";
            for (int i = 1; i < parts.Length; i++)
                m_drivename += " " + parts[i];

            TOC = new CDImageLayout();
            for (int i = 0; i < m_data.NumberOfTracks; i++)
            {
                uint start = m_data.GetTrackStartPosition(i);
                uint next = m_data.GetTrackEndPosition(i);
                TOC.AddTrack(new CDTrack(
                    (uint)i + 1,
                    start,
                    next - start,
                    !m_data.GetTrackDataTrack(i),
                    m_data.GetTrackPreemphasis(i)));
            }
            TOC[1][0].Start = 0U;
            ar = new AccurateRipVerify(TOC, null);
            arTest = new AccurateRipVerify(TOC, null);
            ctdb = new CUEToolsDB(TOC, null);
#if USEAR
			ArId = AccurateRipVerify.CalculateAccurateRipId(TOC);
			ar.ContactAccurateRip(ArId);
#endif
            ctdb.Init(ar);
            this.sequence_ok = true;
            this.m_start_pos = 0;
            this.m_length = 0;
            this.m_test_mode = false;
            this.is_offset_set = aroffset;
            this.is_secure_mode = mode >= 2;
        }
예제 #30
0
        public static CDImageLayout LogToToc(CDImageLayout toc, string eacLog)
        {
            CDImageLayout tocFromLog = new CDImageLayout();
            using (StringReader sr = new StringReader(eacLog))
            {
                bool isEACLog = false;
                bool iscdda2wavlog = false;
                string lineStr;
                int prevTrNo = 1, prevTrStart = 0;
                uint firstPreGap = 0;
                while ((lineStr = sr.ReadLine()) != null)
                {
                    if (isEACLog)
                    {
                        string[] n = lineStr.Split('|');
                        uint trNo, trStart, trEnd;
                        if (n.Length == 5 && uint.TryParse(n[0], out trNo) && uint.TryParse(n[3], out trStart) && uint.TryParse(n[4], out trEnd) && trNo == tocFromLog.TrackCount + 1)
                        {
                            bool isAudio = true;
                            if (tocFromLog.TrackCount >= toc.TrackCount &&
                                trStart == tocFromLog[tocFromLog.TrackCount].End + 1U + 152U * 75U
                                )
                                isAudio = false;
                            if (tocFromLog.TrackCount < toc.TrackCount &&
                                !toc[tocFromLog.TrackCount + 1].IsAudio
                                )
                                isAudio = false;
                            tocFromLog.AddTrack(new CDTrack(trNo, trStart, trEnd + 1 - trStart, isAudio, false));
                        }
                        else
                        {
                            string[] sepTrack = { "Track" };
                            string[] sepGap = { "Pre-gap length" };

                            string[] partsTrack = lineStr.Split(sepTrack, StringSplitOptions.None);
                            if (partsTrack.Length == 2 && uint.TryParse(partsTrack[1], out trNo))
                            {
                                prevTrNo = (int)trNo;
                                continue;
                            }

                            string[] partsGap = lineStr.Split(sepGap, StringSplitOptions.None);
                            if (partsGap.Length == 2)
                            {
                                string[] n1 = partsGap[1].Split(':', '.');
                                int h, m, s, f;
                                if (n1.Length == 4 && int.TryParse(n1[0], out h) && int.TryParse(n1[1], out m) && int.TryParse(n1[2], out s) && int.TryParse(n1[3], out f))
                                {
                                    uint gap = (uint)((f * 3 + 2) / 4 + 75 * (s + 60 * (m + 60 * h)));
                                    if (prevTrNo == 1)
                                        gap -= 150;
                                    if (prevTrNo == 1)
                                        firstPreGap = gap - toc[1].Start;
                                    //else
                                    //firstPreGap += gap;
                                    while (prevTrNo > tocFromLog.TrackCount && toc.TrackCount > tocFromLog.TrackCount)
                                    {
                                        tocFromLog.AddTrack(new CDTrack((uint)tocFromLog.TrackCount + 1,
                                            toc[tocFromLog.TrackCount + 1].Start + firstPreGap,
                                            toc[tocFromLog.TrackCount + 1].Length,
                                            toc[tocFromLog.TrackCount + 1].IsAudio, false));
                                    }
                                    if (prevTrNo <= tocFromLog.TrackCount)
                                        tocFromLog[prevTrNo].Pregap = gap;
                                }
                            }
                        }
                    }
                    else if (iscdda2wavlog)
                    {
                        foreach (string entry in lineStr.Split(','))
                        {
                            string[] n = entry.Split('(');
                            if (n.Length < 2) continue;
                            // assert n.Length == 2;
                            string key = n[0].Trim(' ', '.');
                            int trStart = int.Parse(n[1].Trim(' ', ')'));
                            bool isAudio = true; // !!!
                            if (key != "1")
                                tocFromLog.AddTrack(new CDTrack((uint)prevTrNo, (uint)prevTrStart, (uint)(trStart - prevTrStart), isAudio, false));
                            if (key == "lead-out")
                            {
                                iscdda2wavlog = false;
                                break;
                            }
                            prevTrNo = int.Parse(key);
                            prevTrStart = trStart;
                        }
                    }
                    else if (lineStr.StartsWith("TOC of the extracted CD")
                        || lineStr.StartsWith("Exact Audio Copy")
                        || lineStr.StartsWith("EAC extraction logfile")
                        || lineStr.StartsWith("CUERipper")
                        || lineStr.StartsWith("     Track |   Start  |  Length  | Start sector | End sector")
                        )
                        isEACLog = true;
                    else if (lineStr.StartsWith("Table of Contents: starting sectors"))
                        iscdda2wavlog = true;
                }
            }
            if (tocFromLog.TrackCount == 0)
                return null;
            tocFromLog[1][0].Start = 0;
            return tocFromLog;
        }