mirror of
https://github.com/matrix-construct/construct
synced 2024-12-01 19:22:53 +01:00
Add HTTP CONNECT proxy scanning
This commit is contained in:
parent
bccb7dedef
commit
fabe8b94c5
4 changed files with 89 additions and 6 deletions
|
@ -32,6 +32,7 @@ typedef enum protocol_t
|
|||
PROTO_NONE,
|
||||
PROTO_SOCKS4,
|
||||
PROTO_SOCKS5,
|
||||
PROTO_HTTP_CONNECT,
|
||||
} protocol_t;
|
||||
|
||||
struct opm_lookup
|
||||
|
@ -88,12 +89,14 @@ static bool opm_enable = false;
|
|||
static struct opm_listener listeners[2];
|
||||
|
||||
static inline protocol_t
|
||||
get_protocol_from_string(const char *string)
|
||||
get_protocol_from_string(const char *str)
|
||||
{
|
||||
if(strcasecmp(string, "socks4") == 0)
|
||||
if(strcasecmp(str, "socks4") == 0)
|
||||
return PROTO_SOCKS4;
|
||||
else if(strcasecmp(string, "socks5") == 0)
|
||||
else if(strcasecmp(str, "socks5") == 0)
|
||||
return PROTO_SOCKS5;
|
||||
else if(strcasecmp(str, "httpconnect") == 0)
|
||||
return PROTO_HTTP_CONNECT;
|
||||
else
|
||||
return PROTO_NONE;
|
||||
}
|
||||
|
@ -145,7 +148,7 @@ read_opm_reply(rb_fde_t *F, void *data)
|
|||
{
|
||||
struct opm_proxy *proxy = ptr->data;
|
||||
|
||||
if(strncmp(proxy->note, readbuf, sizeof(readbuf)) == 0)
|
||||
if(strncmp(proxy->note, readbuf, strlen(proxy->note)) == 0)
|
||||
{
|
||||
rb_dlink_node *ptr, *nptr;
|
||||
|
||||
|
@ -293,7 +296,7 @@ static void
|
|||
socks5_connected(rb_fde_t *F, int error, void *data)
|
||||
{
|
||||
struct opm_scan *scan = data;
|
||||
struct opm_lookup *lookup;
|
||||
struct opm_lookup *lookup;
|
||||
struct opm_listener *listener;
|
||||
struct auth_client *auth;
|
||||
uint8_t sendbuf[25]; /* Size we're building */
|
||||
|
@ -307,7 +310,7 @@ socks5_connected(rb_fde_t *F, int error, void *data)
|
|||
goto end;
|
||||
|
||||
/* Build the version header and socks request
|
||||
* version header (3 bytes): version, number of auth methods, auth type (0 for none)
|
||||
* version header (3 bytes): version, number of auth methods, auth type (0 for none)
|
||||
* connect req (3 bytes): version, command (1 = connect), reserved (0)
|
||||
*/
|
||||
memcpy(c, "\x05\x01\x00\x05\x01\x00", 6); c += 6;
|
||||
|
@ -352,6 +355,62 @@ end:
|
|||
rb_free(scan);
|
||||
}
|
||||
|
||||
static void
|
||||
http_connect_connected(rb_fde_t *F, int error, void *data)
|
||||
{
|
||||
struct opm_scan *scan = data;
|
||||
struct opm_lookup *lookup;
|
||||
struct opm_listener *listener;
|
||||
struct auth_client *auth;
|
||||
char sendbuf[128]; /* A bit bigger than we need but better safe than sorry */
|
||||
char *c = sendbuf;
|
||||
ssize_t ret;
|
||||
|
||||
if(scan == NULL || (auth = scan->auth) == NULL || (lookup = auth->data[PROVIDER_OPM]) == NULL)
|
||||
return;
|
||||
|
||||
if(error || !opm_enable)
|
||||
goto end;
|
||||
|
||||
switch(GET_SS_FAMILY(&auth->c_addr))
|
||||
{
|
||||
case AF_INET:
|
||||
listener = &listeners[LISTEN_IPV4];
|
||||
if(!listener->F)
|
||||
goto end;
|
||||
break;
|
||||
#ifdef RB_IPV6
|
||||
case AF_INET6:
|
||||
listener = &listeners[LISTEN_IPV6];
|
||||
if(!listener->F)
|
||||
goto end;
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
goto end;
|
||||
}
|
||||
|
||||
/* Simple enough to build */
|
||||
snprintf(sendbuf, sizeof(sendbuf), "CONNECT %s:%hu HTTP/1.0\r\n\r\n", listener->ip, listener->port);
|
||||
|
||||
/* Send request */
|
||||
if(rb_write(scan->F, sendbuf, strlen(sendbuf)) <= 0)
|
||||
goto end;
|
||||
|
||||
/* Now the note in a separate write */
|
||||
if(rb_write(scan->F, scan->proxy->note, strlen(scan->proxy->note) + 1) <= 0)
|
||||
goto end;
|
||||
|
||||
/* MiroTik needs this, and as a separate write */
|
||||
if(rb_write(scan->F, "\r\n", 2) <= 0)
|
||||
goto end;
|
||||
|
||||
end:
|
||||
rb_close(scan->F);
|
||||
rb_dlinkDelete(&scan->node, &lookup->scans);
|
||||
rb_free(scan);
|
||||
}
|
||||
|
||||
/* Establish connections */
|
||||
static inline void
|
||||
establish_connection(struct auth_client *auth, struct opm_proxy *proxy)
|
||||
|
@ -378,6 +437,8 @@ establish_connection(struct auth_client *auth, struct opm_proxy *proxy)
|
|||
case PROTO_SOCKS5:
|
||||
callback = socks5_connected;
|
||||
break;
|
||||
case PROTO_HTTP_CONNECT:
|
||||
callback = http_connect_connected;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
|
@ -697,6 +758,9 @@ create_opm_scanner(const char *key __unused, int parc __unused, const char **par
|
|||
case PROTO_SOCKS5:
|
||||
snprintf(proxy->note, sizeof(proxy->note), "socks5:%hu", proxy->port);
|
||||
break;
|
||||
case PROTO_HTTP_CONNECT:
|
||||
snprintf(proxy->note, sizeof(proxy->note), "httpconnect:%hu", proxy->port);
|
||||
break;
|
||||
default:
|
||||
warn_opers(L_CRIT, "OPM: got an unknown proxy type: %s (port %hu)", parv[0], proxy->port);
|
||||
exit(EX_PROVIDER_ERROR);
|
||||
|
|
|
@ -475,6 +475,12 @@ opm {
|
|||
* with other scan types. Sensible defaults are given below.
|
||||
*/
|
||||
socks5_ports = 1080, 10800, 443, 80, 8080, 8000;
|
||||
|
||||
/* These are the ports to scan for HTTP connect proxies on (plaintext).
|
||||
* They may overlap with other scan types. Sensible defaults are given
|
||||
* below.
|
||||
*/
|
||||
httpconnect_ports = 80, 8080, 8000;
|
||||
};
|
||||
|
||||
alias "NickServ" {
|
||||
|
|
|
@ -950,6 +950,12 @@ opm {
|
|||
* with other scan types. Sensible defaults are given below.
|
||||
*/
|
||||
socks5_ports = 80, 443, 1080, 8000, 8080, 10800;
|
||||
|
||||
/* These are the ports to scan for HTTP connect proxies on (plaintext).
|
||||
* They may overlap with other scan types. Sensible defaults are given
|
||||
* below.
|
||||
*/
|
||||
httpconnect_ports = 80, 8080, 8000;
|
||||
};
|
||||
|
||||
/*
|
||||
|
|
|
@ -2290,6 +2290,12 @@ conf_set_opm_scan_ports_socks5(void *data)
|
|||
conf_set_opm_scan_ports_all(data, "opm::socks5_ports", "socks5");
|
||||
}
|
||||
|
||||
static void
|
||||
conf_set_opm_scan_ports_httpconnect(void *data)
|
||||
{
|
||||
conf_set_opm_scan_ports_all(data, "opm::httpconnect_ports", "httpconnect");
|
||||
}
|
||||
|
||||
/* public functions */
|
||||
|
||||
|
||||
|
@ -2828,4 +2834,5 @@ newconf_init()
|
|||
add_conf_item("opm", "listen_port", CF_INT, conf_set_opm_listen_port);
|
||||
add_conf_item("opm", "socks4_ports", CF_INT | CF_FLIST, conf_set_opm_scan_ports_socks4);
|
||||
add_conf_item("opm", "socks5_ports", CF_INT | CF_FLIST, conf_set_opm_scan_ports_socks5);
|
||||
add_conf_item("opm", "httpconnect_ports", CF_INT | CF_FLIST, conf_set_opm_scan_ports_httpconnect);
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue