Aprire una finestra su un display X remoto (perché "Impossibile aprire il display")?


81

C'era una volta,

DISPLAY=:0.0 totem /path/to/movie.avi

dopo averlo visto sul mio desktop dal mio laptop, il totem sarebbe stato riprodotto movie.avisul mio desktop.

Ora dà l'errore:

No protocol specified
Cannot open display:

Ho reinstallato Debian Squeeze quando è diventato stabile su entrambi i computer e immagino di aver rotto la configurazione.

Ho cercato su Google su questo, e non posso per la mia vita capire cosa dovrei fare.

(VLC ha un'interfaccia HTTP che funziona, ma non è conveniente come ssh.)

Lo stesso problema si presenta quando provo ad eseguirlo da un cron job.


1
La tua macchina remota mostra un file .Xauthority? L'altra domanda ovvia è: il tuo server ssh e il tuo client sono configurati per consentire l'inoltro X? Quale comando hai usato per ssh?
Faheem Mitha,

1
sto cercando di inoltrare X? Voglio che il comando sia eseguito sull'host, non sul client. Il mio comando ssh è solo ssh me @ host individuare. L'autorizzazione sul computer host non corrisponde ad alcun file.
Justin Cress,

Come Faheem suggerisce, c'è un buon cambiamento nel fatto che il tuo problema è dovuto al fatto di totemnon trovare il tuo cookie X e devi impostare XAUTHORITYil valore corretto, cioè il valore nella tua sessione normale sul desktop. Leggi Linux: wmctrl non può aprire il display quando la sessione viene avviata tramite ssh + screen per alcuni background; vedi anche la risposta correlata Come root posso lanciare un programma grafico sul desktop di un altro utente? .
Gilles,

1
va bene, fisicamente seduto al computer e digitando echo $ XAUTHORITY dà / var / run / gdm3 / auth-for-jcress-bb32gX / database nella sessione ssh, digitando echo $ DISPLAY = (il percorso sopra) non risolve il problema
justin cress,

1
Do la colpa GDM3, perché non avrebbero potuto appena tenuto $XAUTHORITYa ~/.Xauthoritycome tutti si aspettano che sia.
Arrowmaster,

Risposte:


78

(Adattato da Linux: wmctrl non può aprire il display quando la sessione viene avviata tramite ssh + screen )

DISPLAY e AUTORITÀ

Un programma X necessita di due informazioni per connettersi a un display X.

  • Ha bisogno dell'indirizzo del display, che in genere è :0quando si è connessi localmente o :10, :11ecc. Quando si è effettuato l'accesso in remoto (ma il numero può cambiare a seconda di quante connessioni X sono attive). L'indirizzo del display è normalmente indicato nella DISPLAYvariabile d'ambiente.

  • Ha bisogno della password per il display. Le password di visualizzazione X sono chiamate cookie magici . I cookie magici non sono specificati direttamente: sono sempre memorizzati in file di autorità X, che sono una raccolta di record del modulo "display :42has cookie 123456". Il file di autorità X viene normalmente indicato nella XAUTHORITYvariabile di ambiente. Se $XAUTHORITYnon impostato, i programmi usano ~/.Xauthority.

Stai tentando di agire sulle finestre visualizzate sul desktop. Se sei l'unica persona che utilizza il tuo computer desktop, è molto probabile che il nome visualizzato sia :0. Trovare la posizione del file di autorità X è più difficile, perché con gdm come impostato in Debian squeeze o Ubuntu 10.04, si trova in un file con un nome generato casualmente. (Non hai mai avuto problemi prima perché le versioni precedenti di gdm utilizzavano l'impostazione predefinita, ovvero i cookie memorizzati ~/.Xauthority.)

Ottenere i valori delle variabili

