mirror of
https://github.com/aaru-dps/Aaru.git
synced 2025-12-16 19:24:25 +00:00
Remove deprecated FreeBSD code.
This commit is contained in:
@@ -197,7 +197,6 @@ namespace Aaru.Core.Devices.Dumping
|
|||||||
|
|
||||||
if(cdiReadyReadAsAudio)
|
if(cdiReadyReadAsAudio)
|
||||||
{
|
{
|
||||||
// TODO: FreeBSD bug
|
|
||||||
if(offsetBytes < 0)
|
if(offsetBytes < 0)
|
||||||
{
|
{
|
||||||
if(i == 0)
|
if(i == 0)
|
||||||
|
|||||||
@@ -221,7 +221,6 @@ namespace Aaru.Core.Devices.Dumping
|
|||||||
|
|
||||||
if(_fixOffset && !inData)
|
if(_fixOffset && !inData)
|
||||||
{
|
{
|
||||||
// TODO: FreeBSD bug
|
|
||||||
if(offsetBytes < 0)
|
if(offsetBytes < 0)
|
||||||
{
|
{
|
||||||
if(i == 0)
|
if(i == 0)
|
||||||
|
|||||||
@@ -46,7 +46,6 @@ using Aaru.Database.Models;
|
|||||||
using Aaru.Decoders.CD;
|
using Aaru.Decoders.CD;
|
||||||
using Aaru.Devices;
|
using Aaru.Devices;
|
||||||
using Schemas;
|
using Schemas;
|
||||||
using PlatformID = Aaru.CommonTypes.Interop.PlatformID;
|
|
||||||
using TrackType = Aaru.CommonTypes.Enums.TrackType;
|
using TrackType = Aaru.CommonTypes.Enums.TrackType;
|
||||||
using Version = Aaru.CommonTypes.Interop.Version;
|
using Version = Aaru.CommonTypes.Interop.Version;
|
||||||
|
|
||||||
@@ -64,63 +63,63 @@ namespace Aaru.Core.Devices.Dumping
|
|||||||
/// <summary>Dumps a compact disc</summary>
|
/// <summary>Dumps a compact disc</summary>
|
||||||
void CompactDisc()
|
void CompactDisc()
|
||||||
{
|
{
|
||||||
ExtentsULong audioExtents; // Extents with audio sectors
|
ExtentsULong audioExtents; // Extents with audio sectors
|
||||||
ulong blocks; // Total number of positive sectors
|
ulong blocks; // Total number of positive sectors
|
||||||
uint blockSize; // Size of the read sector in bytes
|
uint blockSize; // Size of the read sector in bytes
|
||||||
CdOffset cdOffset; // Read offset from database
|
CdOffset cdOffset; // Read offset from database
|
||||||
byte[] cmdBuf; // Data buffer
|
byte[] cmdBuf; // Data buffer
|
||||||
DumpHardwareType currentTry = null; // Current dump hardware try
|
DumpHardwareType currentTry = null; // Current dump hardware try
|
||||||
double currentSpeed = 0; // Current read speed
|
double currentSpeed = 0; // Current read speed
|
||||||
int? discOffset = null; // Disc write offset
|
int? discOffset = null; // Disc write offset
|
||||||
DateTime dumpStart = DateTime.UtcNow; // Time of dump start
|
DateTime dumpStart = DateTime.UtcNow; // Time of dump start
|
||||||
DateTime end; // Time of operation end
|
DateTime end; // Time of operation end
|
||||||
ExtentsULong extents = null; // Extents
|
ExtentsULong extents = null; // Extents
|
||||||
bool hiddenData; // Hidden track is data
|
bool hiddenData; // Hidden track is data
|
||||||
IbgLog ibgLog; // IMGBurn log
|
IbgLog ibgLog; // IMGBurn log
|
||||||
double imageWriteDuration = 0; // Duration of image write
|
double imageWriteDuration = 0; // Duration of image write
|
||||||
long lastSector; // Last sector number
|
long lastSector; // Last sector number
|
||||||
var leadOutExtents = new ExtentsULong(); // Lead-out extents
|
var leadOutExtents = new ExtentsULong(); // Lead-out extents
|
||||||
Dictionary<int, long> leadOutStarts = new Dictionary<int, long>(); // Lead-out starts
|
Dictionary<int, long> leadOutStarts = new(); // Lead-out starts
|
||||||
double maxSpeed = double.MinValue; // Maximum speed
|
double maxSpeed = double.MinValue; // Maximum speed
|
||||||
MhddLog mhddLog; // MHDD log
|
MhddLog mhddLog; // MHDD log
|
||||||
double minSpeed = double.MaxValue; // Minimum speed
|
double minSpeed = double.MaxValue; // Minimum speed
|
||||||
bool newTrim; // Is trim a new one?
|
bool newTrim; // Is trim a new one?
|
||||||
int offsetBytes = 0; // Read offset
|
int offsetBytes = 0; // Read offset
|
||||||
bool read6 = false; // Device supports READ(6)
|
bool read6 = false; // Device supports READ(6)
|
||||||
bool read10 = false; // Device supports READ(10)
|
bool read10 = false; // Device supports READ(10)
|
||||||
bool read12 = false; // Device supports READ(12)
|
bool read12 = false; // Device supports READ(12)
|
||||||
bool read16 = false; // Device supports READ(16)
|
bool read16 = false; // Device supports READ(16)
|
||||||
bool readcd; // Device supports READ CD
|
bool readcd; // Device supports READ CD
|
||||||
bool ret; // Image writing return status
|
bool ret; // Image writing return status
|
||||||
const uint sectorSize = 2352; // Full sector size
|
const uint sectorSize = 2352; // Full sector size
|
||||||
int sectorsForOffset = 0; // Sectors needed to fix offset
|
int sectorsForOffset = 0; // Sectors needed to fix offset
|
||||||
bool sense = true; // Sense indicator
|
bool sense = true; // Sense indicator
|
||||||
int sessions; // Number of sessions in disc
|
int sessions; // Number of sessions in disc
|
||||||
DateTime start; // Start of operation
|
DateTime start; // Start of operation
|
||||||
SubchannelLog subLog = null; // Subchannel log
|
SubchannelLog subLog = null; // Subchannel log
|
||||||
uint subSize; // Subchannel size in bytes
|
uint subSize; // Subchannel size in bytes
|
||||||
TrackSubchannelType subType; // Track subchannel type
|
TrackSubchannelType subType; // Track subchannel type
|
||||||
bool supportsLongSectors = true; // Supports reading EDC and ECC
|
bool supportsLongSectors = true; // Supports reading EDC and ECC
|
||||||
bool supportsPqSubchannel; // Supports reading PQ subchannel
|
bool supportsPqSubchannel; // Supports reading PQ subchannel
|
||||||
bool supportsRwSubchannel; // Supports reading RW subchannel
|
bool supportsRwSubchannel; // Supports reading RW subchannel
|
||||||
byte[] tmpBuf; // Temporary buffer
|
byte[] tmpBuf; // Temporary buffer
|
||||||
FullTOC.CDFullTOC? toc; // Full CD TOC
|
FullTOC.CDFullTOC? toc; // Full CD TOC
|
||||||
double totalDuration = 0; // Total commands duration
|
double totalDuration = 0; // Total commands duration
|
||||||
Dictionary<byte, byte> trackFlags = new Dictionary<byte, byte>(); // Track flags
|
Dictionary<byte, byte> trackFlags = new(); // Track flags
|
||||||
Track[] tracks; // Tracks in disc
|
Track[] tracks; // Tracks in disc
|
||||||
int firstTrackLastSession; // Number of first track in last session
|
int firstTrackLastSession; // Number of first track in last session
|
||||||
bool hiddenTrack; // Disc has a hidden track before track 1
|
bool hiddenTrack; // Disc has a hidden track before track 1
|
||||||
MmcSubchannel supportedSubchannel; // Drive's maximum supported subchannel
|
MmcSubchannel supportedSubchannel; // Drive's maximum supported subchannel
|
||||||
MmcSubchannel desiredSubchannel; // User requested subchannel
|
MmcSubchannel desiredSubchannel; // User requested subchannel
|
||||||
bool bcdSubchannel = false; // Subchannel positioning is in BCD
|
bool bcdSubchannel = false; // Subchannel positioning is in BCD
|
||||||
Dictionary<byte, string> isrcs = new Dictionary<byte, string>();
|
Dictionary<byte, string> isrcs = new();
|
||||||
string mcn = null;
|
string mcn = null;
|
||||||
HashSet<int> subchannelExtents = new HashSet<int>();
|
HashSet<int> subchannelExtents = new();
|
||||||
bool cdiReadyReadAsAudio = false;
|
bool cdiReadyReadAsAudio = false;
|
||||||
uint firstLba;
|
uint firstLba;
|
||||||
|
|
||||||
Dictionary<MediaTagType, byte[]> mediaTags = new Dictionary<MediaTagType, byte[]>(); // Media tags
|
Dictionary<MediaTagType, byte[]> mediaTags = new(); // Media tags
|
||||||
Dictionary<byte, int> smallestPregapLbaPerTrack = new Dictionary<byte, int>();
|
Dictionary<byte, int> smallestPregapLbaPerTrack = new();
|
||||||
|
|
||||||
MediaType dskType = MediaType.CD;
|
MediaType dskType = MediaType.CD;
|
||||||
|
|
||||||
@@ -565,7 +564,7 @@ namespace Aaru.Core.Devices.Dumping
|
|||||||
_dumpLog.WriteLine("Disc contains a hidden track...");
|
_dumpLog.WriteLine("Disc contains a hidden track...");
|
||||||
UpdateStatus?.Invoke("Disc contains a hidden track...");
|
UpdateStatus?.Invoke("Disc contains a hidden track...");
|
||||||
|
|
||||||
List<Track> trkList = new List<Track>
|
List<Track> trkList = new()
|
||||||
{
|
{
|
||||||
new Track
|
new Track
|
||||||
{
|
{
|
||||||
@@ -721,31 +720,6 @@ namespace Aaru.Core.Devices.Dumping
|
|||||||
// Check if something prevents from dumping the first track pregap
|
// Check if something prevents from dumping the first track pregap
|
||||||
if(_dumpFirstTrackPregap && readcd)
|
if(_dumpFirstTrackPregap && readcd)
|
||||||
{
|
{
|
||||||
if(_dev.PlatformId == PlatformID.FreeBSD &&
|
|
||||||
!_dev.IsRemote)
|
|
||||||
{
|
|
||||||
if(_force)
|
|
||||||
{
|
|
||||||
_dumpLog.
|
|
||||||
WriteLine("FreeBSD panics when reading CD first track pregap, see upstream bug #224253. continuing");
|
|
||||||
|
|
||||||
ErrorMessage?.
|
|
||||||
Invoke("FreeBSD panics when reading CD first track pregap, see upstream bug #224253. continuing");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_dumpLog.
|
|
||||||
WriteLine("FreeBSD panics when reading CD first track pregap, see upstream bug #224253. Not continuing");
|
|
||||||
|
|
||||||
StoppingErrorMessage?.
|
|
||||||
Invoke("FreeBSD panics when reading CD first track pregap, see upstream bug #224253. Not continuing");
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
_dumpFirstTrackPregap = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(!_outputPlugin.SupportedMediaTags.Contains(MediaTagType.CD_FirstTrackPregap))
|
if(!_outputPlugin.SupportedMediaTags.Contains(MediaTagType.CD_FirstTrackPregap))
|
||||||
{
|
{
|
||||||
if(_force)
|
if(_force)
|
||||||
|
|||||||
@@ -56,87 +56,82 @@
|
|||||||
<ConsolePause>false</ConsolePause>
|
<ConsolePause>false</ConsolePause>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Reference Include="System" />
|
<Reference Include="System"/>
|
||||||
<Reference Include="System.Management" />
|
<Reference Include="System.Management"/>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Compile Include="Device\DeviceException.cs" />
|
<Compile Include="Device\DeviceException.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\MediaTek.cs" />
|
<Compile Include="Device\ScsiCommands\MediaTek.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\MiniDisc.cs" />
|
<Compile Include="Device\ScsiCommands\MiniDisc.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Optical.cs" />
|
<Compile Include="Device\ScsiCommands\Optical.cs"/>
|
||||||
<Compile Include="FreeBSD\ListDevices.cs" />
|
<Compile Include="Linux\Extern.cs"/>
|
||||||
<Compile Include="Linux\Extern.cs" />
|
<Compile Include="Linux\Structs.cs"/>
|
||||||
<Compile Include="Linux\Structs.cs" />
|
<Compile Include="Linux\Enums.cs"/>
|
||||||
<Compile Include="Linux\Enums.cs" />
|
<Compile Include="Enums.cs"/>
|
||||||
<Compile Include="Enums.cs" />
|
<Compile Include="Remote\Consts.cs"/>
|
||||||
<Compile Include="Remote\Consts.cs" />
|
<Compile Include="Remote\Enums.cs"/>
|
||||||
<Compile Include="Remote\Enums.cs" />
|
<Compile Include="Remote\Remote.cs"/>
|
||||||
<Compile Include="Remote\Remote.cs" />
|
<Compile Include="Remote\Structs.cs"/>
|
||||||
<Compile Include="Remote\Structs.cs" />
|
<Compile Include="Windows\Extern.cs"/>
|
||||||
<Compile Include="Windows\Extern.cs" />
|
<Compile Include="Windows\ListDevices.cs"/>
|
||||||
<Compile Include="Windows\ListDevices.cs" />
|
<Compile Include="Windows\Structs.cs"/>
|
||||||
<Compile Include="Windows\Structs.cs" />
|
<Compile Include="Windows\Enums.cs"/>
|
||||||
<Compile Include="Windows\Enums.cs" />
|
<Compile Include="Windows\Command.cs"/>
|
||||||
<Compile Include="Windows\Command.cs" />
|
<Compile Include="Linux\Command.cs"/>
|
||||||
<Compile Include="Linux\Command.cs" />
|
<Compile Include="Command.cs"/>
|
||||||
<Compile Include="Command.cs" />
|
<Compile Include="Device\Constructor.cs"/>
|
||||||
<Compile Include="Device\Constructor.cs" />
|
<Compile Include="Device\Variables.cs"/>
|
||||||
<Compile Include="Device\Variables.cs" />
|
<Compile Include="Device\Destructor.cs"/>
|
||||||
<Compile Include="Device\Destructor.cs" />
|
<Compile Include="Device\Commands.cs"/>
|
||||||
<Compile Include="Device\Commands.cs" />
|
<Compile Include="Device\ScsiCommands\MMC.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\MMC.cs" />
|
<Compile Include="Device\ScsiCommands\SPC.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\SPC.cs" />
|
<Compile Include="Device\ScsiCommands\SBC.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\SBC.cs" />
|
<Compile Include="Device\ScsiCommands\Pioneer.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Pioneer.cs" />
|
<Compile Include="Device\ScsiCommands\Plextor.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Plextor.cs" />
|
<Compile Include="Device\ScsiCommands\NEC.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\NEC.cs" />
|
<Compile Include="Device\ScsiCommands\HL-DT-ST.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\HL-DT-ST.cs" />
|
<Compile Include="Device\ScsiCommands\SSC.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\SSC.cs" />
|
<Compile Include="Device\ScsiCommands\SMC.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\SMC.cs" />
|
<Compile Include="Device\ScsiCommands\Adaptec.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Adaptec.cs" />
|
<Compile Include="Device\ScsiCommands\ArchiveCorp.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\ArchiveCorp.cs" />
|
<Compile Include="Device\ScsiCommands\Certance.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Certance.cs" />
|
<Compile Include="Device\ScsiCommands\Fujitsu.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Fujitsu.cs" />
|
<Compile Include="Device\ScsiCommands\HP.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\HP.cs" />
|
<Compile Include="Device\ScsiCommands\Plasmon.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Plasmon.cs" />
|
<Compile Include="Device\ScsiCommands\SyQuest.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\SyQuest.cs" />
|
<Compile Include="Device\AtaCommands\AtaCHS.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\AtaCHS.cs" />
|
<Compile Include="Device\AtaCommands\Atapi.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\Atapi.cs" />
|
<Compile Include="Device\AtaCommands\Ata28.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\Ata28.cs" />
|
<Compile Include="Device\AtaCommands\Ata48.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\Ata48.cs" />
|
<Compile Include="Device\AtaCommands\Smart.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\Smart.cs" />
|
<Compile Include="Device\AtaCommands\Cfa.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\Cfa.cs" />
|
<Compile Include="Device\AtaCommands\MCPT.cs"/>
|
||||||
<Compile Include="Device\AtaCommands\MCPT.cs" />
|
<Compile Include="Device\MmcCommands\MMC.cs"/>
|
||||||
<Compile Include="FreeBSD\Command.cs" />
|
<Compile Include="Device\MmcCommands\SecureDigital.cs"/>
|
||||||
<Compile Include="FreeBSD\Enums.cs" />
|
<Compile Include="Device\ScsiCommands\Kreon.cs"/>
|
||||||
<Compile Include="FreeBSD\Extern.cs" />
|
<Compile Include="Device\List.cs"/>
|
||||||
<Compile Include="FreeBSD\Structs.cs" />
|
<Compile Include="Linux\ListDevices.cs"/>
|
||||||
<Compile Include="Device\MmcCommands\MMC.cs" />
|
<Compile Include="Windows\Usb.cs"/>
|
||||||
<Compile Include="Device\MmcCommands\SecureDigital.cs" />
|
<Compile Include="Windows\UsbFunctions.cs"/>
|
||||||
<Compile Include="Device\ScsiCommands\Kreon.cs" />
|
|
||||||
<Compile Include="Device\List.cs" />
|
|
||||||
<Compile Include="Linux\ListDevices.cs" />
|
|
||||||
<Compile Include="Windows\Usb.cs" />
|
|
||||||
<Compile Include="Windows\UsbFunctions.cs" />
|
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="System.Management" Version="6.0.0-preview.7.21377.19" />
|
<PackageReference Include="System.Management" Version="6.0.0-preview.7.21377.19"/>
|
||||||
<PackageReference Include="Unclassified.NetRevisionTask" Version="0.4.1" PrivateAssets="all" />
|
<PackageReference Include="Unclassified.NetRevisionTask" Version="0.4.1" PrivateAssets="all"/>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ProjectExtensions>
|
<ProjectExtensions>
|
||||||
<MonoDevelop>
|
<MonoDevelop>
|
||||||
<Properties>
|
<Properties>
|
||||||
<Policies>
|
<Policies>
|
||||||
<DotNetNamingPolicy DirectoryNamespaceAssociation="PrefixedHierarchical" ResourceNamePolicy="MSBuild" />
|
<DotNetNamingPolicy DirectoryNamespaceAssociation="PrefixedHierarchical" ResourceNamePolicy="MSBuild"/>
|
||||||
<StandardHeader IncludeInNewFiles="True" Text="/***************************************************************************
Aaru Data Preservation Suite
----------------------------------------------------------------------------
 
Filename : ${FileName}
Author(s) : ${AuthorName} <${AuthorEmail}>

Component : Component
 
--[ Description ] ----------------------------------------------------------
 
 Description
 
--[ License ] --------------------------------------------------------------
 
 This library is free software; you can redistribute it and/or modify
 it under the terms of the GNU Lesser General Public License as
 published by the Free Software Foundation; either version 2.1 of the
 License, or (at your option) any later version.

 This library is distributed in the hope that it will be useful, but
 WITHOUT ANY WARRANTY; without even the implied warranty of
 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 Lesser General Public License for more details.

 You should have received a copy of the GNU Lesser General Public
 License along with this library; if not, see <http://www.gnu.org/licenses/>.

----------------------------------------------------------------------------
Copyright © 2011-${Year} ${CopyrightHolder}
****************************************************************************/" />
|
<StandardHeader IncludeInNewFiles="True" Text="/***************************************************************************
Aaru Data Preservation Suite
----------------------------------------------------------------------------
 
Filename : ${FileName}
Author(s) : ${AuthorName} <${AuthorEmail}>

Component : Component
 
--[ Description ] ----------------------------------------------------------
 
 Description
 
--[ License ] --------------------------------------------------------------
 
 This library is free software; you can redistribute it and/or modify
 it under the terms of the GNU Lesser General Public License as
 published by the Free Software Foundation; either version 2.1 of the
 License, or (at your option) any later version.

 This library is distributed in the hope that it will be useful, but
 WITHOUT ANY WARRANTY; without even the implied warranty of
 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 Lesser General Public License for more details.

 You should have received a copy of the GNU Lesser General Public
 License along with this library; if not, see <http://www.gnu.org/licenses/>.

----------------------------------------------------------------------------
Copyright © 2011-${Year} ${CopyrightHolder}
****************************************************************************/"/>
|
||||||
<TextStylePolicy FileWidth="120" TabWidth="4" IndentWidth="4" RemoveTrailingWhitespace="True" NoTabsAfterNonTabs="False" EolMarker="Native" TabsToSpaces="True" scope="text/x-csharp" />
|
<TextStylePolicy FileWidth="120" TabWidth="4" IndentWidth="4" RemoveTrailingWhitespace="True" NoTabsAfterNonTabs="False" EolMarker="Native" TabsToSpaces="True" scope="text/x-csharp"/>
|
||||||
<CSharpFormattingPolicy IndentBlock="True" IndentBraces="False" IndentSwitchSection="True" IndentSwitchCaseSection="True" LabelPositioning="OneLess" NewLinesForBracesInTypes="True" NewLinesForBracesInMethods="True" NewLinesForBracesInProperties="True" NewLinesForBracesInAccessors="True" NewLinesForBracesInAnonymousMethods="True" NewLinesForBracesInControlBlocks="True" NewLinesForBracesInAnonymousTypes="True" NewLinesForBracesInObjectCollectionArrayInitializers="True" NewLinesForBracesInLambdaExpressionBody="True" NewLineForElse="True" NewLineForCatch="True" NewLineForFinally="True" NewLineForMembersInObjectInit="True" NewLineForMembersInAnonymousTypes="True" NewLineForClausesInQuery="True" SpacingAfterMethodDeclarationName="False" SpaceWithinMethodDeclarationParenthesis="False" SpaceBetweenEmptyMethodDeclarationParentheses="False" SpaceAfterMethodCallName="False" SpaceWithinMethodCallParentheses="False" SpaceBetweenEmptyMethodCallParentheses="False" SpaceWithinExpressionParentheses="False" SpaceWithinCastParentheses="False" SpaceWithinOtherParentheses="False" SpaceAfterCast="False" SpacesIgnoreAroundVariableDeclaration="False" SpaceBeforeOpenSquareBracket="False" SpaceBetweenEmptySquareBrackets="False" SpaceWithinSquareBrackets="False" SpaceAfterColonInBaseTypeDeclaration="True" SpaceAfterComma="True" SpaceAfterDot="False" SpaceAfterSemicolonsInForStatement="True" SpaceBeforeColonInBaseTypeDeclaration="True" SpaceBeforeComma="False" SpaceBeforeDot="False" SpaceBeforeSemicolonsInForStatement="False" SpacingAroundBinaryOperator="Single" WrappingPreserveSingleLine="True" WrappingKeepStatementsOnSingleLine="True" PlaceSystemDirectiveFirst="True" SpaceAfterControlFlowStatementKeyword="False" scope="text/x-csharp" />
|
<CSharpFormattingPolicy IndentBlock="True" IndentBraces="False" IndentSwitchSection="True" IndentSwitchCaseSection="True" LabelPositioning="OneLess" NewLinesForBracesInTypes="True" NewLinesForBracesInMethods="True" NewLinesForBracesInProperties="True" NewLinesForBracesInAccessors="True" NewLinesForBracesInAnonymousMethods="True" NewLinesForBracesInControlBlocks="True" NewLinesForBracesInAnonymousTypes="True" NewLinesForBracesInObjectCollectionArrayInitializers="True" NewLinesForBracesInLambdaExpressionBody="True" NewLineForElse="True" NewLineForCatch="True" NewLineForFinally="True" NewLineForMembersInObjectInit="True" NewLineForMembersInAnonymousTypes="True" NewLineForClausesInQuery="True" SpacingAfterMethodDeclarationName="False" SpaceWithinMethodDeclarationParenthesis="False" SpaceBetweenEmptyMethodDeclarationParentheses="False" SpaceAfterMethodCallName="False" SpaceWithinMethodCallParentheses="False" SpaceBetweenEmptyMethodCallParentheses="False" SpaceWithinExpressionParentheses="False" SpaceWithinCastParentheses="False" SpaceWithinOtherParentheses="False" SpaceAfterCast="False" SpacesIgnoreAroundVariableDeclaration="False" SpaceBeforeOpenSquareBracket="False" SpaceBetweenEmptySquareBrackets="False" SpaceWithinSquareBrackets="False" SpaceAfterColonInBaseTypeDeclaration="True" SpaceAfterComma="True" SpaceAfterDot="False" SpaceAfterSemicolonsInForStatement="True" SpaceBeforeColonInBaseTypeDeclaration="True" SpaceBeforeComma="False" SpaceBeforeDot="False" SpaceBeforeSemicolonsInForStatement="False" SpacingAroundBinaryOperator="Single" WrappingPreserveSingleLine="True" WrappingKeepStatementsOnSingleLine="True" PlaceSystemDirectiveFirst="True" SpaceAfterControlFlowStatementKeyword="False" scope="text/x-csharp"/>
|
||||||
</Policies>
|
</Policies>
|
||||||
</Properties>
|
</Properties>
|
||||||
</MonoDevelop>
|
</MonoDevelop>
|
||||||
</ProjectExtensions>
|
</ProjectExtensions>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ProjectReference Include="..\Aaru.CommonTypes\Aaru.CommonTypes.csproj" />
|
<ProjectReference Include="..\Aaru.CommonTypes\Aaru.CommonTypes.csproj"/>
|
||||||
<ProjectReference Include="..\Aaru.Console\Aaru.Console.csproj">
|
<ProjectReference Include="..\Aaru.Console\Aaru.Console.csproj">
|
||||||
<Project>{CCAA7AFE-C094-4D82-A66D-630DE8A3F545}</Project>
|
<Project>{CCAA7AFE-C094-4D82-A66D-630DE8A3F545}</Project>
|
||||||
<Name>Aaru.Console</Name>
|
<Name>Aaru.Console</Name>
|
||||||
|
|||||||
@@ -33,7 +33,6 @@
|
|||||||
using System;
|
using System;
|
||||||
using Aaru.CommonTypes.Interop;
|
using Aaru.CommonTypes.Interop;
|
||||||
using Aaru.Decoders.ATA;
|
using Aaru.Decoders.ATA;
|
||||||
using Aaru.Devices.FreeBSD;
|
|
||||||
using Aaru.Devices.Windows;
|
using Aaru.Devices.Windows;
|
||||||
using Microsoft.Win32.SafeHandles;
|
using Microsoft.Win32.SafeHandles;
|
||||||
using PlatformID = Aaru.CommonTypes.Interop.PlatformID;
|
using PlatformID = Aaru.CommonTypes.Interop.PlatformID;
|
||||||
@@ -142,36 +141,6 @@ namespace Aaru.Devices
|
|||||||
return Linux.Command.SendScsiCommand((int)fd, cdb, ref buffer, out senseBuffer, timeout, dir,
|
return Linux.Command.SendScsiCommand((int)fd, cdb, ref buffer, out senseBuffer, timeout, dir,
|
||||||
out duration, out sense);
|
out duration, out sense);
|
||||||
}
|
}
|
||||||
case PlatformID.FreeBSD:
|
|
||||||
{
|
|
||||||
CcbFlags flags = 0;
|
|
||||||
|
|
||||||
switch(direction)
|
|
||||||
{
|
|
||||||
case ScsiDirection.In:
|
|
||||||
flags = CcbFlags.CamDirIn;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case ScsiDirection.Out:
|
|
||||||
flags = CcbFlags.CamDirOut;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case ScsiDirection.Bidirectional:
|
|
||||||
flags = CcbFlags.CamDirBoth;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case ScsiDirection.None:
|
|
||||||
flags = CcbFlags.CamDirNone;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return IntPtr.Size == 8
|
|
||||||
? FreeBSD.Command.SendScsiCommand64((IntPtr)fd, cdb, ref buffer, out senseBuffer,
|
|
||||||
timeout, flags, out duration, out sense)
|
|
||||||
: FreeBSD.Command.SendScsiCommand((IntPtr)fd, cdb, ref buffer, out senseBuffer, timeout,
|
|
||||||
flags, out duration, out sense);
|
|
||||||
}
|
|
||||||
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -242,11 +211,6 @@ namespace Aaru.Devices
|
|||||||
transferRegister, ref buffer, timeout, transferBlocks,
|
transferRegister, ref buffer, timeout, transferBlocks,
|
||||||
out duration, out sense);
|
out duration, out sense);
|
||||||
}
|
}
|
||||||
case PlatformID.FreeBSD:
|
|
||||||
{
|
|
||||||
return FreeBSD.Command.SendAtaCommand((IntPtr)fd, registers, out errorRegisters, protocol,
|
|
||||||
ref buffer, timeout, out duration, out sense);
|
|
||||||
}
|
|
||||||
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -317,11 +281,6 @@ namespace Aaru.Devices
|
|||||||
transferRegister, ref buffer, timeout, transferBlocks,
|
transferRegister, ref buffer, timeout, transferBlocks,
|
||||||
out duration, out sense);
|
out duration, out sense);
|
||||||
}
|
}
|
||||||
case PlatformID.FreeBSD:
|
|
||||||
{
|
|
||||||
return FreeBSD.Command.SendAtaCommand((IntPtr)fd, registers, out errorRegisters, protocol,
|
|
||||||
ref buffer, timeout, out duration, out sense);
|
|
||||||
}
|
|
||||||
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -379,9 +338,6 @@ namespace Aaru.Devices
|
|||||||
return Linux.Command.SendAtaCommand((int)fd, registers, out errorRegisters, protocol,
|
return Linux.Command.SendAtaCommand((int)fd, registers, out errorRegisters, protocol,
|
||||||
transferRegister, ref buffer, timeout, transferBlocks,
|
transferRegister, ref buffer, timeout, transferBlocks,
|
||||||
out duration, out sense);
|
out duration, out sense);
|
||||||
case PlatformID.FreeBSD:
|
|
||||||
return FreeBSD.Command.SendAtaCommand((IntPtr)fd, registers, out errorRegisters, protocol,
|
|
||||||
ref buffer, timeout, out duration, out sense);
|
|
||||||
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
default: throw new InvalidOperationException($"Platform {ptId} not yet supported.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -42,14 +42,13 @@ using Aaru.CommonTypes.Structs.Devices.SCSI;
|
|||||||
using Aaru.Decoders.SCSI;
|
using Aaru.Decoders.SCSI;
|
||||||
using Aaru.Decoders.SCSI.MMC;
|
using Aaru.Decoders.SCSI.MMC;
|
||||||
using Aaru.Decoders.SecureDigital;
|
using Aaru.Decoders.SecureDigital;
|
||||||
using Aaru.Devices.FreeBSD;
|
using Aaru.Devices.Linux;
|
||||||
using Aaru.Devices.Windows;
|
using Aaru.Devices.Windows;
|
||||||
using Aaru.Helpers;
|
using Aaru.Helpers;
|
||||||
using Microsoft.Win32.SafeHandles;
|
using Microsoft.Win32.SafeHandles;
|
||||||
using Extern = Aaru.Devices.Windows.Extern;
|
using Extern = Aaru.Devices.Windows.Extern;
|
||||||
using FileAccess = Aaru.Devices.Windows.FileAccess;
|
using FileAccess = Aaru.Devices.Windows.FileAccess;
|
||||||
using FileAttributes = Aaru.Devices.Windows.FileAttributes;
|
using FileAttributes = Aaru.Devices.Windows.FileAttributes;
|
||||||
using FileFlags = Aaru.Devices.Linux.FileFlags;
|
|
||||||
using FileMode = Aaru.Devices.Windows.FileMode;
|
using FileMode = Aaru.Devices.Windows.FileMode;
|
||||||
using FileShare = Aaru.Devices.Windows.FileShare;
|
using FileShare = Aaru.Devices.Windows.FileShare;
|
||||||
using Inquiry = Aaru.CommonTypes.Structs.Devices.SCSI.Inquiry;
|
using Inquiry = Aaru.CommonTypes.Structs.Devices.SCSI.Inquiry;
|
||||||
@@ -151,25 +150,7 @@ namespace Aaru.Devices
|
|||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PlatformID.FreeBSD:
|
default: throw new DeviceException($"Platform {PlatformId} not supported.");
|
||||||
{
|
|
||||||
FileHandle = FreeBSD.Extern.cam_open_device(devicePath, FreeBSD.FileFlags.ReadWrite);
|
|
||||||
|
|
||||||
if(((IntPtr)FileHandle).ToInt64() == 0)
|
|
||||||
{
|
|
||||||
Error = true;
|
|
||||||
LastError = Marshal.GetLastWin32Error();
|
|
||||||
}
|
|
||||||
|
|
||||||
var camDevice = (CamDevice)Marshal.PtrToStructure((IntPtr)FileHandle, typeof(CamDevice));
|
|
||||||
|
|
||||||
if(StringHandlers.CToString(camDevice.SimName) == "ata")
|
|
||||||
throw new
|
|
||||||
DeviceException("Parallel ATA devices are not supported on FreeBSD due to upstream bug #224250.");
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default: throw new DeviceException($"Platform {PlatformId} not yet supported.");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -30,10 +30,9 @@
|
|||||||
// Copyright © 2011-2021 Natalia Portillo
|
// Copyright © 2011-2021 Natalia Portillo
|
||||||
// ****************************************************************************/
|
// ****************************************************************************/
|
||||||
|
|
||||||
using System;
|
using Aaru.CommonTypes.Interop;
|
||||||
using Aaru.Devices.Linux;
|
using Aaru.Devices.Linux;
|
||||||
using Microsoft.Win32.SafeHandles;
|
using Microsoft.Win32.SafeHandles;
|
||||||
using PlatformID = Aaru.CommonTypes.Interop.PlatformID;
|
|
||||||
|
|
||||||
namespace Aaru.Devices
|
namespace Aaru.Devices
|
||||||
{
|
{
|
||||||
@@ -68,10 +67,6 @@ namespace Aaru.Devices
|
|||||||
case PlatformID.Linux:
|
case PlatformID.Linux:
|
||||||
Extern.close((int)FileHandle);
|
Extern.close((int)FileHandle);
|
||||||
|
|
||||||
break;
|
|
||||||
case PlatformID.FreeBSD:
|
|
||||||
FreeBSD.Extern.cam_close_device((IntPtr)FileHandle);
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -107,7 +107,6 @@ namespace Aaru.Devices
|
|||||||
{
|
{
|
||||||
case PlatformID.Win32NT: return Windows.ListDevices.GetList();
|
case PlatformID.Win32NT: return Windows.ListDevices.GetList();
|
||||||
case PlatformID.Linux: return Linux.ListDevices.GetList();
|
case PlatformID.Linux: return Linux.ListDevices.GetList();
|
||||||
case PlatformID.FreeBSD: return FreeBSD.ListDevices.GetList();
|
|
||||||
default:
|
default:
|
||||||
throw new
|
throw new
|
||||||
InvalidOperationException($"Platform {DetectOS.GetRealPlatformID()} not yet supported.");
|
InvalidOperationException($"Platform {DetectOS.GetRealPlatformID()} not yet supported.");
|
||||||
|
|||||||
@@ -1,630 +0,0 @@
|
|||||||
// /***************************************************************************
|
|
||||||
// Aaru Data Preservation Suite
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Filename : Command.cs
|
|
||||||
// Author(s) : Natalia Portillo <claunia@claunia.com>
|
|
||||||
//
|
|
||||||
// Component : FreeBSD direct device access.
|
|
||||||
//
|
|
||||||
// --[ Description ] ----------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Contains a high level representation of the FreeBSD syscalls used to
|
|
||||||
// directly interface devices.
|
|
||||||
//
|
|
||||||
// --[ License ] --------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// This library is free software; you can redistribute it and/or modify
|
|
||||||
// it under the terms of the GNU Lesser General Public License as
|
|
||||||
// published by the Free Software Foundation; either version 2.1 of the
|
|
||||||
// License, or (at your option) any later version.
|
|
||||||
//
|
|
||||||
// This library is distributed in the hope that it will be useful, but
|
|
||||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
// Lesser General Public License for more details.
|
|
||||||
//
|
|
||||||
// You should have received a copy of the GNU Lesser General Public
|
|
||||||
// License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
|
||||||
//
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// Copyright © 2011-2021 Natalia Portillo
|
|
||||||
// ****************************************************************************/
|
|
||||||
|
|
||||||
using System;
|
|
||||||
using System.Diagnostics.CodeAnalysis;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using Aaru.Console;
|
|
||||||
using Aaru.Decoders.ATA;
|
|
||||||
using static Aaru.Devices.FreeBSD.Extern;
|
|
||||||
|
|
||||||
namespace Aaru.Devices.FreeBSD
|
|
||||||
{
|
|
||||||
[SuppressMessage("ReSharper", "BitwiseOperatorOnEnumWithoutFlags"), Obsolete]
|
|
||||||
internal static class Command
|
|
||||||
{
|
|
||||||
const int CAM_MAX_CDBLEN = 16;
|
|
||||||
|
|
||||||
/// <summary>Sends a SCSI command (64-bit arch)</summary>
|
|
||||||
/// <returns>0 if no error occurred, otherwise, errno</returns>
|
|
||||||
/// <param name="dev">CAM device</param>
|
|
||||||
/// <param name="cdb">SCSI CDB</param>
|
|
||||||
/// <param name="buffer">Buffer for SCSI command response</param>
|
|
||||||
/// <param name="senseBuffer">Buffer with the SCSI sense</param>
|
|
||||||
/// <param name="timeout">Timeout in seconds</param>
|
|
||||||
/// <param name="direction">SCSI command transfer direction</param>
|
|
||||||
/// <param name="duration">Time it took to execute the command in milliseconds</param>
|
|
||||||
/// <param name="sense">
|
|
||||||
/// <c>True</c> if SCSI error returned non-OK status and <paramref name="senseBuffer" /> contains SCSI
|
|
||||||
/// sense
|
|
||||||
/// </param>
|
|
||||||
[Obsolete]
|
|
||||||
internal static int SendScsiCommand64(IntPtr dev, byte[] cdb, ref byte[] buffer, out byte[] senseBuffer,
|
|
||||||
uint timeout, CcbFlags direction, out double duration, out bool sense)
|
|
||||||
{
|
|
||||||
senseBuffer = null;
|
|
||||||
duration = 0;
|
|
||||||
sense = false;
|
|
||||||
|
|
||||||
if(buffer == null)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
IntPtr ccbPtr = cam_getccb(dev);
|
|
||||||
IntPtr cdbPtr = IntPtr.Zero;
|
|
||||||
|
|
||||||
if(ccbPtr.ToInt64() == 0)
|
|
||||||
{
|
|
||||||
sense = true;
|
|
||||||
|
|
||||||
return Marshal.GetLastWin32Error();
|
|
||||||
}
|
|
||||||
|
|
||||||
var csio = (CcbScsiio64)Marshal.PtrToStructure(ccbPtr, typeof(CcbScsiio64));
|
|
||||||
csio.ccb_h.func_code = XptOpcode.XptScsiIo;
|
|
||||||
csio.ccb_h.flags = direction;
|
|
||||||
csio.ccb_h.xflags = 0;
|
|
||||||
csio.ccb_h.retry_count = 1;
|
|
||||||
csio.ccb_h.cbfcnp = IntPtr.Zero;
|
|
||||||
csio.ccb_h.timeout = timeout;
|
|
||||||
csio.data_ptr = Marshal.AllocHGlobal(buffer.Length);
|
|
||||||
csio.dxfer_len = (uint)buffer.Length;
|
|
||||||
csio.sense_len = 32;
|
|
||||||
csio.cdb_len = (byte)cdb.Length;
|
|
||||||
|
|
||||||
// TODO: Create enum?
|
|
||||||
csio.tag_action = 0x20;
|
|
||||||
csio.cdb_bytes = new byte[CAM_MAX_CDBLEN];
|
|
||||||
|
|
||||||
if(cdb.Length <= CAM_MAX_CDBLEN)
|
|
||||||
Array.Copy(cdb, 0, csio.cdb_bytes, 0, cdb.Length);
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cdbPtr = Marshal.AllocHGlobal(cdb.Length);
|
|
||||||
byte[] cdbPtrBytes = BitConverter.GetBytes(cdbPtr.ToInt64());
|
|
||||||
Array.Copy(cdbPtrBytes, 0, csio.cdb_bytes, 0, IntPtr.Size);
|
|
||||||
csio.ccb_h.flags |= CcbFlags.CamCdbPointer;
|
|
||||||
}
|
|
||||||
|
|
||||||
csio.ccb_h.flags |= CcbFlags.CamDevQfrzdis;
|
|
||||||
|
|
||||||
Marshal.Copy(buffer, 0, csio.data_ptr, buffer.Length);
|
|
||||||
Marshal.StructureToPtr(csio, ccbPtr, false);
|
|
||||||
|
|
||||||
DateTime start = DateTime.UtcNow;
|
|
||||||
int error = cam_send_ccb(dev, ccbPtr);
|
|
||||||
DateTime end = DateTime.UtcNow;
|
|
||||||
|
|
||||||
if(error < 0)
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
|
|
||||||
csio = (CcbScsiio64)Marshal.PtrToStructure(ccbPtr, typeof(CcbScsiio64));
|
|
||||||
|
|
||||||
if((csio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamReqCmp &&
|
|
||||||
(csio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamScsiStatusError)
|
|
||||||
{
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
AaruConsole.DebugWriteLine("FreeBSD devices", "CAM status {0} error {1}", csio.ccb_h.status, error);
|
|
||||||
sense = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((csio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamScsiStatusError)
|
|
||||||
{
|
|
||||||
sense = true;
|
|
||||||
senseBuffer = new byte[1];
|
|
||||||
senseBuffer[0] = csio.scsi_status;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((csio.ccb_h.status & CamStatus.CamAutosnsValid) != 0)
|
|
||||||
if(csio.sense_len - csio.sense_resid > 0)
|
|
||||||
{
|
|
||||||
sense = (csio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamScsiStatusError;
|
|
||||||
senseBuffer = new byte[csio.sense_len - csio.sense_resid];
|
|
||||||
senseBuffer[0] = csio.sense_data.error_code;
|
|
||||||
Array.Copy(csio.sense_data.sense_buf, 0, senseBuffer, 1, senseBuffer.Length - 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
buffer = new byte[csio.dxfer_len];
|
|
||||||
cdb = new byte[csio.cdb_len];
|
|
||||||
|
|
||||||
Marshal.Copy(csio.data_ptr, buffer, 0, buffer.Length);
|
|
||||||
|
|
||||||
if(csio.ccb_h.flags.HasFlag(CcbFlags.CamCdbPointer))
|
|
||||||
Marshal.Copy(new IntPtr(BitConverter.ToInt64(csio.cdb_bytes, 0)), cdb, 0, cdb.Length);
|
|
||||||
else
|
|
||||||
Array.Copy(csio.cdb_bytes, 0, cdb, 0, cdb.Length);
|
|
||||||
|
|
||||||
duration = (end - start).TotalMilliseconds;
|
|
||||||
|
|
||||||
if(csio.ccb_h.flags.HasFlag(CcbFlags.CamCdbPointer))
|
|
||||||
Marshal.FreeHGlobal(cdbPtr);
|
|
||||||
|
|
||||||
Marshal.FreeHGlobal(csio.data_ptr);
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>Sends a SCSI command (32-bit arch)</summary>
|
|
||||||
/// <returns>0 if no error occurred, otherwise, errno</returns>
|
|
||||||
/// <param name="dev">CAM device</param>
|
|
||||||
/// <param name="cdb">SCSI CDB</param>
|
|
||||||
/// <param name="buffer">Buffer for SCSI command response</param>
|
|
||||||
/// <param name="senseBuffer">Buffer with the SCSI sense</param>
|
|
||||||
/// <param name="timeout">Timeout in seconds</param>
|
|
||||||
/// <param name="direction">SCSI command transfer direction</param>
|
|
||||||
/// <param name="duration">Time it took to execute the command in milliseconds</param>
|
|
||||||
/// <param name="sense">
|
|
||||||
/// <c>True</c> if SCSI error returned non-OK status and <paramref name="senseBuffer" /> contains SCSI
|
|
||||||
/// sense
|
|
||||||
/// </param>
|
|
||||||
[Obsolete]
|
|
||||||
internal static int SendScsiCommand(IntPtr dev, byte[] cdb, ref byte[] buffer, out byte[] senseBuffer,
|
|
||||||
uint timeout, CcbFlags direction, out double duration, out bool sense)
|
|
||||||
{
|
|
||||||
senseBuffer = null;
|
|
||||||
duration = 0;
|
|
||||||
sense = false;
|
|
||||||
|
|
||||||
if(buffer == null)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
IntPtr ccbPtr = cam_getccb(dev);
|
|
||||||
IntPtr cdbPtr = IntPtr.Zero;
|
|
||||||
|
|
||||||
if(ccbPtr.ToInt32() == 0)
|
|
||||||
{
|
|
||||||
sense = true;
|
|
||||||
|
|
||||||
return Marshal.GetLastWin32Error();
|
|
||||||
}
|
|
||||||
|
|
||||||
var csio = (CcbScsiio)Marshal.PtrToStructure(ccbPtr, typeof(CcbScsiio));
|
|
||||||
csio.ccb_h.func_code = XptOpcode.XptScsiIo;
|
|
||||||
csio.ccb_h.flags = direction;
|
|
||||||
csio.ccb_h.xflags = 0;
|
|
||||||
csio.ccb_h.retry_count = 1;
|
|
||||||
csio.ccb_h.cbfcnp = IntPtr.Zero;
|
|
||||||
csio.ccb_h.timeout = timeout;
|
|
||||||
csio.data_ptr = Marshal.AllocHGlobal(buffer.Length);
|
|
||||||
csio.dxfer_len = (uint)buffer.Length;
|
|
||||||
csio.sense_len = 32;
|
|
||||||
csio.cdb_len = (byte)cdb.Length;
|
|
||||||
|
|
||||||
// TODO: Create enum?
|
|
||||||
csio.tag_action = 0x20;
|
|
||||||
csio.cdb_bytes = new byte[CAM_MAX_CDBLEN];
|
|
||||||
|
|
||||||
if(cdb.Length <= CAM_MAX_CDBLEN)
|
|
||||||
Array.Copy(cdb, 0, csio.cdb_bytes, 0, cdb.Length);
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cdbPtr = Marshal.AllocHGlobal(cdb.Length);
|
|
||||||
byte[] cdbPtrBytes = BitConverter.GetBytes(cdbPtr.ToInt32());
|
|
||||||
Array.Copy(cdbPtrBytes, 0, csio.cdb_bytes, 0, IntPtr.Size);
|
|
||||||
csio.ccb_h.flags |= CcbFlags.CamCdbPointer;
|
|
||||||
}
|
|
||||||
|
|
||||||
csio.ccb_h.flags |= CcbFlags.CamDevQfrzdis;
|
|
||||||
|
|
||||||
Marshal.Copy(buffer, 0, csio.data_ptr, buffer.Length);
|
|
||||||
Marshal.StructureToPtr(csio, ccbPtr, false);
|
|
||||||
|
|
||||||
DateTime start = DateTime.UtcNow;
|
|
||||||
int error = cam_send_ccb(dev, ccbPtr);
|
|
||||||
DateTime end = DateTime.UtcNow;
|
|
||||||
|
|
||||||
if(error < 0)
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
|
|
||||||
csio = (CcbScsiio)Marshal.PtrToStructure(ccbPtr, typeof(CcbScsiio));
|
|
||||||
|
|
||||||
if((csio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamReqCmp &&
|
|
||||||
(csio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamScsiStatusError)
|
|
||||||
{
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
AaruConsole.DebugWriteLine("FreeBSD devices", "CAM status {0} error {1}", csio.ccb_h.status, error);
|
|
||||||
sense = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((csio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamScsiStatusError)
|
|
||||||
{
|
|
||||||
sense = true;
|
|
||||||
senseBuffer = new byte[1];
|
|
||||||
senseBuffer[0] = csio.scsi_status;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((csio.ccb_h.status & CamStatus.CamAutosnsValid) != 0)
|
|
||||||
if(csio.sense_len - csio.sense_resid > 0)
|
|
||||||
{
|
|
||||||
sense = (csio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamScsiStatusError;
|
|
||||||
senseBuffer = new byte[csio.sense_len - csio.sense_resid];
|
|
||||||
senseBuffer[0] = csio.sense_data.error_code;
|
|
||||||
Array.Copy(csio.sense_data.sense_buf, 0, senseBuffer, 1, senseBuffer.Length - 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
buffer = new byte[csio.dxfer_len];
|
|
||||||
cdb = new byte[csio.cdb_len];
|
|
||||||
|
|
||||||
Marshal.Copy(csio.data_ptr, buffer, 0, buffer.Length);
|
|
||||||
|
|
||||||
if(csio.ccb_h.flags.HasFlag(CcbFlags.CamCdbPointer))
|
|
||||||
Marshal.Copy(new IntPtr(BitConverter.ToInt32(csio.cdb_bytes, 0)), cdb, 0, cdb.Length);
|
|
||||||
else
|
|
||||||
Array.Copy(csio.cdb_bytes, 0, cdb, 0, cdb.Length);
|
|
||||||
|
|
||||||
duration = (end - start).TotalMilliseconds;
|
|
||||||
|
|
||||||
if(csio.ccb_h.flags.HasFlag(CcbFlags.CamCdbPointer))
|
|
||||||
Marshal.FreeHGlobal(cdbPtr);
|
|
||||||
|
|
||||||
Marshal.FreeHGlobal(csio.data_ptr);
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>Converts ATA protocol to CAM flags</summary>
|
|
||||||
/// <param name="protocol">ATA protocol</param>
|
|
||||||
/// <returns>CAM flags</returns>
|
|
||||||
[Obsolete]
|
|
||||||
static CcbFlags AtaProtocolToCamFlags(AtaProtocol protocol)
|
|
||||||
{
|
|
||||||
switch(protocol)
|
|
||||||
{
|
|
||||||
case AtaProtocol.DeviceDiagnostic:
|
|
||||||
case AtaProtocol.DeviceReset:
|
|
||||||
case AtaProtocol.HardReset:
|
|
||||||
case AtaProtocol.NonData:
|
|
||||||
case AtaProtocol.SoftReset:
|
|
||||||
case AtaProtocol.ReturnResponse: return CcbFlags.CamDirNone;
|
|
||||||
case AtaProtocol.PioIn:
|
|
||||||
case AtaProtocol.UDmaIn: return CcbFlags.CamDirIn;
|
|
||||||
case AtaProtocol.PioOut:
|
|
||||||
case AtaProtocol.UDmaOut: return CcbFlags.CamDirOut;
|
|
||||||
default: return CcbFlags.CamDirNone;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>Sends an ATA command in CHS mode</summary>
|
|
||||||
/// <returns>0 if no error occurred, otherwise, errno</returns>
|
|
||||||
/// <param name="dev">CAM device</param>
|
|
||||||
/// <param name="buffer">Buffer for SCSI command response</param>
|
|
||||||
/// <param name="timeout">Timeout in seconds</param>
|
|
||||||
/// <param name="duration">Time it took to execute the command in milliseconds</param>
|
|
||||||
/// <param name="sense"><c>True</c> if ATA error returned non-OK status</param>
|
|
||||||
/// <param name="registers">Registers to send to drive</param>
|
|
||||||
/// <param name="errorRegisters">Registers returned by drive</param>
|
|
||||||
/// <param name="protocol">ATA protocol to use</param>
|
|
||||||
[Obsolete]
|
|
||||||
internal static int SendAtaCommand(IntPtr dev, AtaRegistersChs registers,
|
|
||||||
out AtaErrorRegistersChs errorRegisters, AtaProtocol protocol,
|
|
||||||
ref byte[] buffer, uint timeout, out double duration, out bool sense)
|
|
||||||
{
|
|
||||||
duration = 0;
|
|
||||||
sense = false;
|
|
||||||
errorRegisters = new AtaErrorRegistersChs();
|
|
||||||
|
|
||||||
if(buffer == null)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
IntPtr ccbPtr = cam_getccb(dev);
|
|
||||||
|
|
||||||
var ataio = (CcbAtaio)Marshal.PtrToStructure(ccbPtr, typeof(CcbAtaio));
|
|
||||||
ataio.ccb_h.func_code = XptOpcode.XptAtaIo;
|
|
||||||
ataio.ccb_h.flags = AtaProtocolToCamFlags(protocol);
|
|
||||||
ataio.ccb_h.xflags = 0;
|
|
||||||
ataio.ccb_h.retry_count = 1;
|
|
||||||
ataio.ccb_h.cbfcnp = IntPtr.Zero;
|
|
||||||
ataio.ccb_h.timeout = timeout;
|
|
||||||
ataio.data_ptr = Marshal.AllocHGlobal(buffer.Length);
|
|
||||||
ataio.dxfer_len = (uint)buffer.Length;
|
|
||||||
ataio.ccb_h.flags |= CcbFlags.CamDevQfrzdis;
|
|
||||||
ataio.cmd.flags = CamAtaIoFlags.NeedResult;
|
|
||||||
|
|
||||||
switch(protocol)
|
|
||||||
{
|
|
||||||
case AtaProtocol.Dma:
|
|
||||||
case AtaProtocol.DmaQueued:
|
|
||||||
case AtaProtocol.UDmaIn:
|
|
||||||
case AtaProtocol.UDmaOut:
|
|
||||||
ataio.cmd.flags |= CamAtaIoFlags.Dma;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case AtaProtocol.FpDma:
|
|
||||||
ataio.cmd.flags |= CamAtaIoFlags.Fpdma;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
ataio.cmd.command = registers.Command;
|
|
||||||
ataio.cmd.lba_high = registers.CylinderHigh;
|
|
||||||
ataio.cmd.lba_mid = registers.CylinderLow;
|
|
||||||
ataio.cmd.device = (byte)(0x40 | registers.DeviceHead);
|
|
||||||
ataio.cmd.features = registers.Feature;
|
|
||||||
ataio.cmd.sector_count = registers.SectorCount;
|
|
||||||
ataio.cmd.lba_low = registers.Sector;
|
|
||||||
|
|
||||||
Marshal.Copy(buffer, 0, ataio.data_ptr, buffer.Length);
|
|
||||||
Marshal.StructureToPtr(ataio, ccbPtr, false);
|
|
||||||
|
|
||||||
DateTime start = DateTime.UtcNow;
|
|
||||||
int error = cam_send_ccb(dev, ccbPtr);
|
|
||||||
DateTime end = DateTime.UtcNow;
|
|
||||||
|
|
||||||
if(error < 0)
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
|
|
||||||
ataio = (CcbAtaio)Marshal.PtrToStructure(ccbPtr, typeof(CcbAtaio));
|
|
||||||
|
|
||||||
if((ataio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamReqCmp &&
|
|
||||||
(ataio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamAtaStatusError)
|
|
||||||
{
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
AaruConsole.DebugWriteLine("FreeBSD devices", "CAM status {0} error {1}", ataio.ccb_h.status, error);
|
|
||||||
sense = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((ataio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamAtaStatusError)
|
|
||||||
sense = true;
|
|
||||||
|
|
||||||
errorRegisters.CylinderHigh = ataio.res.lba_high;
|
|
||||||
errorRegisters.CylinderLow = ataio.res.lba_mid;
|
|
||||||
errorRegisters.DeviceHead = ataio.res.device;
|
|
||||||
errorRegisters.Error = ataio.res.error;
|
|
||||||
errorRegisters.Sector = ataio.res.lba_low;
|
|
||||||
errorRegisters.SectorCount = ataio.res.sector_count;
|
|
||||||
errorRegisters.Status = ataio.res.status;
|
|
||||||
|
|
||||||
buffer = new byte[ataio.dxfer_len];
|
|
||||||
|
|
||||||
Marshal.Copy(ataio.data_ptr, buffer, 0, buffer.Length);
|
|
||||||
duration = (end - start).TotalMilliseconds;
|
|
||||||
|
|
||||||
Marshal.FreeHGlobal(ataio.data_ptr);
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
|
|
||||||
sense = errorRegisters.Error != 0 || (errorRegisters.Status & 0xA5) != 0 || error != 0;
|
|
||||||
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>Sends an ATA command in 28-bit LBA mode</summary>
|
|
||||||
/// <returns>0 if no error occurred, otherwise, errno</returns>
|
|
||||||
/// <param name="dev">CAM device</param>
|
|
||||||
/// <param name="buffer">Buffer for SCSI command response</param>
|
|
||||||
/// <param name="timeout">Timeout in seconds</param>
|
|
||||||
/// <param name="duration">Time it took to execute the command in milliseconds</param>
|
|
||||||
/// <param name="sense"><c>True</c> if ATA error returned non-OK status</param>
|
|
||||||
/// <param name="registers">Registers to send to drive</param>
|
|
||||||
/// <param name="errorRegisters">Registers returned by drive</param>
|
|
||||||
/// <param name="protocol">ATA protocol to use</param>
|
|
||||||
[Obsolete]
|
|
||||||
internal static int SendAtaCommand(IntPtr dev, AtaRegistersLba28 registers,
|
|
||||||
out AtaErrorRegistersLba28 errorRegisters, AtaProtocol protocol,
|
|
||||||
ref byte[] buffer, uint timeout, out double duration, out bool sense)
|
|
||||||
{
|
|
||||||
duration = 0;
|
|
||||||
sense = false;
|
|
||||||
errorRegisters = new AtaErrorRegistersLba28();
|
|
||||||
|
|
||||||
if(buffer == null)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
IntPtr ccbPtr = cam_getccb(dev);
|
|
||||||
|
|
||||||
var ataio = (CcbAtaio)Marshal.PtrToStructure(ccbPtr, typeof(CcbAtaio));
|
|
||||||
ataio.ccb_h.func_code = XptOpcode.XptAtaIo;
|
|
||||||
ataio.ccb_h.flags = AtaProtocolToCamFlags(protocol);
|
|
||||||
ataio.ccb_h.xflags = 0;
|
|
||||||
ataio.ccb_h.retry_count = 1;
|
|
||||||
ataio.ccb_h.cbfcnp = IntPtr.Zero;
|
|
||||||
ataio.ccb_h.timeout = timeout;
|
|
||||||
ataio.data_ptr = Marshal.AllocHGlobal(buffer.Length);
|
|
||||||
ataio.dxfer_len = (uint)buffer.Length;
|
|
||||||
ataio.ccb_h.flags |= CcbFlags.CamDevQfrzdis;
|
|
||||||
ataio.cmd.flags = CamAtaIoFlags.NeedResult;
|
|
||||||
|
|
||||||
switch(protocol)
|
|
||||||
{
|
|
||||||
case AtaProtocol.Dma:
|
|
||||||
case AtaProtocol.DmaQueued:
|
|
||||||
case AtaProtocol.UDmaIn:
|
|
||||||
case AtaProtocol.UDmaOut:
|
|
||||||
ataio.cmd.flags |= CamAtaIoFlags.Dma;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case AtaProtocol.FpDma:
|
|
||||||
ataio.cmd.flags |= CamAtaIoFlags.Fpdma;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
ataio.cmd.command = registers.Command;
|
|
||||||
ataio.cmd.lba_high = registers.LbaHigh;
|
|
||||||
ataio.cmd.lba_mid = registers.LbaMid;
|
|
||||||
ataio.cmd.device = (byte)(0x40 | registers.DeviceHead);
|
|
||||||
ataio.cmd.features = registers.Feature;
|
|
||||||
ataio.cmd.sector_count = registers.SectorCount;
|
|
||||||
ataio.cmd.lba_low = registers.LbaLow;
|
|
||||||
|
|
||||||
Marshal.Copy(buffer, 0, ataio.data_ptr, buffer.Length);
|
|
||||||
Marshal.StructureToPtr(ataio, ccbPtr, false);
|
|
||||||
|
|
||||||
DateTime start = DateTime.UtcNow;
|
|
||||||
int error = cam_send_ccb(dev, ccbPtr);
|
|
||||||
DateTime end = DateTime.UtcNow;
|
|
||||||
|
|
||||||
if(error < 0)
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
|
|
||||||
ataio = (CcbAtaio)Marshal.PtrToStructure(ccbPtr, typeof(CcbAtaio));
|
|
||||||
|
|
||||||
if((ataio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamReqCmp &&
|
|
||||||
(ataio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamAtaStatusError)
|
|
||||||
{
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
AaruConsole.DebugWriteLine("FreeBSD devices", "CAM status {0} error {1}", ataio.ccb_h.status, error);
|
|
||||||
sense = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((ataio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamAtaStatusError)
|
|
||||||
sense = true;
|
|
||||||
|
|
||||||
errorRegisters.LbaHigh = ataio.res.lba_high;
|
|
||||||
errorRegisters.LbaMid = ataio.res.lba_mid;
|
|
||||||
errorRegisters.DeviceHead = ataio.res.device;
|
|
||||||
errorRegisters.Error = ataio.res.error;
|
|
||||||
errorRegisters.LbaLow = ataio.res.lba_low;
|
|
||||||
errorRegisters.SectorCount = ataio.res.sector_count;
|
|
||||||
errorRegisters.Status = ataio.res.status;
|
|
||||||
|
|
||||||
buffer = new byte[ataio.dxfer_len];
|
|
||||||
|
|
||||||
Marshal.Copy(ataio.data_ptr, buffer, 0, buffer.Length);
|
|
||||||
duration = (end - start).TotalMilliseconds;
|
|
||||||
|
|
||||||
Marshal.FreeHGlobal(ataio.data_ptr);
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
|
|
||||||
sense = errorRegisters.Error != 0 || (errorRegisters.Status & 0xA5) != 0 || error != 0;
|
|
||||||
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>Sends an ATA command in 48-bit mode</summary>
|
|
||||||
/// <returns>0 if no error occurred, otherwise, errno</returns>
|
|
||||||
/// <param name="dev">CAM device</param>
|
|
||||||
/// <param name="buffer">Buffer for SCSI command response</param>
|
|
||||||
/// <param name="timeout">Timeout in seconds</param>
|
|
||||||
/// <param name="duration">Time it took to execute the command in milliseconds</param>
|
|
||||||
/// <param name="sense"><c>True</c> if ATA error returned non-OK status</param>
|
|
||||||
/// <param name="registers">Registers to send to drive</param>
|
|
||||||
/// <param name="errorRegisters">Registers returned by drive</param>
|
|
||||||
/// <param name="protocol">ATA protocol to use</param>
|
|
||||||
[Obsolete]
|
|
||||||
internal static int SendAtaCommand(IntPtr dev, AtaRegistersLba48 registers,
|
|
||||||
out AtaErrorRegistersLba48 errorRegisters, AtaProtocol protocol,
|
|
||||||
ref byte[] buffer, uint timeout, out double duration, out bool sense)
|
|
||||||
{
|
|
||||||
duration = 0;
|
|
||||||
sense = false;
|
|
||||||
errorRegisters = new AtaErrorRegistersLba48();
|
|
||||||
|
|
||||||
// 48-bit ATA CAM commands can crash FreeBSD < 9.2-RELEASE
|
|
||||||
if((Environment.Version.Major == 9 && Environment.Version.Minor < 2) ||
|
|
||||||
Environment.Version.Major < 9)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if(buffer == null)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
IntPtr ccbPtr = cam_getccb(dev);
|
|
||||||
|
|
||||||
var ataio = (CcbAtaio)Marshal.PtrToStructure(ccbPtr, typeof(CcbAtaio));
|
|
||||||
ataio.ccb_h.func_code = XptOpcode.XptAtaIo;
|
|
||||||
ataio.ccb_h.flags = AtaProtocolToCamFlags(protocol);
|
|
||||||
ataio.ccb_h.xflags = 0;
|
|
||||||
ataio.ccb_h.retry_count = 1;
|
|
||||||
ataio.ccb_h.cbfcnp = IntPtr.Zero;
|
|
||||||
ataio.ccb_h.timeout = timeout;
|
|
||||||
ataio.data_ptr = Marshal.AllocHGlobal(buffer.Length);
|
|
||||||
ataio.dxfer_len = (uint)buffer.Length;
|
|
||||||
ataio.ccb_h.flags |= CcbFlags.CamDevQfrzdis;
|
|
||||||
ataio.cmd.flags = CamAtaIoFlags.NeedResult | CamAtaIoFlags.ExtendedCommand;
|
|
||||||
|
|
||||||
switch(protocol)
|
|
||||||
{
|
|
||||||
case AtaProtocol.Dma:
|
|
||||||
case AtaProtocol.DmaQueued:
|
|
||||||
case AtaProtocol.UDmaIn:
|
|
||||||
case AtaProtocol.UDmaOut:
|
|
||||||
ataio.cmd.flags |= CamAtaIoFlags.Dma;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case AtaProtocol.FpDma:
|
|
||||||
ataio.cmd.flags |= CamAtaIoFlags.Fpdma;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
ataio.cmd.lba_high_exp = registers.LbaHighCurrent;
|
|
||||||
ataio.cmd.lba_mid_exp = registers.LbaMidCurrent;
|
|
||||||
ataio.cmd.features_exp = (byte)((registers.Feature & 0xFF00) >> 8);
|
|
||||||
ataio.cmd.sector_count_exp = (byte)((registers.SectorCount & 0xFF00) >> 8);
|
|
||||||
ataio.cmd.lba_low_exp = registers.LbaLowCurrent;
|
|
||||||
ataio.cmd.lba_high = registers.LbaHighPrevious;
|
|
||||||
ataio.cmd.lba_mid = registers.LbaMidPrevious;
|
|
||||||
ataio.cmd.features = (byte)(registers.Feature & 0xFF);
|
|
||||||
ataio.cmd.sector_count = (byte)(registers.SectorCount & 0xFF);
|
|
||||||
ataio.cmd.lba_low = registers.LbaLowPrevious;
|
|
||||||
ataio.cmd.command = registers.Command;
|
|
||||||
ataio.cmd.device = (byte)(0x40 | registers.DeviceHead);
|
|
||||||
|
|
||||||
Marshal.Copy(buffer, 0, ataio.data_ptr, buffer.Length);
|
|
||||||
Marshal.StructureToPtr(ataio, ccbPtr, false);
|
|
||||||
|
|
||||||
DateTime start = DateTime.UtcNow;
|
|
||||||
int error = cam_send_ccb(dev, ccbPtr);
|
|
||||||
DateTime end = DateTime.UtcNow;
|
|
||||||
|
|
||||||
if(error < 0)
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
|
|
||||||
ataio = (CcbAtaio)Marshal.PtrToStructure(ccbPtr, typeof(CcbAtaio));
|
|
||||||
|
|
||||||
if((ataio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamReqCmp &&
|
|
||||||
(ataio.ccb_h.status & CamStatus.CamStatusMask) != CamStatus.CamAtaStatusError)
|
|
||||||
{
|
|
||||||
error = Marshal.GetLastWin32Error();
|
|
||||||
AaruConsole.DebugWriteLine("FreeBSD devices", "CAM status {0} error {1}", ataio.ccb_h.status, error);
|
|
||||||
sense = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if((ataio.ccb_h.status & CamStatus.CamStatusMask) == CamStatus.CamAtaStatusError)
|
|
||||||
sense = true;
|
|
||||||
|
|
||||||
errorRegisters.SectorCount = (ushort)((ataio.res.sector_count_exp << 8) + ataio.res.sector_count);
|
|
||||||
errorRegisters.LbaLowCurrent = ataio.res.lba_low_exp;
|
|
||||||
errorRegisters.LbaMidCurrent = ataio.res.lba_mid_exp;
|
|
||||||
errorRegisters.LbaHighCurrent = ataio.res.lba_high_exp;
|
|
||||||
errorRegisters.LbaLowPrevious = ataio.res.lba_low;
|
|
||||||
errorRegisters.LbaMidPrevious = ataio.res.lba_mid;
|
|
||||||
errorRegisters.LbaHighPrevious = ataio.res.lba_high;
|
|
||||||
errorRegisters.DeviceHead = ataio.res.device;
|
|
||||||
errorRegisters.Error = ataio.res.error;
|
|
||||||
errorRegisters.Status = ataio.res.status;
|
|
||||||
|
|
||||||
buffer = new byte[ataio.dxfer_len];
|
|
||||||
|
|
||||||
Marshal.Copy(ataio.data_ptr, buffer, 0, buffer.Length);
|
|
||||||
duration = (end - start).TotalMilliseconds;
|
|
||||||
|
|
||||||
Marshal.FreeHGlobal(ataio.data_ptr);
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
|
|
||||||
sense = errorRegisters.Error != 0 || (errorRegisters.Status & 0xA5) != 0 || error != 0;
|
|
||||||
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,572 +0,0 @@
|
|||||||
// /***************************************************************************
|
|
||||||
// Aaru Data Preservation Suite
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Filename : Enums.cs
|
|
||||||
// Author(s) : Natalia Portillo <claunia@claunia.com>
|
|
||||||
//
|
|
||||||
// Component : FreeBSD direct device access.
|
|
||||||
//
|
|
||||||
// --[ Description ] ----------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Contains enumerations necessary for directly interfacing devices under
|
|
||||||
// FreeBSD.
|
|
||||||
//
|
|
||||||
// --[ License ] --------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// This library is free software; you can redistribute it and/or modify
|
|
||||||
// it under the terms of the GNU Lesser General Public License as
|
|
||||||
// published by the Free Software Foundation; either version 2.1 of the
|
|
||||||
// License, or (at your option) any later version.
|
|
||||||
//
|
|
||||||
// This library is distributed in the hope that it will be useful, but
|
|
||||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
// Lesser General Public License for more details.
|
|
||||||
//
|
|
||||||
// You should have received a copy of the GNU Lesser General Public
|
|
||||||
// License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
|
||||||
//
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// Copyright © 2011-2021 Natalia Portillo
|
|
||||||
// ****************************************************************************/
|
|
||||||
|
|
||||||
using System;
|
|
||||||
|
|
||||||
namespace Aaru.Devices.FreeBSD
|
|
||||||
{
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum FileFlags
|
|
||||||
{
|
|
||||||
/// <summary>O_RDONLY</summary>
|
|
||||||
ReadOnly = 0x00000000,
|
|
||||||
/// <summary>O_WRONLY</summary>
|
|
||||||
WriteOnly = 0x00000001,
|
|
||||||
/// <summary>O_RDWR</summary>
|
|
||||||
ReadWrite = 0x00000002,
|
|
||||||
/// <summary>O_NONBLOCK</summary>
|
|
||||||
NonBlocking = 0x00000004,
|
|
||||||
/// <summary>O_APPEND</summary>
|
|
||||||
Append = 0x00000008,
|
|
||||||
/// <summary>O_SHLOCK</summary>
|
|
||||||
SharedLock = 0x00000010,
|
|
||||||
/// <summary>O_EXLOCK</summary>
|
|
||||||
ExclusiveLock = 0x00000020,
|
|
||||||
/// <summary>O_ASYNC</summary>
|
|
||||||
Async = 0x00000040,
|
|
||||||
/// <summary>O_FSYNC</summary>
|
|
||||||
SyncWrites = 0x00000080,
|
|
||||||
/// <summary>O_NOFOLLOW</summary>
|
|
||||||
NoFollowSymlink = 0x00000100,
|
|
||||||
/// <summary>O_CREAT</summary>
|
|
||||||
OpenOrCreate = 0x00000200,
|
|
||||||
/// <summary>O_TRUNC</summary>
|
|
||||||
Truncate = 0x00000400,
|
|
||||||
/// <summary>O_EXCL</summary>
|
|
||||||
CreateNew = 0x00000800,
|
|
||||||
/// <summary>O_NOCTTY</summary>
|
|
||||||
NoControlTty = 0x00008000,
|
|
||||||
/// <summary>O_DIRECT</summary>
|
|
||||||
Direct = 0x00010000,
|
|
||||||
/// <summary>O_DIRECTORY</summary>
|
|
||||||
Directory = 0x00020000,
|
|
||||||
/// <summary>O_EXEC</summary>
|
|
||||||
Execute = 0x00040000,
|
|
||||||
/// <summary>O_TTY_INIT</summary>
|
|
||||||
InitializeTty = 0x00080000,
|
|
||||||
/// <summary>O_CLOEXEC</summary>
|
|
||||||
CloseOnExec = 0x00100000
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum CamAtaIoFlags : byte
|
|
||||||
{
|
|
||||||
/// <summary>48-bit command</summary>
|
|
||||||
ExtendedCommand = 0x01,
|
|
||||||
/// <summary>FPDMA command</summary>
|
|
||||||
Fpdma = 0x02,
|
|
||||||
/// <summary>Control, not a command</summary>
|
|
||||||
Control = 0x04,
|
|
||||||
/// <summary>Needs result</summary>
|
|
||||||
NeedResult = 0x08,
|
|
||||||
/// <summary>DMA command</summary>
|
|
||||||
Dma = 0x10
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>XPT Opcodes for xpt_action</summary>
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum XptOpcode
|
|
||||||
{
|
|
||||||
// Function code flags are bits greater than 0xff
|
|
||||||
|
|
||||||
/// <summary>Non-immediate function code</summary>
|
|
||||||
XptFcQueued = 0x100, XptFcUserCcb = 0x200,
|
|
||||||
/// <summary>Only for the transport layer device</summary>
|
|
||||||
XptFcXptOnly = 0x400,
|
|
||||||
/// <summary>Passes through the device queues</summary>
|
|
||||||
XptFcDevQueued = 0x800 | XptFcQueued,
|
|
||||||
|
|
||||||
// Common function commands: 0x00->0x0F
|
|
||||||
|
|
||||||
/// <summary>Execute Nothing</summary>
|
|
||||||
XptNoop = 0x00,
|
|
||||||
/// <summary>Execute the requested I/O operation</summary>
|
|
||||||
XptScsiIo = 0x01 | XptFcDevQueued,
|
|
||||||
/// <summary>Get type information for specified device</summary>
|
|
||||||
XptGdevType = 0x02,
|
|
||||||
/// <summary>Get a list of peripheral devices</summary>
|
|
||||||
XptGdevlist = 0x03,
|
|
||||||
/// <summary>Path routing inquiry</summary>
|
|
||||||
XptPathInq = 0x04,
|
|
||||||
/// <summary>Release a frozen device queue</summary>
|
|
||||||
XptRelSimq = 0x05,
|
|
||||||
/// <summary>Set Asynchronous Callback Parameters</summary>
|
|
||||||
XptSasyncCb = 0x06,
|
|
||||||
/// <summary>Set device type information</summary>
|
|
||||||
XptSdevType = 0x07,
|
|
||||||
/// <summary>(Re)Scan the SCSI Bus</summary>
|
|
||||||
XptScanBus = 0x08 | XptFcQueued | XptFcUserCcb | XptFcXptOnly,
|
|
||||||
/// <summary>Get EDT entries matching the given pattern</summary>
|
|
||||||
XptDevMatch = 0x09 | XptFcXptOnly,
|
|
||||||
/// <summary>Turn on debugging for a bus, target or lun</summary>
|
|
||||||
XptDebug = 0x0a,
|
|
||||||
/// <summary>Path statistics (error counts, etc.)</summary>
|
|
||||||
XptPathStats = 0x0b,
|
|
||||||
/// <summary>Device statistics (error counts, etc.)</summary>
|
|
||||||
XptGdevStats = 0x0c,
|
|
||||||
/// <summary>Get/Set Device advanced information</summary>
|
|
||||||
XptDevAdvinfo = 0x0e,
|
|
||||||
/// <summary>Asynchronous event</summary>
|
|
||||||
XptAsync = 0x0f | XptFcQueued | XptFcUserCcb | XptFcXptOnly,
|
|
||||||
|
|
||||||
/// <summary>SCSI Control Functions: 0x10->0x1F</summary>
|
|
||||||
/// <summary>Abort the specified CCB</summary>
|
|
||||||
XptAbort = 0x10,
|
|
||||||
/// <summary>Reset the specified SCSI bus</summary>
|
|
||||||
XptResetBus = 0x11 | XptFcXptOnly,
|
|
||||||
/// <summary>Bus Device Reset the specified SCSI device</summary>
|
|
||||||
XptResetDev = 0x12 | XptFcDevQueued,
|
|
||||||
/// <summary>Terminate the I/O process</summary>
|
|
||||||
XptTermIo = 0x13,
|
|
||||||
/// <summary>Scan Logical Unit</summary>
|
|
||||||
XptScanLun = 0x14 | XptFcQueued | XptFcUserCcb | XptFcXptOnly,
|
|
||||||
/// <summary>Get default/user transfer settings for the target</summary>
|
|
||||||
XptGetTranSettings = 0x15,
|
|
||||||
/// <summary>Set transfer rate/width negotiation settings</summary>
|
|
||||||
XptSetTranSettings = 0x16,
|
|
||||||
/// <summary>Calculate the geometry parameters for a device give the sector size and volume size.</summary>
|
|
||||||
XptCalcGeometry = 0x17,
|
|
||||||
/// <summary>Execute the requested ATA I/O operation</summary>
|
|
||||||
XptAtaIo = 0x18 | XptFcDevQueued,
|
|
||||||
|
|
||||||
/// <summary>Compat only</summary>
|
|
||||||
XptGetSimKnobOld = 0x18,
|
|
||||||
|
|
||||||
/// <summary>Set SIM specific knob values.</summary>
|
|
||||||
XptSetSimKnob = 0x19,
|
|
||||||
/// <summary>Get SIM specific knob values.</summary>
|
|
||||||
XptGetSimKnob = 0x1a,
|
|
||||||
/// <summary>Serial Management Protocol</summary>
|
|
||||||
XptSmpIo = 0x1b | XptFcDevQueued,
|
|
||||||
/// <summary>Scan Target</summary>
|
|
||||||
XptScanTgt = 0x1E | XptFcQueued | XptFcUserCcb | XptFcXptOnly,
|
|
||||||
|
|
||||||
// HBA engine commands 0x20->0x2F
|
|
||||||
|
|
||||||
/// <summary>HBA engine feature inquiry</summary>
|
|
||||||
XptEngInq = 0x20 | XptFcXptOnly,
|
|
||||||
/// <summary>HBA execute engine request</summary>
|
|
||||||
XptEngExec = 0x21 | XptFcDevQueued,
|
|
||||||
|
|
||||||
// Target mode commands: 0x30->0x3F
|
|
||||||
|
|
||||||
/// <summary>Enable LUN as a target</summary>
|
|
||||||
XptEnLun = 0x30,
|
|
||||||
/// <summary>Execute target I/O request</summary>
|
|
||||||
XptTargetIo = 0x31 | XptFcDevQueued,
|
|
||||||
/// <summary>Accept Host Target Mode CDB</summary>
|
|
||||||
XptAcceptTargetIo = 0x32 | XptFcQueued | XptFcUserCcb,
|
|
||||||
/// <summary>Continue Host Target I/O Connection</summary>
|
|
||||||
XptContTargetIo = 0x33 | XptFcDevQueued,
|
|
||||||
/// <summary>Notify Host Target driver of event (obsolete)</summary>
|
|
||||||
XptImmedNotify = 0x34 | XptFcQueued | XptFcUserCcb,
|
|
||||||
/// <summary>Acknowledgement of event (obsolete)</summary>
|
|
||||||
XptNotifyAck = 0x35,
|
|
||||||
/// <summary>Notify Host Target driver of event</summary>
|
|
||||||
XptImmediateNotify = 0x36 | XptFcQueued | XptFcUserCcb,
|
|
||||||
/// <summary>Acknowledgement of event</summary>
|
|
||||||
XptNotifyAcknowledge = 0x37 | XptFcQueued | XptFcUserCcb,
|
|
||||||
|
|
||||||
/// <summary>Vendor Unique codes: 0x80->0x8F</summary>
|
|
||||||
XptVunique = 0x80
|
|
||||||
}
|
|
||||||
|
|
||||||
[Obsolete]
|
|
||||||
internal enum CcbDevMatchStatus
|
|
||||||
{
|
|
||||||
CamDevMatchLast, CamDevMatchMore, CamDevMatchListChanged,
|
|
||||||
CamDevMatchSizeError, CamDevMatchError
|
|
||||||
}
|
|
||||||
|
|
||||||
[Obsolete]
|
|
||||||
internal enum DevMatchType
|
|
||||||
{
|
|
||||||
DevMatchPeriph = 0, DevMatchDevice, DevMatchBus
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum PeriphPatternFlags
|
|
||||||
{
|
|
||||||
PeriphMatchNone = 0x000, PeriphMatchPath = 0x001, PeriphMatchTarget = 0x002,
|
|
||||||
PeriphMatchLun = 0x004, PeriphMatchName = 0x008, PeriphMatchUnit = 0x010
|
|
||||||
|
|
||||||
// PERIPH_MATCH_ANY = 0x01f
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum DevPatternFlags
|
|
||||||
{
|
|
||||||
DevMatchNone = 0x000, DevMatchPath = 0x001, DevMatchTarget = 0x002,
|
|
||||||
DevMatchLun = 0x004, DevMatchInquiry = 0x008, DevMatchDevid = 0x010
|
|
||||||
|
|
||||||
// DEV_MATCH_ANY = 0x00f
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum BusPatternFlags
|
|
||||||
{
|
|
||||||
BusMatchNone = 0x000, BusMatchPath = 0x001, BusMatchName = 0x002,
|
|
||||||
BusMatchUnit = 0x004, BusMatchBusId = 0x008
|
|
||||||
|
|
||||||
// BUS_MATCH_ANY = 0x00f
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum DevResultFlags
|
|
||||||
{
|
|
||||||
DevResultNoflag = 0x00, DevResultUnconfigured = 0x01
|
|
||||||
}
|
|
||||||
|
|
||||||
[Obsolete]
|
|
||||||
internal enum CamProto
|
|
||||||
{
|
|
||||||
ProtoUnknown, ProtoUnspecified,
|
|
||||||
|
|
||||||
/// <summary>Small Computer System Interface</summary>
|
|
||||||
ProtoScsi,
|
|
||||||
|
|
||||||
/// <summary>AT Attachment</summary>
|
|
||||||
ProtoAta,
|
|
||||||
|
|
||||||
/// <summary>AT Attachment Packetized Interface</summary>
|
|
||||||
ProtoAtapi,
|
|
||||||
|
|
||||||
/// <summary>SATA Port Multiplier</summary>
|
|
||||||
ProtoSatapm,
|
|
||||||
|
|
||||||
/// <summary>SATA Enclosure Management Bridge</summary>
|
|
||||||
ProtoSemb,
|
|
||||||
|
|
||||||
/// <summary>NVMe</summary>
|
|
||||||
ProtoNvme,
|
|
||||||
|
|
||||||
/// <summary>MMC, SD, SDIO</summary>
|
|
||||||
ProtoMmcsd
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum MmcCardFeatures
|
|
||||||
{
|
|
||||||
CardFeatureMemory = 0x1, CardFeatureSdhc = 0x1 << 1, CardFeatureSdio = 0x1 << 2,
|
|
||||||
CardFeatureSd20 = 0x1 << 3, CardFeatureMmc = 0x1 << 4, CardFeature18V = 0x1 << 5
|
|
||||||
}
|
|
||||||
|
|
||||||
[Obsolete]
|
|
||||||
internal enum CamGenerations : uint
|
|
||||||
{
|
|
||||||
CamBusGeneration = 0x00, CamTargetGeneration = 0x01, CamDevGeneration = 0x02,
|
|
||||||
CamPeriphGeneration = 0x03
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum DevPosType
|
|
||||||
{
|
|
||||||
CamDevPosNone = 0x000, CamDevPosBus = 0x001, CamDevPosTarget = 0x002,
|
|
||||||
CamDevPosDevice = 0x004, CamDevPosPeriph = 0x008, CamDevPosPdptr = 0x010,
|
|
||||||
|
|
||||||
// CAM_DEV_POS_TYPEMASK = 0xf00,
|
|
||||||
CamDevPosEdt = 0x100, CamDevPosPdrv = 0x200
|
|
||||||
}
|
|
||||||
|
|
||||||
[Obsolete]
|
|
||||||
internal enum FreebsdIoctl : uint
|
|
||||||
{
|
|
||||||
Camiocommand = 0xC4D81802
|
|
||||||
}
|
|
||||||
|
|
||||||
[Flags, Obsolete]
|
|
||||||
internal enum CcbFlags : uint
|
|
||||||
{
|
|
||||||
/// <summary>The CDB field is a pointer</summary>
|
|
||||||
CamCdbPointer = 0x00000001,
|
|
||||||
/// <summary>SIM queue actions are enabled</summary>
|
|
||||||
CamQueueEnable = 0x00000002,
|
|
||||||
/// <summary>CCB contains a linked CDB</summary>
|
|
||||||
CamCdbLinked = 0x00000004,
|
|
||||||
/// <summary>Perform transport negotiation with this command.</summary>
|
|
||||||
CamNegotiate = 0x00000008,
|
|
||||||
/// <summary>Data type with physical addrs</summary>
|
|
||||||
CamDataIsphys = 0x00000010,
|
|
||||||
/// <summary>Disable autosense feature</summary>
|
|
||||||
CamDisAutosense = 0x00000020,
|
|
||||||
/// <summary>Data direction (00:IN/OUT)</summary>
|
|
||||||
CamDirBoth = 0x00000000,
|
|
||||||
/// <summary>Data direction (01:DATA IN)</summary>
|
|
||||||
CamDirIn = 0x00000040,
|
|
||||||
/// <summary>Data direction (10:DATA OUT)</summary>
|
|
||||||
CamDirOut = 0x00000080,
|
|
||||||
/// <summary>Data direction (11:no data)</summary>
|
|
||||||
CamDirNone = 0x000000C0,
|
|
||||||
/// <summary>Data type (000:Virtual)</summary>
|
|
||||||
CamDataVaddr = 0x00000000,
|
|
||||||
/// <summary>Data type (001:Physical)</summary>
|
|
||||||
CamDataPaddr = 0x00000010,
|
|
||||||
/// <summary>Data type (010:sglist)</summary>
|
|
||||||
CamDataSg = 0x00040000,
|
|
||||||
/// <summary>Data type (011:sglist phys)</summary>
|
|
||||||
CamDataSgPaddr = 0x00040010,
|
|
||||||
/// <summary>Data type (100:bio)</summary>
|
|
||||||
CamDataBio = 0x00200000,
|
|
||||||
/// <summary>Use Soft reset alternative</summary>
|
|
||||||
CamSoftRstOp = 0x00000100,
|
|
||||||
/// <summary>Flush resid bytes on complete</summary>
|
|
||||||
CamEngSync = 0x00000200,
|
|
||||||
/// <summary>Disable DEV Q freezing</summary>
|
|
||||||
CamDevQfrzdis = 0x00000400,
|
|
||||||
/// <summary>Freeze DEV Q on execution</summary>
|
|
||||||
CamDevQfreeze = 0x00000800,
|
|
||||||
/// <summary>Command takes a lot of power</summary>
|
|
||||||
CamHighPower = 0x00001000,
|
|
||||||
/// <summary>Sense data is a pointer</summary>
|
|
||||||
CamSensePtr = 0x00002000,
|
|
||||||
/// <summary>Sense pointer is physical addr</summary>
|
|
||||||
CamSensePhys = 0x00004000,
|
|
||||||
/// <summary>Use the tag action in this ccb</summary>
|
|
||||||
CamTagActionValid = 0x00008000,
|
|
||||||
/// <summary>Pass driver does err. recovery</summary>
|
|
||||||
CamPassErrRecover = 0x00010000,
|
|
||||||
/// <summary>Disable disconnect</summary>
|
|
||||||
CamDisDisconnect = 0x00020000,
|
|
||||||
/// <summary>Message buffer ptr is physical</summary>
|
|
||||||
CamMsgBufPhys = 0x00080000,
|
|
||||||
/// <summary>Autosense data ptr is physical</summary>
|
|
||||||
CamSnsBufPhys = 0x00100000,
|
|
||||||
/// <summary>CDB poiner is physical</summary>
|
|
||||||
CamCdbPhys = 0x00400000,
|
|
||||||
/// <summary>SG list is for the HBA engine</summary>
|
|
||||||
CamEngSglist = 0x00800000,
|
|
||||||
|
|
||||||
/* Phase cognizant mode flags */
|
|
||||||
/// <summary>Disable autosave/restore ptrs</summary>
|
|
||||||
CamDisAutosrp = 0x01000000,
|
|
||||||
/// <summary>Disable auto disconnect</summary>
|
|
||||||
CamDisAutodisc = 0x02000000,
|
|
||||||
/// <summary>Target CCB available</summary>
|
|
||||||
CamTgtCcbAvail = 0x04000000,
|
|
||||||
/// <summary>The SIM runs in phase mode</summary>
|
|
||||||
CamTgtPhaseMode = 0x08000000,
|
|
||||||
/// <summary>Message buffer valid</summary>
|
|
||||||
CamMsgbValid = 0x10000000,
|
|
||||||
/// <summary>Status buffer valid</summary>
|
|
||||||
CamStatusValid = 0x20000000,
|
|
||||||
/// <summary>Data buffer valid</summary>
|
|
||||||
CamDatabValid = 0x40000000,
|
|
||||||
/* Host target Mode flags */
|
|
||||||
/// <summary>Send sense data with status</summary>
|
|
||||||
CamSendSense = 0x08000000,
|
|
||||||
/// <summary>Terminate I/O Message sup.</summary>
|
|
||||||
CamTermIo = 0x10000000,
|
|
||||||
/// <summary>Disconnects are mandatory</summary>
|
|
||||||
CamDisconnect = 0x20000000,
|
|
||||||
/// <summary>Send status after data phase</summary>
|
|
||||||
CamSendStatus = 0x40000000,
|
|
||||||
/// <summary>Call callback without lock.</summary>
|
|
||||||
CamUnlocked = 0x80000000
|
|
||||||
}
|
|
||||||
|
|
||||||
[Obsolete]
|
|
||||||
internal enum CamStatus : uint
|
|
||||||
{
|
|
||||||
/// <summary>CCB request is in progress</summary>
|
|
||||||
CamReqInprog = 0x00,
|
|
||||||
|
|
||||||
/// <summary>CCB request completed without error</summary>
|
|
||||||
CamReqCmp = 0x01,
|
|
||||||
|
|
||||||
/// <summary>CCB request aborted by the host</summary>
|
|
||||||
CamReqAborted = 0x02,
|
|
||||||
|
|
||||||
/// <summary>Unable to abort CCB request</summary>
|
|
||||||
CamUaAbort = 0x03,
|
|
||||||
|
|
||||||
/// <summary>CCB request completed with an error</summary>
|
|
||||||
CamReqCmpErr = 0x04,
|
|
||||||
|
|
||||||
/// <summary>CAM subsystem is busy</summary>
|
|
||||||
CamBusy = 0x05,
|
|
||||||
|
|
||||||
/// <summary>CCB request was invalid</summary>
|
|
||||||
CamReqInvalid = 0x06,
|
|
||||||
|
|
||||||
/// <summary>Supplied Path ID is invalid</summary>
|
|
||||||
CamPathInvalid = 0x07,
|
|
||||||
|
|
||||||
/// <summary>SCSI Device Not Installed/there</summary>
|
|
||||||
CamDevNotThere = 0x08,
|
|
||||||
|
|
||||||
/// <summary>Unable to terminate I/O CCB request</summary>
|
|
||||||
CamUaTermio = 0x09,
|
|
||||||
|
|
||||||
/// <summary>Target Selection Timeout</summary>
|
|
||||||
CamSelTimeout = 0x0a,
|
|
||||||
|
|
||||||
/// <summary>Command timeout</summary>
|
|
||||||
CamCmdTimeout = 0x0b,
|
|
||||||
|
|
||||||
/// <summary>SCSI error, look at error code in CCB</summary>
|
|
||||||
CamScsiStatusError = 0x0c,
|
|
||||||
|
|
||||||
/// <summary>Message Reject Received</summary>
|
|
||||||
CamMsgRejectRec = 0x0d,
|
|
||||||
|
|
||||||
/// <summary>SCSI Bus Reset Sent/Received</summary>
|
|
||||||
CamScsiBusReset = 0x0e,
|
|
||||||
|
|
||||||
/// <summary>Uncorrectable parity error occurred</summary>
|
|
||||||
CamUncorParity = 0x0f,
|
|
||||||
|
|
||||||
/// <summary>Autosense: request sense cmd fail</summary>
|
|
||||||
CamAutosenseFail = 0x10,
|
|
||||||
|
|
||||||
/// <summary>No HBA Detected error</summary>
|
|
||||||
CamNoHba = 0x11,
|
|
||||||
|
|
||||||
/// <summary>Data Overrun error</summary>
|
|
||||||
CamDataRunErr = 0x12,
|
|
||||||
|
|
||||||
/// <summary>Unexpected Bus Free</summary>
|
|
||||||
CamUnexpBusfree = 0x13,
|
|
||||||
|
|
||||||
/// <summary>Target Bus Phase Sequence Failure</summary>
|
|
||||||
CamSequenceFail = 0x14,
|
|
||||||
|
|
||||||
/// <summary>CCB length supplied is inadequate</summary>
|
|
||||||
CamCcbLenErr = 0x15,
|
|
||||||
|
|
||||||
/// <summary>Unable to provide requested capability</summary>
|
|
||||||
CamProvideFail = 0x16,
|
|
||||||
|
|
||||||
/// <summary>A SCSI BDR msg was sent to target</summary>
|
|
||||||
CamBdrSent = 0x17,
|
|
||||||
|
|
||||||
/// <summary>CCB request terminated by the host</summary>
|
|
||||||
CamReqTermio = 0x18,
|
|
||||||
|
|
||||||
/// <summary>Unrecoverable Host Bus Adapter Error</summary>
|
|
||||||
CamUnrecHbaError = 0x19,
|
|
||||||
|
|
||||||
/// <summary>Request was too large for this host</summary>
|
|
||||||
CamReqTooBig = 0x1a,
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// This request should be requeued to preserve transaction ordering. This typically occurs when the SIM
|
|
||||||
/// recognizes an error that should freeze the queue and must place additional requests for the target at the sim level
|
|
||||||
/// back into the XPT queue.
|
|
||||||
/// </summary>
|
|
||||||
CamRequeueReq = 0x1b,
|
|
||||||
|
|
||||||
/// <summary>ATA error, look at error code in CCB</summary>
|
|
||||||
CamAtaStatusError = 0x1c,
|
|
||||||
|
|
||||||
/// <summary>Initiator/Target Nexus lost.</summary>
|
|
||||||
CamScsiItNexusLost = 0x1d,
|
|
||||||
|
|
||||||
/// <summary>SMP error, look at error code in CCB</summary>
|
|
||||||
CamSmpStatusError = 0x1e,
|
|
||||||
|
|
||||||
/// <summary>Command completed without error but exceeded the soft timeout threshold.</summary>
|
|
||||||
CamReqSofttimeout = 0x1f,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* 0x20 - 0x32 are unassigned
|
|
||||||
*/
|
|
||||||
|
|
||||||
/// <summary>Initiator Detected Error</summary>
|
|
||||||
CamIde = 0x33,
|
|
||||||
|
|
||||||
/// <summary>Resource Unavailable</summary>
|
|
||||||
CamResrcUnavail = 0x34,
|
|
||||||
|
|
||||||
/// <summary>Unacknowledged Event by Host</summary>
|
|
||||||
CamUnackedEvent = 0x35,
|
|
||||||
|
|
||||||
/// <summary>Message Received in Host Target Mode</summary>
|
|
||||||
CamMessageRecv = 0x36,
|
|
||||||
|
|
||||||
/// <summary>Invalid CDB received in Host Target Mode</summary>
|
|
||||||
CamInvalidCdb = 0x37,
|
|
||||||
|
|
||||||
/// <summary>Lun supplied is invalid</summary>
|
|
||||||
CamLunInvalid = 0x38,
|
|
||||||
|
|
||||||
/// <summary>Target ID supplied is invalid</summary>
|
|
||||||
CamTidInvalid = 0x39,
|
|
||||||
|
|
||||||
/// <summary>The requested function is not available</summary>
|
|
||||||
CamFuncNotavail = 0x3a,
|
|
||||||
|
|
||||||
/// <summary>Nexus is not established</summary>
|
|
||||||
CamNoNexus = 0x3b,
|
|
||||||
|
|
||||||
/// <summary>The initiator ID is invalid</summary>
|
|
||||||
CamIidInvalid = 0x3c,
|
|
||||||
|
|
||||||
/// <summary>The SCSI CDB has been received</summary>
|
|
||||||
CamCdbRecvd = 0x3d,
|
|
||||||
|
|
||||||
/// <summary>The LUN is already enabled for target mode</summary>
|
|
||||||
CamLunAlrdyEna = 0x3e,
|
|
||||||
|
|
||||||
/// <summary>SCSI Bus Busy</summary>
|
|
||||||
CamScsiBusy = 0x3f,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Flags
|
|
||||||
*/
|
|
||||||
|
|
||||||
/// <summary>The DEV queue is frozen w/this err</summary>
|
|
||||||
CamDevQfrzn = 0x40,
|
|
||||||
|
|
||||||
/// <summary>Autosense data valid for target</summary>
|
|
||||||
CamAutosnsValid = 0x80,
|
|
||||||
|
|
||||||
/// <summary>SIM ready to take more commands</summary>
|
|
||||||
CamReleaseSimq = 0x100,
|
|
||||||
|
|
||||||
/// <summary>SIM has this command in its queue</summary>
|
|
||||||
CamSimQueued = 0x200,
|
|
||||||
|
|
||||||
/// <summary>Quality of service data is valid</summary>
|
|
||||||
CamQosValid = 0x400,
|
|
||||||
|
|
||||||
/// <summary>Mask bits for just the status #</summary>
|
|
||||||
CamStatusMask = 0x3F,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Target Specific Adjunct Status
|
|
||||||
*/
|
|
||||||
|
|
||||||
/// <summary>sent sense with status</summary>
|
|
||||||
CamSentSense = 0x40000000
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,66 +0,0 @@
|
|||||||
// /***************************************************************************
|
|
||||||
// Aaru Data Preservation Suite
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Filename : Extern.cs
|
|
||||||
// Author(s) : Natalia Portillo <claunia@claunia.com>
|
|
||||||
//
|
|
||||||
// Component : FreeBSD direct device access.
|
|
||||||
//
|
|
||||||
// --[ Description ] ----------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Contains the P/Invoke definitions of FreeBSD syscalls used to directly
|
|
||||||
// interface devices.
|
|
||||||
//
|
|
||||||
// --[ License ] --------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// This library is free software; you can redistribute it and/or modify
|
|
||||||
// it under the terms of the GNU Lesser General Public License as
|
|
||||||
// published by the Free Software Foundation; either version 2.1 of the
|
|
||||||
// License, or (at your option) any later version.
|
|
||||||
//
|
|
||||||
// This library is distributed in the hope that it will be useful, but
|
|
||||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
// Lesser General Public License for more details.
|
|
||||||
//
|
|
||||||
// You should have received a copy of the GNU Lesser General Public
|
|
||||||
// License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
|
||||||
//
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// Copyright © 2011-2021 Natalia Portillo
|
|
||||||
// ****************************************************************************/
|
|
||||||
|
|
||||||
using System;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
|
|
||||||
namespace Aaru.Devices.FreeBSD
|
|
||||||
{
|
|
||||||
[Obsolete]
|
|
||||||
internal static class Extern
|
|
||||||
{
|
|
||||||
[DllImport("libc", CharSet = CharSet.Ansi, SetLastError = true)]
|
|
||||||
internal static extern int open(string pathname, [MarshalAs(UnmanagedType.U4)] FileFlags flags);
|
|
||||||
|
|
||||||
[DllImport("libc")]
|
|
||||||
internal static extern int close(int fd);
|
|
||||||
|
|
||||||
[DllImport("libcam", CharSet = CharSet.Ansi, SetLastError = true)]
|
|
||||||
internal static extern IntPtr cam_open_device(string path, [MarshalAs(UnmanagedType.U4)] FileFlags flags);
|
|
||||||
|
|
||||||
[DllImport("libcam", CharSet = CharSet.Ansi, SetLastError = true)]
|
|
||||||
internal static extern void cam_close_device(IntPtr dev);
|
|
||||||
|
|
||||||
[DllImport("libcam", CharSet = CharSet.Ansi, SetLastError = true)]
|
|
||||||
internal static extern IntPtr cam_getccb(IntPtr dev);
|
|
||||||
|
|
||||||
[DllImport("libcam", CharSet = CharSet.Ansi, SetLastError = true)]
|
|
||||||
internal static extern void cam_freeccb(IntPtr ccb);
|
|
||||||
|
|
||||||
[DllImport("libcam", CharSet = CharSet.Ansi, SetLastError = true)]
|
|
||||||
internal static extern int cam_send_ccb(IntPtr dev, IntPtr ccb);
|
|
||||||
|
|
||||||
[DllImport("libc")]
|
|
||||||
internal static extern int ioctl(int fd, FreebsdIoctl request, IntPtr argp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,169 +0,0 @@
|
|||||||
// /***************************************************************************
|
|
||||||
// Aaru Data Preservation Suite
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Filename : ListDevices.cs
|
|
||||||
// Author(s) : Natalia Portillo <claunia@claunia.com>
|
|
||||||
//
|
|
||||||
// Component : FreeBSD direct device access.
|
|
||||||
//
|
|
||||||
// --[ Description ] ----------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Gets a list of known devices.
|
|
||||||
//
|
|
||||||
// --[ License ] --------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// This library is free software; you can redistribute it and/or modify
|
|
||||||
// it under the terms of the GNU Lesser General Public License as
|
|
||||||
// published by the Free Software Foundation; either version 2.1 of the
|
|
||||||
// License, or (at your option) any later version.
|
|
||||||
//
|
|
||||||
// This library is distributed in the hope that it will be useful, but
|
|
||||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
// Lesser General Public License for more details.
|
|
||||||
//
|
|
||||||
// You should have received a copy of the GNU Lesser General Public
|
|
||||||
// License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
|
||||||
//
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// Copyright © 2011-2021 Natalia Portillo
|
|
||||||
// ****************************************************************************/
|
|
||||||
|
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
|
||||||
using Aaru.CommonTypes.Structs.Devices.ATA;
|
|
||||||
using Aaru.CommonTypes.Structs.Devices.SCSI;
|
|
||||||
using Aaru.Helpers;
|
|
||||||
using static Aaru.Devices.FreeBSD.Extern;
|
|
||||||
using Marshal = System.Runtime.InteropServices.Marshal;
|
|
||||||
|
|
||||||
namespace Aaru.Devices.FreeBSD
|
|
||||||
{
|
|
||||||
[Obsolete]
|
|
||||||
internal static class ListDevices
|
|
||||||
{
|
|
||||||
/// <summary>Gets a list of all known storage devices on FreeBSD</summary>
|
|
||||||
/// <returns>List of devices</returns>
|
|
||||||
[Obsolete]
|
|
||||||
internal static DeviceInfo[] GetList()
|
|
||||||
{
|
|
||||||
string[] passDevices = Directory.GetFiles("/dev/", "pass*", SearchOption.TopDirectoryOnly);
|
|
||||||
List<DeviceInfo> listDevices = new List<DeviceInfo>();
|
|
||||||
|
|
||||||
foreach(string passDevice in passDevices)
|
|
||||||
{
|
|
||||||
var deviceInfo = new DeviceInfo();
|
|
||||||
IntPtr dev = cam_open_device(passDevice, FileFlags.ReadWrite);
|
|
||||||
var camDevice = (CamDevice)Marshal.PtrToStructure(dev, typeof(CamDevice));
|
|
||||||
|
|
||||||
IntPtr ccbPtr = cam_getccb(dev);
|
|
||||||
|
|
||||||
if(ccbPtr.ToInt64() == 0)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
var cgd = (CcbGetdev)Marshal.PtrToStructure(ccbPtr, typeof(CcbGetdev));
|
|
||||||
|
|
||||||
cgd.ccb_h.func_code = XptOpcode.XptGdevType;
|
|
||||||
|
|
||||||
Marshal.StructureToPtr(cgd, ccbPtr, false);
|
|
||||||
|
|
||||||
int error = cam_send_ccb(dev, ccbPtr);
|
|
||||||
|
|
||||||
if(error < 0)
|
|
||||||
{
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
cgd = (CcbGetdev)Marshal.PtrToStructure(ccbPtr, typeof(CcbGetdev));
|
|
||||||
|
|
||||||
cam_freeccb(ccbPtr);
|
|
||||||
cam_close_device(dev);
|
|
||||||
|
|
||||||
string simName = StringHandlers.CToString(camDevice.SimName);
|
|
||||||
deviceInfo.Path = passDevice;
|
|
||||||
byte[] serialNumber = new byte[camDevice.SerialNumLen];
|
|
||||||
Array.Copy(camDevice.SerialNum, 0, serialNumber, 0, serialNumber.Length);
|
|
||||||
deviceInfo.Serial = StringHandlers.CToString(serialNumber);
|
|
||||||
|
|
||||||
switch(cgd.protocol)
|
|
||||||
{
|
|
||||||
case CamProto.ProtoAta:
|
|
||||||
case CamProto.ProtoAtapi:
|
|
||||||
case CamProto.ProtoSatapm:
|
|
||||||
{
|
|
||||||
// Little-endian FreeBSD gives it resorted
|
|
||||||
// Big-endian FreeBSD, no idea
|
|
||||||
byte[] atadTneid = new byte[512];
|
|
||||||
|
|
||||||
for(int aIndex = 0; aIndex < 512; aIndex += 2)
|
|
||||||
{
|
|
||||||
atadTneid[aIndex] = cgd.ident_data[aIndex + 1];
|
|
||||||
atadTneid[aIndex + 1] = cgd.ident_data[aIndex];
|
|
||||||
}
|
|
||||||
|
|
||||||
Identify.IdentifyDevice? idt = Identify.Decode(atadTneid);
|
|
||||||
|
|
||||||
if(idt.HasValue)
|
|
||||||
{
|
|
||||||
string[] separated = idt.Value.Model.Split(' ');
|
|
||||||
|
|
||||||
if(separated.Length == 1)
|
|
||||||
{
|
|
||||||
deviceInfo.Vendor = "ATA";
|
|
||||||
deviceInfo.Model = separated[0];
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
deviceInfo.Vendor = separated[0];
|
|
||||||
deviceInfo.Model = separated[^1];
|
|
||||||
}
|
|
||||||
|
|
||||||
deviceInfo.Serial = idt.Value.SerialNumber;
|
|
||||||
deviceInfo.Bus = simName == "ahcich" ? "SATA" : "ATA";
|
|
||||||
deviceInfo.Supported = simName != "ata";
|
|
||||||
}
|
|
||||||
|
|
||||||
if(cgd.protocol == CamProto.ProtoAtapi)
|
|
||||||
goto case CamProto.ProtoScsi;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case CamProto.ProtoScsi:
|
|
||||||
{
|
|
||||||
Inquiry? inq = Inquiry.Decode(cgd.inq_data);
|
|
||||||
|
|
||||||
if(inq.HasValue)
|
|
||||||
{
|
|
||||||
deviceInfo.Vendor = StringHandlers.CToString(inq.Value.VendorIdentification).Trim();
|
|
||||||
deviceInfo.Model = StringHandlers.CToString(inq.Value.ProductIdentification).Trim();
|
|
||||||
deviceInfo.Bus = simName == "ata" || simName == "ahcich" ? "ATAPI" : "SCSI";
|
|
||||||
deviceInfo.Supported = simName != "ata";
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case CamProto.ProtoNvme:
|
|
||||||
deviceInfo.Bus = "NVMe";
|
|
||||||
deviceInfo.Supported = false;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case CamProto.ProtoMmcsd:
|
|
||||||
deviceInfo.Model = "Unknown card";
|
|
||||||
deviceInfo.Bus = "MMC/SD";
|
|
||||||
deviceInfo.Supported = false;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
listDevices.Add(deviceInfo);
|
|
||||||
}
|
|
||||||
|
|
||||||
return listDevices.Count > 0 ? listDevices.OrderBy(t => t.Path).ToArray() : null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,711 +0,0 @@
|
|||||||
// /***************************************************************************
|
|
||||||
// Aaru Data Preservation Suite
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Filename : Structs.cs
|
|
||||||
// Author(s) : Natalia Portillo <claunia@claunia.com>
|
|
||||||
//
|
|
||||||
// Component : FreeBSD direct device access.
|
|
||||||
//
|
|
||||||
// --[ Description ] ----------------------------------------------------------
|
|
||||||
//
|
|
||||||
// Contains structures necessary for directly interfacing devices under
|
|
||||||
// FreeBSD.
|
|
||||||
//
|
|
||||||
// --[ License ] --------------------------------------------------------------
|
|
||||||
//
|
|
||||||
// This library is free software; you can redistribute it and/or modify
|
|
||||||
// it under the terms of the GNU Lesser General Public License as
|
|
||||||
// published by the Free Software Foundation; either version 2.1 of the
|
|
||||||
// License, or (at your option) any later version.
|
|
||||||
//
|
|
||||||
// This library is distributed in the hope that it will be useful, but
|
|
||||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
// Lesser General Public License for more details.
|
|
||||||
//
|
|
||||||
// You should have received a copy of the GNU Lesser General Public
|
|
||||||
// License along with this library; if not, see <http://www.gnu.org/licenses/>.
|
|
||||||
//
|
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// Copyright © 2011-2021 Natalia Portillo
|
|
||||||
// ****************************************************************************/
|
|
||||||
|
|
||||||
using System;
|
|
||||||
using System.Diagnostics.CodeAnalysis;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using lun_id_t = System.UInt32;
|
|
||||||
using path_id_t = System.UInt32;
|
|
||||||
using target_id_t = System.UInt32;
|
|
||||||
|
|
||||||
// ReSharper disable BuiltInTypeReferenceStyle
|
|
||||||
|
|
||||||
#pragma warning disable 649
|
|
||||||
#pragma warning disable 169
|
|
||||||
|
|
||||||
namespace Aaru.Devices.FreeBSD
|
|
||||||
{
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct AtaCmd
|
|
||||||
{
|
|
||||||
public CamAtaIoFlags flags;
|
|
||||||
public byte command;
|
|
||||||
public byte features;
|
|
||||||
public byte lba_low;
|
|
||||||
public byte lba_mid;
|
|
||||||
public byte lba_high;
|
|
||||||
public byte device;
|
|
||||||
public byte lba_low_exp;
|
|
||||||
public byte lba_mid_exp;
|
|
||||||
public byte lba_high_exp;
|
|
||||||
public byte features_exp;
|
|
||||||
public byte sector_count;
|
|
||||||
public byte sector_count_exp;
|
|
||||||
public byte control;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct AtaRes
|
|
||||||
{
|
|
||||||
public CamAtaIoFlags flags;
|
|
||||||
public byte status;
|
|
||||||
public byte error;
|
|
||||||
public byte lba_low;
|
|
||||||
public byte lba_mid;
|
|
||||||
public byte lba_high;
|
|
||||||
public byte device;
|
|
||||||
public byte lba_low_exp;
|
|
||||||
public byte lba_mid_exp;
|
|
||||||
public byte lba_high_exp;
|
|
||||||
public byte sector_count;
|
|
||||||
public byte sector_count_exp;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CamPinfo
|
|
||||||
{
|
|
||||||
public uint priority;
|
|
||||||
public uint generation;
|
|
||||||
public int index;
|
|
||||||
}
|
|
||||||
|
|
||||||
[SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct ListEntry
|
|
||||||
{
|
|
||||||
/// <summary>LIST_ENTRY(ccb_hdr)=le->*le_next</summary>
|
|
||||||
public IntPtr LeNext;
|
|
||||||
/// <summary>LIST_ENTRY(ccb_hdr)=le->**le_prev</summary>
|
|
||||||
public IntPtr LePrev;
|
|
||||||
}
|
|
||||||
|
|
||||||
[SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct SlistEntry
|
|
||||||
{
|
|
||||||
/// <summary>SLIST_ENTRY(ccb_hdr)=sle->*sle_next</summary>
|
|
||||||
public IntPtr SleNext;
|
|
||||||
}
|
|
||||||
|
|
||||||
[SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct TailqEntry
|
|
||||||
{
|
|
||||||
/// <summary>TAILQ_ENTRY(ccb_hdr)=tqe->*tqe_next</summary>
|
|
||||||
public IntPtr TqeNext;
|
|
||||||
/// <summary>TAILQ_ENTRY(ccb_hdr)=tqe->**tqe_prev</summary>
|
|
||||||
public IntPtr TqePrev;
|
|
||||||
}
|
|
||||||
|
|
||||||
[SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct StailqEntry
|
|
||||||
{
|
|
||||||
/// <summary>STAILQ_ENTRY(ccb_hdr)=stqe->*stqe_next</summary>
|
|
||||||
public IntPtr StqeNext;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Explicit), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CamqEntry
|
|
||||||
{
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public ListEntry le;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public SlistEntry sle;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public TailqEntry tqe;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public StailqEntry stqe;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct Timeval
|
|
||||||
{
|
|
||||||
public long tv_sec;
|
|
||||||
/// <summary>long</summary>
|
|
||||||
public IntPtr tv_usec;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbQosArea
|
|
||||||
{
|
|
||||||
public Timeval etime;
|
|
||||||
public UIntPtr sim_data;
|
|
||||||
public UIntPtr periph_data;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbHdr
|
|
||||||
{
|
|
||||||
public CamPinfo pinfo;
|
|
||||||
public CamqEntry xpt_links;
|
|
||||||
public CamqEntry sim_links;
|
|
||||||
public CamqEntry periph_links;
|
|
||||||
public uint retry_count;
|
|
||||||
public IntPtr cbfcnp;
|
|
||||||
public XptOpcode func_code;
|
|
||||||
public CamStatus status;
|
|
||||||
public IntPtr path;
|
|
||||||
public uint path_id;
|
|
||||||
public uint target_id;
|
|
||||||
public ulong target_lun;
|
|
||||||
public CcbFlags flags;
|
|
||||||
public uint xflags;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 2)]
|
|
||||||
public IntPtr[] periph_priv;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 2)]
|
|
||||||
public IntPtr[] sim_priv;
|
|
||||||
public CcbQosArea qos;
|
|
||||||
public uint timeout;
|
|
||||||
public Timeval softtimeout;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct ScsiSenseData
|
|
||||||
{
|
|
||||||
const int SSD_FULL_SIZE = 252;
|
|
||||||
public byte error_code;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = SSD_FULL_SIZE - 1)]
|
|
||||||
public byte[] sense_buf;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>SCSI I/O Request CCB used for the XPT_SCSI_IO and XPT_CONT_TARGET_IO function codes.</summary>
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbScsiio
|
|
||||||
{
|
|
||||||
public CcbHdr ccb_h;
|
|
||||||
/// <summary>Ptr for next CCB for action</summary>
|
|
||||||
public IntPtr next_ccb;
|
|
||||||
/// <summary>Ptr to mapping info</summary>
|
|
||||||
public IntPtr req_map;
|
|
||||||
/// <summary>Ptr to the data buf/SG list</summary>
|
|
||||||
public IntPtr data_ptr;
|
|
||||||
/// <summary>Data transfer length</summary>
|
|
||||||
public uint dxfer_len;
|
|
||||||
/// <summary>Autosense storage</summary>
|
|
||||||
public ScsiSenseData sense_data;
|
|
||||||
/// <summary>Number of bytes to autosense</summary>
|
|
||||||
public byte sense_len;
|
|
||||||
/// <summary>Number of bytes for the CDB</summary>
|
|
||||||
public byte cdb_len;
|
|
||||||
/// <summary>Number of SG list entries</summary>
|
|
||||||
public short sglist_cnt;
|
|
||||||
/// <summary>Returned SCSI status</summary>
|
|
||||||
public byte scsi_status;
|
|
||||||
/// <summary>Autosense resid length: 2's comp</summary>
|
|
||||||
public sbyte sense_resid;
|
|
||||||
/// <summary>Transfer residual length: 2's comp</summary>
|
|
||||||
public int resid;
|
|
||||||
/// <summary>Area for the CDB send, or pointer to the CDB bytes to send</summary>
|
|
||||||
const int IOCDBLEN = 16;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = IOCDBLEN)]
|
|
||||||
public byte[] cdb_bytes;
|
|
||||||
/// <summary>Pointer to the message buffer</summary>
|
|
||||||
public IntPtr msg_ptr;
|
|
||||||
/// <summary>Number of bytes for the Message</summary>
|
|
||||||
public short msg_len;
|
|
||||||
/// <summary>
|
|
||||||
/// What to do for tag queueing. The tag action should be either the define below (to send a non-tagged
|
|
||||||
/// transaction) or one of the defined scsi tag messages from scsi_message.h.
|
|
||||||
/// </summary>
|
|
||||||
public byte tag_action;
|
|
||||||
/// <summary>tag id from initator (target mode)</summary>
|
|
||||||
public uint tag_id;
|
|
||||||
/// <summary>initiator id of who selected</summary>
|
|
||||||
public uint init_id;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>SCSI I/O Request CCB used for the XPT_SCSI_IO and XPT_CONT_TARGET_IO function codes.</summary>
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbScsiio64
|
|
||||||
{
|
|
||||||
public CcbHdr ccb_h;
|
|
||||||
/// <summary>Ptr for next CCB for action</summary>
|
|
||||||
public IntPtr next_ccb;
|
|
||||||
/// <summary>Ptr to mapping info</summary>
|
|
||||||
public IntPtr req_map;
|
|
||||||
/// <summary>Ptr to the data buf/SG list</summary>
|
|
||||||
public IntPtr data_ptr;
|
|
||||||
/// <summary>Data transfer length</summary>
|
|
||||||
public uint dxfer_len;
|
|
||||||
/// <summary>Autosense storage</summary>
|
|
||||||
public ScsiSenseData sense_data;
|
|
||||||
/// <summary>Number of bytes to autosense</summary>
|
|
||||||
public byte sense_len;
|
|
||||||
/// <summary>Number of bytes for the CDB</summary>
|
|
||||||
public byte cdb_len;
|
|
||||||
/// <summary>Number of SG list entries</summary>
|
|
||||||
public short sglist_cnt;
|
|
||||||
/// <summary>Returned SCSI status</summary>
|
|
||||||
public byte scsi_status;
|
|
||||||
/// <summary>Autosense resid length: 2's comp</summary>
|
|
||||||
public sbyte sense_resid;
|
|
||||||
/// <summary>Transfer residual length: 2's comp</summary>
|
|
||||||
public int resid;
|
|
||||||
public uint alignment;
|
|
||||||
/// <summary>Area for the CDB send, or pointer to the CDB bytes to send</summary>
|
|
||||||
const int IOCDBLEN = 16;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = IOCDBLEN)]
|
|
||||||
public byte[] cdb_bytes;
|
|
||||||
/// <summary>Pointer to the message buffer</summary>
|
|
||||||
public IntPtr msg_ptr;
|
|
||||||
/// <summary>Number of bytes for the Message</summary>
|
|
||||||
public short msg_len;
|
|
||||||
/// <summary>
|
|
||||||
/// What to do for tag queueing. The tag action should be either the define below (to send a non-tagged
|
|
||||||
/// transaction) or one of the defined scsi tag messages from scsi_message.h.
|
|
||||||
/// </summary>
|
|
||||||
public byte tag_action;
|
|
||||||
/// <summary>tag id from initator (target mode)</summary>
|
|
||||||
public uint tag_id;
|
|
||||||
/// <summary>initiator id of who selected</summary>
|
|
||||||
public uint init_id;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>ATA I/O Request CCB used for the XPT_ATA_IO function code.</summary>
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbAtaio
|
|
||||||
{
|
|
||||||
public CcbHdr ccb_h;
|
|
||||||
/// <summary>Ptr for next CCB for action</summary>
|
|
||||||
public IntPtr next_ccb;
|
|
||||||
/// <summary>ATA command register set</summary>
|
|
||||||
public AtaCmd cmd;
|
|
||||||
/// <summary>ATA result register set</summary>
|
|
||||||
public AtaRes res;
|
|
||||||
/// <summary>Ptr to the data buf/SG list</summary>
|
|
||||||
public IntPtr data_ptr;
|
|
||||||
/// <summary>Data transfer length</summary>
|
|
||||||
public uint dxfer_len;
|
|
||||||
/// <summary>Transfer residual length: 2's comp</summary>
|
|
||||||
public int resid;
|
|
||||||
/// <summary>Flags for the rest of the buffer</summary>
|
|
||||||
public byte ata_flags;
|
|
||||||
public uint aux;
|
|
||||||
public uint unused;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct NvmeCommand
|
|
||||||
{
|
|
||||||
readonly ushort opc_fuse_rsvd1;
|
|
||||||
/// <summary>command identifier</summary>
|
|
||||||
public ushort cid;
|
|
||||||
/// <summary>namespace identifier</summary>
|
|
||||||
public uint nsid;
|
|
||||||
/// <summary>reserved</summary>
|
|
||||||
public uint rsvd2;
|
|
||||||
/// <summary>reserved</summary>
|
|
||||||
public uint rsvd3;
|
|
||||||
/// <summary>metadata pointer</summary>
|
|
||||||
public ulong mptr;
|
|
||||||
/// <summary>prp entry 1</summary>
|
|
||||||
public ulong prp1;
|
|
||||||
/// <summary>prp entry 2</summary>
|
|
||||||
public ulong prp2;
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw10;
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw11;
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw12;
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw13;
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw14;
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw15;
|
|
||||||
|
|
||||||
/// <summary>opcode</summary>
|
|
||||||
public byte Opc => (byte)((opc_fuse_rsvd1 & 0xFF00) >> 8);
|
|
||||||
/// <summary>fused operation</summary>
|
|
||||||
public byte Fuse => (byte)((opc_fuse_rsvd1 & 0xC0) >> 6);
|
|
||||||
/// <summary>reserved</summary>
|
|
||||||
public byte Rsvd1 => (byte)(opc_fuse_rsvd1 & 0x3F);
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct NvmeStatus
|
|
||||||
{
|
|
||||||
readonly ushort status;
|
|
||||||
|
|
||||||
/// <summary>phase tag</summary>
|
|
||||||
public byte P => (byte)((status & 0x8000) >> 15);
|
|
||||||
|
|
||||||
/// <summary>status code</summary>
|
|
||||||
public byte Sc => (byte)((status & 0x7F80) >> 7);
|
|
||||||
|
|
||||||
/// <summary>status code type</summary>
|
|
||||||
public byte Sct => (byte)((status & 0x70) >> 4);
|
|
||||||
|
|
||||||
/// <summary>reserved</summary>
|
|
||||||
public byte Rsvd2 => (byte)((status & 0xC) >> 15);
|
|
||||||
|
|
||||||
/// <summary>more</summary>
|
|
||||||
public byte M => (byte)((status & 0x2) >> 1);
|
|
||||||
|
|
||||||
/// <summary>do not retry</summary>
|
|
||||||
public byte Dnr => (byte)(status & 0x1);
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct NvmeCompletion
|
|
||||||
{
|
|
||||||
/// <summary>command-specific</summary>
|
|
||||||
public uint cdw0;
|
|
||||||
|
|
||||||
/// <summary>reserved</summary>
|
|
||||||
public uint rsvd1;
|
|
||||||
|
|
||||||
/// <summary>submission queue head pointer</summary>
|
|
||||||
public ushort sqhd;
|
|
||||||
|
|
||||||
/// <summary>submission queue identifier</summary>
|
|
||||||
public ushort sqid;
|
|
||||||
|
|
||||||
/// <summary>command identifier</summary>
|
|
||||||
public ushort cid;
|
|
||||||
|
|
||||||
public NvmeStatus status;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>NVMe I/O Request CCB used for the XPT_NVME_IO and XPT_NVME_ADMIN function codes.</summary>
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbNvmeio
|
|
||||||
{
|
|
||||||
public CcbHdr ccb_h;
|
|
||||||
/// <summary>Ptr for next CCB for action</summary>
|
|
||||||
public IntPtr next_ccb;
|
|
||||||
/// <summary>NVME command, per NVME standard</summary>
|
|
||||||
public NvmeCommand cmd;
|
|
||||||
/// <summary>NVME completion, per NVME standard</summary>
|
|
||||||
public NvmeCompletion cpl;
|
|
||||||
/// <summary>Ptr to the data buf/SG list</summary>
|
|
||||||
public IntPtr data_ptr;
|
|
||||||
/// <summary>Data transfer length</summary>
|
|
||||||
public uint dxfer_len;
|
|
||||||
/// <summary>Number of SG list entries</summary>
|
|
||||||
public ushort sglist_cnt;
|
|
||||||
/// <summary>padding for removed uint32_t</summary>
|
|
||||||
public ushort unused;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct PeriphMatchPattern
|
|
||||||
{
|
|
||||||
const int DEV_IDLEN = 16;
|
|
||||||
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = DEV_IDLEN)]
|
|
||||||
public byte[] periph_name;
|
|
||||||
public uint unit_number;
|
|
||||||
public path_id_t path_id;
|
|
||||||
public target_id_t target_id;
|
|
||||||
public lun_id_t target_lun;
|
|
||||||
public PeriphPatternFlags flags;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct DeviceIdMatchPattern
|
|
||||||
{
|
|
||||||
public byte id_len;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 256)]
|
|
||||||
public byte[] id;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct ScsiStaticInquiryPattern
|
|
||||||
{
|
|
||||||
const int SID_VENDOR_SIZE = 8;
|
|
||||||
const int SID_PRODUCT_SIZE = 16;
|
|
||||||
const int SID_REVISION_SIZE = 4;
|
|
||||||
public byte type;
|
|
||||||
public byte media_type;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = SID_VENDOR_SIZE + 1)]
|
|
||||||
public byte[] vendor;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = SID_PRODUCT_SIZE + 1)]
|
|
||||||
public byte[] product;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = SID_REVISION_SIZE + 1)]
|
|
||||||
public byte[] revision;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Explicit), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct DeviceMatchPatternData
|
|
||||||
{
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public ScsiStaticInquiryPattern inq_pat;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public DeviceIdMatchPattern devid_pat;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct DeviceMatchPattern
|
|
||||||
{
|
|
||||||
public uint path_id;
|
|
||||||
public uint target_id;
|
|
||||||
public uint target_lun;
|
|
||||||
public DevPatternFlags flags;
|
|
||||||
public DeviceMatchPatternData data;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct BusMatchPattern
|
|
||||||
{
|
|
||||||
const int DEV_IDLEN = 16;
|
|
||||||
|
|
||||||
public path_id_t path_id;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = DEV_IDLEN)]
|
|
||||||
public byte[] dev_name;
|
|
||||||
public uint unit_number;
|
|
||||||
public uint bus_id;
|
|
||||||
readonly BusPatternFlags flags;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Explicit), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct MatchPattern
|
|
||||||
{
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public PeriphMatchPattern periph_pattern;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public DeviceMatchPattern device_pattern;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public BusMatchPattern bus_pattern;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct DevMatchPattern
|
|
||||||
{
|
|
||||||
public DevMatchType type;
|
|
||||||
public MatchPattern pattern;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct PeriphMatchResult
|
|
||||||
{
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
|
|
||||||
public byte[] periph_name;
|
|
||||||
public uint unit_number;
|
|
||||||
public path_id_t path_id;
|
|
||||||
public target_id_t target_id;
|
|
||||||
public lun_id_t target_lun;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct MmcCid
|
|
||||||
{
|
|
||||||
public uint mid;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 8)]
|
|
||||||
public byte[] pnm;
|
|
||||||
public uint psn;
|
|
||||||
public ushort oid;
|
|
||||||
public ushort mdt_year;
|
|
||||||
public byte mdt_month;
|
|
||||||
public byte prv;
|
|
||||||
public byte fwrev;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct MmcParams
|
|
||||||
{
|
|
||||||
/// <summary>Card model</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 40)]
|
|
||||||
public byte[] model;
|
|
||||||
|
|
||||||
/// <summary>Card OCR</summary>
|
|
||||||
public uint card_ocr;
|
|
||||||
|
|
||||||
/// <summary>OCR of the IO portion of the card</summary>
|
|
||||||
public uint io_ocr;
|
|
||||||
|
|
||||||
/// <summary>Card CID -- raw</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 4)]
|
|
||||||
public uint[] card_cid;
|
|
||||||
|
|
||||||
/// <summary>Card CID -- parsed</summary>
|
|
||||||
public MmcCid cid;
|
|
||||||
|
|
||||||
/// <summary>Card CSD -- raw</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 4)]
|
|
||||||
public uint[] card_csd;
|
|
||||||
|
|
||||||
/// <summary>Card RCA</summary>
|
|
||||||
public ushort card_rca;
|
|
||||||
|
|
||||||
/// <summary>What kind of card is it</summary>
|
|
||||||
public MmcCardFeatures card_features;
|
|
||||||
|
|
||||||
public byte sdio_func_count;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct DeviceMatchResult
|
|
||||||
{
|
|
||||||
public path_id_t path_id;
|
|
||||||
public target_id_t target_id;
|
|
||||||
public lun_id_t target_lun;
|
|
||||||
public CamProto protocol;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 256)]
|
|
||||||
public byte[] inq_data;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 512)]
|
|
||||||
public byte[] ident_data;
|
|
||||||
public DevResultFlags flags;
|
|
||||||
public MmcParams mmc_ident_data;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct BusMatchResult
|
|
||||||
{
|
|
||||||
public path_id_t path_id;
|
|
||||||
const int DEV_IDLEN = 16;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = DEV_IDLEN)]
|
|
||||||
public byte[] dev_name;
|
|
||||||
public uint unit_number;
|
|
||||||
public uint bus_id;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Explicit), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct MatchResult
|
|
||||||
{
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public PeriphMatchResult periph_result;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public DeviceMatchResult device_result;
|
|
||||||
[FieldOffset(0)]
|
|
||||||
public BusMatchResult bus_result;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct DevMatchResult
|
|
||||||
{
|
|
||||||
public DevMatchType type;
|
|
||||||
public MatchResult result;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbDmCookie
|
|
||||||
{
|
|
||||||
public IntPtr bus;
|
|
||||||
public IntPtr target;
|
|
||||||
public IntPtr device;
|
|
||||||
public IntPtr periph;
|
|
||||||
public IntPtr pdrv;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbDevPosition
|
|
||||||
{
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 4)]
|
|
||||||
public CamGenerations[] generations;
|
|
||||||
readonly DevPosType position_type;
|
|
||||||
public CcbDmCookie cookie;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbDevMatch
|
|
||||||
{
|
|
||||||
public CcbHdr ccb_h;
|
|
||||||
readonly CcbDevMatchStatus status;
|
|
||||||
public uint num_patterns;
|
|
||||||
public uint pattern_buf_len;
|
|
||||||
|
|
||||||
/// <summary>dev_match_pattern*</summary>
|
|
||||||
public IntPtr patterns;
|
|
||||||
|
|
||||||
public uint num_matches;
|
|
||||||
public uint match_buf_len;
|
|
||||||
|
|
||||||
/// <summary>dev_match_result*</summary>
|
|
||||||
public IntPtr matches;
|
|
||||||
|
|
||||||
public CcbDevPosition pos;
|
|
||||||
}
|
|
||||||
|
|
||||||
[SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CamDevice
|
|
||||||
{
|
|
||||||
const int MAXPATHLEN = 1024;
|
|
||||||
const int DEV_IDLEN = 16;
|
|
||||||
const int SIM_IDLEN = 16;
|
|
||||||
/// <summary>
|
|
||||||
/// Pathname of the device given by the user. This may be null if the user states the device name and unit number
|
|
||||||
/// separately.
|
|
||||||
/// </summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = MAXPATHLEN)]
|
|
||||||
public byte[] DevicePath;
|
|
||||||
/// <summary>Device name given by the user.</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = DEV_IDLEN + 1)]
|
|
||||||
public byte[] GivenDevName;
|
|
||||||
/// <summary>Unit number given by the user.</summary>
|
|
||||||
public uint GivenUnitNumber;
|
|
||||||
/// <summary>Name of the device, e.g. 'pass'</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = DEV_IDLEN + 1)]
|
|
||||||
public byte[] DeviceName;
|
|
||||||
/// <summary>Unit number of the passthrough device associated with this particular device.</summary>
|
|
||||||
public uint DevUnitNum;
|
|
||||||
/// <summary>Controller name, e.g. 'ahc'</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = SIM_IDLEN + 1)]
|
|
||||||
public byte[] SimName;
|
|
||||||
/// <summary>Controller unit number</summary>
|
|
||||||
public uint SimUnitNumber;
|
|
||||||
/// <summary>Controller bus number</summary>
|
|
||||||
public uint BusId;
|
|
||||||
/// <summary>Logical Unit Number</summary>
|
|
||||||
public lun_id_t TargetLun;
|
|
||||||
/// <summary>Target ID</summary>
|
|
||||||
public target_id_t TargetId;
|
|
||||||
/// <summary>System SCSI bus number</summary>
|
|
||||||
public path_id_t PathId;
|
|
||||||
/// <summary>type of peripheral device</summary>
|
|
||||||
public ushort PdType;
|
|
||||||
/// <summary>SCSI Inquiry data</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 256)]
|
|
||||||
public byte[] InqData;
|
|
||||||
/// <summary>device serial number</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 252)]
|
|
||||||
public byte[] SerialNum;
|
|
||||||
/// <summary>length of the serial number</summary>
|
|
||||||
public byte SerialNumLen;
|
|
||||||
/// <summary>Negotiated sync period</summary>
|
|
||||||
public byte SyncPeriod;
|
|
||||||
/// <summary>Negotiated sync offset</summary>
|
|
||||||
public byte SyncOffset;
|
|
||||||
/// <summary>Negotiated bus width</summary>
|
|
||||||
public byte BusWidth;
|
|
||||||
/// <summary>file descriptor for device</summary>
|
|
||||||
public int Fd;
|
|
||||||
}
|
|
||||||
|
|
||||||
[StructLayout(LayoutKind.Sequential), SuppressMessage("ReSharper", "MemberCanBePrivate.Global"), Obsolete]
|
|
||||||
internal struct CcbGetdev
|
|
||||||
{
|
|
||||||
public CcbHdr ccb_h;
|
|
||||||
public CamProto protocol;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 256)]
|
|
||||||
public byte[] inq_data;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 512)]
|
|
||||||
public byte[] ident_data;
|
|
||||||
/// <summary>device serial number</summary>
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 252)]
|
|
||||||
public byte[] serial_num;
|
|
||||||
public byte inq_flags;
|
|
||||||
/// <summary>length of the serial number</summary>
|
|
||||||
public byte serial_num_len;
|
|
||||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 2)]
|
|
||||||
public IntPtr[] padding;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -153,15 +153,10 @@ Logo and art:
|
|||||||
process.StartInfo.FileName = "cmd";
|
process.StartInfo.FileName = "cmd";
|
||||||
process.StartInfo.Arguments = $"/c start {process.StartInfo.Arguments.Replace("&", "^&")}";
|
process.StartInfo.Arguments = $"/c start {process.StartInfo.Arguments.Replace("&", "^&")}";
|
||||||
}
|
}
|
||||||
else if(RuntimeInformation.IsOSPlatform(OSPlatform.FreeBSD) ||
|
else if(RuntimeInformation.IsOSPlatform(OSPlatform.Linux))
|
||||||
RuntimeInformation.IsOSPlatform(OSPlatform.Linux))
|
|
||||||
{
|
|
||||||
process.StartInfo.FileName = "xdg-open";
|
process.StartInfo.FileName = "xdg-open";
|
||||||
}
|
|
||||||
else if(RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
|
else if(RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
|
||||||
{
|
|
||||||
process.StartInfo.FileName = "open";
|
process.StartInfo.FileName = "open";
|
||||||
}
|
|
||||||
else
|
else
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
|||||||
@@ -28,8 +28,8 @@ Stable releases in [Github](https://github.com/aaru-dps/Aaru/releases).
|
|||||||
|
|
||||||
System requirements
|
System requirements
|
||||||
===================
|
===================
|
||||||
Aaru is created using .NET 6 and can be compiled with all the major IDEs. To run it you require to use one of the
|
Aaru is created using .NET 6 and can be compiled with all the major IDEs. To run it you require to use one of the stable
|
||||||
stable releases, or build it yourself.
|
releases, or build it yourself.
|
||||||
|
|
||||||
Usage
|
Usage
|
||||||
=====
|
=====
|
||||||
@@ -59,8 +59,7 @@ Features
|
|||||||
* Can create standard open XML metadata from existing images.
|
* Can create standard open XML metadata from existing images.
|
||||||
* Can measure readability and speed of media (same that can be dumped, MHDD style)
|
* Can measure readability and speed of media (same that can be dumped, MHDD style)
|
||||||
* Has an online database with drive capabilities, and can report the capabilities of any drive.
|
* Has an online database with drive capabilities, and can report the capabilities of any drive.
|
||||||
* Works on any operating system and architecture where .NET Core is supported (drive access requires Windows, Linux or
|
* Works on any operating system and architecture where .NET Core is supported (drive access requires Windows or Linux).
|
||||||
FreeBSD).
|
|
||||||
* Has a graphical interface (work in progress)
|
* Has a graphical interface (work in progress)
|
||||||
|
|
||||||
Supported disk image formats (read-only)
|
Supported disk image formats (read-only)
|
||||||
|
|||||||
Reference in New Issue
Block a user