# [tproxy] lotta campale con iptables [risolto]

## cloc3

questa volta sono alle prese con un server tproxy.

ma, dove c'è iptables, soccombo ogni volta. non riesco proprio a trovare il punto giusto da dove cominciare a capire quello che sto facendo.

la documentazione di riferimento che sto utilizzando è la seguente:

http://www.balabit.com/downloads/files/tproxy/README.txt

http://wiki.squid-cache.org/Features/Tproxy4

uso una classica rete lineare, con il server proxy nel mezzo tra la lan locale e il router adsl:

internet ---- 192.168.1.1 router adsl ---- 192.168.1.12 server proxy 192.168.0.12 ---- 192.168.0.13 client

per la verità, ci sarebbe un piccolo casino fisico, nel senso che il server e il client si agganciano contemporaneamente allo stesso switch del router adsl.

però il server lo fa con due uscite ethernet indipendenti, quindi ritengo di avere rappresentato la geometria in un modo logicamente corretto.

il client utilizza una tabella di routing elementare:

```

gentoo_client ~ # route -en

Kernel IP routing table

Destination     Gateway         Genmask         Flags   MSS Window  irtt Iface

192.168.0.0     0.0.0.0         255.255.255.0   U         0 0          0 eth0

127.0.0.0       127.0.0.1       255.0.0.0       UG        0 0          0 lo

0.0.0.0         192.168.0.12    0.0.0.0         UG        0 0          0 eth0

```

per il server, invece, mi sono dovuto imparare (si fa per dire  :Rolling Eyes:  )  iproute2:

```

939 ~ # ip route list table all

local default dev lo  table 100  scope host 

192.168.1.0/24 dev eth1  proto kernel  scope link  src 192.168.1.12 

192.168.0.0/24 dev eth0  proto kernel  scope link  src 192.168.0.12 

127.0.0.0/8 via 127.0.0.1 dev lo 

default via 192.168.1.1 dev eth1 

broadcast 192.168.0.255 dev eth0  table local  proto kernel  scope link  src 192.168.0.12 

broadcast 192.168.1.0 dev eth1  table local  proto kernel  scope link  src 192.168.1.12 

broadcast 127.255.255.255 dev lo  table local  proto kernel  scope link  src 127.0.0.1 

local 192.168.0.12 dev eth0  table local  proto kernel  scope host  src 192.168.0.12 

broadcast 192.168.0.0 dev eth0  table local  proto kernel  scope link  src 192.168.0.12 

broadcast 192.168.1.255 dev eth1  table local  proto kernel  scope link  src 192.168.1.12 

local 192.168.1.12 dev eth1  table local  proto kernel  scope host  src 192.168.1.12 

broadcast 127.0.0.0 dev lo  table local  proto kernel  scope link  src 127.0.0.1 

local 127.0.0.1 dev lo  table local  proto kernel  scope host  src 127.0.0.1 

local 127.0.0.0/8 dev lo  table local  proto kernel  scope host  src 127.0.0.1 

```

iptables, invece, è configurato per la sola tabella di mangle:

```

s939 ~ # iptables -t mangle -L -n

Chain PREROUTING (policy ACCEPT)

target     prot opt source               destination         

DIVERT     tcp  --  0.0.0.0/0            0.0.0.0/0           socket 

TPROXY     tcp  --  0.0.0.0/0            0.0.0.0/0           tcp dpt:80 TPROXY redirect 192.168.1.12:3129 mark 0x1/0x1

Chain INPUT (policy ACCEPT)

target     prot opt source               destination         

Chain FORWARD (policy ACCEPT)

target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)

target     prot opt source               destination         

Chain POSTROUTING (policy ACCEPT)

target     prot opt source               destination         

Chain DIVERT (1 references)

target     prot opt source               destination         

MARK       all  --  0.0.0.0/0            0.0.0.0/0           MARK xset 0x1/0xffffffff 

ACCEPT     all  --  0.0.0.0/0            0.0.0.0/0           

```

ho ottenuto questa configurazione applicando le istruzioni trovate nei siti lincati:

```

iptables -t mangle -N DIVERT

iptables -t mangle -A DIVERT -j MARK --set-mark 1

iptables -t mangle -A DIVERT -j ACCEPT

iptables -t mangle -A PREROUTING -p tcp -m socket -j DIVERT

iptables -t mangle -A PREROUTING -p tcp --dport 80 -j TPROXY --tproxy-mark 0x1/0x1 --on-port 3129 --on-ip 192.168.1.12

ip rule add fwmark 1 lookup 100

ip route add local 0.0.0.0/0 dev lo table 100

echo 1 > /proc/sys/net/ipv4/ip_forward

```

unica aggiunta di testa mia, l'opzione --on-ip 192.168.1.12, che dovrebbe redirigere sull'interfaccia eth1   :Question: 

risultato:

flop. il client non vede internet, mentre squid funziona, ma solo per i bot che provano ad accedere al mio server personale dall'esterno.

desolante.

qualcuno sa darmi una mano?

----------

## Apetrini

Se ho capito bene vuoi fare un proxy trasparente. Purtroppo io non ho mai usato la tabella per l'alterazione dei pacchetti (mangle) per fare questo tipo di cose, ho sempre fatto proxy trasparenti sulla stessa macchina che faceva il nat. Usavo appunto la tabella NAT e facevo un redirect di richieste.

Il mio approccio aveva delle limitazioni, ma una volta squid supportava solo quella maniera.

Non ho dato uno sguardo approfondito al tuo problema, anche perche sono al mare e ho sonno che oggi è stata una giornata intensa.

Mi sembra comunque che ciò che manca è proprio il NAT e piu precisamente il destination nat (DNAT).

Forse l'equivalente di questo non è stato fatto (preso dal tuo tutorial):

```
 iptables -t nat -A PREROUTING -j DNAT --to-dest <localip> --to-port <proxyport>

```

----------

## cloc3

 *Apetrini wrote:*   

> 
> 
> Mi sembra comunque che ciò che manca è proprio il NAT e piu precisamente il destination nat (DNAT).
> 
> Forse l'equivalente di questo non è stato fatto (preso dal tuo tutorial):
> ...

 

non credo.

a quanto ho capito, quella è l'impostazione per realìzzare il proxy nel modo consueto.

il pacchetto viene mascherato prima dell'inoltro su internet.

io desidero fare un tproxy. se ho capito correttamente (e questo non è scontato), il pacchetto viene inoltrato su internet senza essere mascherato.

la prima operazione, infatti, sarebbe la catena DIVERT, che marca il pacchetto senza nattarlo e la seconda l'inoltro sulla porta squid per l'accesso alla cache.

----------

## cloc3

allora.

in pratica avevo due problemi.

1. per quanto riguarda l'accesso da remoto al mio server apache, basta riservare la redirezione TPROXY alla sola scheda eth0, connessa alla lan locale.

adesso che ho cominciato a masticarci un pochino, con iptables, sono capace di fare la correzione on the fly   :Rolling Eyes:  :

```

iptables -t mangle -R PREROUTING 2 -p tcp --dport 80 -j TPROXY --tproxy-mark 0x1/0x1 --on-port 3129 --on-ip 192.168.1.12 -i eth0

```

in pratica, si manipola esclusivamente il traffico in input da eth0.

2. invece, per quanto riguarda l'uscita dalla rete, avevi ragione tu. serve un comando di nat.

probabilmente, nel mio caso, anziché in prerouting è opportuno effettuarlo in postrouting:

```

iptables -t nat -A POSTROUTING -o eth1 -j MASQUERADE

```

a questo punto, c'è da chiedersi, però, cosa sia cambiato con il nuovo proxy trasparente nel kernel.