Ecco alcuni modi per ottenere i valori di DISPLAYe XAUTHORITY:

  • È possibile avviare sistematicamente una sessione dello schermo dal desktop, magari automaticamente negli script di accesso (da ~/.profile; ma farlo solo se si accede in X: test se DISPLAYè impostato su un valore che inizia con :(che dovrebbe coprire tutti i casi che è probabile Incontrare)). In ~/.profile:

    case $DISPLAY in
      :*) screen -S local -d -m;;
    esac
    

    Quindi, nella sessione ssh:

    screen -d -r local
    
  • È inoltre possibile salvare i valori di DISPLAYe XAUTHORITYin un file e richiamare i valori. In ~/.profile:

    case $DISPLAY in
      :*) export | grep -E '(^| )(DISPLAY|XAUTHORITY)=' >~/.local-display-setup.sh;;
    esac
    

    Nella sessione ssh:

    . ~/.local-display-setup.sh
    screen
    
  • È possibile rilevare i valori di DISPLAYe XAUTHORITYda un processo in esecuzione. Questo è più difficile da automatizzare. Devi capire il PID di un processo collegato al display su cui vuoi lavorare, quindi ottenere le variabili d'ambiente da /proc/$pid/environ( eval export $(</proc/$pid/environ tr \\0 \\n | grep -E '^(DISPLAY|XAUTHORITY)=')¹).

Copia dei cookie

Un altro approccio (a seguito di un suggerimento di Arrowmaster ) è di non cercare di ottenere il valore di $XAUTHORITYnella sessione ssh, ma piuttosto di fare in modo che la sessione X copi i suoi cookie ~/.Xauthority. Poiché i cookie vengono generati ogni volta che accedi, non è un problema se mantieni i valori non aggiornati ~/.Xauthority.

Può esserci un problema di sicurezza se la tua home directory è accessibile tramite NFS o altri file system di rete che consente agli amministratori remoti di visualizzarne i contenuti. Dovrebbero comunque connettersi al tuo computer in qualche modo, a meno che tu non abbia abilitato le connessioni X TCP (Debian le ha disattivate di default). Quindi, per la maggior parte delle persone, questo non si applica (nessun NFS) o non è un problema (nessuna connessione X TCP).

Per copiare i cookie quando si accede alla sessione X del desktop, aggiungere le seguenti righe a ~/.xprofileo ~/.profile(o qualche altro script letto al momento dell'accesso):

case $DISPLAY:$XAUTHORITY in
  :*:?*)
    # DISPLAY is set and points to a local display, and XAUTHORITY is
    # set, so merge the contents of `$XAUTHORITY` into ~/.Xauthority.
    XAUTHORITY=~/.Xauthority xauth merge "$XAUTHORITY";;
esac

¹ In linea di principio, questo non ha una quotazione corretta, ma in questo caso specifico $DISPLAYe $XAUTHORITYnon conterrà alcun metacarattere shell.


2
Un modo per automatizzare questo sarebbe quello di creare un ~/.xprofileche dovrebbe essere eseguito solo durante il login X e farlo creare / aggiornare ~/.Xauthoritycon le informazioni corrette. Un collegamento simbolico sarebbe sufficiente?
Arrowmaster,

@Arrowmaster: questo è un buon suggerimento. Non ci avevo pensato. Non funzionerà in tutti i casi, ad esempio se accedi a più di una sessione X (su terminali diversi, con vnc, ...), ma è semplice ed è abbastanza buono per un uso tipico. Un collegamento simbolico è il modo migliore. Hmm, in realtà c'è un modo migliore e semplice: puoi copiare le informazioni in ~/.Xauthority.
Gilles,

1
Sarebbe mettere qualcosa di simile xauth extract - $DISPLAY | xauth -f "$HOME/.Xauthority" merge -nel ~/.xprofilerisolvere il caso di molteplici $ DISPLAY di?
Arrowmaster,

