https://foro.gambas-es.org/viewtopic.php?f=1&t=383
-----------------------------------
Pablo-GNU
Miercoles, 27 Enero 2010, 14:07

Dispositivos USB En Listbox (SOLUCIONADO)
-----------------------------------
Estoy intentado mostrar los dispositivos conectados al USB en un ListBox para poder seleccionarlos y al hacer eso que muestre su direccion fisica en una variable (/dev/sdx). He investigado un poco como lo hacen en otras aplicaciones y he encontrado este codigo en python, pero la verdad que no se como adaptarlo a gambas. He leido por hay que gambas es capaz de interpretar python... cosa que no se si es cierta..
[code linenumbers=false syntax=python]
def get_devices():
	for a in glob.glob("/sys/block/sd*"):
		removable = file(a+"/removable").read().startswith("1")
		mb_blocks = int(file(a+"/size").read()) / 2 / 1024
		name = " ".join([ file(a+b).read().strip() for b in ["/device/vendor","/device/model"] ])
		if removable and mb_blocks >= 1000:
			a = a.replace("/sys/block","/dev")
			yield (a,name,mb_blocks)[/code]

Vosotros que pensais? Habra alguna forma? Gracias...


-----------------------------------
fabianfv
Miercoles, 27 Enero 2010, 15:17

Re: Dispositivos USB En Listbox
-----------------------------------
Pablo, al menos las versiones actuales de Gambas no interpretan código Python. No me parece viable a Gambas traducir el código Python que muestras porque no funcionaría (usa bibliotecas de Python que también habría que traducir).

Ejecuta ese código en el intérprete Python para ver exactamente qué información suministra. Si te resulta útil podrías pensar en la forma de ejecutarlo desde Gambas (llamando al intérprete Python, por supuesto).

También puedes usar los comandos:

[b]lspci|grep USB

lsusb -t

lsusb[/b]

Filtrando un poco esos datos probablemente obtengas la información que necesitas. Aún si esa información no es suficiente me parece que la solución pasa por utilizar comandos/utilidades GNU/Linux para obtener datos o bien usar alguna biblioteca C/C++ que puedas utilizar desde Gambas mediante "llamadas externas" (capítulo 9 del libro de Gambas).

Saludos cordiales.


-----------------------------------
Pablo-GNU
Miercoles, 27 Enero 2010, 19:38

Re: Dispositivos USB En Listbox
-----------------------------------
No la verdad que los comandos del terminal no me son de mucha ayuda ya que, no son capaces de resolver esos dos parametros a la vez, lo que intento es traducir el codigo ese de Python a Gambas, porque es Justamente lo que hay que hacer, pero mis conocimientos no son lo suficientemente amplios como para hacerlo...

La idea seria, hacer un listado de todos los directorios del /sys/block/ para obtener lo que van a ser los dispositivos de disco como tal... filtrando para que no muestre  todos los virtuales tales como ram* o loop* o sr. solo los que sean hd* o sd*... Eso creo con un rdir("/sys/block") podria conseguirlo, pero no estoy seguro y luego eso guardarlo en una variable string para con un for volcarlos a otra variable.

Despues habria que filtrar todas esos resultados, mirando que dentro de cada carpeta obtenida (sd*/) tiene que haber un fichero llamado "removable" y si dentro de ese fichero el valor es "1", puede mostrarse ya que es un dispositivo hotplug y no un disco duro nuestro, que en el caso de ser un disco duro nuestro, deberia de ser "0" y no mostrarse en la lista. Una vez filtrado los que se puedan mostrar, habria que leer el archivo que se encuentra dentro de la carpeta devices, que se llama vendor para guardar el fabricante y el archivo model para guardar el modelo y juntar la lectura de ambos en una sola linea, de esta manera ya tendrias que corresponde al, por ejemplo, KINGSTON (fabricante) DATA TRAVELER (modelo), y ademas como ya esta el sd*, a ese sd* le añadiriamos un /dev/ delante, por lo que ya tendriamos tambien la direccion fisica (Ejemplo: /dev/sdb) Y mostrar en el listbox por ejemplo KINGSTON DATA TRAVELER y que al pinchar esa opcion, una variable llamada fisica coja el valor que le corresponda, en ese caso, /dev/sdb/.

No pido que me lo hagais porque jamas se me ocurriria, soy nuevo en el foro y como habeis visto, todos mis posts he posteado la solucion despues de haber investigado. No me gusta que me den las cosas hechas, pero si que me hecheis una mano, os lo agradeceria de corazon.

Saludos.


-----------------------------------
fabianfv
Miercoles, 27 Enero 2010, 21:27

Re: Dispositivos USB En Listbox
-----------------------------------
[strike]No puedes traducir ese código Python a Gambas, no hay nada en Gambas como:[/strike]

[b]Edito[/b]: perdón Pablo, está perfecto que quieras traducir ese código Python a Gambas y es posible porque es bien sencillo (eso me pasa andar tan apurado y no leer el código, supuse que usaba alguna biblioteca de Python para obtener la lista de dispositivos USB).

[quote]
La idea seria, hacer un listado de todos los directorios del /sys/block/ para obtener lo que van a ser los dispositivos de disco como tal... filtrando para que no muestre  todos los virtuales tales como ram* o loop* o sr. solo los que sean hd* o sd*... Eso creo con un rdir("/sys/block") podria conseguirlo, pero no estoy seguro y luego eso guardarlo en una variable string para con un for volcarlos a otra variable.
[/quote]

Con RDIR o si no funciona tal vez sirva algo como:

[code linenumbers=false syntax=gambas]
DIM salida AS String
Dim arrSalida AS String[]

  'Usar alguna expresión regular que haga el filtro que deseas.
  SHELL "ls -l /sys/block|grep usb" TO salida
  arrsalida = split(salida, gb.newline)
[/code]

[quote]
Despues habria que filtrar todas esos resultados, mirando que dentro de cada carpeta obtenida (sd*/) tiene que haber un fichero llamado "removable" y si dentro de ese fichero el valor es "1", puede mostrarse ya que es un dispositivo hotplug y no un disco duro nuestro, que en el caso de ser un disco duro nuestro, deberia de ser "0" y no mostrarse en la lista. Una vez filtrado los que se puedan mostrar, habria que leer el archivo que se encuentra dentro de la carpeta devices, que se llama vendor para guardar el fabricante y el archivo model para guardar el modelo y juntar la lectura de ambos en una sola linea, de esta manera ya tendrias que corresponde al, por ejemplo, KINGSTON (fabricante) DATA TRAVELER (modelo), y ademas como ya esta el sd*, a ese sd* le añadiriamos un /dev/ delante, por lo que ya tendriamos tambien la direccion fisica (Ejemplo: /dev/sdb) Y mostrar en el listbox por ejemplo KINGSTON DATA TRAVELER y que al pinchar esa opcion, una variable llamada fisica coja el valor que le corresponda, en ese caso, /dev/sdb/.
[/quote]

Lo que yo haría en primera instancia sería utilizar EXEC para ejecutar comandos Linux bien conocidos para hacer esto (cat, ls, etc), porque me parece que escribir código Gambas sería más largo.

[quote]
No me gusta que me den las cosas hechas, pero si que me hecheis una mano, os lo agradeceria de corazon.
[/quote]

Ten la seguridad de que si no obtuviste respuestas más adecuadas es porque nadie más tuvo tiempo para responder o nadie más tuvo esta necesidad y por tanto tampoco el conocimiento sobre cómo hacerlo.

Saludos cordiales.


-----------------------------------
soplo
Miercoles, 27 Enero 2010, 21:51

Re: Dispositivos USB En Listbox
-----------------------------------
Hola
Quizá no entiendo bien, pero he hecho un pequeño código para sacar de lsusb lo que se quiere y pegarlo en un treeview. y no se que es lo que tiene esto de malo. Opcionalmente se podría mirar ese dispositivo a ver si es disco duro o impresora o que para ponerle el icono adecuado. Yo no me he preocupado de eso. Solo de sacar la información.

Te pego el código
[code linenumbers=false syntax=gambas]PUBLIC SUB Form_Open()
me.arrangement=arrange.fill
Dim Arbol as new treeview(me)
DIM FTemp AS String, Var AS String

FTemp = Temp 'crear un nombre de archivo temporal
SHELL ("lsusb >" & fTemp) 'Llenar FTemp con la información requerida
LlenarArbol(fTemp) 'Llenar el arbol
KILL FTemp 'borrar el archivo temporal
END[/code]
[code linenumbers=false syntax=gambas]
PRIVATE SUB LlenarArbol(ftemp AS String)
  DIM F AS file, Linea AS String, Partes AS String[], Clave AS String, Dev AS String, Nombre AS String    
  arbol.Add("Bus 0", System.Host, Stock["16/home"]) 'poner el valor raíz
  
  f = OPEN (ftemp) FOR READ 
  f.EndOfLine = gb.Unix
  
  DO WHILE NOT Eof(f)
    LINE INPUT #f, linea 'leer la línea entera
    partes = Split(linea, ":") 'dividirla en tres partes por el :
    clave = Left(partes[0], 7) 'la clave será algo como 'Bus 1'
    insertarbus(clave) 'insertar la el bus en el arbol con padre raíz
    Dev = Right(partes[0], 3) 'obtener el dev nº
    Nombre = Mid(partes[2], 5) 'obtener el nombre del dispositivo
    insertardev(dev, nombre, clave) 'insertar dispositivo en arbol
  LOOP 
  END 
  
  PRIVATE SUB insertarbus(Clave AS String)
  TRY arbol.Add(clave, Clave, Stock["16/connect"], "Bus 0")    
  FINALLY 
  CATCH 

  END 
  
  PRIVATE SUB insertardev(dev AS String, nombre AS String, padre AS String)
  TRY arbol.Add(padre & "/" & dev, dev & ": " & nombre, Stock["16/attach"], padre)
  TRY arbol.item.EnsureVisible
  FINALLY 
  CATCH 
  END [/code]

Solo hay que pastearlo en un form y probar ¿qué tiene eso de malo? ¿Qué le falta?


-----------------------------------
Pablo-GNU
Jueves, 28 Enero 2010, 11:02

Re: Dispositivos USB En Listbox
-----------------------------------
Hola Fabian, muchas gracias por contestarme, ya se porque seguramente la gente no me contesto, pero queria aclarar eso, ya que soy de preguntar mucho las cosas para intentar optimizar al maximo el codigo, soy un buen creyente de que la programacion tiene que estar muy revisada para no tener errores ni dejar cabos sueltos, y como soy "nuevo" pues pregunto lo que no se y asi de paso de optimizar aprendo de la gente que sabe (autodidacta total), aclare eso para que no se me tome como un vago al que le gusta todo hecho. jejeje.

Con respecto al codigo, cre que es una buena opcion lo de tener en cuenta el usar codigo del terminal ya que sino.. podria ser un codigo muy exagerado en gambas el realizar esas tareas. Ire probando y te contare como va quedando.

Soplo, te contesto a ti tambien, estoy intentando probar tu codigo, te cuento lo malo del lsusb, el lsusb, lo malo que tiene, es que, no te muestra todos los datos como tal, y sacar la asociacion con el dispositivo fisico /dev, con los comandos que tiene, no se si es posible, casi todos los codigos que he leido en cuanto codigo, sacan la informacion del /sys/block, pero se puede probar con el lsusb.

Recibo 2 errores con tu codigo, el primero creo que lo he corregido y debe de ser por el orden de las lineas... tu has puesto esto:

[code linenumbers=false syntax=gambas]PUBLIC SUB Form_Open()
me.arrangement=arrange.fill
Dim Arbol as new treeview(me)
DIM FTemp AS String, Var AS String

FTemp = Temp 'crear un nombre de archivo temporal
SHELL ("lsusb >" & fTemp) 'Llenar FTemp con la información requerida
LlenarArbol(fTemp) 'Llenar el arbol
KILL FTemp 'borrar el archivo temporal
END[/code]

Y recibo unexpected DIM

Lo he cambiado por esto:

[code linenumbers=false syntax=gambas]PUBLIC SUB Form_Open()
DIM FTemp AS String, Var AS String
DIM arbol AS NEW treeview(ME)
ME.arrangement = arrange.fill
FTemp = Temp 'crear un nombre de archivo temporal
SHELL ("lsusb >" & fTemp) 'Llenar FTemp con la información requerida
LlenarArbol(fTemp) 'Llenar el arbol
KILL FTemp 'borrar el archivo temporal
END
[/code]

Y ya dejo de recibirlo, simplemente como ves, ha sido mover los dos DIM encima del  ME.arragement.

Pero ahora recibo otro error que es el Unknow Identifier Arbol

[code linenumbers=false syntax=gambas]PRIVATE SUB LlenarArbol(ftemp AS String)
 DIM F AS file, Linea AS String, Partes AS String[], Clave AS String, Dev AS String, Nombre AS String    
 arbol.Add("Bus 0", System.Host, Stock["16/home"]) 'poner el valor raíz
 
 f = OPEN (ftemp) FOR READ
 f.EndOfLine = gb.Unix
 
 DO WHILE NOT Eof(f)
   LINE INPUT #f, linea 'leer la línea entera
   partes = Split(linea, ":") 'dividirla en tres partes por el :
   clave = Left(partes[0], 7) 'la clave será algo como 'Bus 1'
   insertarbus(clave) 'insertar la el bus en el arbol con padre raíz
   Dev = Right(partes[0], 3) 'obtener el dev nº
   Nombre = Mid(partes[2], 5) 'obtener el nombre del dispositivo
   insertardev(dev, nombre, clave) 'insertar dispositivo en arbol
 LOOP
 END
 
 PRIVATE SUB insertarbus(Clave AS String)
 TRY arbol.Add(clave, Clave, Stock["16/connect"], "Bus 0")    
 FINALLY
 CATCH

 END
 
 PRIVATE SUB insertardev(dev AS String, nombre AS String, padre AS String)
 TRY arbol.Add(padre & "/" & dev, dev & ": " & nombre, Stock["16/attach"], padre)
 TRY arbol.item.EnsureVisible
 FINALLY
 CATCH
 END [/code]

He mirado si era cosa de que Arbol arriba lo declaras con  mayusculas en lugar de minusculas la primera letra, pero aunque lo ponga de ambas maneras no funciona de misma manera, tambien he probado a escribir la linea a mano para ver si lo reconoce y empieza a autocompletar, y al escribir "ar..." lo rellena pero al poner el "." las opciones no se despliegan, pero segun creo esto puede deberse a que el objeto no este creado con modo grafico sino a  mano en el codigo. o me equivoco? Bueno voy a ver como puedo probarlo. Saludos y muchisimas gracias por contestarme.

P.D.: Que dificil es escribir o seleccionar codigo en el 4X4 del trabajo mientras vas de copiloto y tu compañero sube a la montaña conduciendo por caminos de tierra y piedra.. xD


-----------------------------------
soplo
Jueves, 28 Enero 2010, 15:21