allora ho postato direttamente nelle mailing list di https://lists.balabit.hu/mailman/listinfo/tproxy e mi hanno rispoto in questo modo:

 *Asif Bakali wrote:*   

> 
> 
> Try to change your network senario 
> 
> Internet --- internet <----> 192.168.1.1 adsl router <----> 192.168.1.2 proxy <----> 192.168.1.13 local_client
> ...

 

in pratica, la cosa nuova è che è possibile realizzare il proxy attribuendo alla rete locale lo stesso dominio del router adsl.

qui a casa mi è impossibile provare, perché entrambe le schede del server proxy sono dirette nello switch del router, e se non le distinguo con il dominio ip viene tutto un pasticcio.

anche in una situazione reale, però, intravedo qualche problema. evitare il nat significa mescolare la lan a monte del server proxy (quella dietro eth0) con la lan a valle (davanti a eth1). e questo potrebbe apparire peggiore del vantaggio di evitare il nat.

----------

## Apetrini

 *cloc3 wrote:*   

> 
> 
> il pacchetto viene mascherato prima dell'inoltro su internet.
> 
> 

 

si hai ragione. Si usa il masquerade.

Ma a parte il redirect della porta 80 e simili, hai provato se dal client si riesce a uscire in rete non web ? Hai scritto "il client non vede internet", vorrei essere sicuro che si intenda internet e non solo il web. E comunque (in teoria) le regole da te postate dovrebbero bastare solo per il web, se uno ha bisogno di usufruire di altri servizi in internet dovrebbe essere nattato visto che il client usa il server come gateway ? O sbaglio? il proxy gestisce solo traffico web.

Curiosità... se sul client imposti esplicitamente il proxy (sempre il tuo server squid) con porta e tutto, riesci a navigare?

Chiedo scusa, ma sono un po' arruginito di networking, una volta che faccio sti lavori dopo per un bel po' non ne faccio piu perche sono cose che una volta messe in piedi funzionano e io vado pian piano dimenticando del perché  :Very Happy: 

Edit: scusate per il post. Ovviamente ho postato(cominciato il post) ancor prima di vedere la soluzione e il tag risolto.

Sono molto contento che sei riuscito a risolvere.

Sarebbe curioso sapere se hanno inventato qualche diavoleria per riuscire a fare un proxy trasparente con autenticazione iniziale via web, anche se sembra di no.

----------

## cloc3

 *Apetrini wrote:*   

> 
> 
> Sarebbe curioso sapere se hanno inventato qualche diavoleria per riuscire a fare un proxy trasparente con autenticazione iniziale via web, anche se sembra di no.

 

non credo che sia un grosso problema.

squid prevede la useflag kerberos.

basta associare la navigazione ad un ticket specifico e il gioco è fatto.

----------

## X-Act!

 *cloc3 wrote:*   

> anche in una situazione reale, però, intravedo qualche problema. evitare il nat significa mescolare la lan a monte del server proxy (quella dietro eth0) con la lan a valle (davanti a eth1). e questo potrebbe apparire peggiore del vantaggio di evitare il nat.

 

In realtà non c'è nessun problema: si tratta solo di spostare la "separazione" dal livello 3 a livello 2.

Cambiano un po' le modalità, ma la filosofia è più o meno la stessa.

E poi infondo, se un proxy deve essere "trasparent" vuol dire che non si deve vedere!

 *Apetrini wrote:*   

> Sarebbe curioso sapere se hanno inventato qualche diavoleria per riuscire a fare un proxy trasparente con autenticazione iniziale via web, anche se sembra di no.

 

Scusa, probabilmente ho capito male, ma che problema c'è a fare un'autenticazione web? Da quel punto di vista che il proxy sia trasaprente o no, non cambia niente. O mi sbaglio?

----------

## Apetrini

 *cloc3 wrote:*   

> 
> 
> non credo che sia un grosso problema.
> 
> squid prevede la useflag kerberos.
> ...

 

