Controlliamo USB/IP

Spesso ci si trova di fronte alla necessità di collegare un dispositivo USB a un PC remoto tramite una rete locale. Qui sotto troverete la mia storia di ricerca in questo ambito, con il percorso verso una soluzione pronta basata su un progetto open-source. USB/IP con una descrizione degli ostacoli che diverse persone hanno incontrato lungo il cammino, e dei modi per superarli.

Parte prima, storica

Se la macchina è virtuale, tutto questo è abbastanza semplice. La funzionalità di inoltro USB dall'host alla virtual machine è disponibile fin dalla versione 4.1 di VMWare. Ma nel mio caso, la chiave di protezione, identificata come WIBU-KEY, doveva essere collegata a diverse macchine in momenti diversi, non solo virtuali.
Il primo passo della mia ricerca nel lontano 2009 mi ha portato a un dispositivo chiamato TrendNet TU2-NU4
Vantaggi:

  • a volte funziona

Contro:

  • non sempre funziona. Ad esempio, la chiave di protezione Guardant Stealth II non si avvia attraverso di essa, restituendo l'errore "il dispositivo non può essere avviato".
  • Il software per la gestione (leggi - montaggio e smontaggio di dispositivi USB) è estremamente scarso. Comandi da riga di comando, automazione - no, non ne abbiamo sentito parlare. Tutto deve essere fatto manualmente. Un incubo.
  • Il software di gestione cerca l'hardware nella rete tramite broadcasting, quindi funziona solo all'interno di un segmento di broadcast. Non è possibile inserire manualmente l'indirizzo IP dell'hardware. L'hardware è in un'altra sottorete? Allora hai un problema.
  • Gli sviluppatori hanno abbandonato il dispositivo, inviare report di bug è inutile.

Il secondo capitolo è avvenuto in un'epoca più recente e mi ha portato al tema di questo articolo — progetto USB/IP. Attira per la sua apertura, soprattutto perché i ragazzi di ReactOS hanno firmato un driver per Windows, quindi ora funziona tutto anche su x64 senza alcun tipo di workaround come la modalità test. A cui un enorme grazie al team di ReactOS! Suona tutto bello, proviamo a vedere se è così anche nella pratica? Purtroppo, il progetto stesso è stato un po' trascurato e non ci si può aspettare supporto — ma dove non c'è, c'è sempre una soluzione, abbiamo il codice sorgente, ce la caveremo!

Parte due, lato server Linux

Il server USB/IP, che condivide dispositivi USB sulla rete, può essere avviato solo su sistemi operativi basati su Linux. Bene, Linux sia, installiamo su una macchina virtuale Debian 8 in configurazione minima, seguendo la procedura standard:

sudo apt-get update
sudo apt-get upgrade
sudo apt-get install usbip

Installati. Poi Internet ci suggerisce di caricare il modulo usbip, ma — buongiorno, i primi ostacoli. Non esiste alcun modulo. Il problema è che la maggior parte delle guide in rete si riferisce a una versione più vecchia 0.1.x, mentre nell'ultima 0.2.0 i moduli usbip hanno nomi diversi.

Quindi:

sudo modprobe usbip-core
sudo modprobe usbip-host
sudo lsmod | grep usbip

Aggiungiamo nel /etc/modules le seguenti righe, in modo da caricarli automaticamente all'avvio del sistema:

usbip-core
usbip-host
vhci-hcd

Avviamo il server usbip:

sudo usbipd -D

Inoltre, la rete ci informa che insieme a usbip ci sono degli script che ci permettono di gestire il server — mostrare quale dispositivo sarà condiviso in rete, controllare lo stato, e così via. Qui ci aspetta un altro attrezzo da giardino: questi script nella versione 0.2.x, di nuovo, sono stati rinominati. Per ottenere un elenco dei comandi, possiamo usare

sudo usbip

Dopo aver letto la descrizione dei comandi, diventa chiaro che per condividere il dispositivo USB richiesto, usbip vuole conoscere il suo Bus ID. Carissimi spettatori, sul palco arrivano i terzi ostacoli: quel Bus ID, che ci darà lsusb (sembrerebbe il modo più ovvio) — non è adatto! Il fatto è che dispositivi come gli hub USB vengono ignorati da usbip. Quindi, useremo il comando integrato:

user@usb-server:~$ sudo usbip list -l
 - busid 1-1 (064f:0bd7)
   WIBU-Systems AG : BOX/U (064f:0bd7)

Nota: qui e nei prossimi elenchi descriverò tutto usando il mio specifico dispositivo USB. I nomi dei vostri dispositivi e la coppia VID:PID possono e saranno diversi. Il mio si chiama Wibu-Systems AG: BOX/U, VID 064F, PID 0BD7.

