I Learned

Compte Twitter Compte Mastodon Flux RSS

Tout savoir sur le protocole SOCKS

· ·

Le protocole Socks est un protocole réseau qui permet à un client de faire transiter ses données par un serveur. D’après le modèle OSI, le protocole SOCKS est une couche intermédiaire entre la couche applicative et la couche transport, donc il “commencerait” couche 5 (session).
Le client, qu’on verra plus tard, peut faire passer dans le socket tout protocole au dessus de la couche de transport (TCP ou UDP). Donc, HTTP(S), FTP(S), SSH, DNS, et j’en passe.

Version 4

La version 4 de socks ne supporte que le protocole TCP et l’IPv4. Il propose au client de se connecter à un serveur distant et prend en charge une possible connexion entrante après une connexion déja établie (comme pour FTP).

Voici la RFC de cette version du protocole.

Header CONNECT et BIND

Le type de connexion BIND devrait être envoyé seulement après une connexion de type CONNECT, ceci est utilisé par les services qui utilisent le “multiple connexion”, par exemple lors d’une connexion FTP en mode “active”, quand le client écoute sur un port pour recevoir les données. Cette option permet donc de ne pas créer de connexions direct entre le serveur et le client.

Version 4a

La version 4a de socks est une mini update de la version 4 avec une bonne idée mais mal implémenté (je trouve).

Voici sa RFC.

Cette nouvelle version ajoute la possibilité de donner au serveur un nom de domaine au lieu d’une adresse IP, et c’est le serveur socks qui doit lui même résoudre le nom de domaine.

Sur le papier c’est cool. L’implémentation c’est une autre histoire.

De ce que j’ai compris, pour envoyer un nom de domaine, il faut mettre les 3 premiers octets du champ DSTIP à 0 et le 4 ème octet doit être une valeur non NULL donc tout sauf 0.

Exemple: Une adresse IP sous forme “texte” donnerait: 0.0.0.42. En représentation décimale, (c’est comme ça que devra être représentée l’adresse IP dans le champ DSTIP) cela donnerait 42 tout simplement.

Pour en savoir plus sur la représentation décimale d’une adresse IP, j’en parle dans cette article

Cette IPv4 est bien entendue invalide, et le serveur “comprend” qu’il doit lui même résoudre un nom de domaine.

mais… ou mettons-nous ce nom de domaine ?!

On le met après l’octet NULL qui termine le nom d’utilisateur, et on rajoute un octet NULL à la fin du nom de domaine.

C’est fastidieux je vous l’accorde, mais heureusement la version 5 de socks implémente cette idée d’une bien meilleure façon, et bien plus encore.

Version 5

La version 5 de socks, rajoute d’autres fonctionnalités au protocole comme:

Voici sa RFC.

Contrairement à la version 4 et 4a de socks, socks5 établit une sorte de “handshake” avec le serveur. Voici comment ça se passe:

  1. Le client se connecte et envoie une annonce qui inclut une liste de méthodes d’authentification qu’il supporte.
  2. Le serveur choisit l’une de ces méthodes ou envoie une erreur si aucune méthode n’est acceptable.
  3. Plusieurs messages sont alors échangés selon la méthode d’authentification choisi.
  4. Une fois authentifié, le client envoie une requête de connexion assez similaire du protocole SOCKS v4(a).
  5. Le serveur répond d’une manière similaire à SOCKS v4.

Header AUTH

Header connexion

Header UDP

Le serveur

Le serveur socks c’est le serveur “intermédiaire” qui sera entre le client et le serveur distant il écoute principalement sur le port 1080 (TCP et UDP).

Il fonctionne comme suit:

schema

Exemple (TCP):

De ce fait, le serveur socks est un proxy/intermédiaire entre le client et le serveur distant, donc tout ce que le client envoie au serveur socks, le serveur socks l’envoie au serveur distant, et inversement.

Pour UDP c’est la même chose, sauf qu’il n’y a pas de “connexion” à proprement parler (voir cet article pour plus de détails par rapport à UDP), il y’a un header précis pour UDP et le client envoie ce header au serveur socks, et en cas de réponse, le serveur socks envoie ce header aussi au client (avec les données “réponse”).

Il est aussi tout à fait possible de demander à un serveur socks de se connecter à un autre serveur socks, c’est ce qu’on appelle une chaine de proxy, et c’est le principe du réseau Tor (le réseau anonyme qui aura son article dédié bientôt) qui utilise le protocole SOCKSv5 et utilise une chaine de proxy pour faire transiter les requêtes du client.

SSH permet aussi la mise en place d’un serveur socks, avec l’argument -D.

Exemple: sur la machine iusearchbtw j’execute cette commande:

[ownesis@iusearchbtw ~]$ ssh ownesis@socks.example.com -D 9090 -N.

Cela ouvre le port 9090 sur la machine iusearchbtw et si j’accède à localhost:9090 sur la dite machine, les données seront transitées vers socks.example.com (qui sera utilisé comme serveur socks) qui relayera ensuite les données vers le serveur cible.

Il existe l’outil microsocks écrit en C qui permet de mettre en place un serveur socks5 facilement.

Le client

Le client socks, comme son nom l’indique, c’est celui qui contactera le serveur socks, c’est l’application qui se connecte au serveur socks et qui dit à ce dernier d’établir une connexion avec un serveur distant.

C’est rare de trouver des clients socks comme ça “native”, c’est généralement une “option” à une application. Par exemple, curl a une option --socks5 permettant de passer par un serveur socks5. Il existe aussi des “wrapper” socks, par exemple : torsocks, tsocks ou proxychains-ng, ces outils permettent de faire passer toutes les connexions TCP ou UDP du programme appelé, par un serveur socks.

Exemple:

Cette commande utilisant curl permet de contacter mikadmin.fr à travers localhost:9090 (localhost ayant un serveur socks écoutant sur le port 9090 comme vu dans la section serveur)

[ownesis@iusearchbtw ~]$ curl --socks5 localhost:9090 mikadmin.fr.

Cette seconde commande utilisant le wrapper proxychains permet d’utiliser le programme telnet pour se connecter à telehack.com sur le port 23 à travers un ou plusieurs serveurs socks.

[ownesis@iusearchbtw ~]$ proxychains telnet telehack.com

ici on ne précise pas de serveur socks car il est dans un fichier de configuration: /etc/proxychains.conf

Conclusion

Lire ensuite :

RSS · Twitter · Mastodon