Non c'è bisogno di usare kerberos per forza, squid lo fa già(nel senso che fornisce già autenticazione usando, se ricordo bene, file), è che non si riesce a fornire qualche tipo di autenticazione volendo tenere il proxy trasparente.

X-Act!: il problema c'è. Il tuo browser quando parla (per esempio) con google.com crede che sia google a rispondergli (visto che il proxy è trasparente e il tuo browser non se ne accorge), ma se a un certo punto fosse proprio il proxy a rispondergli con la richiesta di autenticazione, il tuo browser sarebbe confuso e si rifiuterebe di procedere(anche per via delle impostazioni di sicurezza).

Cito 2 punti dalle faq di squid:

```

Why can't I use authentication together with interception proxying?

Interception Proxying works by having an active agent (the proxy) where there should be none. The browser is not expecting it to be there, and it's for all effects and purposes being cheated or, at best, confused. As an user of that browser, I would require it not to give away any credentials to an unexpected party, wouldn't you agree? Especially so when the user-agent can do so without notifying the user, like Microsoft browsers can do when the proxy offers any of the Microsoft-designed authentication schemes such as NTLM (see ../ProxyAuthentication and NegotiateAuthentication).

In other words, it's not a squid bug, but a browser security feature.

------------------------------------------------------------------------------------------------------

Can I use ''proxy_auth'' with interception?

No, you cannot. See the answer to the previous question. With interception proxying, the client thinks it is talking to an origin server and would never send the Proxy-authorization request header. 

```

P.s. usano il termine "Interception proxy" ma è il transparent proxy comunemente inteso (leggete gli inizi delle faq se siete dubbiosi).

Visto che l'autenticazione canonica via web non si puo fare, l'unica cosa che mi viene in mente è di rendere disponibile un servizio via web(su un altro indirizzo ip o so un'altra porta) con un pannello dove gli utenti possano "autenticarsi"(solo autenticarsi). Da qui il servizio ricorda l'indirizzo ip dell'autenticatore e aggiorna le ACL di squid permettendo il traffico da quell'indirizzo ip (o magari fare in modo che senza autenticazione si hanno dei limiti sulle categorie di siti visitabili).

E un po' grezza(non si puo mantenere nessun tipo di sessione sulla navigazione per cui ci dobbiamo affidare all'indirizzo ip, ma se sulla lan piu di un utente arriva con lo stesso indirizzo ip, magari perche nattati...ci saranno problemi...), ma non ne vedo altre.

----------

## X-Act!

Hai perfettamente ragione, la cosa mi era sfuggita.

Però una soluzione ci deve essere e ne sono sicuro perché in una nostra sede c'era un proxy che funzionava esattamente così anche se non mi sono mai informato sui dettagli... Ora quella sede è inagibile causa sisma (ehm forse si è capito dove lavoro?) ma scrivo immediatamente al collega che l'aveva messa su e vi farò sapere.

----------

## cloc3

 *Apetrini wrote:*   