Re: Dispositivos USB En Listbox
-----------------------------------
Creo que es porque Arbol está definido en Main y no se le ha pasado a LlenarArbol. No puedo probar ahora (de hecho no debería haberlo mirado siquiera je je) pero prueba a cambiar esto en Main:

[code linenumbers=false syntax=gambas]PUBLIC SUB Form_Open()
Dim Arbol as new treeview(me)
DIM FTemp AS String, Var AS String
me.arrangement=arrange.fill

FTemp = Temp 'crear un nombre de archivo temporal
SHELL ("lsusb >" & fTemp) 'Llenar FTemp con la información requerida
LlenarArbol(fTemp,Arbol) 'Llenar el arbol
KILL FTemp 'borrar el archivo temporal
END[/code]

Y luego la rutina LlenarArbol 
[code linenumbers=false syntax=gambas]PRIVATE SUB LlenarArbol(ftemp AS String, Arbol as treeview)
 DIM F AS file, Linea AS String, Partes AS String[], Clave AS String, Dev AS String, Nombre AS String    
 arbol.Add("Bus 0", System.Host, Stock["16/home"]) 'poner el valor raíz
 
 f = OPEN (ftemp) FOR READ
 f.EndOfLine = gb.Unix
 
 DO WHILE NOT Eof(f)
   LINE INPUT #f, linea 'leer la línea entera
   partes = Split(linea, ":") 'dividirla en tres partes por el :
   clave = Left(partes[0], 7) 'la clave será algo como 'Bus 1'
   insertarbus(clave,Arbol) 'insertar la el bus en el arbol con padre raíz
   Dev = Right(partes[0], 3) 'obtener el dev nº
   Nombre = Mid(partes[2], 5) 'obtener el nombre del dispositivo
   insertardev(dev, nombre, clave,Arbol) 'insertar dispositivo en arbol
 LOOP
 END
 
 PRIVATE SUB insertarbus(Clave AS String, Arbol as treeview)
 TRY arbol.Add(clave, Clave, Stock["16/connect"], "Bus 0")    
 FINALLY
 CATCH

 END
 
 PRIVATE SUB insertardev(dev AS String, nombre AS String, padre AS String, Arbol as treeview)
 TRY arbol.Add(padre & "/" & dev, dev & ": " & nombre, Stock["16/attach"], padre)
 TRY arbol.item.EnsureVisible
 FINALLY
 CATCH
 END [/code]
Es decir, para hacerlo mas legible hice que el treeview se creara solo y entonces hay que pasarlo a las respectivas funciones. Nada mas.

Y seguramente te valdrá. En cualquier caso te vale como ejemplo. Yo he volcado lsusb a un archivo temporal y luego he ido leyendo línea a línea lo que me ha interesado y colocándolo en un treeview. De igual manera puedes hacer un udevinfo o algo así y volcar lo que te convenga. Luego lo revisas línea a línea y te quedas con lo que te convenga.

Un saludo


-----------------------------------
fabianfv
Jueves, 28 Enero 2010, 19:14

Re: Dispositivos USB En Listbox
-----------------------------------
Un par de aspectos a considerar: 

Si se usan comandos externos hay que asegurarse que estén presentes en el sistema y para ello, añadir las dependencias "extra" necesarias al paquete de instalación del proyecto es, probablemente, la mejor opción.

Cuando se consulta información de directorios hay que asegurarse que otras distribuciones usan el mismo directorio o añadir las variantes al proyecto. Por ello, generalmente es mejor usar comandos o una biblioteca.

Saludos cordiales.


-----------------------------------
Pablo-GNU
Jueves, 28 Enero 2010, 23:20

Re: Dispositivos USB En Listbox
-----------------------------------
Soplo, he probado tu codigo y ahora no recibo ningun error, pero tampoco observo nada, solo muestra lo que es mi carpeta home... 

FabianFV, creo que habra que hacerlo con codigo gambas, pero estoy dudoso de los medios, porque por ejemplo, he conseguido hacer con rdir, el listado de los dispositivos que me interesan, pero solo filtrandole el sd, y he probado otro metodo que procedo a explicarte, a ti tambien soplo! jejej.

Yo lo primero que iba a hacer es filtrar todo lo que hay dentro de /sys/block, y aplicar un filtro para que me guarde todas las carpetas menos las loop y las ram, ya que son virtuales y no me sirven, y del resultado de eso, tendria que mirar dentro de las carpetas para poder seleccionar las que me quedo segun el contenido que tenga dentro el fichero "removable" ubicado dentro de las carpetas, EJ: si me quedo sda, sdb y sdc, tendre que mirar el fichero que removable dentro de cada carpeta para poder saber si es hotplug, osea que si el removable dentro de sda y este tiene valor "0" tendre que descartarlo del resultado por ser un disco duro como tal, y si miro dentro de sdb y removable tiene valor "1", debo quedarmelo por se extraible al igual que si lo tuviese sdc. Bueno a donde quiero llegar con esto.. pues facil, los virtuales tambien tienen archivo removable y ese fichero contiene valor "0", por lo tanto no deberia hacer todo lo anterior, deberia hacer solamente el filtro de removable y asi de esa manera guardarlo, asi ya tendria dos filtros hechos...

Bien, el tema es el siguiente... si yo hago lo siguiente:

FOR EACH directorio IN Dir("/sys/block", "[^.]*", gb.Directory)
 
obtendria toda la cadena de directorios? o me equivoco? Pero como puedo hacer la continuacion para que mire el fichero removable dentro de cada uno y guardar el nombre del primer directorio (sdx o hdx) dentro de una variable?

Si resolvemos esto, espero que le sirva a mucha gente, porque a mi ya se me ha convertido en un reto personal, por cierto ya tengo el libro de gambas que me acaba de llegar asique en breves ire escaneando a una muy buena calidad y lo subire. Gracias a todos!


-----------------------------------
soplo
Viernes, 29 Enero 2010, 01:42

Re: Dispositivos USB En Listbox
-----------------------------------
[quote]Soplo, he probado tu codigo y ahora no recibo ningun error, pero tampoco observo nada, solo muestra lo que es mi carpeta home...[/quote]
No se porque al ver esto lo he probado yo también y a veces si sale y a veces no sale. Creo que es por el tiempo. Quizá no le ha dado tiempo a crear el archivo cuando llega la siguiente instrucción y por tanto el archivo está vacío y no hay nada que leer.

Digo yo que será por eso porque otra algunas veces que lo he ejecutado ha salido y otras no. Probablemente le falta un wait a la orden shell.

porque salir si sale

De hecho saca alguna información de lsusb, pero podría sacar mucho mas porque interrogando a udev con el vendor y el idproduct se puede sacar lo que se quiera.


-----------------------------------
Pablo-GNU
Viernes, 29 Enero 2010, 10:14

Re: Dispositivos USB En Listbox
-----------------------------------
Pues yo lo he probado y le he dado varias veces y no me muestra nada, no se ha que se debera, si con udev si le interrogas bien le sacas de todo, pero claro podrias saber si es extraible o no?

[code linenumbers=false syntax=gambas]PUBLIC SUB Button1_Click()
DIM listado AS String
DIM corte AS String[]
DIM Contador AS Integer
DIM ruta AS String[]

SHELL "ls /sys/block" TO listado
corte = Split(listado, gb.NewLine)

FOR Contador = 0 TO corte.Max
ruta[Contador] = "/dev/" & corte[Contador]
NEXT [/code]

END

De momento Con esto he conseguido sacar las subcarpetas presentes en /sys/block, pero el problema que tengo es que al intentar añadirlas a ruta metiendole delante el /dev/ para formar el path del dispositivo fisico (de momento sin filtrar), no consigo sacarlo. Me devuelve error Object Null en la linea de accion dentro del FOR. Sigo investigando... Gracias


