Enable user auth support on Linux

pull/13/head
Soner Tari 5 years ago
parent 4f4b41d5ad
commit 0d49ba56db

@ -124,9 +124,10 @@ ones. See [The Risks of SSL Inspection](https://insights.sei.cmu.edu/cert/2015/0
for the reasons of this difference.
If enabled, the UserAuth option requires network users to log in to the system
to use SSLproxy (this feature is currently available on OpenBSD only). When
users are logged in, they should be recorded on the users table in an SQLite3
database. The users table is created using the following SQL statement:
to use SSLproxy (this feature is currently available on OpenBSD and Linux
only). When users are logged in, they should be recorded on the users table in
an SQLite3 database. The users table is created using the following SQL
statement:
CREATE TABLE USERS(
IP CHAR(45) PRIMARY KEY NOT NULL,

@ -1458,10 +1458,10 @@ opts_unset_allow_wrong_host(opts_t *opts)
static void
opts_set_user_auth(UNUSED opts_t *opts)
{
#ifdef __OpenBSD__
// Enable user auth only on OpenBSD
#if defined(__OpenBSD__) || defined(__linux__)
// Enable user auth on OpenBSD and Linux only
opts->user_auth = 1;
#endif /* __OpenBSD__ */
#endif /* __OpenBSD__ || __linux__ */
}
static void

@ -393,7 +393,7 @@ privsep_server_update_atime(opts_t *opts, const userdbkeys_t *keys)
if (rc == SQLITE_DONE) {
log_dbg_printf("privsep_server_update_atime: Updated atime of user %s=%lld\n", keys->user, (long long)atime);
} else {
log_err_level_printf(LOG_ERR, "privsep_server_update_atime: Error updating user atime: %s\n", sqlite3_errmsg(opts->userdb));
log_err_printf("privsep_server_update_atime: Error updating user atime: %s\n", sqlite3_errmsg(opts->userdb));
}
sqlite3_reset(opts->update_user_atime);
return 0;

@ -1491,7 +1491,7 @@ pxy_fd_readcb(evutil_socket_t fd, UNUSED short what, void *arg)
ctx->protoctx->fd_readcb(fd, what, arg);
}
static int
static int NONNULL(1)
call_fd_readcb(pxy_conn_ctx_t *ctx)
{
/* for SSL, defer dst connection setup to initial_readcb */
@ -1507,7 +1507,7 @@ call_fd_readcb(pxy_conn_ctx_t *ctx)
return 0;
}
#ifdef __OpenBSD__
#if defined(__OpenBSD__) || defined(__linux__)
static void
identify_user(UNUSED evutil_socket_t fd, UNUSED short what, void *arg)
{
@ -1551,7 +1551,7 @@ identify_user(UNUSED evutil_socket_t fd, UNUSED short what, void *arg)
goto redirect;
} else if (rc == SQLITE_ROW) {
char *ether = (char *)sqlite3_column_text(ctx->thr->get_user, 1);
if (strncmp(ether, ctx->ether, 17)) {
if (strncasecmp(ether, ctx->ether, 17)) {
#ifdef DEBUG_PROXY
log_dbg_level_printf(LOG_DBG_MODE_FINEST, "identify_user: Ethernet addresses do not match, db=%s, arp cache=%s, ctx->fd=%d\n", ether, ctx->ether, ctx->fd);
#endif /* DEBUG_PROXY */
@ -1607,7 +1607,53 @@ memout:
evutil_closesocket(ctx->fd);
pxy_conn_ctx_free(ctx, 1);
}
#endif /* __OpenBSD__ || __linux__ */
#ifdef __linux__
// Assume proc filesystem support
#define ARP_CACHE "/proc/net/arp"
/*
* We do not care about multiple matches or expiration status of arp cache entries on Linux.
*/
static int NONNULL(1)
get_client_ether(pxy_conn_ctx_t *ctx)
{
int rv = 0;
FILE *arp_cache = fopen(ARP_CACHE, "r");
if (!arp_cache) {
log_err_level_printf(LOG_CRIT, "Failed to open arp cache: \"" ARP_CACHE "\"\n");
return -1;
}
// Skip the first line, which contains the header
char header[1024];
if (!fgets(header, sizeof(header), arp_cache)) {
log_err_level_printf(LOG_CRIT, "Failed to skip arp cache header\n");
rv = -1;
goto out;
}
char ip[46], ether[18];
//192.168.0.1 0x1 0x2 00:50:56:2c:bf:e0 * enp3s0f1
while (fscanf(arp_cache, "%45s %*s %*s %17s %*s %*s", ip, ether) == 2) {
if (!strncasecmp(ip, ctx->srchost_str, 45)) {
ctx->ether = strdup(ether);
rv = 1;
#ifdef DEBUG_PROXY
log_dbg_level_printf(LOG_DBG_MODE_FINEST, "Arp entry for %s: %s\n", ip, ether);
#endif /* DEBUG_PROXY */
goto out;
}
}
out:
fclose(arp_cache);
return rv;
}
#endif /* __linux__ */
#ifdef __OpenBSD__
/*
* This is a modified version of the same function from OpenBSD sources,
* which has a 3-clause BSD license.
@ -1632,7 +1678,7 @@ ether_str(struct sockaddr_dl *sdl)
* This is a modified version of a similar function from OpenBSD sources,
* which has a 3-clause BSD license.
*/
static int
static int NONNULL(2)
get_client_ether(in_addr_t addr, pxy_conn_ctx_t *ctx)
{
int mib[7];
@ -1805,8 +1851,13 @@ pxy_conn_setup(evutil_socket_t fd,
}
if (ctx->opts->user_auth) {
#ifdef __OpenBSD__
int ec = get_client_ether(((struct sockaddr_in *)peeraddr)->sin_addr.s_addr, ctx);
#if defined(__OpenBSD__) || defined(__linux__)
int ec;
#if defined(__OpenBSD__)
ec = get_client_ether(((struct sockaddr_in *)peeraddr)->sin_addr.s_addr, ctx);
#else /* __linux__ */
ec = get_client_ether(ctx);
#endif /* __linux__ */
if (ec == 1) {
ctx->ev = event_new(ctx->evbase, -1, 0, identify_user, ctx);
if (!ctx->ev)
@ -1821,7 +1872,7 @@ pxy_conn_setup(evutil_socket_t fd,
// ec == -1
goto memout;
}
#endif /* __OpenBSD__ */
#endif /* __OpenBSD__ || __linux__ */
log_err_level_printf(LOG_CRIT, "Aborting connection setup (user auth)!\n");
goto out;
} else {

@ -125,9 +125,10 @@ split, SSLsplit accepts all certificates by default, including self-signed
ones.
.LP
If enabled, the UserAuth option requires network users to log in to the system
to use SSLproxy (this feature is currently available on OpenBSD only). When
users are logged in, they should be recorded on the users table in an SQLite3
database. The users table is created using the following SQL statement:
to use SSLproxy (this feature is currently available on OpenBSD and Linux
only). When users are logged in, they should be recorded on the users table in
an SQLite3 database. The users table is created using the following SQL
statement:
.LP
CREATE TABLE USERS(
IP CHAR(45) PRIMARY KEY NOT NULL,

Loading…
Cancel
Save