> 
> 
> Visto che l'autenticazione canonica via web non si puo fare, l'unica cosa che mi viene in mente è di rendere disponibile un servizio via web(su un altro indirizzo ip o so un'altra porta) con un pannello dove gli utenti possano "autenticarsi"(solo autenticarsi). Da qui il servizio ricorda l'indirizzo ip dell'autenticatore e aggiorna le ACL di squid permettendo il traffico da quell'indirizzo ip (o magari fare in modo che senza autenticazione si hanno dei limiti sulle categorie di siti visitabili).
> 
> 

 

insisto a pensare che quello che descrivi sia una complicazione del meccanismo con cui funziona kerberos.

tutta la lan interna è costretta a richiedere al server proxy il servizio di forward dalla scheda eth0 alla scheda eth1.

se il server proxy, a qualunque livello, attiva un meccanismo per cui niente ticket kerberos, niente forward, il gioco è fatto.

----------

## devilheart

piccola domanda: gli indirizzi 192.168.1.1 e 192.168.1.12 di chi sono?

----------

## Apetrini

 *cloc3 wrote:*   

> 
> 
> insisto a pensare che quello che descrivi sia una complicazione del meccanismo con cui funziona kerberos.
> 
> tutta la lan interna è costretta a richiedere al server proxy il servizio di forward dalla scheda eth0 alla scheda eth1.
> ...

 

Il punto è proprio qui. Le richieste http dal browser a google(per esempio) non devono essere "sporcate", perché il browser deve credere di parlare con google e che il proxy non esista. Mi sembra proprio che questo non si può fare con kerberos (per gestire il ticket vengono alterate le richieste http); googlando in rete non ho incontrato nessuno che sia riuscito in una cosa del genere.

Il mio sistema potrebbe funzionare solo perché è molto meno sofisticato di kerberos.

Qualcosa tipo:

- Apri la pagina 192.168.1.10:2211 (non è quindi intercettto da squid)

- Qui ti autentifichi e uno script aggiunge il tuo indirizzo ip al file di configurazione di squid (o quant'altro).

- Ora quando vai su google.com i tuoi header/richieste http non vengono sporcate e squid fa solo il check sull'ip (cosa di cui non deve informare il browser).

La mia comunque era solo un ipotesi tanto per dire, lungi da me voler implementare una schifezza simile.

@X-Act!: cavoli mi dispiace. Comunque per la cronaca credo che il sistema di cui parli tu funzionasse più o meno cosi:

- Sono state create delle regole sul firewall (iptables, pf o quello che è) che impediscono l'accesso alle porte web (principalmente 80) su internet.

- Per poter navigare gli utenti devono esplicitare il proxy nel loro browser.

- Da qui, quando aprono google.com la prima volta, viene fuori la finestra di login e password.

Cosi avevo fatto anche io, perché è utile limitare(sulle categorie di siti permesse) gli utenti per orario/gruppo etc... l'unica cosa è che questo non è proxy trasparente in quanto bisogna eplicitare l'uso del proxy nel browser.

Se qualcuno è riuscito a implementare un proxy trasparente con autenticazione di qualsiasi tipo si faccia vivo perché la cosa mi interessa molto e mi ricordo che qualche anno fa non sono riuscito a fare ciò.

Edit: @X-Act! ma hai l'avatar di The Day of The Tentacle?

----------

## X-Act!

 *Apetrini wrote:*   

> Comunque per la cronaca credo che il sistema di cui parli tu funzionasse più o meno cosi:
> 
> - Sono state create delle regole sul firewall (iptables, pf o quello che è) che impediscono l'accesso alle porte web (principalmente 80) su internet.
> 
> - Per poter navigare gli utenti devono esplicitare il proxy nel loro browser.
> ...

 

Non ho ancora i dettagli dell'implementazione, ma la cosa è un po' una via di mezzo: quel proxy è bridged (non è quindi un gateway di livello 3), ed è trasparente nel senso che non c'è nulla di configurato nei browser, ma non è "trasparente all'esterno" nel senso che tutte le connessioni in uscita escono con l'ip del proxy e non con quello dei client. Forse il bandolo della matassa sta proprio qui... Comunque aspetto dettagli sulla configurazione e vi aggiorno.

P.S.:

 *Apetrini wrote:*   

> Edit: @X-Act! ma hai l'avatar di The Day of The Tentacle?

 

Si, ti piace? non è neanche stato tanto facile trovarlo...

P.S.2:

 *Apetrini wrote:*   

> @X-Act!: cavoli mi dispiace. 

 

Grazie!

----------

## cloc3

 *devilheart wrote:*   

> piccola domanda: gli indirizzi 192.168.1.1 e 192.168.1.12 di chi sono?

 

il primo è l'indirizzo ip del router adsl.

nello schema, avrei dovuto scrivere il numero a destra, perché appartiene alla faccia verso lan.

il secondo è l'indirizzo della scheda eth1 del proxy. quella connessa al router adsl.

----------

