void CommandAudioStartPos() { switch (CommandBuffer[9] & 0xC0) { case 0x00: // Set start offset in LBA units audioStartLBA = (CommandBuffer[3] << 16) | (CommandBuffer[4] << 8) | CommandBuffer[5]; break; case 0x40: // Set start offset in absolute MSF units byte m = CommandBuffer[2].BCDtoBin(); byte s = CommandBuffer[3].BCDtoBin(); byte f = CommandBuffer[4].BCDtoBin(); audioStartLBA = DiscUtils.Convert_AMSF_To_LBA(m, s, f); break; case 0x80: // Set start offset in track units byte trackNo = CommandBuffer[2].BCDtoBin(); audioStartLBA = disc.Session1.Tracks[trackNo].LBA; break; } if (CommandBuffer[1] == 0) { pce.CDAudio.PlayStartingAtLba(audioStartLBA); pce.CDAudio.Pause(); } else { pce.CDAudio.PlayStartingAtLba(audioStartLBA); } SetStatusMessage(STATUS_GOOD, 0); pce.IntDataTransferComplete = true; }
void CommandAudioEndPos() { switch (CommandBuffer[9] & 0xC0) { case 0x00: // Set end offset in LBA units audioEndLBA = (CommandBuffer[3] << 16) | (CommandBuffer[4] << 8) | CommandBuffer[5]; break; case 0x40: // Set end offset in absolute MSF units byte m = CommandBuffer[2].BCDtoBin(); byte s = CommandBuffer[3].BCDtoBin(); byte f = CommandBuffer[4].BCDtoBin(); audioEndLBA = DiscUtils.Convert_AMSF_To_LBA(m, s, f); break; case 0x80: // Set end offset in track units byte trackNo = CommandBuffer[2].BCDtoBin(); if (trackNo - 1 >= disc.Session1.Tracks.Count) { audioEndLBA = disc.Session1.LeadoutLBA; } else { audioEndLBA = disc.Session1.Tracks[trackNo].LBA; } break; } switch (CommandBuffer[1]) { case 0: // end immediately pce.CDAudio.Stop(); break; case 1: // play in loop mode. I guess this constitues A-B looping pce.CDAudio.PlayStartingAtLba(audioStartLBA); pce.CDAudio.EndLBA = audioEndLBA; pce.CDAudio.PlayMode = CDAudio.PlaybackMode_LoopOnCompletion; break; case 2: // Play audio, fire IRQ2 when end position reached, maybe pce.CDAudio.PlayStartingAtLba(audioStartLBA); pce.CDAudio.EndLBA = audioEndLBA; pce.CDAudio.PlayMode = CDAudio.PlaybackMode_CallbackOnCompletion; break; case 3: // Play normal pce.CDAudio.PlayStartingAtLba(audioStartLBA); pce.CDAudio.EndLBA = audioEndLBA; pce.CDAudio.PlayMode = CDAudio.PlaybackMode_StopOnCompletion; break; } SetStatusMessage(STATUS_GOOD, 0); }
void CommandReadTOC() { switch (CommandBuffer[1]) { case 0: // return number of tracks { DataIn.Clear(); DataIn.Enqueue(0x01); DataIn.Enqueue(((byte)disc.Session1.Tracks.Count).BinToBCD()); SetPhase(BusPhase_DataIn); break; } case 1: // return total disc length in minutes/seconds/frames { //zero 07-jul-2015 - I may have broken this int totalLbaLength = disc.Session1.LeadoutLBA; byte m, s, f; DiscUtils.Convert_LBA_To_AMSF(totalLbaLength + 150, out m, out s, out f); DataIn.Clear(); DataIn.Enqueue(m.BinToBCD()); DataIn.Enqueue(s.BinToBCD()); DataIn.Enqueue(f.BinToBCD()); SetPhase(BusPhase_DataIn); break; } case 2: // Return starting position of specified track in MSF format. TODO - did zero adapt this right? track indexing might be off { int track = CommandBuffer[2].BCDtoBin(); var tracks = disc.Session1.Tracks; if (CommandBuffer[2] > 0x99) { throw new Exception("invalid track number BCD request... is something I need to handle?"); } if (track == 0) { track = 1; } int lbaPos; if (track > disc.Session1.InformationTrackCount) { lbaPos = disc.Session1.LeadoutLBA; //zero 03-jul-2015 - did I adapt this right? } else { lbaPos = tracks[track].LBA; } byte m, s, f; DiscUtils.Convert_LBA_To_AMSF(lbaPos, out m, out s, out f); DataIn.Clear(); DataIn.Enqueue(m.BinToBCD()); DataIn.Enqueue(s.BinToBCD()); DataIn.Enqueue(f.BinToBCD()); if (track > tracks.Count || disc.Session1.Tracks[track].IsAudio) { DataIn.Enqueue(0); } else { DataIn.Enqueue(4); } SetPhase(BusPhase_DataIn); break; } default: Console.WriteLine("unimplemented READ TOC command argument!"); break; } }
private void DumpVolume(DiscUtils.Ewf.Section.Volume volume, DataTable dataTable) { PropertyInfo[] vInfo = volume.GetType().GetProperties(); foreach (PropertyInfo pi in vInfo) { object o = pi.GetValue(volume, null); string val = IsNumber(o) ? string.Format("{0:n0}", o) : o.ToString(); dataTable.Rows.Add(pi.Name, val); } long capacity = (long)volume.BytesPerSector * (long)volume.SectorCount; dataTable.Rows.Add("Capacity*", string.Format("{0:n0}", capacity)); dataTable.Rows.Add("Friendly Capacity*", parseSize(capacity)); }
private void DumpHeader(DiscUtils.Ewf.Section.Header2 header, DataTable dataTable) { foreach (DiscUtils.Ewf.Section.Header2.Header2Category Cat in header.Categories) { foreach (KeyValuePair<string, string> info in Cat.Info) { string val = IsNumber(info.Value) ? string.Format("{0:n0}", info.Value) : info.Value.ToString(); dataTable.Rows.Add(info.Key, info.Value); } } }