-----------------------------------
soplo
Viernes, 29 Enero 2010, 15:56

Re: Dispositivos USB En Listbox
-----------------------------------
[code linenumbers=false syntax=gambas]PUBLIC SUB Form_Open()
Dim Arbol as new treeview(me)
DIM FTemp AS String, Var AS String
me.arrangement=arrange.fill

FTemp = Temp 'crear un nombre de archivo temporal
SHELL ("lsusb >" & fTemp) wait  'Llenar FTemp con la información requerida
LlenarArbol(fTemp,Arbol) 'Llenar el arbol
KILL FTemp 'borrar el archivo temporal
END
[/code]

Y luego la rutina LlenarArbol
[code linenumbers=false syntax=gambas]
PRIVATE SUB LlenarArbol(ftemp AS String, Arbol as treeview)
 DIM F AS file, Linea AS String, Partes AS String[], Clave AS String, Dev AS String, Nombre AS String    
 arbol.Add("Bus 0", System.Host, Stock["16/home"]) 'poner el valor raíz
 
 f = OPEN (ftemp) FOR READ
 f.EndOfLine = gb.Unix
 
 DO WHILE NOT Eof(f)
   LINE INPUT #f, linea 'leer la línea entera
   partes = Split(linea, ":") 'dividirla en tres partes por el :
   clave = Left(partes[0], 7) 'la clave será algo como 'Bus 1'
   insertarbus(clave,Arbol) 'insertar la el bus en el arbol con padre raíz
   Dev = Right(partes[0], 3) 'obtener el dev nº
   Nombre = Mid(partes[2], 5) 'obtener el nombre del dispositivo
   insertardev(dev, nombre, clave,Arbol) 'insertar dispositivo en arbol
 LOOP
 END
 
 PRIVATE SUB insertarbus(Clave AS String, Arbol as treeview)
 TRY arbol.Add(clave, Clave, Stock["16/connect"], "Bus 0")    
 FINALLY
 CATCH

 END
 
 PRIVATE SUB insertardev(dev AS String, nombre AS String, padre AS String, Arbol as treeview)
 TRY arbol.Add(padre & "/" & dev, dev & ": " & nombre, Stock["16/attach"], padre)
 TRY arbol.item.EnsureVisible
 FINALLY
 CATCH
 END [/code]
Ya te dije que solo le faltaba un wait porque si no salía nada era por tiempo.

Y en cuanto a lo de udev una línea de lsusb es esta:
[quote]Bus 006 Device 003: ID 03f0:3e17 Hewlett-Packard [/quote]
Y de ahí sabemos que 03f0 es el vendor y que 3E17 es el idProduct de manera que solo por ver esta línea tenemos subsystem="USB, Vendor="03F0" e IdProduct 3E17 con lo cual se puede obtener la información que se quiera sobre ello entre ella el atributo renovable que será 1 si es renovable y 0 si no lo es. Supongo que la opción mas sencilla si quieres mas información que la que sale del lsusb es mediante udevinfo. También hay información sobre el tamaño del dispositivo y no se cuantas cosas mas.

No estoy nada ducho en eso de reglas udev así que es probable que haya opciones mejores. En cualquier caso toma esto como ejemplo de volcar un comando linux a un archivo y extraer lo que conviene. Ese treeview está sacada únicamente de lo que se ve en un usb. Si luego te quieres ir con esa información a buscar el dispositivo en Udev tendrás toda la información que tenga linux sobre él.

Un ejemplo de interrogar a udev por su lugar
udevinfo -a -n /dev/sdb

Eso así sin mas te sacará toda la información que tenga de ese dispositivo y luego se irá a su dispositivo padre y hará igual y luego al abuelo, ..., etc hasta llegar al dispositivo de la placa que gestiona USB de manera que por poder incluso puedes hacer que al pinchar el usb te salga su dispositivo padre con todos sus datos y al pinchar en él la info del abuelo, ..., etc.
 :lol:  :lol:  :lol:  :lol:  :lol:  :lol: 

[Edito para no responderme a mi mismo]
He estado mirando como encontrar toda la info de un usb interrogando a udev y tal y he llegado a la siguiente conclusión:

1. Averiguar que dispositivos de almacenamiento están montados
[quote]ls /dev/disk/by-uuid -la | grep /sd[/quote]

Pongamos que de alli he sacado tres líneas como estas
[quote]lrwxrwxrwx 1 root root  10 ene 29 21:49 1A608B95608B7673 -> ../../sda1
lrwxrwxrwx 1 root root  10 ene 29 21:49 1d31438e-599e-4d5e-9c48-0d6d76d6ffed -> ../../sda2
lrwxrwxrwx 1 root root  10 ene 29 21:49 4A73-4A71 -> ../../sdb1
[/quote]