@Arrowmaster: quale problema vedi con più schermi? Mentre il tuo codice potrebbe essere un po 'più pulito in linea di principio poiché stai solo estraendo informazioni sul display a cui sei interessato, non vedo nulla di sbagliato in una semplice fusione nel caso del richiedente, o addirittura al di fuori di circostanze molto insolite.
Gilles,

1
Leggere l'ambiente da un processo esistente collegato al display è inaspettato da essere deliziosamente malvagio. Approvo con tutto il cuore. Unix.SE ha bisogno di un badge Evil Genius ™ per questo.
derobert il

19

Ho risolto questo problema aggiungendo

xhost +si:localuser:$USER

a ~/.xprofile. Non so se questo è del tutto sicuro (sarei molto interessato a sapere cosa pensano le persone più informate), ma immagino che sia molto meglio che disattivare il controllo di accesso (con xhost +) come è comunemente suggerito quando si google per questo problema.


1
localusergli indirizzi interpretati dal server sono completamente sicuri. Debian lo fa anche di default come parte del processo di login (in /etc/X11/Xsession.d/35x11-common_xhost-local). Vedi la pagina man di Xsecurity per maggiori dettagli.
Sam Morris,

Se sei su una LAN, xhost +probabilmente è abbastanza nella maggior parte dei casi ...
Alexis Wilke,

Saresti in grado di spiegare cosa significa questo comando?
alpha_989,

@ alpha_989: significa "Concedi l'accesso [+] a qualsiasi applicazione [localuser] in esecuzione localmente in esecuzione come me [$ USER]." Il "si" è solo colla (vedi xhost(1)e Xsecurity(7)per documenti). Di per sé, questo comando non consente alcun tipo di accesso remoto o inoltro X11 (per il quale di solito si preferisce il meccanismo "cookie magico" xhost).
Kevin,

7

Devi export DISPLAY=:0.0


No. Unix non richiede un'esportazione quando la variabile è scritta sulla stessa riga. Quella variabile è efficace fino alla fine della linea.
Alexis Wilke,

Anzi, hai ragione.
asoundmove,

Questa risposta è chiaramente sbagliata e dovrebbe essere eliminata.
Piotr Dobrogost,

Non sapevo solo digitando DISPLAY =: 0.0 avrebbe impostato il nome della variabile. Grazie @asoundmove. Tuttavia, penso: 0.0 è il valore per la variabile DISPLAY sul display del server. Se si accede da Putty, la variabile DISPLAY dovrebbe essere 10 o superiore. quindi dovrebbe essere DISPLAY =: 10
alpha_989

3

Funziona per me, Debian Wheezy -> Ubuntu Trust.

Nota: in questo caso il server non esegue un display-manager, è una macchina virtuale "senza testa" senza scheda grafica o monitor collegati.

bob@laptop:~$ grep -iB 1 tcp /etc/gdm3/daemon.conf
[security]
DisallowTCP = false
bob@laptop:~$ ssh -C -R 6000:127.0.0.1:6000 alice@server
X11 forwarding request failed on channel 0
alice@server:~$ export DISPLAY=:0.0
alice@server:~$ xterm

Il display X sul laptop mostra l'output di xterm in esecuzione sul server.

Debug usando:

bob@laptop:~/tmp$ nc -v 127.0.0.1 6001
localhost [127.0.0.1] 6001 (x11-1) : Connection refused
bob@laptop:~/tmp$ nc -v 127.0.0.1 6000
localhost [127.0.0.1] 6000 (x11) open
alice@server:~$ nc -v 127.0.0.1 6000
Connection to 127.0.0.1 6000 port [tcp/x11] succeeded!*
alice@server:~$ strace xterm

strace riverserà un sacco di dettagli cruenti su ciò che sta facendo, dovresti essere in grado di indovinare dove si blocca - in attesa di una connessione o altro.

In una riga ..

ssh -C -R 6000:127.0.0.1:6000 alice@server "DISPLAY=:0.0 xterm"
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.