Ejecter CD-Rom et Clé USB [Résolu]

Programmation d'applications complexes
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Ejecter CD-Rom et Clé USB [Résolu]

Message par Le Soldat Inconnu »

Sujet résolu

Donc voici le code qui permet, a partir de la lettre du lecteur :
- Ejecter un lecteur CD (ou le fermer)
- Retirer un périphérique amovible.

Code testé avec clé USB U3, Clé USB classique

En attente de test pour disque dur USB, Graveur USB, et d'un test sous Vista

Code : Tout sélectionner

Procedure EjectCDRomDrive(DriveLetter.s, Test.l = 0) ; To eject CD, or close CD
  Protected hDevice, Retour = 0, Temps
  DriveLetter = Left(DriveLetter, 1)
  If GetDriveType_(DriveLetter + ":\") = 5 ; Lecteur cd-rom
    
    #IOCTL_STORAGE_EJECT_MEDIA = $D4808
    #IOCTL_STORAGE_LOAD_MEDIA = $2D480C
    
    hDevice = CreateFile_("\\.\" + DriveLetter + ":", #GENERIC_READ, #FILE_SHARE_READ, 0, #OPEN_EXISTING, 0, 0)
    
    If hDevice <> #INVALID_HANDLE_VALUE
      ; Ejecter cd rom
      If Test = 0
        Temps = ElapsedMilliseconds()
        DeviceIoControl_(hDevice, #IOCTL_STORAGE_EJECT_MEDIA, 0, 0, 0, 0, @Retour, 0)
        If ElapsedMilliseconds() - Temps < 50
          ; rentrer cd rom
          DeviceIoControl_(hDevice, #IOCTL_STORAGE_LOAD_MEDIA, 0, 0, 0, 0, @Retour, 0)
        EndIf
      EndIf
      
      CloseHandle_(hDevice)
      Retour = 1
    EndIf
   
  EndIf  
  
  ProcedureReturn Retour
EndProcedure
Procedure IsCDRomDrive(DriveLetter.s) ; To check if drive is CD
  ProcedureReturn EjectCDRomDrive(DriveLetter, 1)
EndProcedure


Procedure RemoveDrive(DriveLetter.s, Test.l = 0) ; To disconnect USB drive
  
  #SPDRP_SERVICE = $4
  
  DataSection ; GUID
    GUID_DEVINTERFACE_FLOPPY: 
    Data.l $53F56311 
    Data.w $B6BF, $11D0 
    Data.b $94, $F2, $00, $A0, $C9, $1E, $FB, $8B 
    GUID_DEVINTERFACE_DISK: 
    Data.l $53F56307 
    Data.w $B6BF, $11D0 
    Data.b $94, $F2, $00, $A0, $C9, $1E, $FB, $8B 
    GUID_DEVINTERFACE_CDROM: 
    Data.l $53F56308 
    Data.w $B6BF, $11D0 
    Data.b $94, $F2, $00, $A0, $C9, $1E, $FB, $8B 
    GUID_DEVINTERFACE_VOLUME:
    Data.l  $53F5630D 
    Data.w $B6BF, $11D0 
    Data.b $94, $F2, $00, $A0, $C9, $1E, $FB, $8B
  EndDataSection
  
  Structure PSP_DEVICE_INTERFACE_DETAIL_DATA 
    cbSize.l 
    DevicePath.s{255} 
  EndStructure 
  
  Structure SP_DEVINFO_DATA 
    cbSize.l 
    ClassGuid.GUID 
    DevInst.l 
    reserved.l 
  EndStructure 
  
  Protected Index, Retour, *VolumeName, *DeviceInstanceId, *DeviceService.l
  Protected DevicePath_Length.l, DeviceLetter.s, DeviceVolume.s, DeviceInstance.l, DeviceID.s
  Protected hDevice.l, *Guid.l, pspdidd.PSP_DEVICE_INTERFACE_DETAIL_DATA, spdid.SP_DEVICE_INTERFACE_DATA, spdd.SP_DEVINFO_DATA 
  Protected Removable_hDevice, Removable_Index, Removable_spdd.SP_DEVINFO_DATA, Removable_DeviceCapabilities.l, Removable_Service.s, RemovableDevice.l, Removable_DeviceID.s
  Protected DriveVolume.s
  
  ; On ouvre les librairies et on charge les fonctions utiles
  dll_Setupapi = OpenLibrary(#PB_Any, "setupapi.dll")
  If dll_Setupapi
    dll_Kernel32 = OpenLibrary(#PB_Any, "Kernel32.dll")
    If dll_Kernel32
      *CM_Locate_DevNode = GetFunction(dll_Setupapi, "CM_Locate_DevNodeA")
      *CM_Request_Device_Eject = GetFunction(dll_Setupapi, "CM_Request_Device_Eject_ExA")
      *CM_Get_Parent = GetFunction(dll_Setupapi, "CM_Get_Parent")
      *CM_Get_Device_ID = GetFunction(dll_Setupapi, "CM_Get_Device_IDA")
      *GetVolumeNameForVolumeMountPoint = GetFunction(dll_Kernel32, "GetVolumeNameForVolumeMountPointA")
      
      ; On récupère le nom de volume du lecteur
      *VolumeName = AllocateMemory(255)
      CallFunctionFast(*GetVolumeNameForVolumeMountPoint, DriveLetter + ":\", *VolumeName, 255)
      DriveVolume=  PeekS(*VolumeName)
      FreeMemory(*VolumeName)

      ; On recherche le volume qui correspond a chaque lettre de lecteur
      *Guid = ?GUID_DEVINTERFACE_VOLUME ; On recherche tous les volumes
      hDevice = SetupDiGetClassDevs_(*Guid, 0, 0, #DIGCF_PRESENT|#DIGCF_DEVICEINTERFACE) 
      
      If hDevice <> #INVALID_HANDLE_VALUE 
        
        ; Paramétrage
        spdid\cbSize = SizeOf(SP_DEVICE_INTERFACE_DATA) 
        
        ; On liste les interfaces
        Index= 0 
        While SetupDiEnumDeviceInterfaces_(hDevice, 0, *Guid, Index, @spdid) 
          
          ; Taille du buffer nécessaire pour lire l'information
          SetupDiGetDeviceInterfaceDetail_(hDevice, @spdid, 0, 0, @DevicePath_Length, 0)
          If DevicePath_Length <> 0 And DevicePath_Length < 255 ; On teste pour savoir si le texte n'est pas trop long
            
            pspdidd\cbSize = 5    ; Unicode=6, ASCII=5 
            spdd\cbSize = SizeOf(SP_DEVINFO_DATA) 
            
            If SetupDiGetDeviceInterfaceDetail_(hDevice, @spdid, @pspdidd, DevicePath_Length, 0, @spdd) 
              
              *VolumeName = AllocateMemory(255)
              CallFunctionFast(*GetVolumeNameForVolumeMountPoint, pspdidd\DevicePath + "\", *VolumeName, 255)
              DeviceVolume =  PeekS(*VolumeName)
              FreeMemory(*VolumeName)
              
              If DriveVolume = DeviceVolume
                ; On a trouvé le volume correspondant à la lettre de lecteur
                
                DeviceInstance = spdd\DevInst
                Repeat ; On parcourt la liste des parents à la recherche d'un périphérique amovible
                  If CallFunctionFast(*CM_Get_Parent, @DeviceParent, DeviceInstance, 0) = 0
                    DeviceInstance = DeviceParent
                    *DeviceInstanceId = AllocateMemory(255)
                    CallFunctionFast(*CM_Get_Device_ID, DeviceInstance, *DeviceInstanceId, 255, 0) ; On récupère l'ID du device
                    DeviceID = PeekS(*DeviceInstanceId)
                    FreeMemory(*DeviceInstanceId)
                    
                    ; On recherche si le device est amovible
                    RemovableDevice = 0
                    Removable_hDevice = SetupDiGetClassDevs_(0, 0, 0, #DIGCF_PRESENT | #DIGCF_ALLCLASSES)
                    If Removable_hDevice <> #INVALID_HANDLE_VALUE
                      Removable_spdd\cbSize = SizeOf(SP_DEVINFO_DATA)
                      Removable_Index = 0
                      While SetupDiEnumDeviceInfo_(Removable_hDevice, Removable_Index, @Removable_spdd)
                        *DeviceInstanceId = AllocateMemory(255)
                        SetupDiGetDeviceInstanceId_(Removable_hDevice, Removable_spdd, *DeviceInstanceId, 255, 0)
                        Removable_DeviceID = PeekS(*DeviceInstanceId)
                        FreeMemory(*DeviceInstanceId)
                        If Removable_DeviceID = DeviceID
                          *DeviceService = AllocateMemory(255)
                          SetupDiGetDeviceRegistryProperty_(Removable_hDevice, Removable_spdd, #SPDRP_SERVICE, 0, *DeviceService, 255, 0)
                          Removable_Service = LCase(PeekS(*DeviceService))
                          FreeMemory(*DeviceService)
                          If Removable_Service = "usbstor"
                            RemovableDevice = 1
                            Break
                          EndIf
                        EndIf
                        Removable_Index + 1
                      Wend
                      SetupDiDestroyDeviceInfoList_(Removable_hDevice)
                    EndIf
                    
                    If RemovableDevice ; Si le lecteur est amovible
                      Retour = 1 ; On retourne une réponse positive
                      If Test = 0 ; Si on veut retirer le lecteur
                        
                        If CallFunctionFast(*CM_Locate_DevNode, @DeviceInstance.l, DeviceID, 0) = 0 ; On va sur le noeud du device
                          CallFunctionFast(*CM_Request_Device_Eject, DeviceInstance, 0, 0, 0, 0, 0) ; On éjecte le device
                        EndIf
                        
                      EndIf
                      Break 2 ; On s'arrête sur le premier périphérique amovible
                    EndIf
                    
                  EndIf
                Until DeviceInstance <> DeviceParent ; on a listé tous les parents
                
              EndIf
            EndIf
          EndIf
          
          ; On passe à l'élément suivant
          Index + 1
        Wend
        
        SetupDiDestroyDeviceInfoList_(hDevice) ; On ferme
      EndIf
      CloseLibrary(dll_Kernel32)
    EndIf
    CloseLibrary(dll_Setupapi)
  EndIf
  
  ProcedureReturn Retour
EndProcedure
Procedure IsRemovableDrive(DriveLetter.s) ; To check if drive is USB drive
  ProcedureReturn RemoveDrive(DriveLetter, 1)
EndProcedure




;- Test
Lecteur.s = "i"
If IsCDRomDrive(Lecteur)
  EjectCDRomDrive(Lecteur)
EndIf
If IsRemovableDrive(Lecteur)
  RemoveDrive(Lecteur)
EndIf


Ancien sujet avant résolution
--------------------------------------------------------------------------------

Bon, voilà une belle galère

Pour éjecter le cd-rom, c'est ok, j'ai trouvé quelque chose de fonctionnel

A partir du code
http://www.purebasic.fr/english/viewtop ... highlight=

Par contre, pour les clés USB, c'est une autre galère
j'ai trouvé un code qui éjecte les clés usb mais ... (si si, un petit mais) ... ca éjecte toutes les clés usb alors que je cherche a éjecter un lecteur particulier à partir de sa lettre
http://www.purebasic.fr/english/viewtop ... highlight=

Donc je cherche, si vous avez une idée, merci
Dernière modification par Le Soldat Inconnu le mar. 03/févr./2009 11:01, modifié 2 fois.
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
KarLKoX
Messages : 1191
Inscription : jeu. 26/févr./2004 15:36
Localisation : France
Contact :

Message par KarLKoX »

En lisant le code de Michael Vogel, je vois cette procédure :

Code : Tout sélectionner

Procedure EjectVolume(DriveLetter.s) 
Avec ce commentaire :

Code : Tout sélectionner

 ; [ 1 ] Volume "\\.\X:" öffnen...
   Handle=OpenVolume(DriveLetter) 
Ca ne fonctionne pas ? (j'ai prêté ma cle usb, peut pas tester)
"Qui baise trop bouffe un poil." P. Desproges
Avatar de l’utilisateur
GeBonet
Messages : 453
Inscription : ven. 29/févr./2008 16:17
Localisation : Belgique

Message par GeBonet »

Bonsoir,
J'ai un "HP Pavilion Media Center TV m7380.be"... Et en origine un gciel pré installé qui fait exactement ça... Ce soir c'est tard... Mais demain je vais essayé de trouver à partir de quoi... Et p'tete ben oui... Alors essayer de désassembler pour trouver...hum, la "clef" :? De l'API birthday :lol:
A+
Avatar de l’utilisateur
GeBonet
Messages : 453
Inscription : ven. 29/févr./2008 16:17
Localisation : Belgique

Message par GeBonet »

Un détail que je viens de me rappeler... Mes clef USB sont aussi affecté par l'OS comme si c'était des lecteurs... Je ne sais pas si pour toutes c'est comme ça ? En principe, ça devrait... Aussi demain j'essaye aussi de fouiller sur base de "vos" gciel...
Bonne nuit
Ge
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Message par Le Soldat Inconnu »

j'ai essayer ça :
marche pas chez moi

Code : Tout sélectionner

hDevice = CreateFile_("\\.\"+DriveLetter+":",#GENERIC_READ,#FILE_SHARE_READ|#FILE_SHARE_WRITE,0,#OPEN_EXISTING,0,0) 
    
    FlushFileBuffers_(hDevice)
    
    If DeviceIoControl_(hDevice, #FSCTL_LOCK_VOLUME, 0, 0, 0, 0, @Retour, 0)
      If DeviceIoControl_(hDevice, #FSCTL_DISMOUNT_VOLUME, 0, 0, 0, 0, @Retour, 0)
        DeviceIoControl_(hDevice, #IOCTL_STORAGE_EJECT_MEDIA, 0, 0, 0, 0, @Retour, 0)
      EndIf
    EndIf
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Message par Le Soldat Inconnu »

donc les clés USB, voilà ou j'en suis

j'arrive à lister les Device du PC

J'ai le nom, la description et si je peux l'éjecter.
J'ai toujours pas la lettre du letteur associé

Code : Tout sélectionner

Procedure RemoveDevice(DriveLetter.s)
  #DIGCF_PRESENT = $2
  #DIGCF_ALLCLASSES = $4
  
  ; Constantes pour SetupDiGetDeviceRegistryProperty
  #SPDRP_ADDRESS = $1C
  #SPDRP_BUSNUMBER = $15
  #SPDRP_BUSTYPEGUID = $13
  #SPDRP_CAPABILITIES = $F
  #SPDRP_CHARACTERISTICS = $1B
  #SPDRP_CLASS = $7
  #SPDRP_CLASSGUID = $8
  #SPDRP_COMPATIBLEIDS = $2
  #SPDRP_CONFIGFLAGS = $A
  #SPDRP_DEVICEDESC = $0
  #SPDRP_DEVTYPE = $19
  #SPDRP_DRIVER = $9
  #SPDRP_ENUMERATOR_NAME = $16
  #SPDRP_EXCLUSIVE = $1A
  #SPDRP_FRIENDLYNAME = $C
  #SPDRP_HARDWAREID = $1
  #SPDRP_LEGACYBUSTYPE = $14
  #SPDRP_LOCATION_INFORMATION = $D
  #SPDRP_LOWERFILTERS = $12
  #SPDRP_MAXIMUM_PROPERTY = $1C
  #SPDRP_MFG = $B
  #SPDRP_PHYSICAL_DEVICE_OBJECT_NAME = $E
  #SPDRP_SECURITY = $17
  #SPDRP_SECURITY_SDS = $18
  #SPDRP_SERVICE = $4
  #SPDRP_UI_NUMBER = $10
  #SPDRP_UI_NUMBER_DESC_FORMAT = $1E
  #SPDRP_UNUSED0 = $3
  #SPDRP_UNUSED1 = $5
  #SPDRP_UNUSED2 = $6
  #SPDRP_UPPERFILTERS = $11
  
  ; Caractéristiques du device
  #CM_DEVCAP_LOCKSUPPORTED  = $1
  #CM_DEVCAP_EJECTSUPPORTED  = $2
  #CM_DEVCAP_REMOVABLE  = $4
  #CM_DEVCAP_DOCKDEVICE  = $8
  #CM_DEVCAP_UNIQUEID  = $10
  #CM_DEVCAP_SILENTINSTALL  = $20
  #CM_DEVCAP_RAWDEVICEOK  = $40
  #CM_DEVCAP_SURPRISEREMOVALOK  = $80
  #CM_DEVCAP_HARDWAREDISABLED  = $100
  #CM_DEVCAP_NONDYNAMIC  = $200
  
  Structure SP_DEVINFO_DATA
    cbSize.l
    ClassGuid.GUID
    DevInst.l
    reserved.l
  EndStructure
  
  #Memoire_Taille = 200
  
  Protected DeviceInfoData.SP_DEVINFO_DATA, DeviceCapabilities.l
  Protected *Memoire, Index
  
  DeviceInfoData\cbSize = SizeOf(DeviceInfoData)
  
  hDeviceInfoSet = SetupDiGetClassDevs_(0, 0, 0, #DIGCF_PRESENT | #DIGCF_ALLCLASSES)
  If hDeviceInfoSet <>#INVALID_HANDLE_VALUE
    Library = OpenLibrary(#PB_Any, "setupapi.dll")
    If Library
      
      *SetupDiGetDeviceInstanceId = GetFunction(Library, "SetupDiGetDeviceInstanceIdA")
      *SetupDiGetDeviceRegistryProperty = GetFunction(Library, "SetupDiGetDeviceRegistryPropertyA")
      *CM_Locate_DevNode = GetFunction(Library, "CM_Locate_DevNodeA")
      *CM_Request_Device_Eject = GetFunction(Library, "CM_Request_Device_Eject_ExA")
      *CM_Get_DevNode_Registry_Property = GetFunction(Library, "CM_Get_DevNode_Registry_PropertyA")
      
      While SetupDiEnumDeviceInfo_(hDeviceInfoSet, Index, @DeviceInfoData)
        
        *DeviceService = AllocateMemory(#Memoire_Taille)
        *DevicePhysicalName = AllocateMemory(#Memoire_Taille)
        *DeviceName = AllocateMemory(#Memoire_Taille)
        *DeviceDescription = AllocateMemory(#Memoire_Taille)
        
        CallFunctionFast(*SetupDiGetDeviceRegistryProperty, hDeviceInfoSet, DeviceInfoData, #SPDRP_SERVICE, 0, *DeviceService, #Memoire_Taille, 0)
        Debug PeekS(*DeviceService)
        CallFunctionFast(*SetupDiGetDeviceRegistryProperty, hDeviceInfoSet, DeviceInfoData, #SPDRP_PHYSICAL_DEVICE_OBJECT_NAME, 0, *DevicePhysicalName, #Memoire_Taille, 0)
        Debug PeekS(*DevicePhysicalName)
        CallFunctionFast(*SetupDiGetDeviceRegistryProperty, hDeviceInfoSet, DeviceInfoData, #SPDRP_FRIENDLYNAME, 0, *DeviceName, #Memoire_Taille, 0)
        Debug PeekS(*DeviceName)
        CallFunctionFast(*SetupDiGetDeviceRegistryProperty, hDeviceInfoSet, DeviceInfoData, #SPDRP_DEVICEDESC, 0, *DeviceDescription, #Memoire_Taille, 0)
        Debug PeekS(*DeviceDescription)
        CallFunctionFast(*SetupDiGetDeviceRegistryProperty, hDeviceInfoSet, DeviceInfoData, #SPDRP_CAPABILITIES, 0, @DeviceCapabilities, 4, 0)
        Debug DeviceCapabilities
        ; If DeviceCapabilities & #CM_DEVCAP_LOCKSUPPORTED
          ; Debug "CM_DEVCAP_LOCKSUPPORTED"
        ; EndIf
        If DeviceCapabilities & #CM_DEVCAP_EJECTSUPPORTED
          Debug "CM_DEVCAP_EJECTSUPPORTED"
        EndIf
        If DeviceCapabilities & #CM_DEVCAP_REMOVABLE
          Debug "CM_DEVCAP_REMOVABLE"
        EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_DOCKDEVICE
          ; Debug "CM_DEVCAP_DOCKDEVICE"
        ; EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_UNIQUEID
          ; Debug "CM_DEVCAP_UNIQUEID"
        ; EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_SILENTINSTALL
          ; Debug "CM_DEVCAP_SILENTINSTALL"
        ; EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_RAWDEVICEOK
          ; Debug "CM_DEVCAP_RAWDEVICEOK"
        ; EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_SURPRISEREMOVALOK
          ; Debug "CM_DEVCAP_RAWDEVICEOK"
        ; EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_HARDWAREDISABLED
          ; Debug "CM_DEVCAP_HARDWAREDISABLED"
        ; EndIf
        ; If DeviceCapabilities & #CM_DEVCAP_NONDYNAMIC
          ; Debug "CM_DEVCAP_NONDYNAMIC"
        ; EndIf
        
        ;- Pour éjecter toutes les clés USB
        ; If UCase(PeekS(*DeviceService)) = "USBSTOR"
          ; *DeviceId = AllocateMemory(#Memoire_Taille)
          ; CallFunctionFast(*SetupDiGetDeviceInstanceId, hDeviceInfoSet, DeviceInfoData, *DeviceId, #Memoire_Taille, 0)
          ; If CallFunctionFast(*CM_Locate_DevNode, @DevInst.l, PeekS(*DeviceId), 0) = 0
          ; CallFunctionFast(*CM_Request_Device_Eject, DevInst, 0, 0, 0, 0, 0)
          ; EndIf
          ; FreeMemory(*DeviceId)
        ; EndIf
        
        FreeMemory(*DeviceService)
        FreeMemory(*DevicePhysicalName)
        FreeMemory(*DeviceName)
        FreeMemory(*DeviceDescription)
        
        
        Debug "_____________________"
        Index + 1
      Wend
      
      CloseLibrary(Librairie)
    EndIf
    SetupDiDestroyDeviceInfoList_(hDeviceInfoSet)
  EndIf
  
  
  
  
EndProcedure

RemoveDevice("M:\")
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

Le Soldat Inconnu a écrit :donc les clés USB, voilà ou j'en suis

j'arrive à lister les Device du PC
heu ! excuse moi mais j'avais deja un code tout fait pour lister les devices
si j'avais su que tu recherchais ça :oops:

Code : Tout sélectionner

  Structure   DriveInfos
    DriveLetter.s
    DriveType.l
    DriveTypeString.s
    NameOfVolume.s
EndStructure
Global NewList DriveList.DriveInfos()

Procedure GetDrive(ListDriveType.l)
    Protected Drive.s, DriveLetter.s, DriveType.l, Start.l, LengthDrive.l, DriveTypeString.s
    #REMOVABLE_DRIVE = 1
    #FIXED_DRIVE = 2
    #REMOTE_DRIVE = 4
    #CDROM_DRIVE = 8
    #RAMDISK_DRIVE = 16
    #UNKNOWN_DRIVE = 32
    #ALL_DRIVE = 63
    
    ; On vide la liste
    ClearList (DriveList())
    
    ; On récupère la lettre des différents lecteurs présent sur l'ordinateur
    Drive = Space (255)
    LengthDrive = GetLogicalDriveStrings_ (255, @Drive)
    
    For Start = 0 To LengthDrive - 4 Step 4
        
        DriveLetter.s = PeekS (@Drive + Start, 3) ; on récupère une lettre
        
        DriveType.l = GetDriveType_ (@DriveLetter) ; on récupère le type du lecteur
        
        Select DriveType ; On donne un nom au type de lecteur
            Case #DRIVE_REMOVABLE : DriveType = #REMOVABLE_DRIVE : DriveTypeString.s = "Disquette"
            Case #DRIVE_FIXED : DriveType = #FIXED_DRIVE : DriveTypeString.s = "Disque dur"
            Case #DRIVE_REMOTE : DriveType = #REMOTE_DRIVE : DriveTypeString.s = "Lecteur réseau"
            Case #DRIVE_CDROM : DriveType = #CDROM_DRIVE : DriveTypeString.s = "CD-ROM"
            Case #DRIVE_RAMDISK : DriveType = #RAMDISK_DRIVE : DriveTypeString.s = "RamDisk"
            Case #DRIVE_UNKNOWN : DriveType = #UNKNOWN_DRIVE : DriveTypeString.s = ""
        EndSelect
        
        If DriveType & ListDriveType ; on regarde si le type du lecteur correspond à ceux demandés
            AddElement (DriveList())
            DriveList()\DriveLetter = RemoveString (DriveLetter, "" )
            DriveList()\DriveType = DriveType
            DriveList()\DriveTypeString = DriveTypeString
            
            If DriveLetter <> "A:" And DriveLetter <> "B:"
                DriveList()\NameOfVolume = Space (255)
                GetVolumeInformation_ (@DriveLetter, @DriveList()\NameOfVolume, 255, 0, 0, 0, 0, 0)
                DriveList()\NameOfVolume = Trim (DriveList()\NameOfVolume)
            Else
                DriveList()\NameOfVolume = ""
            EndIf
            
        EndIf
        
    Next
EndProcedure




;- Debut du test

GetDrive( #REMOVABLE_DRIVE | #CDROM_DRIVE | #FIXED_DRIVE )

ResetList (DriveList())
While NextElement (DriveList())
    Debug DriveList()\DriveLetter + " " + DriveList()\DriveTypeString + " " + DriveList()\NameOfVolume
Wend 
Le Soldat Inconnu a écrit :donc les clés USB, voilà ou j'en suis

j'arrive à lister les Device du PC

J'ai le nom, la description et si je peux l'éjecter.
J'ai toujours pas la lettre du letteur associé
tout tourne autour de

Code : Tout sélectionner

 LengthDrive = GetLogicalDriveStrings_ (255, @Drive)
je l'avais aussi sous cette forme

Code : Tout sélectionner

 Enumeration
    #DRIVE_UNKNOWN
    #DRIVE_ABSENT
    #DRIVE_REMOVABLE
    #DRIVE_FIXED
    #DRIVE_REMOTE
    #DRIVE_CDROM
    #DRIVE_RAMDISK
EndEnumeration

Procedure.s GetDriveType(Drive.s)
    Select GetDriveType_(Drive)
        Case #DRIVE_UNKNOWN   : ProcedureReturn "Unknown"
        Case #DRIVE_ABSENT    : ProcedureReturn "Absent"
        Case #DRIVE_REMOVABLE : ProcedureReturn "Removable"
        Case #DRIVE_FIXED     : ProcedureReturn "Fixed"
        Case #DRIVE_REMOTE    : ProcedureReturn "Remote"
        Case #DRIVE_CDROM     : ProcedureReturn "CD-Rom"
        Case #DRIVE_RAMDISK   : ProcedureReturn "RAM Disk"
    EndSelect
EndProcedure

Procedure EnumDrives()
    For i=0 To 25
        If ( GetLogicalDrives_() & Int(Pow(2,i)) ) <> 0
            Drive.s = Chr(65+i) + ":"
            Debug Drive + " " + GetDriveType(Drive)
        EndIf
    Next
EndProcedure

EnumDrives()
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Message par Le Soldat Inconnu »

C'est gentil de me redonner mes codes :roll: :lol:
en plus, il est pas à jour, tiens v'la la dernière version

Code : Tout sélectionner

; Auteur : Le Soldat Inconnu
; Version de PB : 4
;
; Explication du programme :
; Récupérer la lettre et le type (disquette, disque dur, etc...) de tous les lecteurs présents sur l'ordinateur.



Procedure GetDrive(Search_Type.l = -1)
  Structure DriveInfos
    Letter.s
    Type.l
    Name.s
    ; Device.s
  EndStructure
  Global NewList Drive.DriveInfos()
  
  ; Value for Search_Type :
  ; 
  ; DRIVE_UNKNOWN
  ; 0
  ; The Drive Type cannot be determined.
  ; 
  ; DRIVE_NO_ROOT_DIR
  ; 1
  ; The root Path is invalid; for example, there is no volume is mounted at the path.
  ; 
  ; DRIVE_REMOVABLE
  ; 2
  ; The Drive has removable media; for example, a floppy drive, thumb drive, or flash card reader.
  ; 
  ; DRIVE_FIXED
  ; 3
  ; The Drive has fixed media; for example, a hard drive or flash drive.
  ; 
  ; DRIVE_REMOTE
  ; 4
  ; The Drive is a remote (network) Drive.
  ; 
  ; DRIVE_CDROM
  ; 5
  ; The Drive is a CD-ROM Drive.
  ; 
  ; DRIVE_RAMDISK
  ; 6
  ; The drive is a RAM disk.
  
  Protected DriveString_Length.l, DriveString.l, DriveIndex.l, FileInfo.SHFILEINFO
  
  
  ; On vide la liste
  ClearList(Drive())
  
  ; On récupère la liste des lecteurs
  DriveString_Length = GetLogicalDriveStrings_(0, 0) 
  *DriveString = AllocateMemory(DriveString_Length) 
  GetLogicalDriveStrings_(DriveString_Length, *DriveString) 
  
  For DriveIndex = 0 To DriveString_Length - 4 Step 4
    AddElement(Drive())
    
    Drive()\Letter = PeekS(*DriveString + DriveIndex) ; lettre
    
    Drive()\Type = GetDriveType_(@Drive()\Letter) ; type de lecteur
    
    ; DeviceLength = 200
    ; *Device = AllocateMemory(DeviceLength)
    ; If QueryDosDevice_(Left(Drive()\Letter, 2), *Device, DeviceLength)
      ; Drive()\Device = PeekS(*Device)
    ; EndIf
    
    If Drive()\Type = Search_Type Or Search_Type = -1
      
      SHGetFileInfo_(Drive()\Letter, 0, @FileInfo, SizeOf(SHFILEINFO), #SHGFI_DISPLAYNAME) 
      Drive()\Name = PeekS(@FileInfo\szDisplayName)
      
    Else
      DeleteElement(Drive())
    EndIf
  Next
  
  FreeMemory(*DriveString)
  
EndProcedure




;- Debut du test

GetDrive()

ForEach Drive()
  Debug "'" + Drive()\Letter + "'   '" + Str(Drive()\Type) + "'   '" + Drive()\Name + "'   '" + Drive()\Device + "'"
Next



Mon souci, c'est ça :

- J'ai ma liste de lecteurs
- J'arrive à ejecter toutes les clés USB
- Mais je n'arrive pas à éjecter une clé USB à partir de la lettre de lecteur

J'ai encore trouvé de lien entre le Device (le matériel) et le lecteur M:\ affiché dans l'explorateur
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

je savais bien que l'un des 2 code était de toi, mais je pensais que tu l'avais perdu :)
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

une piste peut etre ...

http://www.developpez.net/forums/d31650 ... on-disque/


un code complet en VB

Code : Tout sélectionner

# 'A mettre dans un module
# Option Explicit
#
#
# 'API functions
# Public Declare Function DeviceIoControl Lib "kernel32" (ByVal hDevice As Long, ByVal dwIoControlCode As Long, lpInBuffer As Any, ByVal nInBufferSize As Long, lpOutBuffer As Any, ByVal nOutBufferSize As Long, lpBytesReturned As Long, lpOverlapped As Long) As Long
# Public Declare Function CreateFile Lib "kernel32" Alias "CreateFileA" (ByVal lpFileName As String, ByVal dwDesiredAccess As Long, ByVal dwShareMode As Long, lpSecurityAttributes As Long, ByVal dwCreationDisposition As Long, ByVal dwFlagsAndAttributes As Long, ByVal hTemplateFile As Long) As Long
# Public Declare Function FlushFileBuffers Lib "kernel32" (ByVal hFile As Long) As Long
# Public Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long
#
#
# 'API Constants
# Const GENERIC_READ = &H80000000
# Const FILE_FLAG_WRITE_THROUGH = &H80000000
# Const GENERIC_WRITE = &H40000000
# Const FILE_SHARE_READ = &H1
# Const FILE_SHARE_WRITE = &H2
#
# Const CREATE_NEW = 1
# Const CREATE_ALWAYS = 2
# Const OPEN_EXISTING = 3
# Const OPEN_ALWAYS = 4
# Const TRUNCATE_EXISTING = 5
#
#
# Const IOCTL_STORAGE_EJECT_MEDIA = 2967560
# Const IOCTL_STORAGE_LOAD_MEDIA = 2967564
#
#
#
# Public Function EjectDrive(driveLetter As String) As Boolean
# Dim hDisk As Long
# Dim dwRc As Long
# Dim sDisk As String
#
# 'Generate a volume name
# sDisk = "\\.\" & UCase(Mid(driveLetter, 1, 1)) & ":"
#
# 'We should get back a handle to the volume
# hDisk = CreateFile(sDisk, GENERIC_READ Or GENERIC_WRITE, FILE_SHARE_READ Or _
# FILE_SHARE_WRITE, ByVal CLng(0), OPEN_EXISTING, FILE_FLAG_WRITE_THROUGH, _
# ByVal CLng(0))
#
# If hDisk = -1 Then
# EjectDrive = False
# Exit Function
# End If
#
# 'Clear any cache from the disk
# FlushFileBuffers (hDisk)
#
# 'Control the device (in this case, eject it)
# If DeviceIoControl(hDisk, IOCTL_STORAGE_EJECT_MEDIA, _
# ByVal CLng(0), 0, ByVal CLng(0), 0, _
# dwRc, ByVal CLng(0)) = 0 Then
# EjectDrive = False
# Else
# EjectDrive = True
# End If
#
# 'Always close your handles!
# CloseHandle (hDisk)
#
# End Function
#
#
# Public Function LoadDrive(driveLetter As String) As Boolean
# Dim hDisk As Long
# Dim dwRc As Long
# Dim sDisk As String
#
# 'Generate a volume name
# sDisk = "\\.\" & UCase(Mid(driveLetter, 1, 1)) & ":"
#
# 'We should get back a handle to the volume
# hDisk = CreateFile(sDisk, GENERIC_READ Or GENERIC_WRITE, FILE_SHARE_READ Or _
# FILE_SHARE_WRITE, ByVal CLng(0), OPEN_EXISTING, FILE_FLAG_WRITE_THROUGH, _
# ByVal CLng(0))
#
# If hDisk = -1 Then
# LoadDrive = False
# Exit Function
# End If
#
# 'Clear any cache from the disk
# FlushFileBuffers (hDisk)
#
# 'Control the device (in this case, eject it)
# If DeviceIoControl(hDisk, IOCTL_STORAGE_LOAD_MEDIA, _
# ByVal CLng(0), 0, ByVal CLng(0), 0, _
# dwRc, ByVal CLng(0)) = 0 Then
# LoadDrive = False
# Else
# LoadDrive = True
# End If
#
# 'Always close your handles!
# CloseHandle (hDisk)
#
# End Function 
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

regarde bien ça :

extrait du code vb ci dessus

Code : Tout sélectionner

If DeviceIoControl(hDisk, IOCTL_STORAGE_EJECT_MEDIA, _
# ByVal CLng(0), 0, ByVal CLng(0), 0, _
# dwRc, ByVal CLng(0)) = 0 Then
# EjectDrive = False
# Else
# EjectDrive = True
# End If 
ne seraice pas une api ce

Code : Tout sélectionner

DeviceIoControl(hDisk, IOCTL_STORAGE_EJECT_MEDIA, _
# ByVal CLng(0), 0, ByVal CLng(0), 0, _
# dwRc, ByVal CLng(0)) = 0 
??



code original ici :
http://www.vbfrance.com/codes/EJECTER-C ... _3812.aspx
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Message par Le Soldat Inconnu »

j'ai trouvé un exemple en VB de ce que je veux

mais je galère pour le traduire pour le moment

http://www.codeproject.com/KB/system/Re ... etter.aspx

J'ai fait le premier code

Code : Tout sélectionner

hVolume = CreateFile_("\\.\L:", #GENERIC_READ|#GENERIC_WRITE, #FILE_SHARE_READ | #FILE_SHARE_WRITE, 0, #OPEN_EXISTING, 0, 0)
If hVolume <> #INVALID_HANDLE_VALUE
  Debug hVolume
  sdn.STORAGE_DEVICE_NUMBER
  dwBytesReturned.l
  res = DeviceIoControl_(hVolume, #IOCTL_STORAGE_GET_DEVICE_NUMBER, 0, 0, @sdn, SizeOf(STORAGE_DEVICE_NUMBER), @dwBytesReturned, 0)
  If res
    Debug sdn\DeviceNumber
    
  EndIf
  CloseHandle_(hVolume)
    
EndIf
Mais c'est le second qui m'intéresse et je galère. Je pige pas tout de ce qui est écrit dans la déclaration des structures
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
Backup
Messages : 14526
Inscription : lun. 26/avr./2004 0:40

Message par Backup »

pour moi c'est clair !! tout tourne autour de cette API

http://msdn.microsoft.com/en-us/library/ms790831.aspx

;)
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Message par Le Soldat Inconnu »

oui, ça j'arrive a m'en servir, voir code plus haut.
C'est la fonction qui permet d'ejecter un Device
Ca fait la même chose que "retirer le périphérique sous win XP"

Mon problème, c'est que j'ai pas le nom du lecteur du device, en gros, je ne sais pas ce que j'éjecte mais j'arrive à l'éjecter :?
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
Avatar de l’utilisateur
Jacobus
Messages : 1559
Inscription : mar. 06/avr./2004 10:35
Contact :

Message par Jacobus »

Est-ce qu'au moins tu as essayé en ayant branché une clé usb ? Car dans ce cas là tu connais la lettre correspondante à la clé et il suffit de la sélectionner dans un combobox par exemple. Ou bien tu fais ça à l'aveuglette: recherche d'une clé branchée et éjection ? là je dirais que c'est normal que tout ce qui est trouvé soit éjecté.
Quand tous les glands seront tombés, les feuilles dispersées, la vigueur retombée... Dans la morne solitude, ancré au coeur de ses racines, c'est de sa force maturité qu'il renaîtra en pleine magnificence...Jacobus.
Répondre