Answer the question
In order to leave comments, you need to log in
C# pass parameter to Win32Api function?
You need to call the Win32Api DeviceIoControl function with the IOCTL_DISK_SET_DISK_ATTRIBUTES parameter and pass the SET_DISK_ATTRIBUTES structure, such a command should set the disk as read-only.
[DllImport("kernel32.dll", ExactSpelling = true, SetLastError = true, CharSet = CharSet.Auto)]
private static extern bool DeviceIoControl(
IntPtr hDevice,
uint dwIoControlCode,
IntPtr lpInBuffer,
uint nInBufferSize,
IntPtr lpOutBuffer,
uint nOutBufferSize,
out uint lpBytesReturned,
IntPtr lpOverlapped
);
const ulong DISK_ATTRIBUTE_READ_ONLY = 0x0000000000000002;
struct SET_DISK_ATTRIBUTES
{
public uint Version;
public bool Persist;
public byte[] Reserved1;
public ulong Attributes;
public ulong AttributesMask;
public uint[] Reserved2;
};
private bool SetReadonly(IntPtr handle)
{
var sda = new SET_DISK_ATTRIBUTES();
sda.Reserved1 = new byte[3];
sda.Reserved2 = new uint[4];
sda.AttributesMask = DISK_ATTRIBUTE_READ_ONLY;
sda.Attributes = DISK_ATTRIBUTE_READ_ONLY;
int nPtrQryBytes = Marshal.SizeOf(sda);
IntPtr ptrQuery = Marshal.AllocHGlobal(nPtrQryBytes);
uint byteReturned;
var res = DeviceIoControl(handle, IOCTL_DISK_SET_DISK_ATTRIBUTES, ptrQuery, (uint)nPtrQryBytes, IntPtr.Zero, 0, out byteReturned, IntPtr.Zero);
var ex = new Win32Exception(Marshal.GetLastWin32Error());
MessageBox.Show(ex.Message);
return res;
}
Answer the question
In order to leave comments, you need to log in
The issue was resolved here https://stackoverflow.com/questions/53898839/c-sha...
First, these arrays should be placed in the structure itself, not managed references to them. It's strange that the marshaling did not spit out the exception. It should be something like this:
struct SET_DISK_ATTRIBUTES
{
public uint Version;
public bool Persist;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 3)]
public byte[] Reserved1;
public ulong Attributes;
public ulong AttributesMask;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 4)]
public uint[] Reserved2;
};
Open Total Commander or a similar file manager,
go to c:\Program Files\dotnet\
Do a search for all dll files and search by content: DeviceIoControl
Next, use the .Net Reflector application (there is a 15-day trial ;) )
Load the found dlls (File /Open Assembly..)
In the search bar DeviceIoControl and "Search member" search type.
He finds everything.
In the tree, select the found method and in the Analyze context menu
. In the Analyze window that opens, select "Used by" and then "Go to member".
It remains only to convert the found examples to suit your own needs.
Didn't find what you were looking for?
Ask your questionAsk a Question
731 491 924 answers to any question