mirror of
https://github.com/aaru-dps/Aaru.git
synced 2025-12-16 19:24:25 +00:00
Refactor rename "Revision" to "FirmwareRevision".
This commit is contained in:
@@ -117,7 +117,7 @@ namespace DiscImageChef.Core.Devices.Dumping
|
|||||||
|
|
||||||
// Search for device in master database
|
// Search for device in master database
|
||||||
_dbDev = _ctx.Devices.FirstOrDefault(d => d.Manufacturer == _dev.Manufacturer && d.Model == _dev.Model &&
|
_dbDev = _ctx.Devices.FirstOrDefault(d => d.Manufacturer == _dev.Manufacturer && d.Model == _dev.Model &&
|
||||||
d.Revision == _dev.Revision);
|
d.Revision == _dev.FirmwareRevision);
|
||||||
|
|
||||||
if(_dbDev is null)
|
if(_dbDev is null)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
Type = dev.Type;
|
Type = dev.Type;
|
||||||
Manufacturer = dev.Manufacturer;
|
Manufacturer = dev.Manufacturer;
|
||||||
Model = dev.Model;
|
Model = dev.Model;
|
||||||
Revision = dev.Revision;
|
FirmwareRevision = dev.FirmwareRevision;
|
||||||
Serial = dev.Serial;
|
Serial = dev.Serial;
|
||||||
ScsiType = dev.ScsiType;
|
ScsiType = dev.ScsiType;
|
||||||
IsRemovable = dev.IsRemovable;
|
IsRemovable = dev.IsRemovable;
|
||||||
@@ -78,22 +78,30 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
{
|
{
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "STATUS = 0x{0:X2}", errorRegisters.Status);
|
DicConsole.DebugWriteLine("Device-Info command", "STATUS = 0x{0:X2}", errorRegisters.Status);
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "ERROR = 0x{0:X2}", errorRegisters.Error);
|
DicConsole.DebugWriteLine("Device-Info command", "ERROR = 0x{0:X2}", errorRegisters.Error);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "NSECTOR = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "NSECTOR = 0x{0:X2}",
|
||||||
errorRegisters.SectorCount);
|
errorRegisters.SectorCount);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "SECTOR = 0x{0:X2}", errorRegisters.Sector);
|
DicConsole.DebugWriteLine("Device-Info command", "SECTOR = 0x{0:X2}", errorRegisters.Sector);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "CYLHIGH = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "CYLHIGH = 0x{0:X2}",
|
||||||
errorRegisters.CylinderHigh);
|
errorRegisters.CylinderHigh);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "CYLLOW = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "CYLLOW = 0x{0:X2}",
|
||||||
errorRegisters.CylinderLow);
|
errorRegisters.CylinderLow);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "DEVICE = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "DEVICE = 0x{0:X2}",
|
||||||
errorRegisters.DeviceHead);
|
errorRegisters.DeviceHead);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "Error code = {0}", dev.LastError);
|
DicConsole.DebugWriteLine("Device-Info command", "Error code = {0}", dev.LastError);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(dev.Error)
|
if(dev.Error)
|
||||||
{
|
{
|
||||||
DicConsole.ErrorWriteLine("Error {0} querying ATA IDENTIFY", dev.LastError);
|
DicConsole.ErrorWriteLine("Error {0} querying ATA IDENTIFY", dev.LastError);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -101,7 +109,8 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
|
|
||||||
dev.EnableMediaCardPassThrough(out errorRegisters, dev.Timeout, out _);
|
dev.EnableMediaCardPassThrough(out errorRegisters, dev.Timeout, out _);
|
||||||
|
|
||||||
if(errorRegisters.Sector == 0xAA && errorRegisters.SectorCount == 0x55)
|
if(errorRegisters.Sector == 0xAA &&
|
||||||
|
errorRegisters.SectorCount == 0x55)
|
||||||
AtaMcptError = errorRegisters;
|
AtaMcptError = errorRegisters;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@@ -115,21 +124,30 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
{
|
{
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "STATUS = 0x{0:X2}", errorRegisters.Status);
|
DicConsole.DebugWriteLine("Device-Info command", "STATUS = 0x{0:X2}", errorRegisters.Status);
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "ERROR = 0x{0:X2}", errorRegisters.Error);
|
DicConsole.DebugWriteLine("Device-Info command", "ERROR = 0x{0:X2}", errorRegisters.Error);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "NSECTOR = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "NSECTOR = 0x{0:X2}",
|
||||||
errorRegisters.SectorCount);
|
errorRegisters.SectorCount);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "SECTOR = 0x{0:X2}", errorRegisters.Sector);
|
DicConsole.DebugWriteLine("Device-Info command", "SECTOR = 0x{0:X2}", errorRegisters.Sector);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "CYLHIGH = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "CYLHIGH = 0x{0:X2}",
|
||||||
errorRegisters.CylinderHigh);
|
errorRegisters.CylinderHigh);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "CYLLOW = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "CYLLOW = 0x{0:X2}",
|
||||||
errorRegisters.CylinderLow);
|
errorRegisters.CylinderLow);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "DEVICE = 0x{0:X2}",
|
DicConsole.DebugWriteLine("Device-Info command", "DEVICE = 0x{0:X2}",
|
||||||
errorRegisters.DeviceHead);
|
errorRegisters.DeviceHead);
|
||||||
|
|
||||||
DicConsole.DebugWriteLine("Device-Info command", "Error code = {0}", dev.LastError);
|
DicConsole.DebugWriteLine("Device-Info command", "Error code = {0}", dev.LastError);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!dev.Error) AtapiIdentify = ataBuf;
|
if(!dev.Error)
|
||||||
else DicConsole.ErrorWriteLine("Error {0} querying ATA PACKET IDENTIFY", dev.LastError);
|
AtapiIdentify = ataBuf;
|
||||||
|
else
|
||||||
|
DicConsole.ErrorWriteLine("Error {0} querying ATA PACKET IDENTIFY", dev.LastError);
|
||||||
|
|
||||||
// ATAPI devices are also SCSI devices
|
// ATAPI devices are also SCSI devices
|
||||||
goto case DeviceType.SCSI;
|
goto case DeviceType.SCSI;
|
||||||
@@ -142,6 +160,7 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
if(sense)
|
if(sense)
|
||||||
{
|
{
|
||||||
DicConsole.ErrorWriteLine("SCSI error:\n{0}", Sense.PrettifySense(senseBuf));
|
DicConsole.ErrorWriteLine("SCSI error:\n{0}", Sense.PrettifySense(senseBuf));
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -160,50 +179,69 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
foreach(byte page in pages)
|
foreach(byte page in pages)
|
||||||
{
|
{
|
||||||
sense = dev.ScsiInquiry(out inqBuf, out senseBuf, page);
|
sense = dev.ScsiInquiry(out inqBuf, out senseBuf, page);
|
||||||
if(sense) continue;
|
|
||||||
|
if(sense)
|
||||||
|
continue;
|
||||||
|
|
||||||
ScsiEvpdPages.Add(page, inqBuf);
|
ScsiEvpdPages.Add(page, inqBuf);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PeripheralDeviceTypes devType = (PeripheralDeviceTypes)ScsiInquiry.Value.PeripheralDeviceType;
|
var devType = (PeripheralDeviceTypes)ScsiInquiry.Value.PeripheralDeviceType;
|
||||||
|
|
||||||
sense = dev.ModeSense10(out byte[] modeBuf, out senseBuf, false, true,
|
sense = dev.ModeSense10(out byte[] modeBuf, out senseBuf, false, true,
|
||||||
ScsiModeSensePageControl.Current, 0x3F, 0xFF, 5, out _);
|
ScsiModeSensePageControl.Current, 0x3F, 0xFF, 5, out _);
|
||||||
|
|
||||||
if(!sense && !dev.Error) ScsiModeSense10 = modeBuf;
|
if(!sense &&
|
||||||
|
!dev.Error)
|
||||||
|
ScsiModeSense10 = modeBuf;
|
||||||
|
|
||||||
if(sense || dev.Error)
|
if(sense || dev.Error)
|
||||||
{
|
{
|
||||||
sense = dev.ModeSense10(out modeBuf, out senseBuf, false, true,
|
sense = dev.ModeSense10(out modeBuf, out senseBuf, false, true,
|
||||||
ScsiModeSensePageControl.Current, 0x3F, 0x00, 5, out _);
|
ScsiModeSensePageControl.Current, 0x3F, 0x00, 5, out _);
|
||||||
if(!sense && !dev.Error) ScsiModeSense10 = modeBuf;
|
|
||||||
|
if(!sense &&
|
||||||
|
!dev.Error)
|
||||||
|
ScsiModeSense10 = modeBuf;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!sense && !dev.Error) ScsiMode = Modes.DecodeMode10(modeBuf, devType);
|
if(!sense &&
|
||||||
|
!dev.Error)
|
||||||
|
ScsiMode = Modes.DecodeMode10(modeBuf, devType);
|
||||||
|
|
||||||
bool useMode10 = !(sense || dev.Error || !ScsiMode.HasValue);
|
bool useMode10 = !(sense || dev.Error || !ScsiMode.HasValue);
|
||||||
|
|
||||||
sense = dev.ModeSense6(out modeBuf, out senseBuf, false, ScsiModeSensePageControl.Current, 0x3F,
|
sense = dev.ModeSense6(out modeBuf, out senseBuf, false, ScsiModeSensePageControl.Current, 0x3F,
|
||||||
0xFF, 5, out _);
|
0xFF, 5, out _);
|
||||||
|
|
||||||
if(!sense && !dev.Error) ScsiModeSense6 = modeBuf;
|
if(!sense &&
|
||||||
|
!dev.Error)
|
||||||
|
ScsiModeSense6 = modeBuf;
|
||||||
|
|
||||||
if(sense || dev.Error)
|
if(sense || dev.Error)
|
||||||
{
|
{
|
||||||
sense = dev.ModeSense6(out modeBuf, out senseBuf, false, ScsiModeSensePageControl.Current, 0x3F,
|
sense = dev.ModeSense6(out modeBuf, out senseBuf, false, ScsiModeSensePageControl.Current, 0x3F,
|
||||||
0x00, 5, out _);
|
0x00, 5, out _);
|
||||||
|
|
||||||
if(!sense && !dev.Error) ScsiModeSense6 = modeBuf;
|
if(!sense &&
|
||||||
|
!dev.Error)
|
||||||
|
ScsiModeSense6 = modeBuf;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(sense || dev.Error)
|
if(sense || dev.Error)
|
||||||
{
|
{
|
||||||
sense = dev.ModeSense(out modeBuf, out senseBuf, 5, out _);
|
sense = dev.ModeSense(out modeBuf, out senseBuf, 5, out _);
|
||||||
if(!sense && !dev.Error) ScsiModeSense6 = modeBuf;
|
|
||||||
|
if(!sense &&
|
||||||
|
!dev.Error)
|
||||||
|
ScsiModeSense6 = modeBuf;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!sense && !dev.Error && !useMode10) ScsiMode = Modes.DecodeMode6(modeBuf, devType);
|
if(!sense &&
|
||||||
|
!dev.Error &&
|
||||||
|
!useMode10)
|
||||||
|
ScsiMode = Modes.DecodeMode6(modeBuf, devType);
|
||||||
|
|
||||||
switch(devType)
|
switch(devType)
|
||||||
{
|
{
|
||||||
@@ -211,7 +249,8 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
{
|
{
|
||||||
sense = dev.GetConfiguration(out byte[] confBuf, out senseBuf, dev.Timeout, out _);
|
sense = dev.GetConfiguration(out byte[] confBuf, out senseBuf, dev.Timeout, out _);
|
||||||
|
|
||||||
if(!sense) MmcConfiguration = confBuf;
|
if(!sense)
|
||||||
|
MmcConfiguration = confBuf;
|
||||||
|
|
||||||
// TODO: DVD drives respond correctly to BD status.
|
// TODO: DVD drives respond correctly to BD status.
|
||||||
// While specification says if no medium is present
|
// While specification says if no medium is present
|
||||||
@@ -271,8 +310,10 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
case"DVDR PX-708A2":
|
case"DVDR PX-708A2":
|
||||||
case"DVDR PX-712A":
|
case"DVDR PX-712A":
|
||||||
plxtDvd = true;
|
plxtDvd = true;
|
||||||
|
|
||||||
plxtSense = dev.PlextorReadEeprom(out plxtBuf, out senseBuf, dev.Timeout,
|
plxtSense = dev.PlextorReadEeprom(out plxtBuf, out senseBuf, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case"DVDR PX-714A":
|
case"DVDR PX-714A":
|
||||||
case"DVDR PX-716A":
|
case"DVDR PX-716A":
|
||||||
@@ -281,17 +322,21 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
case"DVDR PX-760A":
|
case"DVDR PX-760A":
|
||||||
{
|
{
|
||||||
plxtBuf = new byte[256 * 4];
|
plxtBuf = new byte[256 * 4];
|
||||||
|
|
||||||
for(byte i = 0; i < 4; i++)
|
for(byte i = 0; i < 4; i++)
|
||||||
{
|
{
|
||||||
plxtSense = dev.PlextorReadEepromBlock(out byte[] plxtBufSmall,
|
plxtSense = dev.PlextorReadEepromBlock(out byte[] plxtBufSmall,
|
||||||
out senseBuf, i, 256, dev.Timeout,
|
out senseBuf, i, 256, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
if(plxtSense) break;
|
|
||||||
|
if(plxtSense)
|
||||||
|
break;
|
||||||
|
|
||||||
Array.Copy(plxtBufSmall, 0, plxtBuf, i * 256, 256);
|
Array.Copy(plxtBufSmall, 0, plxtBuf, i * 256, 256);
|
||||||
}
|
}
|
||||||
|
|
||||||
plxtDvd = true;
|
plxtDvd = true;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -300,11 +345,15 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
if(dev.Model.StartsWith("CD-R ", StringComparison.Ordinal))
|
if(dev.Model.StartsWith("CD-R ", StringComparison.Ordinal))
|
||||||
plxtSense = dev.PlextorReadEepromCdr(out plxtBuf, out senseBuf, dev.Timeout,
|
plxtSense = dev.PlextorReadEepromCdr(out plxtBuf, out senseBuf, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PlextorFeatures = new Plextor {IsDvd = plxtDvd};
|
PlextorFeatures = new Plextor
|
||||||
|
{
|
||||||
|
IsDvd = plxtDvd
|
||||||
|
};
|
||||||
|
|
||||||
if(!plxtSense)
|
if(!plxtSense)
|
||||||
{
|
{
|
||||||
@@ -328,6 +377,7 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
|
|
||||||
plxtSense = dev.PlextorGetPoweRec(out senseBuf, out bool plxtPwrRecEnabled,
|
plxtSense = dev.PlextorGetPoweRec(out senseBuf, out bool plxtPwrRecEnabled,
|
||||||
out ushort plxtPwrRecSpeed, dev.Timeout, out _);
|
out ushort plxtPwrRecSpeed, dev.Timeout, out _);
|
||||||
|
|
||||||
if(!plxtSense)
|
if(!plxtSense)
|
||||||
{
|
{
|
||||||
PlextorFeatures.PoweRec = true;
|
PlextorFeatures.PoweRec = true;
|
||||||
@@ -352,6 +402,7 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
|
|
||||||
// TODO: Check it with a drive
|
// TODO: Check it with a drive
|
||||||
plxtSense = dev.PlextorGetSilentMode(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
plxtSense = dev.PlextorGetSilentMode(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
||||||
|
|
||||||
if(!plxtSense)
|
if(!plxtSense)
|
||||||
if(plxtBuf[0] == 1)
|
if(plxtBuf[0] == 1)
|
||||||
{
|
{
|
||||||
@@ -374,44 +425,68 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
}
|
}
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetGigaRec(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
plxtSense = dev.PlextorGetGigaRec(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
||||||
if(!plxtSense) PlextorFeatures.GigaRec = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.GigaRec = true;
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetSecuRec(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
plxtSense = dev.PlextorGetSecuRec(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
||||||
if(!plxtSense) PlextorFeatures.SecuRec = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.SecuRec = true;
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetSpeedRead(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
plxtSense = dev.PlextorGetSpeedRead(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
||||||
|
|
||||||
if(!plxtSense)
|
if(!plxtSense)
|
||||||
{
|
{
|
||||||
PlextorFeatures.SpeedRead = true;
|
PlextorFeatures.SpeedRead = true;
|
||||||
if((plxtBuf[2] & 0x01) == 0x01) PlextorFeatures.SpeedReadEnabled = true;
|
|
||||||
|
if((plxtBuf[2] & 0x01) == 0x01)
|
||||||
|
PlextorFeatures.SpeedReadEnabled = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetHiding(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
plxtSense = dev.PlextorGetHiding(out plxtBuf, out senseBuf, dev.Timeout, out _);
|
||||||
|
|
||||||
if(!plxtSense)
|
if(!plxtSense)
|
||||||
{
|
{
|
||||||
PlextorFeatures.Hiding = true;
|
PlextorFeatures.Hiding = true;
|
||||||
if((plxtBuf[2] & 0x02) == 0x02) PlextorFeatures.HidesRecordables = true;
|
|
||||||
if((plxtBuf[2] & 0x01) == 0x01) PlextorFeatures.HidesSessions = true;
|
if((plxtBuf[2] & 0x02) == 0x02)
|
||||||
|
PlextorFeatures.HidesRecordables = true;
|
||||||
|
|
||||||
|
if((plxtBuf[2] & 0x01) == 0x01)
|
||||||
|
PlextorFeatures.HidesSessions = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetVariRec(out plxtBuf, out senseBuf, false, dev.Timeout, out _);
|
plxtSense = dev.PlextorGetVariRec(out plxtBuf, out senseBuf, false, dev.Timeout, out _);
|
||||||
if(!plxtSense) PlextorFeatures.VariRec = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.VariRec = true;
|
||||||
|
|
||||||
if(plxtDvd)
|
if(plxtDvd)
|
||||||
{
|
{
|
||||||
plxtSense = dev.PlextorGetVariRec(out plxtBuf, out senseBuf, true, dev.Timeout,
|
plxtSense = dev.PlextorGetVariRec(out plxtBuf, out senseBuf, true, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
if(!plxtSense) PlextorFeatures.VariRecDvd = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.VariRecDvd = true;
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetBitsetting(out plxtBuf, out senseBuf, false, dev.Timeout,
|
plxtSense = dev.PlextorGetBitsetting(out plxtBuf, out senseBuf, false, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
if(!plxtSense) PlextorFeatures.BitSetting = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.BitSetting = true;
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetBitsetting(out plxtBuf, out senseBuf, true, dev.Timeout,
|
plxtSense = dev.PlextorGetBitsetting(out plxtBuf, out senseBuf, true, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
if(!plxtSense) PlextorFeatures.BitSettingDl = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.BitSettingDl = true;
|
||||||
|
|
||||||
plxtSense = dev.PlextorGetTestWriteDvdPlus(out plxtBuf, out senseBuf, dev.Timeout,
|
plxtSense = dev.PlextorGetTestWriteDvdPlus(out plxtBuf, out senseBuf, dev.Timeout,
|
||||||
out _);
|
out _);
|
||||||
if(!plxtSense) PlextorFeatures.DvdPlusWriteTest = true;
|
|
||||||
|
if(!plxtSense)
|
||||||
|
PlextorFeatures.DvdPlusWriteTest = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endregion Plextor
|
#endregion Plextor
|
||||||
@@ -420,17 +495,21 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
if(!dev.KreonGetFeatureList(out senseBuf, out KreonFeatures krFeatures, dev.Timeout,
|
if(!dev.KreonGetFeatureList(out senseBuf, out KreonFeatures krFeatures, dev.Timeout,
|
||||||
out _))
|
out _))
|
||||||
KreonFeatures = krFeatures;
|
KreonFeatures = krFeatures;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
case PeripheralDeviceTypes.SequentialAccess:
|
case PeripheralDeviceTypes.SequentialAccess:
|
||||||
{
|
{
|
||||||
sense = dev.ReadBlockLimits(out byte[] seqBuf, out senseBuf, dev.Timeout, out _);
|
sense = dev.ReadBlockLimits(out byte[] seqBuf, out senseBuf, dev.Timeout, out _);
|
||||||
|
|
||||||
if(sense)
|
if(sense)
|
||||||
DicConsole.ErrorWriteLine("READ BLOCK LIMITS:\n{0}", Sense.PrettifySense(senseBuf));
|
DicConsole.ErrorWriteLine("READ BLOCK LIMITS:\n{0}", Sense.PrettifySense(senseBuf));
|
||||||
else BlockLimits = seqBuf;
|
else
|
||||||
|
BlockLimits = seqBuf;
|
||||||
|
|
||||||
sense = dev.ReportDensitySupport(out seqBuf, out senseBuf, dev.Timeout, out _);
|
sense = dev.ReportDensitySupport(out seqBuf, out senseBuf, dev.Timeout, out _);
|
||||||
|
|
||||||
if(sense)
|
if(sense)
|
||||||
DicConsole.ErrorWriteLine("REPORT DENSITY SUPPORT:\n{0}",
|
DicConsole.ErrorWriteLine("REPORT DENSITY SUPPORT:\n{0}",
|
||||||
Sense.PrettifySense(senseBuf));
|
Sense.PrettifySense(senseBuf));
|
||||||
@@ -441,6 +520,7 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
}
|
}
|
||||||
|
|
||||||
sense = dev.ReportDensitySupport(out seqBuf, out senseBuf, true, false, dev.Timeout, out _);
|
sense = dev.ReportDensitySupport(out seqBuf, out senseBuf, true, false, dev.Timeout, out _);
|
||||||
|
|
||||||
if(sense)
|
if(sense)
|
||||||
DicConsole.ErrorWriteLine("REPORT DENSITY SUPPORT (MEDIUM):\n{0}",
|
DicConsole.ErrorWriteLine("REPORT DENSITY SUPPORT (MEDIUM):\n{0}",
|
||||||
Sense.PrettifySense(senseBuf));
|
Sense.PrettifySense(senseBuf));
|
||||||
@@ -460,35 +540,54 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
case DeviceType.MMC:
|
case DeviceType.MMC:
|
||||||
{
|
{
|
||||||
bool sense = dev.ReadCid(out byte[] mmcBuf, out _, dev.Timeout, out _);
|
bool sense = dev.ReadCid(out byte[] mmcBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) CID = mmcBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
CID = mmcBuf;
|
||||||
|
|
||||||
sense = dev.ReadCsd(out mmcBuf, out _, dev.Timeout, out _);
|
sense = dev.ReadCsd(out mmcBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) CSD = mmcBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
CSD = mmcBuf;
|
||||||
|
|
||||||
sense = dev.ReadOcr(out mmcBuf, out _, dev.Timeout, out _);
|
sense = dev.ReadOcr(out mmcBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) OCR = mmcBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
OCR = mmcBuf;
|
||||||
|
|
||||||
sense = dev.ReadExtendedCsd(out mmcBuf, out _, dev.Timeout, out _);
|
sense = dev.ReadExtendedCsd(out mmcBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) ExtendedCSD = mmcBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
ExtendedCSD = mmcBuf;
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.SecureDigital:
|
case DeviceType.SecureDigital:
|
||||||
{
|
{
|
||||||
bool sense = dev.ReadCid(out byte[] sdBuf, out _, dev.Timeout, out _);
|
bool sense = dev.ReadCid(out byte[] sdBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) CID = sdBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
CID = sdBuf;
|
||||||
|
|
||||||
sense = dev.ReadCsd(out sdBuf, out _, dev.Timeout, out _);
|
sense = dev.ReadCsd(out sdBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) CSD = sdBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
CSD = sdBuf;
|
||||||
|
|
||||||
sense = dev.ReadSdocr(out sdBuf, out _, dev.Timeout, out _);
|
sense = dev.ReadSdocr(out sdBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) OCR = sdBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
OCR = sdBuf;
|
||||||
|
|
||||||
sense = dev.ReadScr(out sdBuf, out _, dev.Timeout, out _);
|
sense = dev.ReadScr(out sdBuf, out _, dev.Timeout, out _);
|
||||||
if(!sense) SCR = sdBuf;
|
|
||||||
|
if(!sense)
|
||||||
|
SCR = sdBuf;
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
DicConsole.ErrorWriteLine("Unknown device type {0}, cannot get information.", dev.Type);
|
DicConsole.ErrorWriteLine("Unknown device type {0}, cannot get information.", dev.Type);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -66,7 +66,7 @@ namespace DiscImageChef.Core.Devices.Info
|
|||||||
public DeviceType Type { get; }
|
public DeviceType Type { get; }
|
||||||
public string Manufacturer { get; }
|
public string Manufacturer { get; }
|
||||||
public string Model { get; }
|
public string Model { get; }
|
||||||
public string Revision { get; }
|
public string FirmwareRevision { get; }
|
||||||
public string Serial { get; }
|
public string Serial { get; }
|
||||||
public PeripheralDeviceTypes ScsiType { get; }
|
public PeripheralDeviceTypes ScsiType { get; }
|
||||||
public bool IsRemovable { get; }
|
public bool IsRemovable { get; }
|
||||||
|
|||||||
@@ -36,42 +36,46 @@ using System.Reflection;
|
|||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
using DiscImageChef.CommonTypes.Interop;
|
using DiscImageChef.CommonTypes.Interop;
|
||||||
using DiscImageChef.Devices;
|
using DiscImageChef.Devices;
|
||||||
|
using PlatformID = DiscImageChef.CommonTypes.Interop.PlatformID;
|
||||||
using Version = DiscImageChef.CommonTypes.Interop.Version;
|
using Version = DiscImageChef.CommonTypes.Interop.Version;
|
||||||
|
|
||||||
namespace DiscImageChef.Core.Logging
|
namespace DiscImageChef.Core.Logging
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>Creates a dump log</summary>
|
||||||
/// Creates a dump log
|
|
||||||
/// </summary>
|
|
||||||
public class DumpLog
|
public class DumpLog
|
||||||
{
|
{
|
||||||
private readonly StreamWriter logSw;
|
readonly StreamWriter logSw;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Initializes the dump log</summary>
|
||||||
/// Initializes the dump log
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="outputFile">Output log file</param>
|
/// <param name="outputFile">Output log file</param>
|
||||||
/// <param name="dev">Device</param>
|
/// <param name="dev">Device</param>
|
||||||
public DumpLog(string outputFile, Device dev)
|
public DumpLog(string outputFile, Device dev)
|
||||||
{
|
{
|
||||||
if (string.IsNullOrEmpty(outputFile)) return;
|
if(string.IsNullOrEmpty(outputFile))
|
||||||
|
return;
|
||||||
|
|
||||||
logSw = new StreamWriter(outputFile, true);
|
logSw = new StreamWriter(outputFile, true);
|
||||||
|
|
||||||
logSw.WriteLine("Start logging at {0}", DateTime.Now);
|
logSw.WriteLine("Start logging at {0}", DateTime.Now);
|
||||||
|
|
||||||
var platId = DetectOS.GetRealPlatformID();
|
PlatformID platId = DetectOS.GetRealPlatformID();
|
||||||
var platVer = DetectOS.GetVersion();
|
string platVer = DetectOS.GetVersion();
|
||||||
|
|
||||||
var assemblyVersion =
|
var assemblyVersion =
|
||||||
Attribute.GetCustomAttribute(typeof(DumpLog).Assembly, typeof(AssemblyInformationalVersionAttribute)) as
|
Attribute.GetCustomAttribute(typeof(DumpLog).Assembly, typeof(AssemblyInformationalVersionAttribute)) as
|
||||||
AssemblyInformationalVersionAttribute;
|
AssemblyInformationalVersionAttribute;
|
||||||
|
|
||||||
logSw.WriteLine("################# System information #################");
|
logSw.WriteLine("################# System information #################");
|
||||||
|
|
||||||
logSw.WriteLine("{0} {1} ({2}-bit)", DetectOS.GetPlatformName(platId, platVer), platVer,
|
logSw.WriteLine("{0} {1} ({2}-bit)", DetectOS.GetPlatformName(platId, platVer), platVer,
|
||||||
Environment.Is64BitOperatingSystem ? 64 : 32);
|
Environment.Is64BitOperatingSystem ? 64 : 32);
|
||||||
if (DetectOS.IsMono) logSw.WriteLine("Mono {0}", Version.GetMonoVersion());
|
|
||||||
else if (DetectOS.IsNetCore) logSw.WriteLine(".NET Core {0}", Version.GetNetCoreVersion());
|
if(DetectOS.IsMono)
|
||||||
else logSw.WriteLine(RuntimeInformation.FrameworkDescription);
|
logSw.WriteLine("Mono {0}", Version.GetMonoVersion());
|
||||||
|
else if(DetectOS.IsNetCore)
|
||||||
|
logSw.WriteLine(".NET Core {0}", Version.GetNetCoreVersion());
|
||||||
|
else
|
||||||
|
logSw.WriteLine(RuntimeInformation.FrameworkDescription);
|
||||||
|
|
||||||
logSw.WriteLine();
|
logSw.WriteLine();
|
||||||
|
|
||||||
@@ -89,8 +93,10 @@ namespace DiscImageChef.Core.Logging
|
|||||||
logSw.WriteLine("################# Remote information #################");
|
logSw.WriteLine("################# Remote information #################");
|
||||||
logSw.WriteLine("Server: {0}", dev.RemoteApplication);
|
logSw.WriteLine("Server: {0}", dev.RemoteApplication);
|
||||||
logSw.WriteLine("Version: {0}", dev.RemoteVersion);
|
logSw.WriteLine("Version: {0}", dev.RemoteVersion);
|
||||||
|
|
||||||
logSw.WriteLine("Operating system: {0} {1}", dev.RemoteOperatingSystem,
|
logSw.WriteLine("Operating system: {0} {1}", dev.RemoteOperatingSystem,
|
||||||
dev.RemoteOperatingSystemVersion);
|
dev.RemoteOperatingSystemVersion);
|
||||||
|
|
||||||
logSw.WriteLine("Architecture: {0}", dev.RemoteArchitecture);
|
logSw.WriteLine("Architecture: {0}", dev.RemoteArchitecture);
|
||||||
logSw.WriteLine("Protocol version: {0}", dev.RemoteProtocolVersion);
|
logSw.WriteLine("Protocol version: {0}", dev.RemoteProtocolVersion);
|
||||||
logSw.WriteLine("######################################################");
|
logSw.WriteLine("######################################################");
|
||||||
@@ -99,13 +105,14 @@ namespace DiscImageChef.Core.Logging
|
|||||||
logSw.WriteLine("################# Device information #################");
|
logSw.WriteLine("################# Device information #################");
|
||||||
logSw.WriteLine("Manufacturer: {0}", dev.Manufacturer);
|
logSw.WriteLine("Manufacturer: {0}", dev.Manufacturer);
|
||||||
logSw.WriteLine("Model: {0}", dev.Model);
|
logSw.WriteLine("Model: {0}", dev.Model);
|
||||||
logSw.WriteLine("Firmware revision: {0}", dev.Revision);
|
logSw.WriteLine("Firmware revision: {0}", dev.FirmwareRevision);
|
||||||
logSw.WriteLine("Serial number: {0}", dev.Serial);
|
logSw.WriteLine("Serial number: {0}", dev.Serial);
|
||||||
logSw.WriteLine("Removable device: {0}", dev.IsRemovable);
|
logSw.WriteLine("Removable device: {0}", dev.IsRemovable);
|
||||||
logSw.WriteLine("Device type: {0}", dev.Type);
|
logSw.WriteLine("Device type: {0}", dev.Type);
|
||||||
logSw.WriteLine("CompactFlash device: {0}", dev.IsCompactFlash);
|
logSw.WriteLine("CompactFlash device: {0}", dev.IsCompactFlash);
|
||||||
logSw.WriteLine("PCMCIA device: {0}", dev.IsPcmcia);
|
logSw.WriteLine("PCMCIA device: {0}", dev.IsPcmcia);
|
||||||
logSw.WriteLine("USB device: {0}", dev.IsUsb);
|
logSw.WriteLine("USB device: {0}", dev.IsUsb);
|
||||||
|
|
||||||
if(dev.IsUsb)
|
if(dev.IsUsb)
|
||||||
{
|
{
|
||||||
logSw.WriteLine("USB manufacturer: {0}", dev.UsbManufacturerString);
|
logSw.WriteLine("USB manufacturer: {0}", dev.UsbManufacturerString);
|
||||||
@@ -116,6 +123,7 @@ namespace DiscImageChef.Core.Logging
|
|||||||
}
|
}
|
||||||
|
|
||||||
logSw.WriteLine("FireWire device: {0}", dev.IsFireWire);
|
logSw.WriteLine("FireWire device: {0}", dev.IsFireWire);
|
||||||
|
|
||||||
if(dev.IsFireWire)
|
if(dev.IsFireWire)
|
||||||
{
|
{
|
||||||
logSw.WriteLine("FireWire vendor: {0}", dev.FireWireVendorName);
|
logSw.WriteLine("FireWire vendor: {0}", dev.FireWireVendorName);
|
||||||
@@ -132,23 +140,20 @@ namespace DiscImageChef.Core.Logging
|
|||||||
logSw.Flush();
|
logSw.Flush();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Adds a new line to the dump log</summary>
|
||||||
/// Adds a new line to the dump log
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="format">Format string</param>
|
/// <param name="format">Format string</param>
|
||||||
/// <param name="args">Arguments</param>
|
/// <param name="args">Arguments</param>
|
||||||
public void WriteLine(string format, params object[] args)
|
public void WriteLine(string format, params object[] args)
|
||||||
{
|
{
|
||||||
if (logSw == null) return;
|
if(logSw == null)
|
||||||
|
return;
|
||||||
|
|
||||||
var text = string.Format(format, args);
|
string text = string.Format(format, args);
|
||||||
logSw.WriteLine("{0:s} {1}", DateTime.Now, text);
|
logSw.WriteLine("{0:s} {1}", DateTime.Now, text);
|
||||||
logSw.Flush();
|
logSw.Flush();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Finishes and closes the dump log</summary>
|
||||||
/// Finishes and closes the dump log
|
|
||||||
/// </summary>
|
|
||||||
public void Close()
|
public void Close()
|
||||||
{
|
{
|
||||||
logSw?.WriteLine("######################################################");
|
logSw?.WriteLine("######################################################");
|
||||||
|
|||||||
@@ -38,33 +38,30 @@ using DiscImageChef.Devices;
|
|||||||
|
|
||||||
namespace DiscImageChef.Core.Logging
|
namespace DiscImageChef.Core.Logging
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>Implements a log in the format used by IMGBurn</summary>
|
||||||
/// Implements a log in the format used by IMGBurn
|
internal class IbgLog
|
||||||
/// </summary>
|
|
||||||
class IbgLog
|
|
||||||
{
|
{
|
||||||
readonly CultureInfo ibgCulture;
|
readonly CultureInfo ibgCulture;
|
||||||
DateTime ibgDatePoint;
|
|
||||||
readonly double ibgDivider;
|
readonly double ibgDivider;
|
||||||
|
readonly string ibgMediaType;
|
||||||
|
readonly StringBuilder ibgSb;
|
||||||
|
readonly string logFile;
|
||||||
|
DateTime ibgDatePoint;
|
||||||
ulong ibgIntSector;
|
ulong ibgIntSector;
|
||||||
double ibgIntSpeed;
|
double ibgIntSpeed;
|
||||||
double ibgMaxSpeed;
|
double ibgMaxSpeed;
|
||||||
readonly string ibgMediaType;
|
|
||||||
int ibgSampleRate;
|
int ibgSampleRate;
|
||||||
readonly StringBuilder ibgSb;
|
|
||||||
int ibgSnaps;
|
int ibgSnaps;
|
||||||
bool ibgStartSet;
|
bool ibgStartSet;
|
||||||
double ibgStartSpeed;
|
double ibgStartSpeed;
|
||||||
readonly string logFile;
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Initializes the IMGBurn log</summary>
|
||||||
/// Initializes the IMGBurn log
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="outputFile">Log file</param>
|
/// <param name="outputFile">Log file</param>
|
||||||
/// <param name="currentProfile">Profile as defined by SCSI MultiMedia Commands specification</param>
|
/// <param name="currentProfile">Profile as defined by SCSI MultiMedia Commands specification</param>
|
||||||
internal IbgLog(string outputFile, ushort currentProfile)
|
internal IbgLog(string outputFile, ushort currentProfile)
|
||||||
{
|
{
|
||||||
if(string.IsNullOrEmpty(outputFile)) return;
|
if(string.IsNullOrEmpty(outputFile))
|
||||||
|
return;
|
||||||
|
|
||||||
logFile = outputFile;
|
logFile = outputFile;
|
||||||
ibgSb = new StringBuilder();
|
ibgSb = new StringBuilder();
|
||||||
@@ -81,153 +78,186 @@ namespace DiscImageChef.Core.Logging
|
|||||||
case 0x0001:
|
case 0x0001:
|
||||||
ibgMediaType = "HDD";
|
ibgMediaType = "HDD";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0002:
|
case 0x0002:
|
||||||
ibgMediaType = "PD-650";
|
ibgMediaType = "PD-650";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0005:
|
case 0x0005:
|
||||||
ibgMediaType = "CD-MO";
|
ibgMediaType = "CD-MO";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0008:
|
case 0x0008:
|
||||||
ibgMediaType = "CD-ROM";
|
ibgMediaType = "CD-ROM";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0009:
|
case 0x0009:
|
||||||
ibgMediaType = "CD-R";
|
ibgMediaType = "CD-R";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x000A:
|
case 0x000A:
|
||||||
ibgMediaType = "CD-RW";
|
ibgMediaType = "CD-RW";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0010:
|
case 0x0010:
|
||||||
ibgMediaType = "DVD-ROM";
|
ibgMediaType = "DVD-ROM";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0011:
|
case 0x0011:
|
||||||
ibgMediaType = "DVD-R";
|
ibgMediaType = "DVD-R";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0012:
|
case 0x0012:
|
||||||
ibgMediaType = "DVD-RAM";
|
ibgMediaType = "DVD-RAM";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0013:
|
case 0x0013:
|
||||||
case 0x0014:
|
case 0x0014:
|
||||||
ibgMediaType = "DVD-RW";
|
ibgMediaType = "DVD-RW";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0015:
|
case 0x0015:
|
||||||
case 0x0016:
|
case 0x0016:
|
||||||
ibgMediaType = "DVD-R DL";
|
ibgMediaType = "DVD-R DL";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0017:
|
case 0x0017:
|
||||||
ibgMediaType = "DVD-RW DL";
|
ibgMediaType = "DVD-RW DL";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0018:
|
case 0x0018:
|
||||||
ibgMediaType = "DVD-Download";
|
ibgMediaType = "DVD-Download";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x001A:
|
case 0x001A:
|
||||||
ibgMediaType = "DVD+RW";
|
ibgMediaType = "DVD+RW";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x001B:
|
case 0x001B:
|
||||||
ibgMediaType = "DVD+R";
|
ibgMediaType = "DVD+R";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0020:
|
case 0x0020:
|
||||||
ibgMediaType = "DDCD-ROM";
|
ibgMediaType = "DDCD-ROM";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0021:
|
case 0x0021:
|
||||||
ibgMediaType = "DDCD-R";
|
ibgMediaType = "DDCD-R";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0022:
|
case 0x0022:
|
||||||
ibgMediaType = "DDCD-RW";
|
ibgMediaType = "DDCD-RW";
|
||||||
ibgDivider = 150;
|
ibgDivider = 150;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x002A:
|
case 0x002A:
|
||||||
ibgMediaType = "DVD+RW DL";
|
ibgMediaType = "DVD+RW DL";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x002B:
|
case 0x002B:
|
||||||
ibgMediaType = "DVD+R DL";
|
ibgMediaType = "DVD+R DL";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0040:
|
case 0x0040:
|
||||||
ibgMediaType = "BD-ROM";
|
ibgMediaType = "BD-ROM";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0041:
|
case 0x0041:
|
||||||
case 0x0042:
|
case 0x0042:
|
||||||
ibgMediaType = "BD-R";
|
ibgMediaType = "BD-R";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0043:
|
case 0x0043:
|
||||||
ibgMediaType = "BD-RE";
|
ibgMediaType = "BD-RE";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0050:
|
case 0x0050:
|
||||||
ibgMediaType = "HD DVD-ROM";
|
ibgMediaType = "HD DVD-ROM";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0051:
|
case 0x0051:
|
||||||
ibgMediaType = "HD DVD-R";
|
ibgMediaType = "HD DVD-R";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0052:
|
case 0x0052:
|
||||||
ibgMediaType = "HD DVD-RAM";
|
ibgMediaType = "HD DVD-RAM";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0053:
|
case 0x0053:
|
||||||
ibgMediaType = "HD DVD-RW";
|
ibgMediaType = "HD DVD-RW";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x0058:
|
case 0x0058:
|
||||||
ibgMediaType = "HD DVD-R DL";
|
ibgMediaType = "HD DVD-R DL";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 0x005A:
|
case 0x005A:
|
||||||
ibgMediaType = "HD DVD-RW DL";
|
ibgMediaType = "HD DVD-RW DL";
|
||||||
ibgDivider = 4500;
|
ibgDivider = 4500;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
ibgMediaType = "Unknown";
|
ibgMediaType = "Unknown";
|
||||||
ibgDivider = 1353;
|
ibgDivider = 1353;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Adds a new speed snapshot to the log</summary>
|
||||||
/// Adds a new speed snapshot to the log
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="sector">Sector for the snapshot</param>
|
/// <param name="sector">Sector for the snapshot</param>
|
||||||
/// <param name="currentSpeed">Current speed at the snapshot</param>
|
/// <param name="currentSpeed">Current speed at the snapshot</param>
|
||||||
internal void Write(ulong sector, double currentSpeed)
|
internal void Write(ulong sector, double currentSpeed)
|
||||||
{
|
{
|
||||||
if(logFile == null) return;
|
if(logFile == null)
|
||||||
|
return;
|
||||||
|
|
||||||
ibgIntSpeed += currentSpeed;
|
ibgIntSpeed += currentSpeed;
|
||||||
ibgSampleRate += (int)Math.Floor((DateTime.Now - ibgDatePoint).TotalMilliseconds);
|
ibgSampleRate += (int)Math.Floor((DateTime.Now - ibgDatePoint).TotalMilliseconds);
|
||||||
ibgSnaps++;
|
ibgSnaps++;
|
||||||
|
|
||||||
if(ibgSampleRate < 100) return;
|
if(ibgSampleRate < 100)
|
||||||
|
return;
|
||||||
|
|
||||||
if(ibgIntSpeed > 0 && !ibgStartSet)
|
if(ibgIntSpeed > 0 &&
|
||||||
|
!ibgStartSet)
|
||||||
{
|
{
|
||||||
ibgStartSpeed = ibgIntSpeed / ibgSnaps / ibgDivider;
|
ibgStartSpeed = ibgIntSpeed / ibgSnaps / ibgDivider;
|
||||||
ibgStartSet = true;
|
ibgStartSet = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
ibgSb.AppendFormat("{0:0.00},{1},{2:0},0", ibgIntSpeed / ibgSnaps / ibgDivider, ibgIntSector, ibgSampleRate)
|
ibgSb.AppendFormat("{0:0.00},{1},{2:0},0", ibgIntSpeed / ibgSnaps / ibgDivider, ibgIntSector,
|
||||||
.AppendLine();
|
ibgSampleRate).AppendLine();
|
||||||
if(ibgIntSpeed / ibgSnaps / ibgDivider > ibgMaxSpeed) ibgMaxSpeed = ibgIntSpeed / ibgDivider;
|
|
||||||
|
if(ibgIntSpeed / ibgSnaps / ibgDivider > ibgMaxSpeed)
|
||||||
|
ibgMaxSpeed = ibgIntSpeed / ibgDivider;
|
||||||
|
|
||||||
ibgDatePoint = DateTime.Now;
|
ibgDatePoint = DateTime.Now;
|
||||||
ibgIntSpeed = 0;
|
ibgIntSpeed = 0;
|
||||||
@@ -236,9 +266,7 @@ namespace DiscImageChef.Core.Logging
|
|||||||
ibgIntSector = sector;
|
ibgIntSector = sector;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Closes the IMGBurn log</summary>
|
||||||
/// Closes the IMGBurn log
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="dev">Device</param>
|
/// <param name="dev">Device</param>
|
||||||
/// <param name="blocks">Media blocks</param>
|
/// <param name="blocks">Media blocks</param>
|
||||||
/// <param name="blockSize">Bytes per block</param>
|
/// <param name="blockSize">Bytes per block</param>
|
||||||
@@ -246,19 +274,22 @@ namespace DiscImageChef.Core.Logging
|
|||||||
/// <param name="currentSpeed">Speed at the end</param>
|
/// <param name="currentSpeed">Speed at the end</param>
|
||||||
/// <param name="averageSpeed">Average speed</param>
|
/// <param name="averageSpeed">Average speed</param>
|
||||||
/// <param name="devicePath">Device path</param>
|
/// <param name="devicePath">Device path</param>
|
||||||
internal void Close(Device dev, ulong blocks, ulong blockSize, double totalSeconds,
|
internal void Close(Device dev, ulong blocks, ulong blockSize, double totalSeconds, double currentSpeed,
|
||||||
double currentSpeed,
|
|
||||||
double averageSpeed, string devicePath)
|
double averageSpeed, string devicePath)
|
||||||
{
|
{
|
||||||
if(logFile == null) return;
|
if(logFile == null)
|
||||||
|
return;
|
||||||
|
|
||||||
FileStream ibgFs = new FileStream(logFile, FileMode.Create);
|
var ibgFs = new FileStream(logFile, FileMode.Create);
|
||||||
StringBuilder ibgHeader = new StringBuilder();
|
var ibgHeader = new StringBuilder();
|
||||||
string ibgBusType;
|
string ibgBusType;
|
||||||
|
|
||||||
if(dev.IsUsb) ibgBusType = "USB";
|
if(dev.IsUsb)
|
||||||
else if(dev.IsFireWire) ibgBusType = "FireWire";
|
ibgBusType = "USB";
|
||||||
else ibgBusType = dev.Type.ToString();
|
else if(dev.IsFireWire)
|
||||||
|
ibgBusType = "FireWire";
|
||||||
|
else
|
||||||
|
ibgBusType = dev.Type.ToString();
|
||||||
|
|
||||||
ibgHeader.AppendLine("IBGD");
|
ibgHeader.AppendLine("IBGD");
|
||||||
ibgHeader.AppendLine();
|
ibgHeader.AppendLine();
|
||||||
@@ -270,11 +301,13 @@ namespace DiscImageChef.Core.Logging
|
|||||||
ibgHeader.AppendFormat("SAMPLE_RATE={0}", 100).AppendLine();
|
ibgHeader.AppendFormat("SAMPLE_RATE={0}", 100).AppendLine();
|
||||||
|
|
||||||
ibgHeader.AppendLine();
|
ibgHeader.AppendLine();
|
||||||
|
|
||||||
ibgHeader.AppendFormat("DEVICE=[0:0:0] {0} {1} ({2}) ({3})", dev.Manufacturer, dev.Model, devicePath,
|
ibgHeader.AppendFormat("DEVICE=[0:0:0] {0} {1} ({2}) ({3})", dev.Manufacturer, dev.Model, devicePath,
|
||||||
ibgBusType).AppendLine();
|
ibgBusType).AppendLine();
|
||||||
|
|
||||||
ibgHeader.AppendLine("DEVICE_ADDRESS=0:0:0");
|
ibgHeader.AppendLine("DEVICE_ADDRESS=0:0:0");
|
||||||
ibgHeader.AppendFormat("DEVICE_MAKEMODEL={0} {1}", dev.Manufacturer, dev.Model).AppendLine();
|
ibgHeader.AppendFormat("DEVICE_MAKEMODEL={0} {1}", dev.Manufacturer, dev.Model).AppendLine();
|
||||||
ibgHeader.AppendFormat("DEVICE_FIRMWAREVERSION={0}", dev.Revision).AppendLine();
|
ibgHeader.AppendFormat("DEVICE_FIRMWAREVERSION={0}", dev.FirmwareRevision).AppendLine();
|
||||||
ibgHeader.AppendFormat("DEVICE_DRIVELETTER={0}", devicePath).AppendLine();
|
ibgHeader.AppendFormat("DEVICE_DRIVELETTER={0}", devicePath).AppendLine();
|
||||||
ibgHeader.AppendFormat("DEVICE_BUSTYPE={0}", ibgBusType).AppendLine();
|
ibgHeader.AppendFormat("DEVICE_BUSTYPE={0}", ibgBusType).AppendLine();
|
||||||
ibgHeader.AppendLine();
|
ibgHeader.AppendLine();
|
||||||
@@ -307,7 +340,7 @@ namespace DiscImageChef.Core.Logging
|
|||||||
ibgHeader.AppendLine();
|
ibgHeader.AppendLine();
|
||||||
ibgHeader.Replace("\r\n", "\n").Replace("\r", "\n").Replace("\n", "\r\n");
|
ibgHeader.Replace("\r\n", "\n").Replace("\r", "\n").Replace("\n", "\r\n");
|
||||||
|
|
||||||
StreamWriter sr = new StreamWriter(ibgFs);
|
var sr = new StreamWriter(ibgFs);
|
||||||
sr.Write(ibgHeader);
|
sr.Write(ibgHeader);
|
||||||
sr.Close();
|
sr.Close();
|
||||||
ibgFs.Close();
|
ibgFs.Close();
|
||||||
|
|||||||
@@ -39,17 +39,13 @@ using DiscImageChef.Devices;
|
|||||||
|
|
||||||
namespace DiscImageChef.Core.Logging
|
namespace DiscImageChef.Core.Logging
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>Implements a log in the format used by MHDD</summary>
|
||||||
/// Implements a log in the format used by MHDD
|
internal class MhddLog
|
||||||
/// </summary>
|
|
||||||
class MhddLog
|
|
||||||
{
|
{
|
||||||
string logFile;
|
readonly string logFile;
|
||||||
MemoryStream mhddFs;
|
readonly MemoryStream mhddFs;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Initializes the MHDD log</summary>
|
||||||
/// Initializes the MHDD log
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="outputFile">Log file</param>
|
/// <param name="outputFile">Log file</param>
|
||||||
/// <param name="dev">Device</param>
|
/// <param name="dev">Device</param>
|
||||||
/// <param name="blocks">Blocks in media</param>
|
/// <param name="blocks">Blocks in media</param>
|
||||||
@@ -57,7 +53,9 @@ namespace DiscImageChef.Core.Logging
|
|||||||
/// <param name="blocksToRead">How many blocks read at once</param>
|
/// <param name="blocksToRead">How many blocks read at once</param>
|
||||||
internal MhddLog(string outputFile, Device dev, ulong blocks, ulong blockSize, ulong blocksToRead)
|
internal MhddLog(string outputFile, Device dev, ulong blocks, ulong blockSize, ulong blocksToRead)
|
||||||
{
|
{
|
||||||
if(dev == null || string.IsNullOrEmpty(outputFile)) return;
|
if(dev == null ||
|
||||||
|
string.IsNullOrEmpty(outputFile))
|
||||||
|
return;
|
||||||
|
|
||||||
mhddFs = new MemoryStream();
|
mhddFs = new MemoryStream();
|
||||||
logFile = outputFile;
|
logFile = outputFile;
|
||||||
@@ -69,31 +67,39 @@ namespace DiscImageChef.Core.Logging
|
|||||||
case DeviceType.ATA:
|
case DeviceType.ATA:
|
||||||
case DeviceType.ATAPI:
|
case DeviceType.ATAPI:
|
||||||
mode = "MODE: IDE";
|
mode = "MODE: IDE";
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.SCSI:
|
case DeviceType.SCSI:
|
||||||
mode = "MODE: SCSI";
|
mode = "MODE: SCSI";
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.MMC:
|
case DeviceType.MMC:
|
||||||
mode = "MODE: MMC";
|
mode = "MODE: MMC";
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.NVMe:
|
case DeviceType.NVMe:
|
||||||
mode = "MODE: NVMe";
|
mode = "MODE: NVMe";
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.SecureDigital:
|
case DeviceType.SecureDigital:
|
||||||
mode = "MODE: SD";
|
mode = "MODE: SD";
|
||||||
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
mode = "MODE: IDE";
|
mode = "MODE: IDE";
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
string device = $"DEVICE: {dev.Manufacturer} {dev.Model}";
|
string device = $"DEVICE: {dev.Manufacturer} {dev.Model}";
|
||||||
string fw = $"F/W: {dev.Revision}";
|
string fw = $"F/W: {dev.FirmwareRevision}";
|
||||||
string sn = $"S/N: {dev.Serial}";
|
string sn = $"S/N: {dev.Serial}";
|
||||||
string sectors = string.Format(new CultureInfo("en-US"), "SECTORS: {0:n0}", blocks);
|
string sectors = string.Format(new CultureInfo("en-US"), "SECTORS: {0:n0}", blocks);
|
||||||
string sectorsize = string.Format(new CultureInfo("en-US"), "SECTOR SIZE: {0:n0} bytes", blockSize);
|
string sectorsize = string.Format(new CultureInfo("en-US"), "SECTOR SIZE: {0:n0} bytes", blockSize);
|
||||||
|
|
||||||
string scanblocksize =
|
string scanblocksize =
|
||||||
string.Format(new CultureInfo("en-US"), "SCAN BLOCK SIZE: {0:n0} sectors", blocksToRead);
|
string.Format(new CultureInfo("en-US"), "SCAN BLOCK SIZE: {0:n0} sectors", blocksToRead);
|
||||||
|
|
||||||
const string MHDD_VER = "VER:2 ";
|
const string MHDD_VER = "VER:2 ";
|
||||||
|
|
||||||
byte[] deviceBytes = Encoding.ASCII.GetBytes(device);
|
byte[] deviceBytes = Encoding.ASCII.GetBytes(device);
|
||||||
@@ -108,7 +114,7 @@ namespace DiscImageChef.Core.Logging
|
|||||||
uint pointer = (uint)(deviceBytes.Length + modeBytes.Length + fwBytes.Length +
|
uint pointer = (uint)(deviceBytes.Length + modeBytes.Length + fwBytes.Length +
|
||||||
snBytes.Length +
|
snBytes.Length +
|
||||||
sectorsBytes.Length + sectorsizeBytes.Length + scanblocksizeBytes.Length +
|
sectorsBytes.Length + sectorsizeBytes.Length + scanblocksizeBytes.Length +
|
||||||
verBytes.Length + 2 * 9 + // New lines
|
verBytes.Length + (2 * 9) + // New lines
|
||||||
4); // Pointer
|
4); // Pointer
|
||||||
|
|
||||||
byte[] newLine = new byte[2];
|
byte[] newLine = new byte[2];
|
||||||
@@ -135,14 +141,13 @@ namespace DiscImageChef.Core.Logging
|
|||||||
mhddFs.Write(newLine, 0, 2);
|
mhddFs.Write(newLine, 0, 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Logs a new read</summary>
|
||||||
/// Logs a new read
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="sector">Starting sector</param>
|
/// <param name="sector">Starting sector</param>
|
||||||
/// <param name="duration">Duration in milliseconds</param>
|
/// <param name="duration">Duration in milliseconds</param>
|
||||||
internal void Write(ulong sector, double duration)
|
internal void Write(ulong sector, double duration)
|
||||||
{
|
{
|
||||||
if(logFile == null) return;
|
if(logFile == null)
|
||||||
|
return;
|
||||||
|
|
||||||
byte[] sectorBytes = BitConverter.GetBytes(sector);
|
byte[] sectorBytes = BitConverter.GetBytes(sector);
|
||||||
byte[] durationBytes = BitConverter.GetBytes((ulong)(duration * 1000));
|
byte[] durationBytes = BitConverter.GetBytes((ulong)(duration * 1000));
|
||||||
@@ -151,14 +156,13 @@ namespace DiscImageChef.Core.Logging
|
|||||||
mhddFs.Write(durationBytes, 0, 8);
|
mhddFs.Write(durationBytes, 0, 8);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>Closes and writes to file the MHDD log</summary>
|
||||||
/// Closes and writes to file the MHDD log
|
|
||||||
/// </summary>
|
|
||||||
internal void Close()
|
internal void Close()
|
||||||
{
|
{
|
||||||
if(logFile == null) return;
|
if(logFile == null)
|
||||||
|
return;
|
||||||
|
|
||||||
FileStream fs = new FileStream(logFile, FileMode.Create);
|
var fs = new FileStream(logFile, FileMode.Create);
|
||||||
mhddFs.WriteTo(fs);
|
mhddFs.WriteTo(fs);
|
||||||
mhddFs.Close();
|
mhddFs.Close();
|
||||||
fs.Close();
|
fs.Close();
|
||||||
|
|||||||
@@ -1272,7 +1272,8 @@ namespace DiscImageChef.Core
|
|||||||
|
|
||||||
ctx.SeenDevices.Add(new DeviceStat
|
ctx.SeenDevices.Add(new DeviceStat
|
||||||
{
|
{
|
||||||
Bus = deviceBus, Manufacturer = dev.Manufacturer, Model = dev.Model, Revision = dev.Revision,
|
Bus = deviceBus, Manufacturer = dev.Manufacturer, Model = dev.Model,
|
||||||
|
Revision = dev.FirmwareRevision,
|
||||||
Synchronized = false
|
Synchronized = false
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -40,6 +40,7 @@ using DiscImageChef.CommonTypes.Interop;
|
|||||||
using DiscImageChef.Decoders.ATA;
|
using DiscImageChef.Decoders.ATA;
|
||||||
using DiscImageChef.Decoders.SCSI;
|
using DiscImageChef.Decoders.SCSI;
|
||||||
using DiscImageChef.Decoders.SCSI.MMC;
|
using DiscImageChef.Decoders.SCSI.MMC;
|
||||||
|
using DiscImageChef.Decoders.SecureDigital;
|
||||||
using DiscImageChef.Devices.FreeBSD;
|
using DiscImageChef.Devices.FreeBSD;
|
||||||
using DiscImageChef.Devices.Windows;
|
using DiscImageChef.Devices.Windows;
|
||||||
using Microsoft.Win32.SafeHandles;
|
using Microsoft.Win32.SafeHandles;
|
||||||
@@ -56,9 +57,7 @@ namespace DiscImageChef.Devices
|
|||||||
{
|
{
|
||||||
public partial class Device
|
public partial class Device
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>Opens the device for sending direct commands</summary>
|
||||||
/// Opens the device for sending direct commands
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="devicePath">Device path</param>
|
/// <param name="devicePath">Device path</param>
|
||||||
public Device(string devicePath)
|
public Device(string devicePath)
|
||||||
{
|
{
|
||||||
@@ -70,13 +69,13 @@ namespace DiscImageChef.Devices
|
|||||||
if(devicePath.StartsWith("dic://"))
|
if(devicePath.StartsWith("dic://"))
|
||||||
{
|
{
|
||||||
devicePath = devicePath.Substring(6);
|
devicePath = devicePath.Substring(6);
|
||||||
var pieces = devicePath.Split('/');
|
string[] pieces = devicePath.Split('/');
|
||||||
var host = pieces[0];
|
string host = pieces[0];
|
||||||
devicePath = devicePath.Substring(host.Length);
|
devicePath = devicePath.Substring(host.Length);
|
||||||
|
|
||||||
_remote = new Remote.Remote(host);
|
_remote = new Remote.Remote(host);
|
||||||
|
|
||||||
Error = !_remote.Open(devicePath, out var errno);
|
Error = !_remote.Open(devicePath, out int errno);
|
||||||
LastError = errno;
|
LastError = errno;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -86,9 +85,9 @@ namespace DiscImageChef.Devices
|
|||||||
case PlatformID.Win32NT:
|
case PlatformID.Win32NT:
|
||||||
{
|
{
|
||||||
FileHandle = Extern.CreateFile(devicePath, FileAccess.GenericRead | FileAccess.GenericWrite,
|
FileHandle = Extern.CreateFile(devicePath, FileAccess.GenericRead | FileAccess.GenericWrite,
|
||||||
FileShare.Read | FileShare.Write, IntPtr.Zero,
|
FileShare.Read | FileShare.Write,
|
||||||
FileMode.OpenExisting,
|
IntPtr.Zero,
|
||||||
FileAttributes.Normal, IntPtr.Zero);
|
FileMode.OpenExisting, FileAttributes.Normal, IntPtr.Zero);
|
||||||
|
|
||||||
if(((SafeFileHandle)FileHandle).IsInvalid)
|
if(((SafeFileHandle)FileHandle).IsInvalid)
|
||||||
{
|
{
|
||||||
@@ -108,9 +107,11 @@ namespace DiscImageChef.Devices
|
|||||||
{
|
{
|
||||||
LastError = Marshal.GetLastWin32Error();
|
LastError = Marshal.GetLastWin32Error();
|
||||||
|
|
||||||
if (LastError == 13 || LastError == 30) // EACCES or EROFS
|
if(LastError == 13 ||
|
||||||
|
LastError == 30) // EACCES or EROFS
|
||||||
{
|
{
|
||||||
FileHandle = Linux.Extern.open(devicePath, FileFlags.Readonly | FileFlags.NonBlocking);
|
FileHandle = Linux.Extern.open(devicePath, FileFlags.Readonly | FileFlags.NonBlocking);
|
||||||
|
|
||||||
if((int)FileHandle < 0)
|
if((int)FileHandle < 0)
|
||||||
{
|
{
|
||||||
Error = true;
|
Error = true;
|
||||||
@@ -141,8 +142,7 @@ namespace DiscImageChef.Devices
|
|||||||
|
|
||||||
if(StringHandlers.CToString(camDevice.SimName) == "ata")
|
if(StringHandlers.CToString(camDevice.SimName) == "ata")
|
||||||
throw new
|
throw new
|
||||||
DeviceException(
|
DeviceException("Parallel ATA devices are not supported on FreeBSD due to upstream bug #224250.");
|
||||||
"Parallel ATA devices are not supported on FreeBSD due to upstream bug #224250.");
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -150,7 +150,8 @@ namespace DiscImageChef.Devices
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Error) throw new DeviceException(LastError);
|
if(Error)
|
||||||
|
throw new DeviceException(LastError);
|
||||||
|
|
||||||
Type = DeviceType.Unknown;
|
Type = DeviceType.Unknown;
|
||||||
ScsiType = PeripheralDeviceTypes.UnknownDevice;
|
ScsiType = PeripheralDeviceTypes.UnknownDevice;
|
||||||
@@ -158,9 +159,10 @@ namespace DiscImageChef.Devices
|
|||||||
byte[] ataBuf;
|
byte[] ataBuf;
|
||||||
byte[] inqBuf = null;
|
byte[] inqBuf = null;
|
||||||
|
|
||||||
if (Error) throw new DeviceException(LastError);
|
if(Error)
|
||||||
|
throw new DeviceException(LastError);
|
||||||
|
|
||||||
var scsiSense = true;
|
bool scsiSense = true;
|
||||||
|
|
||||||
if(_remote is null)
|
if(_remote is null)
|
||||||
{
|
{
|
||||||
@@ -173,22 +175,25 @@ namespace DiscImageChef.Devices
|
|||||||
query.QueryType = StorageQueryType.Standard;
|
query.QueryType = StorageQueryType.Standard;
|
||||||
query.AdditionalParameters = new byte[1];
|
query.AdditionalParameters = new byte[1];
|
||||||
|
|
||||||
var descriptorPtr = Marshal.AllocHGlobal(1000);
|
IntPtr descriptorPtr = Marshal.AllocHGlobal(1000);
|
||||||
var descriptorB = new byte[1000];
|
byte[] descriptorB = new byte[1000];
|
||||||
|
|
||||||
uint returned = 0;
|
uint returned = 0;
|
||||||
var error = 0;
|
int error = 0;
|
||||||
|
|
||||||
var hasError = !Extern.DeviceIoControlStorageQuery((SafeFileHandle) FileHandle,
|
bool hasError = !Extern.DeviceIoControlStorageQuery((SafeFileHandle)FileHandle,
|
||||||
WindowsIoctl.IoctlStorageQueryProperty,
|
WindowsIoctl.IoctlStorageQueryProperty,
|
||||||
ref query, (uint)Marshal.SizeOf(query),
|
ref query, (uint)Marshal.SizeOf(query),
|
||||||
descriptorPtr, 1000, ref returned, IntPtr.Zero);
|
descriptorPtr, 1000, ref returned,
|
||||||
|
IntPtr.Zero);
|
||||||
|
|
||||||
if (hasError) error = Marshal.GetLastWin32Error();
|
if(hasError)
|
||||||
|
error = Marshal.GetLastWin32Error();
|
||||||
|
|
||||||
Marshal.Copy(descriptorPtr, descriptorB, 0, 1000);
|
Marshal.Copy(descriptorPtr, descriptorB, 0, 1000);
|
||||||
|
|
||||||
if (!hasError && error == 0)
|
if(!hasError &&
|
||||||
|
error == 0)
|
||||||
{
|
{
|
||||||
var descriptor = new StorageDeviceDescriptor
|
var descriptor = new StorageDeviceDescriptor
|
||||||
{
|
{
|
||||||
@@ -197,7 +202,8 @@ namespace DiscImageChef.Devices
|
|||||||
DeviceType = descriptorB[8],
|
DeviceType = descriptorB[8],
|
||||||
DeviceTypeModifier = descriptorB[9],
|
DeviceTypeModifier = descriptorB[9],
|
||||||
RemovableMedia = descriptorB[10] > 0,
|
RemovableMedia = descriptorB[10] > 0,
|
||||||
CommandQueueing = descriptorB[11] > 0,
|
CommandQueueing =
|
||||||
|
descriptorB[11] > 0,
|
||||||
VendorIdOffset = BitConverter.ToInt32(descriptorB, 12),
|
VendorIdOffset = BitConverter.ToInt32(descriptorB, 12),
|
||||||
ProductIdOffset = BitConverter.ToInt32(descriptorB, 16),
|
ProductIdOffset = BitConverter.ToInt32(descriptorB, 16),
|
||||||
ProductRevisionOffset = BitConverter.ToInt32(descriptorB, 20),
|
ProductRevisionOffset = BitConverter.ToInt32(descriptorB, 20),
|
||||||
@@ -205,7 +211,9 @@ namespace DiscImageChef.Devices
|
|||||||
BusType = (StorageBusType)BitConverter.ToUInt32(descriptorB, 28),
|
BusType = (StorageBusType)BitConverter.ToUInt32(descriptorB, 28),
|
||||||
RawPropertiesLength = BitConverter.ToUInt32(descriptorB, 32)
|
RawPropertiesLength = BitConverter.ToUInt32(descriptorB, 32)
|
||||||
};
|
};
|
||||||
|
|
||||||
descriptor.RawDeviceProperties = new byte[descriptor.RawPropertiesLength];
|
descriptor.RawDeviceProperties = new byte[descriptor.RawPropertiesLength];
|
||||||
|
|
||||||
Array.Copy(descriptorB, 36, descriptor.RawDeviceProperties, 0,
|
Array.Copy(descriptorB, 36, descriptor.RawDeviceProperties, 0,
|
||||||
descriptor.RawPropertiesLength);
|
descriptor.RawPropertiesLength);
|
||||||
|
|
||||||
@@ -217,30 +225,38 @@ namespace DiscImageChef.Devices
|
|||||||
case StorageBusType.iSCSI:
|
case StorageBusType.iSCSI:
|
||||||
case StorageBusType.SAS:
|
case StorageBusType.SAS:
|
||||||
Type = DeviceType.SCSI;
|
Type = DeviceType.SCSI;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.FireWire:
|
case StorageBusType.FireWire:
|
||||||
IsFireWire = true;
|
IsFireWire = true;
|
||||||
Type = DeviceType.SCSI;
|
Type = DeviceType.SCSI;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.USB:
|
case StorageBusType.USB:
|
||||||
IsUsb = true;
|
IsUsb = true;
|
||||||
Type = DeviceType.SCSI;
|
Type = DeviceType.SCSI;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.ATAPI:
|
case StorageBusType.ATAPI:
|
||||||
Type = DeviceType.ATAPI;
|
Type = DeviceType.ATAPI;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.ATA:
|
case StorageBusType.ATA:
|
||||||
case StorageBusType.SATA:
|
case StorageBusType.SATA:
|
||||||
Type = DeviceType.ATA;
|
Type = DeviceType.ATA;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.MultiMediaCard:
|
case StorageBusType.MultiMediaCard:
|
||||||
Type = DeviceType.MMC;
|
Type = DeviceType.MMC;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.SecureDigital:
|
case StorageBusType.SecureDigital:
|
||||||
Type = DeviceType.SecureDigital;
|
Type = DeviceType.SecureDigital;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case StorageBusType.NVMe:
|
case StorageBusType.NVMe:
|
||||||
Type = DeviceType.NVMe;
|
Type = DeviceType.NVMe;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -249,16 +265,18 @@ namespace DiscImageChef.Devices
|
|||||||
case DeviceType.SCSI:
|
case DeviceType.SCSI:
|
||||||
case DeviceType.ATAPI:
|
case DeviceType.ATAPI:
|
||||||
scsiSense = ScsiInquiry(out inqBuf, out _);
|
scsiSense = ScsiInquiry(out inqBuf, out _);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.ATA:
|
case DeviceType.ATA:
|
||||||
var atapiSense = AtapiIdentify(out ataBuf, out _);
|
bool atapiSense = AtapiIdentify(out ataBuf, out _);
|
||||||
|
|
||||||
if(!atapiSense)
|
if(!atapiSense)
|
||||||
{
|
{
|
||||||
Type = DeviceType.ATAPI;
|
Type = DeviceType.ATAPI;
|
||||||
var ataid = Identify.Decode(ataBuf);
|
Identify.IdentifyDevice? ataid = Identify.Decode(ataBuf);
|
||||||
|
|
||||||
if (ataid.HasValue) scsiSense = ScsiInquiry(out inqBuf, out _);
|
if(ataid.HasValue)
|
||||||
|
scsiSense = ScsiInquiry(out inqBuf, out _);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -273,13 +291,13 @@ namespace DiscImageChef.Devices
|
|||||||
|
|
||||||
if(Windows.Command.IsSdhci((SafeFileHandle)FileHandle))
|
if(Windows.Command.IsSdhci((SafeFileHandle)FileHandle))
|
||||||
{
|
{
|
||||||
var sdBuffer = new byte[16];
|
byte[] sdBuffer = new byte[16];
|
||||||
|
|
||||||
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle, MmcCommands.SendCsd,
|
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle, MmcCommands.SendCsd,
|
||||||
false, false,
|
false, false,
|
||||||
MmcFlags.ResponseSpiR2 | MmcFlags.ResponseR2 |
|
MmcFlags.ResponseSpiR2 | MmcFlags.ResponseR2 |
|
||||||
MmcFlags.CommandAc, 0, 16, 1, ref sdBuffer, out _,
|
MmcFlags.CommandAc, 0, 16, 1, ref sdBuffer,
|
||||||
out _, out var sense);
|
out _, out _, out bool sense);
|
||||||
|
|
||||||
if(!sense)
|
if(!sense)
|
||||||
{
|
{
|
||||||
@@ -292,8 +310,8 @@ namespace DiscImageChef.Devices
|
|||||||
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle, MmcCommands.SendCid,
|
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle, MmcCommands.SendCid,
|
||||||
false, false,
|
false, false,
|
||||||
MmcFlags.ResponseSpiR2 | MmcFlags.ResponseR2 |
|
MmcFlags.ResponseSpiR2 | MmcFlags.ResponseR2 |
|
||||||
MmcFlags.CommandAc, 0, 16, 1, ref sdBuffer, out _,
|
MmcFlags.CommandAc, 0, 16, 1, ref sdBuffer,
|
||||||
out _, out sense);
|
out _, out _, out sense);
|
||||||
|
|
||||||
if(!sense)
|
if(!sense)
|
||||||
{
|
{
|
||||||
@@ -304,11 +322,11 @@ namespace DiscImageChef.Devices
|
|||||||
sdBuffer = new byte[8];
|
sdBuffer = new byte[8];
|
||||||
|
|
||||||
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle,
|
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle,
|
||||||
(MmcCommands) SecureDigitalCommands.SendScr, false,
|
(MmcCommands)SecureDigitalCommands.SendScr,
|
||||||
true,
|
false, true,
|
||||||
MmcFlags.ResponseSpiR1 | MmcFlags.ResponseR1 |
|
MmcFlags.ResponseSpiR1 | MmcFlags.ResponseR1 |
|
||||||
MmcFlags.CommandAdtc, 0, 8, 1, ref sdBuffer, out _,
|
MmcFlags.CommandAdtc, 0, 8, 1, ref sdBuffer,
|
||||||
out _, out sense);
|
out _, out _, out sense);
|
||||||
|
|
||||||
if(!sense)
|
if(!sense)
|
||||||
{
|
{
|
||||||
@@ -320,8 +338,8 @@ namespace DiscImageChef.Devices
|
|||||||
|
|
||||||
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle,
|
LastError = Windows.Command.SendMmcCommand((SafeFileHandle)FileHandle,
|
||||||
cachedScr != null
|
cachedScr != null
|
||||||
? (MmcCommands) SecureDigitalCommands
|
? (MmcCommands)SecureDigitalCommands.
|
||||||
.SendOperatingCondition
|
SendOperatingCondition
|
||||||
: MmcCommands.SendOpCond, false, true,
|
: MmcCommands.SendOpCond, false, true,
|
||||||
MmcFlags.ResponseSpiR3 | MmcFlags.ResponseR3 |
|
MmcFlags.ResponseSpiR3 | MmcFlags.ResponseR3 |
|
||||||
MmcFlags.CommandBcr, 0, 4, 1, ref sdBuffer,
|
MmcFlags.CommandBcr, 0, 4, 1, ref sdBuffer,
|
||||||
@@ -342,42 +360,49 @@ namespace DiscImageChef.Devices
|
|||||||
{
|
{
|
||||||
scsiSense = ScsiInquiry(out inqBuf, out _);
|
scsiSense = ScsiInquiry(out inqBuf, out _);
|
||||||
}
|
}
|
||||||
|
|
||||||
// MultiMediaCard and SecureDigital go here
|
// MultiMediaCard and SecureDigital go here
|
||||||
else if(devicePath.StartsWith("/dev/mmcblk", StringComparison.Ordinal))
|
else if(devicePath.StartsWith("/dev/mmcblk", StringComparison.Ordinal))
|
||||||
{
|
{
|
||||||
var devPath = devicePath.Substring(5);
|
string devPath = devicePath.Substring(5);
|
||||||
|
|
||||||
if(File.Exists("/sys/block/" + devPath + "/device/csd"))
|
if(File.Exists("/sys/block/" + devPath + "/device/csd"))
|
||||||
{
|
{
|
||||||
var len =
|
int len = ConvertFromHexAscii("/sys/block/" + devPath + "/device/csd", out cachedCsd);
|
||||||
ConvertFromHexAscii("/sys/block/" + devPath + "/device/csd", out cachedCsd);
|
|
||||||
if (len == 0) cachedCsd = null;
|
if(len == 0)
|
||||||
|
cachedCsd = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(File.Exists("/sys/block/" + devPath + "/device/cid"))
|
if(File.Exists("/sys/block/" + devPath + "/device/cid"))
|
||||||
{
|
{
|
||||||
var len =
|
int len = ConvertFromHexAscii("/sys/block/" + devPath + "/device/cid", out cachedCid);
|
||||||
ConvertFromHexAscii("/sys/block/" + devPath + "/device/cid", out cachedCid);
|
|
||||||
if (len == 0) cachedCid = null;
|
if(len == 0)
|
||||||
|
cachedCid = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(File.Exists("/sys/block/" + devPath + "/device/scr"))
|
if(File.Exists("/sys/block/" + devPath + "/device/scr"))
|
||||||
{
|
{
|
||||||
var len =
|
int len = ConvertFromHexAscii("/sys/block/" + devPath + "/device/scr", out cachedScr);
|
||||||
ConvertFromHexAscii("/sys/block/" + devPath + "/device/scr", out cachedScr);
|
|
||||||
if (len == 0) cachedScr = null;
|
if(len == 0)
|
||||||
|
cachedScr = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(File.Exists("/sys/block/" + devPath + "/device/ocr"))
|
if(File.Exists("/sys/block/" + devPath + "/device/ocr"))
|
||||||
{
|
{
|
||||||
var len =
|
int len = ConvertFromHexAscii("/sys/block/" + devPath + "/device/ocr", out cachedOcr);
|
||||||
ConvertFromHexAscii("/sys/block/" + devPath + "/device/ocr", out cachedOcr);
|
|
||||||
if (len == 0) cachedOcr = null;
|
if(len == 0)
|
||||||
|
cachedOcr = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
scsiSense = ScsiInquiry(out inqBuf, out _);
|
scsiSense = ScsiInquiry(out inqBuf, out _);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -390,6 +415,7 @@ namespace DiscImageChef.Devices
|
|||||||
case DeviceType.ATAPI:
|
case DeviceType.ATAPI:
|
||||||
case DeviceType.SCSI:
|
case DeviceType.SCSI:
|
||||||
scsiSense = ScsiInquiry(out inqBuf, out _);
|
scsiSense = ScsiInquiry(out inqBuf, out _);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case DeviceType.SecureDigital:
|
case DeviceType.SecureDigital:
|
||||||
case DeviceType.MMC:
|
case DeviceType.MMC:
|
||||||
@@ -404,7 +430,6 @@ namespace DiscImageChef.Devices
|
|||||||
}
|
}
|
||||||
|
|
||||||
#region SecureDigital / MultiMediaCard
|
#region SecureDigital / MultiMediaCard
|
||||||
|
|
||||||
if(cachedCid != null)
|
if(cachedCid != null)
|
||||||
{
|
{
|
||||||
ScsiType = PeripheralDeviceTypes.DirectAccess;
|
ScsiType = PeripheralDeviceTypes.DirectAccess;
|
||||||
@@ -413,27 +438,31 @@ namespace DiscImageChef.Devices
|
|||||||
if(cachedScr != null)
|
if(cachedScr != null)
|
||||||
{
|
{
|
||||||
Type = DeviceType.SecureDigital;
|
Type = DeviceType.SecureDigital;
|
||||||
var decoded = Decoders.SecureDigital.Decoders.DecodeCID(cachedCid);
|
CID decoded = Decoders.SecureDigital.Decoders.DecodeCID(cachedCid);
|
||||||
Manufacturer = VendorString.Prettify(decoded.Manufacturer);
|
Manufacturer = VendorString.Prettify(decoded.Manufacturer);
|
||||||
Model = decoded.ProductName;
|
Model = decoded.ProductName;
|
||||||
Revision = $"{(decoded.ProductRevision & 0xF0) >> 4:X2}.{decoded.ProductRevision & 0x0F:X2}";
|
|
||||||
|
FirmwareRevision =
|
||||||
|
$"{(decoded.ProductRevision & 0xF0) >> 4:X2}.{decoded.ProductRevision & 0x0F:X2}";
|
||||||
|
|
||||||
Serial = $"{decoded.ProductSerialNumber}";
|
Serial = $"{decoded.ProductSerialNumber}";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Type = DeviceType.MMC;
|
Type = DeviceType.MMC;
|
||||||
var decoded = Decoders.MMC.Decoders.DecodeCID(cachedCid);
|
Decoders.MMC.CID decoded = Decoders.MMC.Decoders.DecodeCID(cachedCid);
|
||||||
Manufacturer = Decoders.MMC.VendorString.Prettify(decoded.Manufacturer);
|
Manufacturer = Decoders.MMC.VendorString.Prettify(decoded.Manufacturer);
|
||||||
Model = decoded.ProductName;
|
Model = decoded.ProductName;
|
||||||
Revision = $"{(decoded.ProductRevision & 0xF0) >> 4:X2}.{decoded.ProductRevision & 0x0F:X2}";
|
|
||||||
|
FirmwareRevision =
|
||||||
|
$"{(decoded.ProductRevision & 0xF0) >> 4:X2}.{decoded.ProductRevision & 0x0F:X2}";
|
||||||
|
|
||||||
Serial = $"{decoded.ProductSerialNumber}";
|
Serial = $"{decoded.ProductSerialNumber}";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion SecureDigital / MultiMediaCard
|
#endregion SecureDigital / MultiMediaCard
|
||||||
|
|
||||||
#region USB
|
#region USB
|
||||||
|
|
||||||
if(_remote is null)
|
if(_remote is null)
|
||||||
{
|
{
|
||||||
switch(PlatformId)
|
switch(PlatformId)
|
||||||
@@ -443,10 +472,12 @@ namespace DiscImageChef.Devices
|
|||||||
devicePath.StartsWith("/dev/sr", StringComparison.Ordinal) ||
|
devicePath.StartsWith("/dev/sr", StringComparison.Ordinal) ||
|
||||||
devicePath.StartsWith("/dev/st", StringComparison.Ordinal))
|
devicePath.StartsWith("/dev/st", StringComparison.Ordinal))
|
||||||
{
|
{
|
||||||
var devPath = devicePath.Substring(5);
|
string devPath = devicePath.Substring(5);
|
||||||
|
|
||||||
if(Directory.Exists("/sys/block/" + devPath))
|
if(Directory.Exists("/sys/block/" + devPath))
|
||||||
{
|
{
|
||||||
var resolvedLink = Linux.Command.ReadLink("/sys/block/" + devPath);
|
string resolvedLink = Linux.Command.ReadLink("/sys/block/" + devPath);
|
||||||
|
|
||||||
if(!string.IsNullOrEmpty(resolvedLink))
|
if(!string.IsNullOrEmpty(resolvedLink))
|
||||||
{
|
{
|
||||||
resolvedLink = "/sys" + resolvedLink.Substring(2);
|
resolvedLink = "/sys" + resolvedLink.Substring(2);
|
||||||
@@ -454,29 +485,35 @@ namespace DiscImageChef.Devices
|
|||||||
while(resolvedLink.Contains("usb"))
|
while(resolvedLink.Contains("usb"))
|
||||||
{
|
{
|
||||||
resolvedLink = Path.GetDirectoryName(resolvedLink);
|
resolvedLink = Path.GetDirectoryName(resolvedLink);
|
||||||
|
|
||||||
if(!File.Exists(resolvedLink + "/descriptors") ||
|
if(!File.Exists(resolvedLink + "/descriptors") ||
|
||||||
!File.Exists(resolvedLink + "/idProduct") ||
|
!File.Exists(resolvedLink + "/idProduct") ||
|
||||||
!File.Exists(resolvedLink + "/idVendor")) continue;
|
!File.Exists(resolvedLink + "/idVendor"))
|
||||||
|
continue;
|
||||||
|
|
||||||
var usbFs = new FileStream(resolvedLink + "/descriptors",
|
var usbFs = new FileStream(resolvedLink + "/descriptors",
|
||||||
System.IO.FileMode.Open,
|
System.IO.FileMode.Open, System.IO.FileAccess.Read);
|
||||||
System.IO.FileAccess.Read);
|
|
||||||
var usbBuf = new byte[65536];
|
byte[] usbBuf = new byte[65536];
|
||||||
var usbCount = usbFs.Read(usbBuf, 0, 65536);
|
int usbCount = usbFs.Read(usbBuf, 0, 65536);
|
||||||
UsbDescriptors = new byte[usbCount];
|
UsbDescriptors = new byte[usbCount];
|
||||||
Array.Copy(usbBuf, 0, UsbDescriptors, 0, usbCount);
|
Array.Copy(usbBuf, 0, UsbDescriptors, 0, usbCount);
|
||||||
usbFs.Close();
|
usbFs.Close();
|
||||||
|
|
||||||
var usbSr = new StreamReader(resolvedLink + "/idProduct");
|
var usbSr = new StreamReader(resolvedLink + "/idProduct");
|
||||||
var usbTemp = usbSr.ReadToEnd();
|
string usbTemp = usbSr.ReadToEnd();
|
||||||
|
|
||||||
ushort.TryParse(usbTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
ushort.TryParse(usbTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
||||||
out usbProduct);
|
out usbProduct);
|
||||||
|
|
||||||
usbSr.Close();
|
usbSr.Close();
|
||||||
|
|
||||||
usbSr = new StreamReader(resolvedLink + "/idVendor");
|
usbSr = new StreamReader(resolvedLink + "/idVendor");
|
||||||
usbTemp = usbSr.ReadToEnd();
|
usbTemp = usbSr.ReadToEnd();
|
||||||
|
|
||||||
ushort.TryParse(usbTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
ushort.TryParse(usbTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
||||||
out usbVendor);
|
out usbVendor);
|
||||||
|
|
||||||
usbSr.Close();
|
usbSr.Close();
|
||||||
|
|
||||||
if(File.Exists(resolvedLink + "/manufacturer"))
|
if(File.Exists(resolvedLink + "/manufacturer"))
|
||||||
@@ -501,6 +538,7 @@ namespace DiscImageChef.Devices
|
|||||||
}
|
}
|
||||||
|
|
||||||
IsUsb = true;
|
IsUsb = true;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -512,14 +550,16 @@ namespace DiscImageChef.Devices
|
|||||||
Usb.UsbDevice usbDevice = null;
|
Usb.UsbDevice usbDevice = null;
|
||||||
|
|
||||||
// I have to search for USB disks, floppies and CD-ROMs as separate device types
|
// I have to search for USB disks, floppies and CD-ROMs as separate device types
|
||||||
foreach (var devGuid in new[]
|
foreach(string devGuid in new[]
|
||||||
{
|
{
|
||||||
Usb.GuidDevinterfaceFloppy, Usb.GuidDevinterfaceCdrom, Usb.GuidDevinterfaceDisk,
|
Usb.GuidDevinterfaceFloppy, Usb.GuidDevinterfaceCdrom, Usb.GuidDevinterfaceDisk,
|
||||||
Usb.GuidDevinterfaceTape
|
Usb.GuidDevinterfaceTape
|
||||||
})
|
})
|
||||||
{
|
{
|
||||||
usbDevice = Usb.FindDrivePath(devicePath, devGuid);
|
usbDevice = Usb.FindDrivePath(devicePath, devGuid);
|
||||||
if (usbDevice != null) break;
|
|
||||||
|
if(usbDevice != null)
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(usbDevice != null)
|
if(usbDevice != null)
|
||||||
@@ -529,22 +569,24 @@ namespace DiscImageChef.Devices
|
|||||||
usbProduct = (ushort)usbDevice.DeviceDescriptor.idProduct;
|
usbProduct = (ushort)usbDevice.DeviceDescriptor.idProduct;
|
||||||
UsbManufacturerString = usbDevice.Manufacturer;
|
UsbManufacturerString = usbDevice.Manufacturer;
|
||||||
UsbProductString = usbDevice.Product;
|
UsbProductString = usbDevice.Product;
|
||||||
|
|
||||||
UsbSerialString =
|
UsbSerialString =
|
||||||
usbDevice
|
usbDevice.
|
||||||
.SerialNumber; // This is incorrect filled by Windows with SCSI/ATA serial number
|
SerialNumber; // This is incorrect filled by Windows with SCSI/ATA serial number
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
IsUsb = false;
|
IsUsb = false;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (_remote.GetUsbData(out var remoteUsbDescriptors, out var remoteUsbVendor,
|
if(_remote.GetUsbData(out byte[] remoteUsbDescriptors, out ushort remoteUsbVendor,
|
||||||
out var remoteUsbProduct, out var remoteUsbManufacturer, out var remoteUsbProductString,
|
out ushort remoteUsbProduct, out string remoteUsbManufacturer,
|
||||||
out var remoteUsbSerial))
|
out string remoteUsbProductString, out string remoteUsbSerial))
|
||||||
{
|
{
|
||||||
IsUsb = true;
|
IsUsb = true;
|
||||||
UsbDescriptors = remoteUsbDescriptors;
|
UsbDescriptors = remoteUsbDescriptors;
|
||||||
@@ -555,15 +597,13 @@ namespace DiscImageChef.Devices
|
|||||||
UsbSerialString = remoteUsbSerial;
|
UsbSerialString = remoteUsbSerial;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion USB
|
#endregion USB
|
||||||
|
|
||||||
#region FireWire
|
#region FireWire
|
||||||
|
|
||||||
if(!(_remote is null))
|
if(!(_remote is null))
|
||||||
{
|
{
|
||||||
if (_remote.GetFireWireData(out firewireVendor, out firewireModel,
|
if(_remote.GetFireWireData(out firewireVendor, out firewireModel, out firewireGuid,
|
||||||
out firewireGuid, out var remoteFireWireVendorName, out var remoteFireWireModelName))
|
out string remoteFireWireVendorName, out string remoteFireWireModelName))
|
||||||
{
|
{
|
||||||
IsFireWire = true;
|
IsFireWire = true;
|
||||||
FireWireVendorName = remoteFireWireVendorName;
|
FireWireVendorName = remoteFireWireVendorName;
|
||||||
@@ -578,35 +618,45 @@ namespace DiscImageChef.Devices
|
|||||||
devicePath.StartsWith("/dev/sr", StringComparison.Ordinal) ||
|
devicePath.StartsWith("/dev/sr", StringComparison.Ordinal) ||
|
||||||
devicePath.StartsWith("/dev/st", StringComparison.Ordinal))
|
devicePath.StartsWith("/dev/st", StringComparison.Ordinal))
|
||||||
{
|
{
|
||||||
var devPath = devicePath.Substring(5);
|
string devPath = devicePath.Substring(5);
|
||||||
|
|
||||||
if(Directory.Exists("/sys/block/" + devPath))
|
if(Directory.Exists("/sys/block/" + devPath))
|
||||||
{
|
{
|
||||||
var resolvedLink = Linux.Command.ReadLink("/sys/block/" + devPath);
|
string resolvedLink = Linux.Command.ReadLink("/sys/block/" + devPath);
|
||||||
resolvedLink = "/sys" + resolvedLink.Substring(2);
|
resolvedLink = "/sys" + resolvedLink.Substring(2);
|
||||||
|
|
||||||
if(!string.IsNullOrEmpty(resolvedLink))
|
if(!string.IsNullOrEmpty(resolvedLink))
|
||||||
while(resolvedLink.Contains("firewire"))
|
while(resolvedLink.Contains("firewire"))
|
||||||
{
|
{
|
||||||
resolvedLink = Path.GetDirectoryName(resolvedLink);
|
resolvedLink = Path.GetDirectoryName(resolvedLink);
|
||||||
|
|
||||||
if(!File.Exists(resolvedLink + "/model") ||
|
if(!File.Exists(resolvedLink + "/model") ||
|
||||||
!File.Exists(resolvedLink + "/vendor") ||
|
!File.Exists(resolvedLink + "/vendor") ||
|
||||||
!File.Exists(resolvedLink + "/guid")) continue;
|
!File.Exists(resolvedLink + "/guid"))
|
||||||
|
continue;
|
||||||
|
|
||||||
var fwSr = new StreamReader(resolvedLink + "/model");
|
var fwSr = new StreamReader(resolvedLink + "/model");
|
||||||
var fwTemp = fwSr.ReadToEnd();
|
string fwTemp = fwSr.ReadToEnd();
|
||||||
|
|
||||||
uint.TryParse(fwTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
uint.TryParse(fwTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
||||||
out firewireModel);
|
out firewireModel);
|
||||||
|
|
||||||
fwSr.Close();
|
fwSr.Close();
|
||||||
|
|
||||||
fwSr = new StreamReader(resolvedLink + "/vendor");
|
fwSr = new StreamReader(resolvedLink + "/vendor");
|
||||||
fwTemp = fwSr.ReadToEnd();
|
fwTemp = fwSr.ReadToEnd();
|
||||||
|
|
||||||
uint.TryParse(fwTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
uint.TryParse(fwTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
||||||
out firewireVendor);
|
out firewireVendor);
|
||||||
|
|
||||||
fwSr.Close();
|
fwSr.Close();
|
||||||
|
|
||||||
fwSr = new StreamReader(resolvedLink + "/guid");
|
fwSr = new StreamReader(resolvedLink + "/guid");
|
||||||
fwTemp = fwSr.ReadToEnd();
|
fwTemp = fwSr.ReadToEnd();
|
||||||
|
|
||||||
ulong.TryParse(fwTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
ulong.TryParse(fwTemp, NumberStyles.HexNumber, CultureInfo.InvariantCulture,
|
||||||
out firewireGuid);
|
out firewireGuid);
|
||||||
|
|
||||||
fwSr.Close();
|
fwSr.Close();
|
||||||
|
|
||||||
if(File.Exists(resolvedLink + "/model_name"))
|
if(File.Exists(resolvedLink + "/model_name"))
|
||||||
@@ -624,22 +674,22 @@ namespace DiscImageChef.Devices
|
|||||||
}
|
}
|
||||||
|
|
||||||
IsFireWire = true;
|
IsFireWire = true;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Implement for other operating systems
|
// TODO: Implement for other operating systems
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
IsFireWire = false;
|
IsFireWire = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion FireWire
|
#endregion FireWire
|
||||||
|
|
||||||
#region PCMCIA
|
#region PCMCIA
|
||||||
|
|
||||||
if(_remote is null)
|
if(_remote is null)
|
||||||
{
|
{
|
||||||
if(PlatformId == PlatformID.Linux)
|
if(PlatformId == PlatformID.Linux)
|
||||||
@@ -648,41 +698,51 @@ namespace DiscImageChef.Devices
|
|||||||
devicePath.StartsWith("/dev/sr", StringComparison.Ordinal) ||
|
devicePath.StartsWith("/dev/sr", StringComparison.Ordinal) ||
|
||||||
devicePath.StartsWith("/dev/st", StringComparison.Ordinal))
|
devicePath.StartsWith("/dev/st", StringComparison.Ordinal))
|
||||||
{
|
{
|
||||||
var devPath = devicePath.Substring(5);
|
string devPath = devicePath.Substring(5);
|
||||||
|
|
||||||
if(Directory.Exists("/sys/block/" + devPath))
|
if(Directory.Exists("/sys/block/" + devPath))
|
||||||
{
|
{
|
||||||
var resolvedLink = Linux.Command.ReadLink("/sys/block/" + devPath);
|
string resolvedLink = Linux.Command.ReadLink("/sys/block/" + devPath);
|
||||||
resolvedLink = "/sys" + resolvedLink.Substring(2);
|
resolvedLink = "/sys" + resolvedLink.Substring(2);
|
||||||
|
|
||||||
if(!string.IsNullOrEmpty(resolvedLink))
|
if(!string.IsNullOrEmpty(resolvedLink))
|
||||||
while(resolvedLink.Contains("/sys/devices"))
|
while(resolvedLink.Contains("/sys/devices"))
|
||||||
{
|
{
|
||||||
resolvedLink = Path.GetDirectoryName(resolvedLink);
|
resolvedLink = Path.GetDirectoryName(resolvedLink);
|
||||||
if (!Directory.Exists(resolvedLink + "/pcmcia_socket")) continue;
|
|
||||||
|
|
||||||
var subdirs = Directory.GetDirectories(resolvedLink + "/pcmcia_socket",
|
if(!Directory.Exists(resolvedLink + "/pcmcia_socket"))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
string[] subdirs = Directory.GetDirectories(resolvedLink + "/pcmcia_socket",
|
||||||
"pcmcia_socket*",
|
"pcmcia_socket*",
|
||||||
SearchOption.TopDirectoryOnly);
|
SearchOption.TopDirectoryOnly);
|
||||||
|
|
||||||
if (subdirs.Length <= 0) continue;
|
if(subdirs.Length <= 0)
|
||||||
|
continue;
|
||||||
|
|
||||||
var possibleDir = Path.Combine(resolvedLink, "pcmcia_socket", subdirs[0]);
|
string possibleDir = Path.Combine(resolvedLink, "pcmcia_socket", subdirs[0]);
|
||||||
if (!File.Exists(possibleDir + "/card_type") || !File.Exists(possibleDir + "/cis"))
|
|
||||||
|
if(!File.Exists(possibleDir + "/card_type") ||
|
||||||
|
!File.Exists(possibleDir + "/cis"))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
var cisFs = new FileStream(possibleDir + "/cis", System.IO.FileMode.Open,
|
var cisFs = new FileStream(possibleDir + "/cis", System.IO.FileMode.Open,
|
||||||
System.IO.FileAccess.Read);
|
System.IO.FileAccess.Read);
|
||||||
var cisBuf = new byte[65536];
|
|
||||||
var cisCount = cisFs.Read(cisBuf, 0, 65536);
|
byte[] cisBuf = new byte[65536];
|
||||||
|
int cisCount = cisFs.Read(cisBuf, 0, 65536);
|
||||||
Cis = new byte[cisCount];
|
Cis = new byte[cisCount];
|
||||||
Array.Copy(cisBuf, 0, Cis, 0, cisCount);
|
Array.Copy(cisBuf, 0, Cis, 0, cisCount);
|
||||||
cisFs.Close();
|
cisFs.Close();
|
||||||
|
|
||||||
IsPcmcia = true;
|
IsPcmcia = true;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Implement for other operating systems
|
// TODO: Implement for other operating systems
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -691,61 +751,74 @@ namespace DiscImageChef.Devices
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (_remote.GetPcmciaData(out var cisBuf))
|
if(_remote.GetPcmciaData(out byte[] cisBuf))
|
||||||
{
|
{
|
||||||
IsPcmcia = true;
|
IsPcmcia = true;
|
||||||
Cis = cisBuf;
|
Cis = cisBuf;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion PCMCIA
|
#endregion PCMCIA
|
||||||
|
|
||||||
if(!scsiSense)
|
if(!scsiSense)
|
||||||
{
|
{
|
||||||
var inquiry = Inquiry.Decode(inqBuf);
|
Inquiry.SCSIInquiry? inquiry = Inquiry.Decode(inqBuf);
|
||||||
|
|
||||||
Type = DeviceType.SCSI;
|
Type = DeviceType.SCSI;
|
||||||
var serialSense = ScsiInquiry(out inqBuf, out _, 0x80);
|
bool serialSense = ScsiInquiry(out inqBuf, out _, 0x80);
|
||||||
if (!serialSense) Serial = EVPD.DecodePage80(inqBuf);
|
|
||||||
|
if(!serialSense)
|
||||||
|
Serial = EVPD.DecodePage80(inqBuf);
|
||||||
|
|
||||||
if(inquiry.HasValue)
|
if(inquiry.HasValue)
|
||||||
{
|
{
|
||||||
var tmp = StringHandlers.CToString(inquiry.Value.ProductRevisionLevel);
|
string tmp = StringHandlers.CToString(inquiry.Value.ProductRevisionLevel);
|
||||||
if (tmp != null) Revision = tmp.Trim();
|
|
||||||
|
if(tmp != null)
|
||||||
|
FirmwareRevision = tmp.Trim();
|
||||||
|
|
||||||
tmp = StringHandlers.CToString(inquiry.Value.ProductIdentification);
|
tmp = StringHandlers.CToString(inquiry.Value.ProductIdentification);
|
||||||
if (tmp != null) Model = tmp.Trim();
|
|
||||||
|
if(tmp != null)
|
||||||
|
Model = tmp.Trim();
|
||||||
|
|
||||||
tmp = StringHandlers.CToString(inquiry.Value.VendorIdentification);
|
tmp = StringHandlers.CToString(inquiry.Value.VendorIdentification);
|
||||||
if (tmp != null) Manufacturer = tmp.Trim();
|
|
||||||
|
if(tmp != null)
|
||||||
|
Manufacturer = tmp.Trim();
|
||||||
|
|
||||||
IsRemovable = inquiry.Value.RMB;
|
IsRemovable = inquiry.Value.RMB;
|
||||||
|
|
||||||
ScsiType = (PeripheralDeviceTypes)inquiry.Value.PeripheralDeviceType;
|
ScsiType = (PeripheralDeviceTypes)inquiry.Value.PeripheralDeviceType;
|
||||||
}
|
}
|
||||||
|
|
||||||
var atapiSense = AtapiIdentify(out ataBuf, out _);
|
bool atapiSense = AtapiIdentify(out ataBuf, out _);
|
||||||
|
|
||||||
if(!atapiSense)
|
if(!atapiSense)
|
||||||
{
|
{
|
||||||
Type = DeviceType.ATAPI;
|
Type = DeviceType.ATAPI;
|
||||||
var ataId = Identify.Decode(ataBuf);
|
Identify.IdentifyDevice? ataId = Identify.Decode(ataBuf);
|
||||||
|
|
||||||
if (ataId.HasValue) Serial = ataId.Value.SerialNumber;
|
if(ataId.HasValue)
|
||||||
|
Serial = ataId.Value.SerialNumber;
|
||||||
}
|
}
|
||||||
|
|
||||||
LastError = 0;
|
LastError = 0;
|
||||||
Error = false;
|
Error = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (scsiSense && (IsUsb || IsFireWire) || Manufacturer == "ATA")
|
if((scsiSense && (IsUsb || IsFireWire)) ||
|
||||||
|
Manufacturer == "ATA")
|
||||||
{
|
{
|
||||||
var ataSense = AtaIdentify(out ataBuf, out _);
|
bool ataSense = AtaIdentify(out ataBuf, out _);
|
||||||
|
|
||||||
if(!ataSense)
|
if(!ataSense)
|
||||||
{
|
{
|
||||||
Type = DeviceType.ATA;
|
Type = DeviceType.ATA;
|
||||||
var ataid = Identify.Decode(ataBuf);
|
Identify.IdentifyDevice? ataid = Identify.Decode(ataBuf);
|
||||||
|
|
||||||
if(ataid.HasValue)
|
if(ataid.HasValue)
|
||||||
{
|
{
|
||||||
var separated = ataid.Value.Model.Split(' ');
|
string[] separated = ataid.Value.Model.Split(' ');
|
||||||
|
|
||||||
if(separated.Length == 1)
|
if(separated.Length == 1)
|
||||||
{
|
{
|
||||||
@@ -757,7 +830,7 @@ namespace DiscImageChef.Devices
|
|||||||
Model = separated[separated.Length - 1];
|
Model = separated[separated.Length - 1];
|
||||||
}
|
}
|
||||||
|
|
||||||
Revision = ataid.Value.FirmwareRevision;
|
FirmwareRevision = ataid.Value.FirmwareRevision;
|
||||||
Serial = ataid.Value.SerialNumber;
|
Serial = ataid.Value.SerialNumber;
|
||||||
|
|
||||||
ScsiType = PeripheralDeviceTypes.DirectAccess;
|
ScsiType = PeripheralDeviceTypes.DirectAccess;
|
||||||
@@ -766,7 +839,8 @@ namespace DiscImageChef.Devices
|
|||||||
IsRemovable |=
|
IsRemovable |=
|
||||||
(ataid.Value.GeneralConfiguration & Identify.GeneralConfigurationBit.Removable) ==
|
(ataid.Value.GeneralConfiguration & Identify.GeneralConfigurationBit.Removable) ==
|
||||||
Identify.GeneralConfigurationBit.Removable;
|
Identify.GeneralConfigurationBit.Removable;
|
||||||
else IsCompactFlash = true;
|
else
|
||||||
|
IsCompactFlash = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -775,59 +849,75 @@ namespace DiscImageChef.Devices
|
|||||||
{
|
{
|
||||||
Manufacturer = null;
|
Manufacturer = null;
|
||||||
Model = null;
|
Model = null;
|
||||||
Revision = null;
|
FirmwareRevision = null;
|
||||||
Serial = null;
|
Serial = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(IsUsb)
|
if(IsUsb)
|
||||||
{
|
{
|
||||||
if (string.IsNullOrEmpty(Manufacturer)) Manufacturer = UsbManufacturerString;
|
if(string.IsNullOrEmpty(Manufacturer))
|
||||||
if (string.IsNullOrEmpty(Model)) Model = UsbProductString;
|
Manufacturer = UsbManufacturerString;
|
||||||
if (string.IsNullOrEmpty(Serial)) Serial = UsbSerialString;
|
|
||||||
|
if(string.IsNullOrEmpty(Model))
|
||||||
|
Model = UsbProductString;
|
||||||
|
|
||||||
|
if(string.IsNullOrEmpty(Serial))
|
||||||
|
Serial = UsbSerialString;
|
||||||
else
|
else
|
||||||
foreach (var c in Serial.Where(char.IsControl))
|
foreach(char c in Serial.Where(char.IsControl))
|
||||||
Serial = UsbSerialString;
|
Serial = UsbSerialString;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(IsFireWire)
|
if(IsFireWire)
|
||||||
{
|
{
|
||||||
if (string.IsNullOrEmpty(Manufacturer)) Manufacturer = FireWireVendorName;
|
if(string.IsNullOrEmpty(Manufacturer))
|
||||||
if (string.IsNullOrEmpty(Model)) Model = FireWireModelName;
|
Manufacturer = FireWireVendorName;
|
||||||
if (string.IsNullOrEmpty(Serial)) Serial = $"{firewireGuid:X16}";
|
|
||||||
|
if(string.IsNullOrEmpty(Model))
|
||||||
|
Model = FireWireModelName;
|
||||||
|
|
||||||
|
if(string.IsNullOrEmpty(Serial))
|
||||||
|
Serial = $"{firewireGuid:X16}";
|
||||||
else
|
else
|
||||||
foreach (var c in Serial.Where(char.IsControl))
|
foreach(char c in Serial.Where(char.IsControl))
|
||||||
Serial = $"{firewireGuid:X16}";
|
Serial = $"{firewireGuid:X16}";
|
||||||
}
|
}
|
||||||
|
|
||||||
// Some optical drives are not getting the correct serial, and IDENTIFY PACKET DEVICE is blocked without
|
// Some optical drives are not getting the correct serial, and IDENTIFY PACKET DEVICE is blocked without
|
||||||
// administrator privileges
|
// administrator privileges
|
||||||
if (ScsiType != PeripheralDeviceTypes.MultiMediaDevice) return;
|
if(ScsiType != PeripheralDeviceTypes.MultiMediaDevice)
|
||||||
|
return;
|
||||||
|
|
||||||
var featureSense = GetConfiguration(out var featureBuffer, out _, 0x0108, MmcGetConfigurationRt.Single,
|
bool featureSense = GetConfiguration(out byte[] featureBuffer, out _, 0x0108, MmcGetConfigurationRt.Single,
|
||||||
Timeout, out _);
|
Timeout, out _);
|
||||||
|
|
||||||
if (featureSense) return;
|
if(featureSense)
|
||||||
|
return;
|
||||||
|
|
||||||
var features = Features.Separate(featureBuffer);
|
Features.SeparatedFeatures features = Features.Separate(featureBuffer);
|
||||||
if (features.Descriptors?.Length != 1 || features.Descriptors[0].Code != 0x0108) return;
|
|
||||||
|
|
||||||
var serialFeature = Features.Decode_0108(features.Descriptors[0].Data);
|
if(features.Descriptors?.Length != 1 ||
|
||||||
|
features.Descriptors[0].Code != 0x0108)
|
||||||
|
return;
|
||||||
|
|
||||||
if (serialFeature is null) return;
|
Feature_0108? serialFeature = Features.Decode_0108(features.Descriptors[0].Data);
|
||||||
|
|
||||||
|
if(serialFeature is null)
|
||||||
|
return;
|
||||||
|
|
||||||
Serial = serialFeature.Value.Serial;
|
Serial = serialFeature.Value.Serial;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static int ConvertFromHexAscii(string file, out byte[] outBuf)
|
static int ConvertFromHexAscii(string file, out byte[] outBuf)
|
||||||
{
|
{
|
||||||
var sr = new StreamReader(file);
|
var sr = new StreamReader(file);
|
||||||
var ins = sr.ReadToEnd().Trim();
|
string ins = sr.ReadToEnd().Trim();
|
||||||
outBuf = new byte[ins.Length / 2];
|
outBuf = new byte[ins.Length / 2];
|
||||||
var count = 0;
|
int count = 0;
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
for (var i = 0; i < ins.Length; i += 2)
|
for(int i = 0; i < ins.Length; i += 2)
|
||||||
{
|
{
|
||||||
outBuf[i / 2] = Convert.ToByte(ins.Substring(i, 2), 16);
|
outBuf[i / 2] = Convert.ToByte(ins.Substring(i, 2), 16);
|
||||||
count++;
|
count++;
|
||||||
@@ -839,6 +929,7 @@ namespace DiscImageChef.Devices
|
|||||||
}
|
}
|
||||||
|
|
||||||
sr.Close();
|
sr.Close();
|
||||||
|
|
||||||
return count;
|
return count;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -100,10 +100,10 @@ namespace DiscImageChef.Devices
|
|||||||
public string Model { get; }
|
public string Model { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets the device's revision.
|
/// Gets the device's firmware version.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <value>The revision.</value>
|
/// <value>The firmware version.</value>
|
||||||
public string Revision { get; }
|
public string FirmwareRevision { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets the device's serial number.
|
/// Gets the device's serial number.
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
{
|
{
|
||||||
public class pnlDeviceInfo : Panel
|
public class pnlDeviceInfo : Panel
|
||||||
{
|
{
|
||||||
DeviceInfo devInfo;
|
readonly DeviceInfo devInfo;
|
||||||
|
|
||||||
public pnlDeviceInfo(DeviceInfo devInfo)
|
public pnlDeviceInfo(DeviceInfo devInfo)
|
||||||
{
|
{
|
||||||
@@ -54,7 +54,7 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
txtType.Text = devInfo.Type.ToString();
|
txtType.Text = devInfo.Type.ToString();
|
||||||
txtManufacturer.Text = devInfo.Manufacturer;
|
txtManufacturer.Text = devInfo.Manufacturer;
|
||||||
txtModel.Text = devInfo.Model;
|
txtModel.Text = devInfo.Model;
|
||||||
txtRevision.Text = devInfo.Revision;
|
txtRevision.Text = devInfo.FirmwareRevision;
|
||||||
txtSerial.Text = devInfo.Serial;
|
txtSerial.Text = devInfo.Serial;
|
||||||
txtScsiType.Text = devInfo.ScsiType.ToString();
|
txtScsiType.Text = devInfo.ScsiType.ToString();
|
||||||
chkRemovable.Checked = devInfo.IsRemovable;
|
chkRemovable.Checked = devInfo.IsRemovable;
|
||||||
@@ -83,14 +83,15 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
|
|
||||||
if(devInfo.IsPcmcia)
|
if(devInfo.IsPcmcia)
|
||||||
{
|
{
|
||||||
tabPcmciaInfo tabPcmciaInfo = new tabPcmciaInfo();
|
var tabPcmciaInfo = new tabPcmciaInfo();
|
||||||
tabPcmciaInfo.LoadData(devInfo.Cis);
|
tabPcmciaInfo.LoadData(devInfo.Cis);
|
||||||
tabInfos.Pages.Add(tabPcmciaInfo);
|
tabInfos.Pages.Add(tabPcmciaInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(devInfo.AtaIdentify != null || devInfo.AtapiIdentify != null)
|
if(devInfo.AtaIdentify != null ||
|
||||||
|
devInfo.AtapiIdentify != null)
|
||||||
{
|
{
|
||||||
tabAtaInfo tabAtaInfo = new tabAtaInfo();
|
var tabAtaInfo = new tabAtaInfo();
|
||||||
tabAtaInfo.LoadData(devInfo.AtaIdentify, devInfo.AtapiIdentify, devInfo.AtaMcptError);
|
tabAtaInfo.LoadData(devInfo.AtaIdentify, devInfo.AtapiIdentify, devInfo.AtaMcptError);
|
||||||
|
|
||||||
tabInfos.Pages.Add(tabAtaInfo);
|
tabInfos.Pages.Add(tabAtaInfo);
|
||||||
@@ -98,7 +99,8 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
|
|
||||||
if(devInfo.ScsiInquiryData != null)
|
if(devInfo.ScsiInquiryData != null)
|
||||||
{
|
{
|
||||||
tabScsiInfo tabScsiInfo = new tabScsiInfo();
|
var tabScsiInfo = new tabScsiInfo();
|
||||||
|
|
||||||
tabScsiInfo.LoadData(devInfo.ScsiInquiryData, devInfo.ScsiInquiry, devInfo.ScsiEvpdPages,
|
tabScsiInfo.LoadData(devInfo.ScsiInquiryData, devInfo.ScsiInquiry, devInfo.ScsiEvpdPages,
|
||||||
devInfo.ScsiMode, devInfo.ScsiType, devInfo.ScsiModeSense6,
|
devInfo.ScsiMode, devInfo.ScsiType, devInfo.ScsiModeSense6,
|
||||||
devInfo.ScsiModeSense10, devInfo.MmcConfiguration);
|
devInfo.ScsiModeSense10, devInfo.MmcConfiguration);
|
||||||
@@ -108,18 +110,23 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
if(devInfo.PlextorFeatures != null)
|
if(devInfo.PlextorFeatures != null)
|
||||||
{
|
{
|
||||||
tabPlextor.Visible = true;
|
tabPlextor.Visible = true;
|
||||||
|
|
||||||
if(devInfo.PlextorFeatures.Eeprom != null)
|
if(devInfo.PlextorFeatures.Eeprom != null)
|
||||||
{
|
{
|
||||||
stkPlextorEeprom.Visible = true;
|
stkPlextorEeprom.Visible = true;
|
||||||
txtPlextorDiscs.Text = $"{devInfo.PlextorFeatures.Discs}";
|
txtPlextorDiscs.Text = $"{devInfo.PlextorFeatures.Discs}";
|
||||||
txtPlextorCdReadTime.Text = TimeSpan.FromSeconds(devInfo.PlextorFeatures.CdReadTime).ToString();
|
txtPlextorCdReadTime.Text = TimeSpan.FromSeconds(devInfo.PlextorFeatures.CdReadTime).ToString();
|
||||||
|
|
||||||
txtPlextorCdWriteTime.Text =
|
txtPlextorCdWriteTime.Text =
|
||||||
TimeSpan.FromSeconds(devInfo.PlextorFeatures.CdWriteTime).ToString();
|
TimeSpan.FromSeconds(devInfo.PlextorFeatures.CdWriteTime).ToString();
|
||||||
|
|
||||||
if(devInfo.PlextorFeatures.IsDvd)
|
if(devInfo.PlextorFeatures.IsDvd)
|
||||||
{
|
{
|
||||||
stkPlextorDvdTimes.Visible = true;
|
stkPlextorDvdTimes.Visible = true;
|
||||||
|
|
||||||
txtPlextorDvdReadTime.Text =
|
txtPlextorDvdReadTime.Text =
|
||||||
TimeSpan.FromSeconds(devInfo.PlextorFeatures.DvdReadTime).ToString();
|
TimeSpan.FromSeconds(devInfo.PlextorFeatures.DvdReadTime).ToString();
|
||||||
|
|
||||||
txtPlextorDvdWriteTime.Text =
|
txtPlextorDvdWriteTime.Text =
|
||||||
TimeSpan.FromSeconds(devInfo.PlextorFeatures.DvdWriteTime).ToString();
|
TimeSpan.FromSeconds(devInfo.PlextorFeatures.DvdWriteTime).ToString();
|
||||||
}
|
}
|
||||||
@@ -139,6 +146,7 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
if(devInfo.PlextorFeatures.PoweRecRecommendedSpeed > 0)
|
if(devInfo.PlextorFeatures.PoweRecRecommendedSpeed > 0)
|
||||||
{
|
{
|
||||||
stkPlextorPoweRecRecommended.Visible = true;
|
stkPlextorPoweRecRecommended.Visible = true;
|
||||||
|
|
||||||
txtPlextorPoweRecRecommended.Text =
|
txtPlextorPoweRecRecommended.Text =
|
||||||
$"{devInfo.PlextorFeatures.PoweRecRecommendedSpeed} Kb/sec.";
|
$"{devInfo.PlextorFeatures.PoweRecRecommendedSpeed} Kb/sec.";
|
||||||
}
|
}
|
||||||
@@ -146,6 +154,7 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
if(devInfo.PlextorFeatures.PoweRecSelected > 0)
|
if(devInfo.PlextorFeatures.PoweRecSelected > 0)
|
||||||
{
|
{
|
||||||
stkPlextorPoweRecSelected.Visible = true;
|
stkPlextorPoweRecSelected.Visible = true;
|
||||||
|
|
||||||
txtPlextorPoweRecSelected.Text =
|
txtPlextorPoweRecSelected.Text =
|
||||||
$"{devInfo.PlextorFeatures.PoweRecSelected} Kb/sec.";
|
$"{devInfo.PlextorFeatures.PoweRecSelected} Kb/sec.";
|
||||||
}
|
}
|
||||||
@@ -179,21 +188,19 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
|
|
||||||
txtPlextorSilentModeCdReadSpeedLimit.Text =
|
txtPlextorSilentModeCdReadSpeedLimit.Text =
|
||||||
devInfo.PlextorFeatures.CdReadSpeedLimit > 0
|
devInfo.PlextorFeatures.CdReadSpeedLimit > 0
|
||||||
? $"{devInfo.PlextorFeatures.CdReadSpeedLimit}x"
|
? $"{devInfo.PlextorFeatures.CdReadSpeedLimit}x" : "unlimited";
|
||||||
: "unlimited";
|
|
||||||
|
|
||||||
txtPlextorSilentModeCdWriteSpeedLimit.Text =
|
txtPlextorSilentModeCdWriteSpeedLimit.Text =
|
||||||
devInfo.PlextorFeatures.CdWriteSpeedLimit > 0
|
devInfo.PlextorFeatures.CdWriteSpeedLimit > 0
|
||||||
? $"{devInfo.PlextorFeatures.CdReadSpeedLimit}x"
|
? $"{devInfo.PlextorFeatures.CdReadSpeedLimit}x" : "unlimited";
|
||||||
: "unlimited";
|
|
||||||
|
|
||||||
if(devInfo.PlextorFeatures.IsDvd)
|
if(devInfo.PlextorFeatures.IsDvd)
|
||||||
{
|
{
|
||||||
stkPlextorSilentModeDvdReadSpeedLimit.Visible = true;
|
stkPlextorSilentModeDvdReadSpeedLimit.Visible = true;
|
||||||
|
|
||||||
txtPlextorSilentModeDvdReadSpeedLimit.Text =
|
txtPlextorSilentModeDvdReadSpeedLimit.Text =
|
||||||
devInfo.PlextorFeatures.DvdReadSpeedLimit > 0
|
devInfo.PlextorFeatures.DvdReadSpeedLimit > 0
|
||||||
? $"{devInfo.PlextorFeatures.DvdReadSpeedLimit}x"
|
? $"{devInfo.PlextorFeatures.DvdReadSpeedLimit}x" : "unlimited";
|
||||||
: "unlimited";
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -209,6 +216,7 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
}
|
}
|
||||||
|
|
||||||
chkPlextorHiding.Checked = devInfo.PlextorFeatures.Hiding;
|
chkPlextorHiding.Checked = devInfo.PlextorFeatures.Hiding;
|
||||||
|
|
||||||
if(devInfo.PlextorFeatures.Hiding)
|
if(devInfo.PlextorFeatures.Hiding)
|
||||||
{
|
{
|
||||||
stkPlextorHiding.Visible = true;
|
stkPlextorHiding.Visible = true;
|
||||||
@@ -235,8 +243,10 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
chkKreonDecryptSs.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.DecryptSs);
|
chkKreonDecryptSs.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.DecryptSs);
|
||||||
chkKreonXtremeUnlock.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.XtremeUnlock);
|
chkKreonXtremeUnlock.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.XtremeUnlock);
|
||||||
chkKreonWxripperUnlock.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.WxripperUnlock);
|
chkKreonWxripperUnlock.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.WxripperUnlock);
|
||||||
|
|
||||||
chkKreonChallengeResponse360.Checked =
|
chkKreonChallengeResponse360.Checked =
|
||||||
devInfo.KreonFeatures.HasFlag(KreonFeatures.ChallengeResponse360);
|
devInfo.KreonFeatures.HasFlag(KreonFeatures.ChallengeResponse360);
|
||||||
|
|
||||||
chkKreonDecryptSs360.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.DecryptSs360);
|
chkKreonDecryptSs360.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.DecryptSs360);
|
||||||
chkKreonXtremeUnlock360.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.XtremeUnlock360);
|
chkKreonXtremeUnlock360.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.XtremeUnlock360);
|
||||||
chkKreonWxripperUnlock360.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.WxripperUnlock360);
|
chkKreonWxripperUnlock360.Checked = devInfo.KreonFeatures.HasFlag(KreonFeatures.WxripperUnlock360);
|
||||||
@@ -251,9 +261,11 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
if(blockLimits.HasValue)
|
if(blockLimits.HasValue)
|
||||||
{
|
{
|
||||||
tabSsc.Visible = true;
|
tabSsc.Visible = true;
|
||||||
|
|
||||||
if(blockLimits.Value.minBlockLen == blockLimits.Value.maxBlockLen)
|
if(blockLimits.Value.minBlockLen == blockLimits.Value.maxBlockLen)
|
||||||
{
|
{
|
||||||
lblMinBlockSize.Visible = true;
|
lblMinBlockSize.Visible = true;
|
||||||
|
|
||||||
lblMinBlockSize.Text =
|
lblMinBlockSize.Text =
|
||||||
$"Device's block size is fixed at {blockLimits.Value.minBlockLen} bytes";
|
$"Device's block size is fixed at {blockLimits.Value.minBlockLen} bytes";
|
||||||
}
|
}
|
||||||
@@ -265,12 +277,14 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
lblMaxBlockSize.Text = blockLimits.Value.maxBlockLen > 0
|
lblMaxBlockSize.Text = blockLimits.Value.maxBlockLen > 0
|
||||||
? $"Device's maximum block size is {blockLimits.Value.maxBlockLen} bytes"
|
? $"Device's maximum block size is {blockLimits.Value.maxBlockLen} bytes"
|
||||||
: "Device does not specify a maximum block size";
|
: "Device does not specify a maximum block size";
|
||||||
|
|
||||||
lblMinBlockSize.Text =
|
lblMinBlockSize.Text =
|
||||||
$"Device's minimum block size is {blockLimits.Value.minBlockLen} bytes";
|
$"Device's minimum block size is {blockLimits.Value.minBlockLen} bytes";
|
||||||
|
|
||||||
if(blockLimits.Value.granularity > 0)
|
if(blockLimits.Value.granularity > 0)
|
||||||
{
|
{
|
||||||
lblBlockSizeGranularity.Visible = true;
|
lblBlockSizeGranularity.Visible = true;
|
||||||
|
|
||||||
lblBlockSizeGranularity.Text =
|
lblBlockSizeGranularity.Text =
|
||||||
$"Device's needs a block size granularity of 2^{blockLimits.Value.granularity} ({Math.Pow(2, blockLimits.Value.granularity)}) bytes";
|
$"Device's needs a block size granularity of 2^{blockLimits.Value.granularity} ({Math.Pow(2, blockLimits.Value.granularity)}) bytes";
|
||||||
}
|
}
|
||||||
@@ -298,7 +312,8 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
tabSdMmcInfo tabSdMmcInfo = new tabSdMmcInfo();
|
var tabSdMmcInfo = new tabSdMmcInfo();
|
||||||
|
|
||||||
tabSdMmcInfo.LoadData(devInfo.Type, devInfo.CID, devInfo.CSD, devInfo.OCR, devInfo.ExtendedCSD,
|
tabSdMmcInfo.LoadData(devInfo.Type, devInfo.CID, devInfo.CSD, devInfo.OCR, devInfo.ExtendedCSD,
|
||||||
devInfo.SCR);
|
devInfo.SCR);
|
||||||
|
|
||||||
@@ -307,13 +322,23 @@ namespace DiscImageChef.Gui.Panels
|
|||||||
|
|
||||||
protected void OnBtnSaveUsbDescriptors(object sender, EventArgs e)
|
protected void OnBtnSaveUsbDescriptors(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
SaveFileDialog dlgSaveBinary = new SaveFileDialog();
|
var dlgSaveBinary = new SaveFileDialog();
|
||||||
dlgSaveBinary.Filters.Add(new FileFilter {Extensions = new[] {"*.bin"}, Name = "Binary"});
|
|
||||||
|
dlgSaveBinary.Filters.Add(new FileFilter
|
||||||
|
{
|
||||||
|
Extensions = new[]
|
||||||
|
{
|
||||||
|
"*.bin"
|
||||||
|
},
|
||||||
|
Name = "Binary"
|
||||||
|
});
|
||||||
|
|
||||||
DialogResult result = dlgSaveBinary.ShowDialog(this);
|
DialogResult result = dlgSaveBinary.ShowDialog(this);
|
||||||
|
|
||||||
if(result != DialogResult.Ok) return;
|
if(result != DialogResult.Ok)
|
||||||
|
return;
|
||||||
|
|
||||||
FileStream saveFs = new FileStream(dlgSaveBinary.FileName, FileMode.Create);
|
var saveFs = new FileStream(dlgSaveBinary.FileName, FileMode.Create);
|
||||||
saveFs.Write(devInfo.UsbDescriptors, 0, devInfo.UsbDescriptors.Length);
|
saveFs.Write(devInfo.UsbDescriptors, 0, devInfo.UsbDescriptors.Length);
|
||||||
|
|
||||||
saveFs.Close();
|
saveFs.Close();
|
||||||
|
|||||||
@@ -129,19 +129,19 @@ namespace DiscImageChef.Commands.Device
|
|||||||
|
|
||||||
var report = new DeviceReportV2
|
var report = new DeviceReportV2
|
||||||
{
|
{
|
||||||
Manufacturer = dev.Manufacturer, Model = dev.Model, Revision = dev.Revision, Type = dev.Type
|
Manufacturer = dev.Manufacturer, Model = dev.Model, Revision = dev.FirmwareRevision, Type = dev.Type
|
||||||
};
|
};
|
||||||
|
|
||||||
bool removable = false;
|
bool removable = false;
|
||||||
string jsonFile;
|
string jsonFile;
|
||||||
|
|
||||||
if(!string.IsNullOrWhiteSpace(dev.Manufacturer) &&
|
if(!string.IsNullOrWhiteSpace(dev.Manufacturer) &&
|
||||||
!string.IsNullOrWhiteSpace(dev.Revision))
|
!string.IsNullOrWhiteSpace(dev.FirmwareRevision))
|
||||||
jsonFile = dev.Manufacturer + "_" + dev.Model + "_" + dev.Revision + ".json";
|
jsonFile = dev.Manufacturer + "_" + dev.Model + "_" + dev.FirmwareRevision + ".json";
|
||||||
else if(!string.IsNullOrWhiteSpace(dev.Manufacturer))
|
else if(!string.IsNullOrWhiteSpace(dev.Manufacturer))
|
||||||
jsonFile = dev.Manufacturer + "_" + dev.Model + ".json";
|
jsonFile = dev.Manufacturer + "_" + dev.Model + ".json";
|
||||||
else if(!string.IsNullOrWhiteSpace(dev.Revision))
|
else if(!string.IsNullOrWhiteSpace(dev.FirmwareRevision))
|
||||||
jsonFile = dev.Model + "_" + dev.Revision + ".json";
|
jsonFile = dev.Model + "_" + dev.FirmwareRevision + ".json";
|
||||||
else
|
else
|
||||||
jsonFile = dev.Model + ".json";
|
jsonFile = dev.Model + ".json";
|
||||||
|
|
||||||
|
|||||||
@@ -1078,7 +1078,7 @@ namespace DiscImageChef.Commands.Device
|
|||||||
// Search for device in master database
|
// Search for device in master database
|
||||||
Database.Models.Device dbDev =
|
Database.Models.Device dbDev =
|
||||||
ctx.Devices.FirstOrDefault(d => d.Manufacturer == dev.Manufacturer && d.Model == dev.Model &&
|
ctx.Devices.FirstOrDefault(d => d.Manufacturer == dev.Manufacturer && d.Model == dev.Model &&
|
||||||
d.Revision == dev.Revision);
|
d.Revision == dev.FirmwareRevision);
|
||||||
|
|
||||||
if(dbDev is null)
|
if(dbDev is null)
|
||||||
DicConsole.WriteLine("Device not in database, please create a device report and attach it to a Github issue.");
|
DicConsole.WriteLine("Device not in database, please create a device report and attach it to a Github issue.");
|
||||||
|
|||||||
@@ -557,7 +557,7 @@ namespace DiscImageChef.Commands.Media
|
|||||||
// Search for device in master database
|
// Search for device in master database
|
||||||
Database.Models.Device dbDev =
|
Database.Models.Device dbDev =
|
||||||
ctx.Devices.FirstOrDefault(d => d.Manufacturer == dev.Manufacturer && d.Model == dev.Model &&
|
ctx.Devices.FirstOrDefault(d => d.Manufacturer == dev.Manufacturer && d.Model == dev.Model &&
|
||||||
d.Revision == dev.Revision);
|
d.Revision == dev.FirmwareRevision);
|
||||||
|
|
||||||
Dump.SolveTrackPregaps(dev, null, null, tracks, supportsPqSubchannel, supportsRwSubchannel, dbDev,
|
Dump.SolveTrackPregaps(dev, null, null, tracks, supportsPqSubchannel, supportsRwSubchannel, dbDev,
|
||||||
out bool inexactPositioning);
|
out bool inexactPositioning);
|
||||||
|
|||||||
Reference in New Issue
Block a user