Membalikkan tunneling port

59

Saya perlu menunjukkan kepada seseorang situs web yang berjalan di komputer lokal saya besok. Biasanya saya akan melakukan ini dengan port forwarding pada router lokal saya tetapi berkat kegagalan hardware dan penggantinya menjadi mengerikan, router saya saat ini tidak membiarkan saya melakukan port forwarding.

Begitu terjebak dengan keterlambatan ini dan tidak ingin mendorong semuanya ke server yang tepat, saya punya ide gila: Bisakah saya meneruskan port saya ke server eksternal melalui SSH?

Saya telah melakukan tunneling port sebelumnya tetapi saya biasanya melakukannya dengan benar:

  • Saya terhubung ke kotak jauh dan meminta port 12345 muncul di mesin lokal saya di port 12345.
  • Saya memulai sesuatu di P12345 pada mesin jarak jauh
  • Saya dapat mengaksesnya melalui localhost: 12345

Apa yang ingin saya lakukan:

  • Terhubung ke PC remote dan meminta bahwa nya P12345 lokal mengambil hal-hal dari P12345 lokal saya (di atas terowongan)
  • Saya memulai sesuatu di komputer lokal saya di P12345
  • Orang lain dapat mengakses jarak jauh: 12345 dan melihat localhost saya: 12345
Oli
sumber

Jawaban:

96

Perintah untuk meneruskan port 80 dari mesin lokal Anda ( localhost) ke host jarak jauh pada port 8000 adalah:

ssh -R 8000:localhost:80 oli@remote-machine

Ini membutuhkan perubahan tambahan pada server SSH, tambahkan baris ke /etc/ssh/sshd_config:

Match User oli
   GatewayPorts yes

Selanjutnya, muat ulang konfigurasi dengan mengeksekusi server sudo reload ssh.

Pengaturan ini GatewayPorts yesmenyebabkan SSH mengikat port 8000 pada alamat wildcard, sehingga menjadi tersedia untuk alamat publik remote-machine( remote-machine:8000).

Jika Anda perlu memiliki opsi untuk tidak mengikat semuanya pada alamat wildcard, ubah GatewayPorts yeske GatewayPorts clientspecified. Karena sshmengikat ke alamat loopback secara default, Anda perlu menentukan yang kosong bind_addressuntuk mengikat alamat wildcard:

ssh -R :8000:localhost:80 oli@remote-machine

The :sebelum 8000adalah wajib jika GatewayPortsdiatur ke clientspecifieddan Anda ingin mengizinkan akses publik ke remote-machine:8000.

Kutipan manual yang relevan:

ssh (1)

-R [bind_address:] port: host: hostport
Menentukan bahwa port yang diberikan pada host remote (server) akan diteruskan ke host dan port yang diberikan di sisi lokal. Ini bekerja dengan mengalokasikan soket untuk mendengarkan port di sisi jarak jauh, dan setiap kali koneksi dibuat ke port ini, koneksi diteruskan melalui saluran aman, dan koneksi dibuat untuk meng-host port hostport dari mesin lokal. Secara default, soket pendengaran di server akan terikat ke antarmuka loopback saja. Ini mungkin ditimpa dengan menetapkan bind_address. Bind_address kosong, atau alamat '*', menunjukkan bahwa soket jarak jauh harus mendengarkan semua antarmuka. Menentukan bind_address jarak jauh hanya akan berhasil jika opsi GatewayPorts server diaktifkan (lihat sshd_config (5)).

sshd_config (5)

GatewayPorts
Menentukan apakah host jarak jauh diizinkan untuk terhubung ke port yang diteruskan untuk klien. GatewayPorts dapat digunakan untuk menentukan bahwa sshd harus memungkinkan penerusan port jarak jauh untuk mengikat ke alamat non-loopback, sehingga memungkinkan host lain untuk terhubung. Argumennya mungkin 'tidak' untuk memaksa penerusan port jarak jauh hanya tersedia untuk host lokal, 'ya' untuk memaksa penerusan port jarak jauh untuk mengikat ke alamat wildcard, atau 'klien yang ditentukan' untuk memungkinkan klien memilih alamat yang penerusannya terikat. Standarnya adalah 'tidak'.

Lihat juga:

Lekensteyn
sumber
7
GatewayPortsadalah peluru ajaib di sini. Saya suka bahwa Anda telah menemukan versi yang dapat memungkinkan saya untuk membatasi teknik yang cukup kuat ini untuk pengguna tertentu.
Oli
1
Yang membingungkan bagi saya adalah bahwa GatewayPort harus diset pada mesin yang menjalankan perintah ssh yang sebenarnya untuk memulai reverse tunnel (local). Dalam pikiran saya entah bagaimana lebih logis bahwa ujung yang lain (jarak jauh) akan berurusan dengan di mana menerima koneksi dari, karena di situlah Anda terhubung dan dialihkan dari. Butuh waktu lama untuk menyiasatinya.
Ars Magika
2
@ArsMagika Saya tidak yakin apakah saya mengerti Anda. GatewayPorts harus ditetapkan pada server SSH, bukan pada mesin lokal Anda yang menjalankan sshperintah. Ini mengkonfigurasi apakah klien lain dapat berkomunikasi dengan port yang diteruskan di server.
Lekensteyn
Kelemahan dari solusi ini: Anda kehilangan kemampuan untuk menentukan alamat IP klien di log akses server web. Adakah cara untuk mengatasi gangguan itu juga?
Twonky
@Twonky Jika Anda tidak perlu tahu alamat IP yang tepat dari klien (hanya saja itu jarak jauh dan bukan "localhost"), dan server lokal Anda mendengarkan pada alamat wildcard (yaitu menerima koneksi dari alamat mana pun), maka Anda dapat mencoba meneruskan ke -R :8000:127.0.1.1:80(atau 127.x.x.xalamat lain ). Jika tidak, tidak, Anda tidak akan dapat mempelajari alamat IP jarak jauh.
Lekensteyn
14

Jika server memiliki GatewayPorts no, Anda dapat mencapai hasil yang sama dengan mengeksekusi ssh -g -L 8001:localhost:8000 oli@remote-machinedi server setelah Anda menjalankan ssh -Rperintah pada klien. Ini akan membuat loopback port 8000 pada server dapat diakses pada semua antarmuka pada port 8001.

FaST4
sumber