Ahora interrogo a udev sobre esos dispositivos (sda1 y sda2 forman parte del dispositivo sda pero probablemente cuesta menos que haga los dos a que quite letra y examine el dispositivo sda que es el que interesa[quote]
udevinfo -a -n /dev/sda1 'para obtener información de /dev/sda1
udevinfo -a -n /dev/sda2 'para obtener información de /dev/sda2
udevinfo -a -n /dev/sdb1 'para obtener información de /dev/sdb1[/quote]
Pongo el resultado de examinar /dev/sdb1
[quote]Udevinfo starts with the device specified by the devpath and then
walks up the chain of parent devices. It prints for every device
found, all possible attributes in the udev rules key format.
A rule to match, can be composed by the attributes of the device
and the attributes from one single parent device.

  looking at device '/block/sdb/sdb1':
    KERNEL=="sdb1"
    SUBSYSTEM=="block"
    DRIVER==""
    ATTR{start}=="8064"
    ATTR{size}=="7815296"
    ATTR{stat}=="      51      103      987      204        0        0        0        0        0      148      204"

  looking at parent device '/block/sdb':
    KERNELS=="sdb"
    SUBSYSTEMS=="block"
    DRIVERS==""
    ATTRS{range}=="16"
    ATTRS{removable}=="1"
    ATTRS{size}=="7823360"
    ATTRS{capability}=="13"
    ATTRS{stat}=="      76      205     2003      308        0        0        0        0        0      196      308"
[/quote]
Es mucho mas largo porque sale desde sdb1 a su padre que es sdb a su abuelo que será el host usb en placa, el bisabuelo que será otro dispositivo en placa, ..., etc, pero los que nos importan son estos dos. El primero es sdb1 y su padre es sdb que es el dispositivo en sí mismo. Allí está la propiedad "removable" que en este caso es 1 con lo que se que estoy ante un dispositivo usb removible y montado.

Si quisiera saber mas podría mirar en /etc/mtab o en /proc/mounts donde habrá una línea como esta
[quote]/dev/sdb1 /home/casa/m vfat rw 0 0[/quote]
de la que obtengo el sistema de ficheros con que está montado el dispositivo y en que directorio está montado, con lo que ya tengo toda la información que el sistema tiene sobre ese dispositivo.

Un poco lioso pero desde el punto de vista informático fácil porque para los humanos andar buscando strings es una lata pero para una máquina es un momento así que todo es volcar esos comandos a un archivo o string y luego buscar la string adecuada. Suena complicado cuando se lee, pero para un ordenador no es nada.

Hay otra forma de hacer esto a traves del vendor e idproduct y también a traves del serial, pero todos vienen a hacer lo mismo porque la información está repartida de esa forma.

Ha estado entretenido esto je je je
 :mryellow:  :mryellow:
[/editado]


-----------------------------------
Pablo-GNU
Sabado, 30 Enero 2010, 09:14

Re: Dispositivos USB En Listbox
-----------------------------------
Tambien me parece un buen metodo, la verdad, sobre todo el udevinfo, pero creo que tienes que tener una version anterior a ubuntu 9.04 o no usar ubuntu, porque udevinfo ha sido reemplazado por udevadm, y el comando se formularia de esta manera:

[code linenumbers=false syntax=gambas]udevadm info --attribute-walk --name /dev/sdg[/code]

Ahora yo quiero preguntarte una cosa y por eso era el tema de usar el /sys/block/, de que manera trata a las pcmcia? Se que estan en desuso, pero en mi trabajo hay portatiles con lector de compact flash por pcmcia y posiblemente usen esas para montar los dispositivos, cambiando tambien de sdx a hdx. Con lo que creo que lsusb no nos devolveria nada respecto a ella, por eso me gusta la parte primera de tu ultimo ejemplo que no usas el lsusb y usas informacion de disco, eso tambien esta muy bien. Y el comando de udevadm esta muy bien porque con guardar todo lo que veas es muy sencillo.

Ademas si por ahorrar filtro, le metes el udevadm a alguno de los dispositivos virtuales, puedes pedir que busque en el resultado presente la linea de removable = "1" tambien y al estar a 0 que la descarte.

SHELL "ls /sys/block" TO listado
corte = Split(listado, gb.NewLine)

Entonces asi tienes ya todos los ramx, loopx. sdx. y hdx. Y con eso ya preguntar directamente a udevadm para poder buscar el removable "1", el que lo tenga "0" a la basura y el que lo tenga a "1", Cojemos su fabricante y modelo y a una variable con la referencia a su dispositivo fisico, que te parece? Es mas corto asi que todo lo que deciamos antes?

EDITO Al igual que tu para no contestarme a mi mismo

He hecho esto...

[code linenumbers=false syntax=gambas]PUBLIC SUB Button1_Click()
DIM salida AS String
DIM direccion AS String[]
DIM Contadordev AS Integer
DIM Contadorrem AS Integer
DIM path AS String[]
DIM removable AS String




SHELL "ls /sys/block" TO salida                     ' ################## SACO EL CONTENIDO DE UNIDADES #################
direccion = Split(salida, gb.NewLine)               ' ################## LISTO LAS UNIDADES SOLAS SIN DEV ##############
path = Split(salida, gb.NewLine)                    ' ################## LISTO LAS UNIDADES PARA AÑADIR DEV ############
direccion.Resize(direccion.Length - 1)
path.Resize(path.Length - 1)

FOR Contadordev = 0 TO path.Max                      ' ##############################################################################
path[Contadordev] = "/dev" &/ path[Contadordev]      ' ############## AÑADO EL /DEV/ A PATH PARA USARLO DE REFERENCIA ###############
NEXT                                                 ' ##############################################################################

removable = Temp
FOR Contadorrem = 0 TO path.Max
SHELL "udevadm info --attribute-walk --name " & path[Contadorrem] & " >>" & removable WAIT 
NEXT 

END[/code]

Entonces saco todos los datos de todos los ficheros que me interesa, Pero me he dado cuenta de que el comando se aplica correctamente, pero no me muestra el nombre de la compact Flash que tengo pinchada en el lector de tarjeta, pero no me muestra el nombre de la Compact Flash, que seria lo interesante, ya que sino me mostraria simpre el Lector y todas sus unidades posibles y no la que realmente tiene pinchada, por eso te decia de hacerlo leyendo ficheros desde /sys/block. Como lo ves?

Seria usar lo siguiente, el lugar de:

[code linenumbers=false syntax=gambas]removable = Temp
FOR Contadorrem = 0 TO path.Max
SHELL "udevadm info --attribute-walk --name " & path[Contadorrem] & " >>" & removable WAIT 
NEXT [/code]

Por esto otro:

[code linenumbers=false syntax=gambas]removable = Temp
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable >>" & removable WAIT 
NEXT [/code]

Y ahora tendriamos que filtrar por los valores que obtenga un "1", y relacionarlos con su correspondiente valor en direccion[] osea el /sdb/ por ejemplo... una vez sacado eso, seria repetir el codigo otra vez pero esta vez que le meta lo que seria el fichero vendor y el device ubicado en /device, pero bueno eso seria mas adelante, una vez resuelto lo anterior, y la verdad es que se me escapa bastante, tu como lo harias? Gracias por hecharme una mano... de verdad...

EDITO 2:

Ahora he probado a hacer lo siguiente:

[code linenumbers=false syntax=gambas]DIM salida AS String
DIM direccion AS String[]
DIM Contadordev AS Integer
DIM Contadorrem AS Integer
DIM path AS String[]
DIM removable AS String
DIM removableleer AS String[]




SHELL "ls /sys/block" TO salida                     ' ################## SACO EL CONTENIDO DE UNIDADES #################
direccion = Split(salida, gb.NewLine)               ' ################## LISTO LAS UNIDADES SOLAS SIN DEV ##############
path = Split(salida, gb.NewLine)                    ' ################## LISTO LAS UNIDADES PARA AÑADIR DEV ############
direccion.Resize(direccion.Length - 1)
path.Resize(path.Length - 1)

FOR Contadordev = 0 TO path.Max                      ' ##############################################################################
path[Contadordev] = "/dev" &/ path[Contadordev]      ' ############## AÑADO EL /DEV/ A PATH PARA USARLO DE REFERENCIA ###############
NEXT                                                 ' ##############################################################################


removable = Temp
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor >>" & removable WAIT   ' ##### AÑADO FABRICANTE A TEMPORAL #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model >>" & removable WAIT    ' ##### AÑADO MODELO A TEMPORAL #########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable >>" & removable WAIT       ' ##### AÑADO REMOVABLE A TEMPORAL #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size >>" & removable WAIT            ' ##### AÑADO TAMAÑO A TEMPORAL #########
NEXT 
removableleer = Split(File.Load(removable), gb.NewLine)
KILL removable[/code]


He probado ha volcaro todos esos valores a un temporal y cargarlos en una array, asi tengo ya toda la salida de valores en gambas, pero claro, tendria que tener una manera de poder filtrarlo ya que, por ejemplo en las virtuales y en las ram no existe vendor y device, de hecho en nada mas que las ram existe dato, que seria el tamaño. Ahora habria que encontrar la manera de filtrarlo... Como lo ves?


-----------------------------------
soplo
Sabado, 30 Enero 2010, 15:21

Re: Dispositivos USB En Listbox
-----------------------------------
Es que tu todo lo haces haciendo un ls a /sys/block y yo creo que eso es un error. Cualqueir dispositivo de disco estará montado y por tanto aparecerá en /etc/mtab o en /proc/mounts o podría estar desmontado pero estar presente en /etcl/fstab.

Así que basta con revisar /etc/mtab lpara ver que dispositivos hay. Te quedas los que no te interesan y preguntas por el resto.
Por ejemplo[code linenumbers=false syntax=bash]
cat /proc/mounts | grep /sd >Dispositivos.txt
cat /proc/mounts | grep /hd >>Dispositivos.txt[/code]
Ahora en Dispositivos.txt tienes todos los /sd y los /hd montados.
Ahora recorres el fichero interrogando a cada uno por si es renovable o no como hemos dicho
udevadm info --attribute-walk --name /dev/xx

Como hemos dicho antes (entiendo que funciona igual que udevinfo) los que montas serán hda1 o sda1 y a tí te interesa el dispositivo padre sda o hda. Miras si es renovable y ya está.

De hecho en /proc/mounts o en /etc/mtab además tienes el sistema de ficheros que tienen esos dispositivos y el directorio donde se montan cosa que veo útil para trabajar con la info que haya en ellos.
 :mryellow:


-----------------------------------
Pablo-GNU
Sabado, 30 Enero 2010, 19:52

Re: Dispositivos USB En Listbox
-----------------------------------
He estado jugando mas con el codigo, el tema es que el dispositivo puede estar montado o no, pero bueno, la mejor manera segun he leido por muchos sitios es leer directamente sobre /sys/block, ya que casi todos los comandos como udevinfo o udevadm leen sobre esos ficheros para sacar los datos.. por eso se recomienda trabajar desde la base. He conseguido filtrarlo aun mas y organizar los datos a leer para que siempre se repitan en una misma manera y descartar ya los virtuales... Te enseño el codigo y el fichero resultante:

[code linenumbers=false syntax=gambas]PUBLIC SUB Button1_Click()
DIM direccion AS String[]
DIM Contadordev AS Integer
DIM Contadorrem AS Integer
DIM path AS String[]
DIM removable AS String
DIM removableleer AS String[]
DIM unidades AS String


unidades = Temp
SHELL "ls /sys/block | grep sd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES SD ##############
SHELL "ls /sys/block | grep hd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES HD ##############
direccion = Split(File.Load(unidades), gb.NewLine)               ' ############ LISTO LAS UNIDADES SOLAS SIN DEV ##############
path = Split(File.Load(unidades), gb.NewLine)                    ' ########### LISTO LAS UNIDADES PARA AÑADIR DEV ############
direccion.Resize(direccion.Length - 1)
path.Resize(path.Length - 1)
KILL unidades

FOR Contadordev = 0 TO path.Max                      ' ##############################################################################
path[Contadordev] = "/dev" &/ path[Contadordev]      ' ############## AÑADO EL /DEV/ A PATH PARA USARLO DE REFERENCIA ###############
NEXT                                                 ' ##############################################################################


removable = Temp
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor >>" & removable WAIT   ' ##### AÑADO FABRICANTE A TEMPORAL #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model >>" & removable WAIT    ' ##### AÑADO MODELO A TEMPORAL #########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable >>" & removable WAIT       ' ##### AÑADO REMOVABLE A TEMPORAL #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size >>" & removable WAIT            ' ##### AÑADO TAMAÑO A TEMPORAL #########
NEXT 
removableleer = Split(File.Load(removable), gb.NewLine)
removableleer.Resize(removableleer.Length - 1)
KILL removable
END
[/code]

Ahora te adjunto una imagen de como se ve el pantallazo, de manera detallada:

 [img]http://foro.gambas-es.org/files/images/549/arrays.jpg[/img] 

Como puedes ver, el indice 0 del array direccion se corresponde con los valores de los indices 0 a 3 del array removableleer. Entonces como puedo hacer que un Listbox liste los valores de esta manera, siempre y cuando el valor de Removable sea "1":

Fabricante & Dispositivo & Tamaño & Unidad.

Y si yo lo selecciono, haga la referencia correcta al dispositivo fisico que le corresponda segun la array direccion. Joe que lio.. espero haberme explicado bien... Es que la verdad, no se como trabajar bien con las arrays, me hago un poco de confusion y aun no controlo todas las opciones de un for y demas... te agradezco toda tu ayuda... gracias...


-----------------------------------
soplo
Sabado, 30 Enero 2010, 20:53

Re: Dispositivos USB En Listbox
-----------------------------------
Yo creo que tienes un error en esto:
[code linenumbers=false syntax=gambas]removable = Temp
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor >>" & removable WAIT   ' ##### AÑADO FABRICANTE A TEMPORAL #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model >>" & removable WAIT    ' ##### AÑADO MODELO A TEMPORAL #########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable >>" & removable WAIT       ' ##### AÑADO REMOVABLE A TEMPORAL #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size >>" & removable WAIT            ' ##### AÑADO TAMAÑO A TEMPORAL #########
NEXT
removableleer = Split(File.Load(removable), gb.NewLine)
removableleer.Resize(removableleer.Length - 1)
KILL removable[/code]
Bueno, no es que esté mal pero grabas varios registros de un mismo dispositivo lo cual te complica todo a la hora de trabajarlo posteriormente.
así que yo haría lo siguiente:
[code linenumbers=false syntax=gambas]Dim Vendedor as string, Modelo as string, Reno as string, Tamano as long
Dim F as file

...
...
...

removable = Temp
f=open removable for create
f.endofline=gb.unix
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor >>" & removable to Vendedor ' ##### METO EL FABRICANTE EN UNA VARIABLE Vendedor #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model >>" & removable to Modelo  ' ##### AÑADO MODELO A una variable Modelo #########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable >>" & removable to Reno    ' ##### AÑADO REMOVABLE A UNA VARIABLE Reno #####
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size >>" & removable To Tamano           ' ##### AÑADO TAMAÑO A VARIABLE TAMANO #########
print #f, direccion[Contadorrem];;Vendedor;;Modelo;;renovable;;tamano 'grabar info en archivo
NEXT
close #f[/code]

y así obtienes un fichero que tiene dirección,vendedor, producto, renovable si/no,tamaño separados por espacios
A partir de ahí meterlo donde quieras u ordenarlo o lo que sea no tiene ningún problema. Por ejemplo meterlo en un list
[code linenumbers=false syntax=gambas]F=open removable for input
do while not eof(f)
   input #f,Direccion, Vendedor,Modelo, Reno, Tamano
   list1.add(Direccion & (" & Vendedor & ":" & Modelo & ") " & tamano /1024 & "K" & iif(Renovable="1","Sí","No")
loop
close #f
kill removable[/code]


-----------------------------------
Pablo-GNU
Sabado, 30 Enero 2010, 22:47

Re: Dispositivos USB En Listbox
-----------------------------------
Hola soplo, tu ultima aclaracion es bastante buena, la verdad es que simplificaria bastante la forma de trabajar... pero al probarlo le encuentro un problema, las salidas del terminal no las guarda en las variables. He parado el programa en cada paso que da al hacer el cat, pero en las variables a las que envias con el TO la salida, no contienen nada dentro... Miro a ver que le encuentro... Luego he cambiado un poco el tema de listarlo para verlo como a mi me interesaria, y tengo un fallo de Variables, me devuelve que espera un Wanted String[], got String instead. Y la variable de Tamano tambien he tenido que cambiartela al tipo String.

EDITO

Lo de las variables lo he solucionado y he modificado el print para que lo ordene un poco mejor ya que juntaba direccion con vendor sin salto de linea entre ellos. Pero no resuelvo el tipo de variable... que te parece la modificacion?

[code linenumbers=false syntax=gambas]removable = Temp
f = OPEN removable FOR CREATE
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor" WAIT TO Vendedor ' ##### METO EL FABRICANTE EN UNA VARIABLE Vendedor #####"
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model" WAIT TO Modelo  ' ##### AÑADO MODELO A una variable Modelo #########"
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable" WAIT TO Reno    ' ##### AÑADO REMOVABLE A UNA VARIABLE Reno #####"
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size" WAIT TO Tamano           ' ##### AÑADO TAMAÑO A VARIABLE TAMANO #########
PRINT #f, direccion[Contadorrem] & "\n" & Vendedor; Modelo; Tamano; Reno 'grabar info en archivo
NEXT
CLOSE #f


f = OPEN removable FOR INPUT 
DO WHILE NOT Eof(f)
   INPUT #f, direccion; Vendedor; Modelo; Tamano; Reno
   list1.add(direccion & Vendedor & Modelo & (Tamano / 2 / 1024) & "K" & IIf(Reno = "1", "Si", "No"))
LOOP
CLOSE #f
KILL removable[/code]


-----------------------------------
fabianfv
Domingo, 31 Enero 2010, 00:07

Re: Dispositivos USB En Listbox
-----------------------------------
Pablo, quita la cláusula WAIT de las sentencias EXEC.


-----------------------------------
Pablo-GNU
Domingo, 31 Enero 2010, 00:19

Re: Dispositivos USB En Listbox
-----------------------------------
Fabianfv, no tengo ninguna sentencia EXEC, tengo todas SHELL, tambien me recomiendas quitarlas? Porque? Te pregunto porque asi aprendo.. jejeje. Muchas gracias y lo dicho, espero que esto sirva para mas gente, porque se esta haciendo eterna... siento que sea tan larga...


-----------------------------------
fabianfv
Domingo, 31 Enero 2010, 01:03

Re: Dispositivos USB En Listbox
-----------------------------------
Pruébalo. Hace unos meses tuve ese problema, no obtenía la salida del comando (SHELL o EXEC, da igual) y sólo al quitar la cláusula WAIT pude obtenerla. No encuentro una razón para explicar ese comportamiento, excepto que se tratara de un bug de Gambas. Si mal no recuerdo la versión que usaba en ese momento era la 2.15 o 2.16.

Por otro lado ¿por qué necesitas la cláusula WAIT para ejecutar "cat"? ¿supones que esos archivos pueden ser muy grandes y por tanto sea necesaria una ejecución síncrona?

Edición:

Tengo pendiente escribir una rutina que realice un reconocimiento de los dispositivos de almacenamiento conectados al sistema y que obtenga otra información complementaria, pero no tenía planeado hacerlo hasta dentro de al menos un mes. Veré si puedo adelantarlo para la próxima semana así intercambiamos las posibles soluciones.


-----------------------------------
Pablo-GNU
Domingo, 31 Enero 2010, 10:37

Re: Dispositivos USB En Listbox
-----------------------------------
El problema no pasaba por el wait, pasaba porque se redireccionaban los datos desde el terminal y desde gambas al mismo fichero y no podia capturar la salida, pero eso esta arreglado, daba igual que hubiese un wait puesto, de todos modos sigo tu consejo y lo he quitado. Mira, al terminar de hacer el fichero, soplo tambien me paso un codigo para listar el fichero en un Listbox, pero me da errores de variable. Te adjunto el codigo para que lo mires porque no se por donde van los tiros, te agradeceria que me explicases el fallo asi lo termino de comprender, porque no lo encuentro el problema. Desde ya gracias.

[code linenumbers=false syntax=gambas]PUBLIC SUB Button1_Click()
DIM direccion AS String[]
DIM Contadordev AS Integer
DIM Contadorrem AS Integer
DIM path AS String[]
DIM removable AS String
DIM removableleer AS String[]
DIM unidades AS String
DIM Vendedor AS String
DIM Modelo AS String
DIM Reno AS String
DIM Tamano AS String
DIM f AS File



unidades = Temp
SHELL "ls /sys/block | grep sd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES SD ##############
SHELL "ls /sys/block | grep hd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES HD ##############
direccion = Split(File.Load(unidades), gb.NewLine)               ' ############ LISTO LAS UNIDADES SOLAS SIN DEV ##############
path = Split(File.Load(unidades), gb.NewLine)                    ' ############ LISTO LAS UNIDADES PARA AÑADIR DEV ############
direccion.Resize(direccion.Length - 1)
path.Resize(path.Length - 1)
KILL unidades

FOR Contadordev = 0 TO path.Max                      ' ##############################################################################
path[Contadordev] = "/dev" &/ path[Contadordev]      ' ############## AÑADO EL /DEV/ A PATH PARA USARLO DE REFERENCIA ###############
NEXT                                                 ' ##############################################################################

removable = Temp
f = OPEN removable FOR CREATE
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor" TO Vendedor ' ######## METO EL FABRICANTE EN UNA VARIABLE Vendedor ########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model" TO Modelo    ' ######## AÑADO MODELO A una variable Modelo #################
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable" TO Reno         ' ######## AÑADO REMOVABLE A UNA VARIABLE Reno ################
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size" TO Tamano            ' ######## AÑADO TAMAÑO A VARIABLE TAMANO #####################
PRINT #f, direccion[Contadorrem] & "\n" & Vendedor; Modelo; Tamano; Reno        ' ######## AÑADIR TODO A ARCHIVO ##############################
NEXT
CLOSE #f


f = OPEN removable FOR INPUT 
DO WHILE NOT Eof(f)
INPUT #f, direccion; Vendedor; Modelo; Tamano; Reno
   list1.add(direccion & Vendedor & Modelo & (Tamano / 2 / 1024) & "K" & IIf(Reno = "1", "Si", "No"))
LOOP
CLOSE #f
KILL removable


END[/code]


-----------------------------------
soplo
Domingo, 31 Enero 2010, 18:44

Re: Dispositivos USB En Listbox
-----------------------------------
Hola
Shell admite dos formatos distintos e incompatibles entre sí.
[quote][ Process = ] SHELL Command [ WAIT ] [ FOR { { READ | INPUT } | { WRITE | OUTPUT } } ] [ AS Name ]

SHELL Command TO Variable[/quote]

De manera que si utilizara TO no podría usar WAIT.
[url=http://gambasdoc.org/help/lang/shell?es]Shell 

A modo de información añado que en el primer formato devuelve un objeto process que tiene sus propios eventos y métodos.

Por último utilizar exec en vez de shell es mas rápido y ocupa menos memoria porque shell hace lo mismo pero invocando a bash para hacerlo. Es decir shell llama a bash o sh o ksh o el que sea y le pasa el string a ejecutar. Exec directamente ejecuta el comando.

Respecto al problema de las variables que dices veo que la variable que se pone tras el TO debe ser string.

 :mryellow:


-----------------------------------
Pablo-GNU
Domingo, 31 Enero 2010, 19:15

Re: Dispositivos USB En Listbox
-----------------------------------
Creo que el problema estaba mas bien en las variables que utilizabamos para el DO, que no podian ser las mismas que para el FOR. Ahora ya esta, ya lista los dispositivos de manera correcta, he tenido que corregir el problema de caracteres en blanco ya que afectaba a la hora de leer del F. Que ta parece? Solo nos queda el hacer el combobox al seleccionar el valor, por ejemplo, pendrive 4GB, nos devuelva a una variable su direccion correspondiente. He pensado en hacer que al volcar los datos al combobox y sobrevivir al filtro de si son desmontables o no, tambien guarde la direccion en una array, entonces al seleccionar el list[2], nos apunte al valor 2 del array, asi al estar alineados, se correspondan tambien... tu que crees? Saludos y gracias, ya va quedando menos!!!!

[code linenumbers=false syntax=gambas]PUBLIC SUB Button1_Click()
DIM direccion AS String[]
DIM Contadordev AS Integer
DIM Contadorrem AS Integer
DIM path AS String[]
DIM removable AS String
DIM removableleer AS String[]
DIM unidades AS String
DIM Vendedor AS String
DIM Modelo AS String
DIM Reno AS String
DIM Tamano AS String
DIM dire AS String
DIM Vende AS String
DIM Mode AS String
DIM Re AS String
DIM Tama AS Float
DIM f AS File


ComboBox1.Clear
unidades = Temp
SHELL "ls /sys/block | grep sd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES SD ##############
SHELL "ls /sys/block | grep hd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES HD ##############
direccion = Split(File.Load(unidades), gb.NewLine)               ' ############ LISTO LAS UNIDADES SOLAS SIN DEV ##############
path = Split(File.Load(unidades), gb.NewLine)                    ' ############ LISTO LAS UNIDADES PARA AÑADIR DEV ############
direccion.Resize(direccion.Length - 1)
path.Resize(path.Length - 1)
KILL unidades

FOR Contadordev = 0 TO path.Max                      ' ##############################################################################
path[Contadordev] = "/dev" &/ path[Contadordev]      ' ############## AÑADO EL /DEV/ A PATH PARA USARLO DE REFERENCIA ###############
NEXT                                                 ' ##############################################################################

removable = Temp
f = OPEN removable FOR CREATE
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor" TO Vendedor ' ######## METO EL FABRICANTE EN UNA VARIABLE Vendedor ########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model" TO Modelo    ' ######## AÑADO MODELO A una variable Modelo #################
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable" TO Reno         ' ######## AÑADO REMOVABLE A UNA VARIABLE Reno ################
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size" TO Tamano            ' ######## AÑADO TAMAÑO A VARIABLE TAMANO #####################
Vendedor = Trim(Vendedor)
Modelo = Replace(Trim$(Modelo), " ", "")
Reno = Trim(Reno)
Tamano = Trim(Tamano)
PRINT #f, direccion[Contadorrem];; Vendedor;; Modelo;; Tamano;; Reno        ' ######## AÑADIR TODO A ARCHIVO ##############################
NEXT
CLOSE #f

f = OPEN removable FOR INPUT                         ' ####################### LOOP PARA INTRODUCIR VALOR A COMBOBOX ###########################
DO WHILE NOT Eof(f)
INPUT #f, dire; Vende; Mode; Tama; Re
   IF Re = "1" THEN
   ComboBox1.Add(Vende & " " & Mode & " Capacidad: " & (Round((Tama / 2048), 2)) & " Mb")
   ENDIF
LOOP  
CLOSE #f
KILL removable

END[/code]

EDITO:

Mira si queda menos, que de momento ya esta!! Os pego el codigo para ver si lo veis bien o le veis algun fallo, ya que ahora que funciona, si se optimiza o se queda asi, lo pegare en la seccion de Aplicaciones/Fragmento de codigo, para que si alguien lo necesita lo pueda utilizar. Muchas gracias a todos, os habeis portado muy bien conmigo... Nos seguimos hablando y viendo por aqui... para lo que necesiteis, aqui estoy... gracias..

[code linenumbers=false syntax=gambas]
PUBLIC SUB Button1_Click()
DIM direccion AS String[]
DIM Contadordev AS Integer
DIM Contadorrem AS Integer
DIM path AS String[]
DIM removable AS String
DIM removableleer AS String[]
DIM unidades AS String
DIM Vendedor AS String
DIM Modelo AS String
DIM Reno AS String
DIM Tamano AS String
DIM dire AS String
DIM Vende AS String
DIM Mode AS String
DIM Re AS String
DIM Tama AS Float
DIM f AS File


ComboBox1.Clear
unidades = Temp
SHELL "ls /sys/block | grep sd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES SD ##############
SHELL "ls /sys/block | grep hd >> " & unidades WAIT              ' ############ SACO EL CONTENIDO DE UNIDADES HD ##############
direccion = Split(File.Load(unidades), gb.NewLine)               ' ############ LISTO LAS UNIDADES SOLAS SIN DEV ##############
path = Split(File.Load(unidades), gb.NewLine)                    ' ############ LISTO LAS UNIDADES PARA AÑADIR DEV ############
direccion.Resize(direccion.Length - 1)
path.Resize(path.Length - 1)
KILL unidades

removable = Temp
f = OPEN removable FOR CREATE
FOR Contadorrem = 0 TO direccion.Max
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/vendor" TO Vendedor ' ######## METO EL FABRICANTE EN UNA VARIABLE Vendedor ########
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/device/model" TO Modelo    ' ######## AÑADO MODELO A una variable Modelo #################
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/removable" TO Reno         ' ######## AÑADO REMOVABLE A UNA VARIABLE Reno ################
SHELL "cat /sys/block/" & direccion[Contadorrem] & "/size" TO Tamano            ' ######## AÑADO TAMAÑO A VARIABLE TAMANO #####################
Vendedor = Trim(Vendedor)
Modelo = Replace(Trim$(Modelo), " ", "")
Reno = Trim(Reno)
Tamano = Trim(Tamano)
PRINT #f, direccion[Contadorrem];; Vendedor;; Modelo;; Tamano;; Reno        ' ######## AÑADIR TODO A ARCHIVO ##############################
NEXT
CLOSE #f

f = OPEN removable FOR INPUT                         ' ####################### LOOP PARA INTRODUCIR VALOR A COMBOBOX ###########################
DO WHILE NOT Eof(f)
INPUT #f, dire; Vende; Mode; Tama; Re
   IF Re = "1" THEN
   ComboBox1.Add(Vende & " " & Mode & " Capacidad: " & (Round((Tama / 2048), 2)) & " Mb" & " " & dire)
   ENDIF
LOOP  
CLOSE #f
KILL removable

END

PUBLIC SUB ComboBox1_Click()
DIM ar AS String
DIM edit AS File
DIM a AS String
DIM b AS String
DIM c AS String
DIM d AS String
DIM e AS String
DIM local AS String

ar = Temp
edit = OPEN ar FOR CREATE 
PRINT #edit, ComboBox1.Text
CLOSE #edit

edit = OPEN ar FOR INPUT 
INPUT #edit, a; b; c; d; e; local
unidad.Text = local
unipath.Text = "/dev/" & local
CLOSE #edit
KILL ar

END[/code]


-----------------------------------
fabianfv
Lunes, 01 Febrero 2010, 21:32

Re: Dispositivos USB En Listbox
-----------------------------------
[quote]
EDITO:
Mira si queda menos, que de momento ya esta!! Os pego el codigo para ver si lo veis bien o le veis algun fallo, ya que ahora que funciona, si se optimiza o se queda asì
[/quote]

Sí que se puede optimizar, pero lo primero es determinar el objetivo de esa optimización.

Para optimizar el código para facilitar su mantenimiento te sugiero empezar con estas tareas:

[list]
[*]Usa sangrías (indentación) para mostrar el nivel de anidamiento.
[*]Quita los símbolos # de los comentarios porque dificultan la lectura del código.
[*]Deja únicamente los comentarios que sean pertinentes (lo que no sea evidente al leer el código).
[*]Usa nombres completos para los nombres de las variables con el estilo [b]YoSoyUnaVariable[/b].
[*]Parece haber variables duplicadas en el código, revísalas y elimina las que efectivamente estén duplicadas.
[*]Revisa que los nombres de variables sean apropiados para lograr que el código sea autoexplicativo.
[/list]

Bien, esto para empezar. Si quieres luego seguimos con más.

Saludos cordiales.


-----------------------------------
soplo
Miercoles, 03 Febrero 2010, 21:09

Re: Dispositivos USB En Listbox (SOLUCIONADO)
-----------------------------------
Yo creo que podrías hacer una clase con ese software de tal forma que tuvieras con un único método ObtenerUsb y que tuviera un parámetro true o false.

Si es true te devuelve los usb montados. Si es false te devuelve todos los usb del sistema.

De esa forma en tus aplicaciones con solo incluir esa clase podrías llamar a ese método y obtener un array con todos los usb que quieres bien para meterlos en un combo o para hacer con ellos lo que quieras.

Si decides hacerlo asegúrate de que borras los temporales que creaste para dejar el sistema limpio.

Es una sugerencia nada mas.
 :mryellow:


