diff --git a/Aaru.Images/AaruFormat/Unimplemented.cs b/Aaru.Images/AaruFormat/Unimplemented.cs index 8800c25d0..f31b070d9 100644 --- a/Aaru.Images/AaruFormat/Unimplemented.cs +++ b/Aaru.Images/AaruFormat/Unimplemented.cs @@ -24,10 +24,6 @@ public sealed partial class AaruFormat /// public bool SetImageInfo(ImageInfo imageInfo) => throw new NotImplementedException(); - /// - public bool? VerifySectors(ulong sectorAddress, uint length, out List failingLbas, - out List unknownLbas) => throw new NotImplementedException(); - /// public ErrorNumber ReadSectorTag(ulong sectorAddress, uint track, SectorTagType tag, out byte[] buffer) => throw new NotImplementedException(); diff --git a/Aaru.Images/AaruFormat/Verify.cs b/Aaru.Images/AaruFormat/Verify.cs index d23559f34..158a5adc9 100644 --- a/Aaru.Images/AaruFormat/Verify.cs +++ b/Aaru.Images/AaruFormat/Verify.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using Aaru.Checksums; @@ -34,6 +35,53 @@ public sealed partial class AaruFormat return errno != ErrorNumber.NoError ? null : CdChecksums.CheckCdSector(buffer); } + /// + public bool? VerifySectors(ulong sectorAddress, uint length, out List failingLbas, + out List unknownLbas) + { + failingLbas = []; + unknownLbas = []; + + // Right now only CompactDisc sectors are verifiable + if(_imageInfo.MetadataMediaType != MetadataMediaType.OpticalDisc) + { + for(ulong i = sectorAddress; i < sectorAddress + length; i++) unknownLbas.Add(i); + + return null; + } + + ErrorNumber errno = ReadSectorsLong(sectorAddress, length, out byte[] buffer); + + if(errno != ErrorNumber.NoError) return null; + + var bps = (int)(buffer.Length / length); + var sector = new byte[bps]; + failingLbas = []; + unknownLbas = []; + + for(var i = 0; i < length; i++) + { + Array.Copy(buffer, i * bps, sector, 0, bps); + bool? sectorStatus = CdChecksums.CheckCdSector(sector); + + switch(sectorStatus) + { + case null: + unknownLbas.Add((ulong)i + sectorAddress); + + break; + case false: + failingLbas.Add((ulong)i + sectorAddress); + + break; + } + } + + if(unknownLbas.Count > 0) return null; + + return failingLbas.Count <= 0; + } + #endregion // AARU_EXPORT int32_t AARU_CALL aaruf_verify_image(void *context)