Sosilo Posted February 12, 2008 Share Posted February 12, 2008 (edited) Well - my first post here - so Hello @ all at first ... Now my problem: I want to unmount my Portable USB-Drive or USB-Stick (means FIXED and REMOVEABLE Partitions) automatically. Up until now I have used MountVol.exe + AutoIT for that purpose (if needed i can post the code) - but my problem is that it won't work unless I have Administrator-Rights on the Local Machine (which isn't the case on most of the systems). Is there ANY alternative way (and i mean ANY - like an existing wrapper, function hook with autoit or c ... even an precompiled console-exe would be ok for my purposes) to unmount an USB-Drive or USB-Stick WITHOUT Admin-Rights (running under WIN32 XP) ??? I haven't found anything via Google or in this Forum so far and hope someone can give me a little advice/point me in the right direction here. Argh, I just hate it when some kind of so-called "Network-Admin" spys on my sensitive data ... €: As you probably allready know - there is the "Remove Hardware Safely"-Agent running on most of the systems (can that be deactivated/won't it work for Non-Admins?). How are they dismounting the device? Would it be possible to use the same API Functions they are using to get what I want (autodismount even when beeing an Restricted-User)? If so - what functions are they using at all? Does anyone know that? :-/ Edited February 12, 2008 by Sosilo Link to comment Share on other sites More sharing options...
SpookMeister Posted February 12, 2008 Share Posted February 12, 2008 Welcome. I'm not sure I follow what you are trying to do... Some kind of auto start password checker and if the PW fails then unmount the drive? [u]Helpful tips:[/u]If you want better answers to your questions, take the time to reproduce your issue in a small "stand alone" example script whenever possible. Also, make sure you tell us 1) what you tried, 2) what you expected to happen, and 3) what happened instead.[u]Useful links:[/u]BrettF's update to LxP's "How to AutoIt" pdfValuater's Autoit 1-2-3 Download page for the latest versions of Autoit and SciTE[quote]<glyph> For example - if you came in here asking "how do I use a jackhammer" we might ask "why do you need to use a jackhammer"<glyph> If the answer to the latter question is "to knock my grandmother's head off to let out the evil spirits that gave her cancer", then maybe the problem is actually unrelated to jackhammers[/quote] Link to comment Share on other sites More sharing options...
FreeFry Posted February 12, 2008 Share Posted February 12, 2008 (edited) I found this on the net:http://support.microsoft.com/kb/165721The examples is written in C though, so you would have to figure you the DllCall equivalent.Otherwise, this might work: http://www.a1vbcode.com/app.asp?ID=1814I have tested neither of them though.Edit:Found those by this simple googgle btw: http://www.google.com/search?q=eject+flash...lly&spell=1 Edited February 12, 2008 by FreeFry Link to comment Share on other sites More sharing options...
Sosilo Posted February 12, 2008 Author Share Posted February 12, 2008 (edited) Hey SpookMeister, I just need a way to actually unmount an USB-Drive/Stick while beeing logged in as an Restricted-User on a WIN XP (32-Bit) System... I don't have any problems on the other hand - all I need is a working method to achive that, nothing else. €: Thanks FreeFry I'll have a look at that (haven't thought about using the term "programmatically" O.o) Edited February 12, 2008 by Sosilo Link to comment Share on other sites More sharing options...
FreeFry Posted February 12, 2008 Share Posted February 12, 2008 Hehe, it just came to me that some people have used that word on some sitatuations, and I tried it. ^___^ Link to comment Share on other sites More sharing options...
Sosilo Posted February 13, 2008 Author Share Posted February 13, 2008 (edited) Well ... ok i'm stuck atm ... I first tryed it by manually unmounting each logical partition (getting the volumeIDs with WMI) - well and somehow it worked ... BUT as the Win32_LogicalPartition Class hasn't implemented any method or element to check/get the InterfaceType (to check if it's an USB-/ FireWire-Device) I decited to switch over to the Win32_DiskDrive Class (http://msdn2.microsoft.com/en-us/library/aa394132(VS.85).aspx). Now somehow it returns correct values for the Handle and the various methods (lock, unmount etc.) ... well at least it tells me that - in reality it does NOTHING Here is what i got so far - maybe i'm just overworked and overlooking something really stupid ... Help please! expandcollapse popupGlobal $strComputer = "." Global $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\cimv2") Func getPortableDrives() $driveList = $objWMIService.ExecQuery("Select * from Win32_DiskDrive"); ; http://msdn2.microsoft.com/en-us/library/aa394132(VS.85).aspx ; Model, Name, InterfaceType, MediaType For $drive in $driveList If $drive.MediaType = "Removable" Or $drive.InterfaceType = "USB" Or $drive.InterfaceType = "1394" Then ConsoleWrite($drive.DeviceID & @CRLF) ConsoleWrite($drive.MediaType & " " & $drive.Name & " " & $drive.InterfaceType & @CRLF) Local $hVol = OpenVolume($drive.Name) LockVolume($hVol) DismountVolume($hVol) CloseVolume($hVol) AutoEjectVolume($hVol) EndIf Next ;Local $test[1] = ["0"] ;return $test EndFunc Func OpenVolume($szVolumeName) Local $dwAccessFlags, $hVolume Local $uDriveType = DriveGetType($szVolumeName) ;$szVolumeName = "\\.\" & "G" & ":" ConsoleWrite($szVolumeName & " "& $uDriveType & @CRLF) Select Case $uDriveType == "Removable" $dwAccessFlags = BitOR($GENERIC_READ,$GENERIC_WRITE) Case $uDriveType == "Fixed" $dwAccessFlags = $GENERIC_ALL Case $uDriveType == "CDROM" $dwAccessFlags = $GENERIC_READ Case Else MsgBox(4096,"Error","Cannot eject. Drive type is incorrect.") Return $INVALID_HANDLE_VALUE EndSelect $hVolume = DllCall( "kernel32.dll", "hwnd", "CreateFile", "str", $szVolumeName, _ "long", $dwAccessFlags, "long", BitOR($FILE_SHARE_READ, $FILE_SHARE_WRITE), _ "ptr", 0, "long", $OPEN_EXISTING, "long", 0, "long", 0 ) If $hVolume[0] = $INVALID_HANDLE_VALUE Then ReportError("CreateFile") EndIf ConsoleWrite("Volume Handle: "& $hVolume[0] & @CRLF) Return $hVolume[0] EndFunc Func ReportError($szMsg) $ret = DLLCall("kernel32.dll","int","GetLastError") MsgBox(4096,"Error","Error " & $ret[0] & ": " & $szMsg) EndFunc Func LockVolume(ByRef $hVolume) Local $dwBytesReturned, $nTryCount, $ret Local $dwSleepAmount = $LOCK_TIMEOUT / $LOCK_RETRIES ; Do this in a loop until a timeout period has expired For $nTryCount = 0 To $LOCK_RETRIES $ret = DLLCall("kernel32.dll","int","DeviceIoControl","hwnd",$hVolume, _ "int",$FSCTL_LOCK_VOLUME,"ptr",0,"int",0,"ptr",0,"int",0, _ "int*",$dwBytesReturned,"ptr",0) If $ret[0] Then Return 1 Sleep($dwSleepAmount) Next return 0 EndFunc Func DismountVolume(ByRef $hVolume) Local $dwBytesReturned Local $ret = DLLCall("kernel32.dll","int","DeviceIoControl","hwnd",$hVolume, _ "int",$FSCTL_DISMOUNT_VOLUME,"ptr",0,"int",0,"ptr",0,"int",0, _ "int*",$dwBytesReturned,"ptr",0) ConsoleWrite("DismountVolume: "&$ret[0] & @CRLF) Return $ret[0] EndFunc Func CloseVolume(ByRef $hVolume) Local $ret = DLLCall("kernel32.dll","int","CloseHandle","hwnd",$hVolume) ConsoleWrite("CloseVolume: "&$ret[0]& @CRLF) Return $ret[0] EndFunc Func AutoEjectVolume(ByRef $hVolume) Local $dwBytesReturned Local $ret = DLLCall("kernel32.dll","int","DeviceIoControl","hwnd",$hVolume, _ "int",$IOCTL_STORAGE_EJECT_MEDIA,"ptr",0,"int",0,"ptr",0,"int",0, _ "int*",$dwBytesReturned,"ptr",0) ConsoleWrite("AutoEjectVolume: "&$ret[0]) Return $ret[0] EndFunc This code produces the following messages - but NO results Fixed hard disk media \\.\PHYSICALDRIVE1 USB \\.\PHYSICALDRIVE1 Fixed Volume Handle: 0x00000634 DismountVolume: 1 CloseVolume: 1 AutoEjectVolume: 0 Edited February 13, 2008 by Sosilo Link to comment Share on other sites More sharing options...
FreeFry Posted February 13, 2008 Share Posted February 13, 2008 That code doesn't work when I try to run it, all the constants are not defined.. Link to comment Share on other sites More sharing options...
Xenobiologist Posted February 13, 2008 Share Posted February 13, 2008 Try this:If Not _ejectUSB() = 1 Then MsgBox(16, 'Error', 'Es ist ein Fehler aufgetreten!', 5) Func _ejectUSB($drive = '') Local $path = @TempDir & '\12345USB54321.exe' If $drive = '' Or $drive = Default Then $drive = StringLeft(@ScriptDir, 2) If $cmdLine[0] = 1 And ($cmdLine[1] = '-?' Or $cmdLine[1] = '/?') Then MsgBox(64, 'Information', 'Parameter : (Drive) e.g. : E:', 5) Exit (0) EndIf If $cmdLine[0] = 1 Then $drive = $cmdLine[1] FileInstall('EjectMedia.exe', $path, 1) If Not FileExists($drive) Then Return -1 If Not FileExists($path) Then Return -2 Run($path & ' ' & $drive & ' -l -f -s -w:1000', @TempDir, @SW_HIDE) Return 1 EndFunc ;==>_ejectUSBhttp://www.uwe-sieber.de/usbstick_e.htmlMega Scripts & functions Organize Includes Let Scite organize the include files Yahtzee The game "Yahtzee" (Kniffel, DiceLion) LoginWrapper Secure scripts by adding a query (authentication) _RunOnlyOnThis UDF Make sure that a script can only be executed on ... (Windows / HD / ...) Internet-Café Server/Client Application Open CD, Start Browser, Lock remote client, etc. MultipleFuncsWithOneHotkey Start different funcs by hitting one hotkey different times Link to comment Share on other sites More sharing options...
Sosilo Posted February 13, 2008 Author Share Posted February 13, 2008 Thanks Mega. I found some (usefull) Example Code for unmounting on this site which is well explaint. I'll have a look at it now. About the Constants - yeh I forgot to post the includes and a few definitions (was late night yesterday ...). I'll fix that and post the updated code later on. Greetings Sosilo Link to comment Share on other sites More sharing options...
FreeFry Posted February 13, 2008 Share Posted February 13, 2008 ok I was wondering where you got those constants, as I couldn't find all of them. Link to comment Share on other sites More sharing options...
Sosilo Posted February 13, 2008 Author Share Posted February 13, 2008 #include <Constants.au3> Global CONST $LOCK_TIMEOUT = 10000 Global CONST $LOCK_RETRIES = 20 Global CONST $INVALID_HANDLE_VALUE = 0xFFFFFFFF Global CONST $FSCTL_LOCK_VOLUME = 0x00090018 Global CONST $FSCTL_DISMOUNT_VOLUME = 0x00090020 Global CONST $IOCTL_STORAGE_MEDIA_REMOVAL = 0x002D0804 Global CONST $IOCTL_STORAGE_EJECT_MEDIA = 0x002D0808 here they are ... Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now