Ora possiamo condividere il nostro dispositivo:

user@usb-server:~$ sudo usbip bind --busid=1-1
usbip: info: bind device on busid 1-1: complete

Evviva, compagni!

user@usb-server:~$ sudo usbip list -r localhost
Device USB esportabili
======================
 - localhost
        1-1: WIBU-Systems AG : BOX/U (064f:0bd7)
           : /sys/devices/pci0000:00/0000:00:11.0/0000:02:00.0/usb1/1-1
           : Classe specifica del venditore / sottoclasse sconosciuta / protocollo sconosciuto (ff/00/ff)

Tre volte evviva, compagni! Il server ha condiviso il dispositivo in rete e possiamo collegarlo! Non resta che aggiungere l'avvio automatico del demone usbip in /etc/rc.local

usbipd -D

Parte tre, cliente e ingarbugliata

Ho provato a collegare il dispositivo condiviso in rete alla macchina con Debian immediatamente sullo stesso server, e tutto si è collegato perfettamente:

sudo usbip attach --remote=localhost --busid=1-1

Passiamo a Windows. Nel mio caso si trattava di Windows Server 2008R2 Standard Edition. La guida ufficiale chiede di installare prima il driver. La procedura è ben descritta nel readme allegato al client di Windows, seguendo le istruzioni tutto funziona. Funziona anche su XP senza alcuna difficoltà.

Dopo aver estratto il client, proviamo a montare la nostra chiavetta:

C:Program FilesUSB-IP>usbip -a %server-ip% 1-1
usbip err: usbip_network.c: 121 (usbip_recv_op_common) recv op_common, -1
usbip err: usbip_windows.c: 756 (query_interface0) recv op_common
usbip err: usbip_windows.c: 829 (attach_device) impossibile trovare il dispositivo

Oh-oh. Qualcosa è andato storto. Utilizziamo la nostra abilità di ricerca su Google. Ci sono alcune menzioni sparse che qualcosa non funziona con le costanti, nella parte del server gli sviluppatori hanno cambiato la versione del protocollo passando alla 0.2.0, ma nel client per Windows si sono dimenticati di farlo. La soluzione proposta è cambiare la costante nel codice sorgente e ricompilare il client.

Non voglio proprio scaricare Visual Studio per questa procedura. Tuttavia, ho il vecchio Hiew. Nel codice sorgente la costante è dichiarata come word doppio. Cerchiamo nel file 0x00000106, sostituendo con 0x00000111. Non dimentichiamo, l'ordine dei byte è inverso. Risultato — due corrispondenze, patchiamo:

[usbip.exe]
00000CBC: 06 11
00000E0A: 06 11

Eeeee… sì!

C:Program FilesUSB-IP>usbip -a %server-ip% 1-1
nuovo dispositivo USB collegato alla porta usbvbus 1

Qui si potrebbe concludere il racconto, ma la musica non durò a lungo. Dopo aver riavviato il server, ho scoperto che il dispositivo sul client non si monta!

C:Program FilesUSB-IP>usbip -a %server-ip% 1-1
usbip err: usbip_windows.c: 829 (attach_device) impossibile trovare il dispositivo

E basta. Neanche il onnisciente Google ha potuto darmi una risposta. Tuttavia, il comando per visualizzare i dispositivi disponibili sul server mostra correttamente — ecco la chiave, puoi montarla. Provo a montarla da Linux — funziona! E se adesso provo da Windows? Oh orrore — funziona!

Ultimo inconveniente: c'è qualcosa nel codice del server che non è stato completato. Durante la condivisione del dispositivo, non legge il numero di USB descriptor. Ma quando il dispositivo viene montato da Linux, questo campo viene riempito. Purtroppo, conosco lo sviluppo su Linux solo a livello di «make && make install». Quindi, ho risolto il problema con un hack piuttosto goffo — aggiungendo a /etc/rc.local.

usbip attach --remote=localhost --busid=1-1
usbip port
usbip detach --port=00

Parte finale

Dopo qualche tribolazione, ora funziona. L'oggetto desiderato è stato ottenuto, e ora la chiave può essere montata su qualsiasi PC (e smontata, ovviamente) anche al di fuori del segmento broadcast della rete. Se lo si desidera, è possibile farlo utilizzando uno script della shell. La cosa bella è che è completamente gratuito.
Spero che la mia esperienza aiuti gli utenti di Habrahabr a evitare gli stessi errori che ho commesso io. Grazie per l'attenzione!

Fonte: habr.com

Acquista hosting affidabile per siti web con protezione DDoS, VPS VDS server 🔥 Acquista hosting affidabile per siti web con protezione DDoS, VPS VDS server | ProHoster