PDA

Ver la Versión Completa : como hago que solo funcione en Pendriver


darkbits
08-02-2013, 22:29:34
un saludo

tengo una aplicacion que esta funcionando bien en PC

pero me piden que solo funcione en pendriveres
ahi me agarraron en curva... :(
consulto a ustedes expertos como se hace esto ?
solo tengo una idea de colocar un IF es pendriver then si es verdad que continue de lo contrario lo cierro la aplicacion.

Al González
08-02-2013, 23:13:35
Puede que te sirva la función GetDriveType, de la API de Windows. Que como dice la ayuda (busca el archivo Win32.hlp):

The GetDriveType function determines whether a disk drive is a removable, fixed, CD-ROM, RAM disk, or network drive.

UINT GetDriveType(
LPCTSTR lpRootPathName // address of root path
);


Parameters

lpRootPathName

Points to a null-terminated string that specifies the root directory of the disk to return information about. If lpRootPathName is NULL, the function uses the root of the current directory.

Return Values

The return value specifies the type of drive. It can be one of the following values:

Value Meaning
0 The drive type cannot be determined.
1 The root directory does not exist.
DRIVE_REMOVABLE The drive can be removed from the drive.
DRIVE_FIXED The disk cannot be removed from the drive.
DRIVE_REMOTE The drive is a remote (network) drive.
DRIVE_CDROM The drive is a CD-ROM drive.
DRIVE_RAMDISK The drive is a RAM disk.

Espero te sirva, saludos. :)

ecfisa
09-02-2013, 00:08:37
Hola.

Como Al, opino que la función GetDriveType (http://msdn.microsoft.com/en-us/library/windows/desktop/aa364939%28v=vs.85%29.aspx) te servirá para el propósito.

Por ejemplo podrías hacer:

program Tu_proyecto;

uses
Windows, ...

begin
if GetDriveType(PChar(Application.ExeName[1]+':\')) = DRIVE_REMOVABLE then
begin
Application.Initialize;
Application.CreateForm(TMainForm, MainForm);
//...
Application.Run;
end
else
MessageBox(Application.Handle,
'Esta aplicación sólo puede ejecutarse en medios removibles',
'ERROR', MB_ICONERROR + MB_OK);
end.


Saludos.

Neftali [Germán.Estévez]
11-02-2013, 11:13:47
A parte de las opciones comentadas, te puedo redirigir a la página de las librerías GLibWMI (http://neftali.clubdelphi.com/?page_id=578), que incluyen un componente para DiskDriveInfo para acceder a las propiedades de los discos.

En este caso, puedes obtener algunas propiedades que te pueden ayudar:

http://img687.imageshack.us/img687/8366/imagen292.png

Si no deseas instalar toda la librería de componentes, otra opción es utilizar WMI (que es lo que utiliza esta librerías al fin y al cabo) para obtener la misma información.
En concreto para este caso se usa la clase Win32_DiskDrive (http://msdn.microsoft.com/en-us/library/windows/desktop/aa394132(v=vs.85).aspx). Si miras esta página podrás ver las propiedades que te devuelve esta clase.

Si buscas ejemplos sobre esta clase podrás encontrar alguno son problemas (por ejemplo, este que acabo de encontrar en el FTP (http://terawiki.clubdelphi.com/Delphi/Ejemplos/Win-API/?download=InformacionDisco.zip)).

MAXIUM
11-02-2013, 16:06:41
Debes capturar el número de serie de fabrica. El cual no se borra aúnque se formatee.

En cuanto tenga acceso a mi equipo te doy el código necesario.

Neftali [Germán.Estévez]
11-02-2013, 16:11:13
... tengo una aplicacion que esta funcionando bien en PC
pero me piden que solo funcione en pendriveres
...




...Debes capturar el número de serie de fabrica. El cual no se borra aúnque se formatee.


No acabo de ver qué tiene que ver la pregunta con la respuesta.
Este usuario necesita que la aplicación funcione en los dispositivos de tipo "PENDRIVE", entiendo que en general, cualquier dispositivo de almacenamiento conectado por USB.

¿Porqué hay que comprobar el número de serie del disco?
Tal vez no has leído bien la pregunta... :confused::confused:

MAXIUM
11-02-2013, 16:38:36
Tienes razón Neftali. Era solo para que no copiasen la aplicación de un pendrive a otro.

Ok, olvida mi código :p

darkbits
15-02-2013, 02:08:45
Gracias!
si me llego a funcionar la opcion de ecfisa


MAXIUM me intereso lo que comentaste de como sacar el ID unico del pendriver por mas que se llege a formatear please si podes compartirme el codigo

Neftali [Germán.Estévez]
15-02-2013, 08:34:09
Era solo para que no copiasen la aplicación de un pendrive a otro.


Al final si que vas a acertar con el comentario... ;)

nlsgarcia
15-02-2013, 19:04:00
darkbits,


...como sacar el ID unico del pendriver por mas que se llege a formatear...


Revisa este código:

unit Unit1;

interface

uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, FileCtrl, StrUtils, ActiveX, ComObj, XPMan;

type
TForm1 = class(TForm)
ListBox1: TListBox;
Button2: TButton;
procedure Button2Click(Sender: TObject);
procedure ListBox1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;

var
Form1: TForm1;

implementation

{$R *.dfm}

function VarStrNull(const V:OleVariant):string; //avoid issues with null variants
begin
Result:='';
if not VarIsNull(V) then
Result:=VarToStr(V);
end;

// Obtiene el Número de Serial un Drive USB por medio de la propiedad PnPDeviceID de Windows Management Instrumentation (WMI)
function GetUsbDriveSerial(const Drive : AnsiChar) : string;
var
FSWbemLocator : OleVariant;
objWMIService : OLEVariant;
colDiskDrives : OLEVariant;
colLogicalDisks : OLEVariant;
colPartitions : OLEVariant;
objDiskDrive : OLEVariant;
objPartition : OLEVariant;
objLogicalDisk : OLEVariant;
oEnumDiskDrive : IEnumvariant;
oEnumPartition : IEnumvariant;
oEnumLogical : IEnumvariant;
iValue : LongWord;
DeviceID : string;

begin;

Result:='';

FSWbemLocator := CreateOleObject('WbemScripting.SWbemLocator');
objWMIService := FSWbemLocator.ConnectServer('.', 'root\CIMV2', '', '');
colDiskDrives := objWMIService.ExecQuery('SELECT * FROM Win32_DiskDrive WHERE InterfaceType="USB"','WQL',0);
oEnumDiskDrive:= IUnknown(colDiskDrives._NewEnum) as IEnumVariant;

while oEnumDiskDrive.Next(1, objDiskDrive, iValue) = 0 do
begin

//Escape the `\` chars in the DeviceID value because the '\' is a reserved character in WMI.
DeviceID := StringReplace(VarStrNull(objDiskDrive.DeviceID),'\','\\',[rfReplaceAll]);

//link the Win32_DiskDrive class with the Win32_DiskDriveToDiskPartition class
colPartitions := objWMIService.ExecQuery(Format('ASSOCIATORS OF {Win32_DiskDrive.DeviceID="%s"} WHERE AssocClass = Win32_DiskDriveToDiskPartition',[DeviceID]));

oEnumPartition := IUnknown(colPartitions._NewEnum) as IEnumVariant;

while oEnumPartition.Next(1, objPartition, iValue) = 0 do
begin

//link the Win32_DiskPartition class with theWin32_LogicalDiskToPartition class.
colLogicalDisks := objWMIService.ExecQuery('ASSOCIATORS OF {Win32_DiskPartition.DeviceID="'+VarStrNull(objPartition.DeviceID)+'"} WHERE AssocClass = Win32_LogicalDiskToPartition');

oEnumLogical := IUnknown(colLogicalDisks._NewEnum) as IEnumVariant;

while oEnumLogical.Next(1, objLogicalDisk, iValue) = 0 do
begin

if SameText(VarStrNull(objLogicalDisk.DeviceID),Drive+':') then //compare the device id
begin

Result := VarStrNull(objDiskDrive.PnPDeviceID);

if AnsiStartsText('USBSTOR', Result) then
begin
iValue := LastDelimiter('\', Result);
Result := Copy(Result, iValue+1, Length(Result));
end;

objLogicalDisk:=Unassigned;

Exit;

end;

objLogicalDisk:=Unassigned;

end;

objPartition:=Unassigned;

end;

objDiskDrive:=Unassigned;

end;
end;

procedure TForm1.Button2Click(Sender: TObject);
var
Drive : Char;
begin
ListBox1.Clear;
for Drive := 'A' to 'Z' do
if GetDriveType(PChar(Drive + ':\')) = DRIVE_REMOVABLE then
ListBox1.Items.Add(UpperCase(Drive));
end;

procedure TForm1.ListBox1Click(Sender: TObject);
var
Drive : String;
begin
Drive := ListBox1.Items.Strings[ListBox1.ItemIndex];
ShowMessage('USB Serial Number : ' + GetUsbDriveSerial(Drive[1]));
end;

end.

El ejemplo anterior lista las unidades removibles del sistema en un control TListBox y muestra el serial de cada una de ellas al ser seleccionadas por medio del evento OnClick.

El código fuente del ejemplo esta disponible en el link : http://terawiki.clubdelphi.com/Delphi/Ejemplos/Win-API/?download=USB+Serial+Number.rar

El ejemplo mostrado esta basado en el código encontrado en el link : http://stackoverflow.com/questions/4292395/how-to-get-manufacturer-serial-number-of-an-usb-flash-drive

Espero sea útil :)

Nelson.