示例#1
0
		public void Run()
		{
			using (var fs = File.OpenRead(IN_Path))
			{
				BinaryReader br = new BinaryReader(fs);
				string sig = br.ReadStringFixedAscii(4);
				if (sig != "SBI\0")
					throw new SBIParseException("Missing magic number");

				SubQPatchData ret = new SubQPatchData();
				List<short> bytes = new List<short>();

				//read records until done
				for (; ; )
				{
					//graceful end
					if (fs.Position == fs.Length)
						break;

					if (fs.Position + 4 > fs.Length) throw new SBIParseException("Broken record");
					var m = BCD2.BCDToInt(br.ReadByte());
					var s = BCD2.BCDToInt(br.ReadByte());
					var f = BCD2.BCDToInt(br.ReadByte());
					var ts = new Timestamp(m, s, f);
					ret.ABAs.Add(ts.Sector);
					int type = br.ReadByte();
					switch (type)
					{
						case 1: //Q0..Q9
							if (fs.Position + 10 > fs.Length) throw new SBIParseException("Broken record");
							for (int i = 0; i <= 9; i++) bytes.Add(br.ReadByte());
							for (int i = 10; i <= 11; i++) bytes.Add(-1);
							break;
						case 2: //Q3..Q5
							if (fs.Position + 3 > fs.Length) throw new SBIParseException("Broken record");
							for (int i = 0; i <= 2; i++) bytes.Add(-1);
							for (int i = 3; i <= 5; i++) bytes.Add(br.ReadByte());
							for (int i = 6; i <= 11; i++) bytes.Add(-1);
							break;
						case 3: //Q7..Q9
							if (fs.Position + 3 > fs.Length) throw new SBIParseException("Broken record");
							for (int i = 0; i <= 6; i++) bytes.Add(-1);
							for (int i = 7; i <= 9; i++) bytes.Add(br.ReadByte());
							for (int i = 10; i <= 11; i++) bytes.Add(-1);
							break;
						default:
							throw new SBIParseException("Broken record");
					}
				}

				ret.subq = bytes.ToArray();

				OUT_Data = ret;
			}
		}
示例#2
0
        /// <summary>
        /// applies an SBI file to the disc
        /// </summary>
        public void Run(Disc disc, SBI.SubQPatchData sbi, bool asMednafen)
        {
            //TODO - could implement as a blob, to avoid allocating so many byte buffers

            //save this, it's small, and we'll want it for disc processing a/b checks
            disc.Memos["sbi"] = sbi;

            DiscSectorReader dsr = new DiscSectorReader(disc);

            int n = sbi.ABAs.Count;
            int b = 0;

            for (int i = 0; i < n; i++)
            {
                int lba = sbi.ABAs[i] - 150;

                //create a synthesizer which can return the patched data
                var ss_patchq = new SS_PatchQ()
                {
                    Original = disc._Sectors[lba + 150]
                };
                byte[] subQbuf = ss_patchq.Buffer_SubQ;

                //read the old subcode
                dsr.ReadLBA_SubQ(lba, subQbuf, 0);

                //insert patch
                disc._Sectors[lba + 150] = ss_patchq;

                //apply SBI patch
                for (int j = 0; j < 12; j++)
                {
                    short patch = sbi.subq[b++];
                    if (patch == -1)
                    {
                        continue;
                    }
                    else
                    {
                        subQbuf[j] = (byte)patch;
                    }
                }

                //Apply mednafen hacks
                //The reasoning here is that we know we expect these sectors to have a wrong checksum. therefore, generate a checksum, and make it wrong
                //However, this seems senseless to me. The whole point of the SBI data is that it stores the patches needed to generate an acceptable subQ, right?
                if (asMednafen)
                {
                    SynthUtils.SubQ_SynthChecksum(subQbuf, 0);
                    subQbuf[10] ^= 0xFF;
                    subQbuf[11] ^= 0xFF;
                }
            }
        }
示例#3
0
        /// <exception cref="SBIParseException">file at <see cref="IN_Path"/> does not contain valid header or contains misformatted record</exception>
        public override void Run()
        {
            using var fs = File.OpenRead(IN_Path);
            BinaryReader br  = new BinaryReader(fs);
            string       sig = br.ReadStringFixedAscii(4);

            if (sig != "SBI\0")
            {
                throw new SBIParseException("Missing magic number");
            }

            SubQPatchData ret   = new SubQPatchData();
            List <short>  bytes = new List <short>();

            //read records until done
            for (; ;)
            {
                //graceful end
                if (fs.Position == fs.Length)
                {
                    break;
                }

                if (fs.Position + 4 > fs.Length)
                {
                    throw new SBIParseException("Broken record");
                }
                var m  = BCD2.BCDToInt(br.ReadByte());
                var s  = BCD2.BCDToInt(br.ReadByte());
                var f  = BCD2.BCDToInt(br.ReadByte());
                var ts = new Timestamp(m, s, f);
                ret.ABAs.Add(ts.Sector);
                int type = br.ReadByte();
                switch (type)
                {
                case 1:                         //Q0..Q9
                    if (fs.Position + 10 > fs.Length)
                    {
                        throw new SBIParseException("Broken record");
                    }
                    for (int i = 0; i <= 9; i++)
                    {
                        bytes.Add(br.ReadByte());
                    }
                    for (int i = 10; i <= 11; i++)
                    {
                        bytes.Add(-1);
                    }
                    break;

                case 2:                         //Q3..Q5
                    if (fs.Position + 3 > fs.Length)
                    {
                        throw new SBIParseException("Broken record");
                    }
                    for (int i = 0; i <= 2; i++)
                    {
                        bytes.Add(-1);
                    }
                    for (int i = 3; i <= 5; i++)
                    {
                        bytes.Add(br.ReadByte());
                    }
                    for (int i = 6; i <= 11; i++)
                    {
                        bytes.Add(-1);
                    }
                    break;

                case 3:                         //Q7..Q9
                    if (fs.Position + 3 > fs.Length)
                    {
                        throw new SBIParseException("Broken record");
                    }
                    for (int i = 0; i <= 6; i++)
                    {
                        bytes.Add(-1);
                    }
                    for (int i = 7; i <= 9; i++)
                    {
                        bytes.Add(br.ReadByte());
                    }
                    for (int i = 10; i <= 11; i++)
                    {
                        bytes.Add(-1);
                    }
                    break;

                default:
                    throw new SBIParseException("Broken record");
                }
            }

            ret.subq = bytes.ToArray();

            OUT_Data = ret;
        }