Пример #1
0
/*
 * Resolve a hostname through Tor and set the ip address in the given pointer.
 *
 * Return 0 on success else a negative value and the result addr is untouched.
 */
int tsocks_tor_resolve_ptr(const char *addr, char **ip, int af)
{
	int ret;
	struct connection conn;
	uint8_t socks5_method;

	assert(addr);
	assert(ip);

	DBG("Resolving %" PRIu32 " on the Tor network", addr);

	conn.fd = tsocks_libc_socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
	if (conn.fd < 0) {
		PERROR("socket");
		ret = -errno;
		goto error;
	}
	conn.dest_addr.domain = CONNECTION_DOMAIN_INET;

	/* Is this configuration is set to use SOCKS5 authentication. */
	if (tsocks_config.socks5_use_auth) {
		socks5_method = SOCKS5_USER_PASS_METHOD;
	} else {
		socks5_method = SOCKS5_NO_AUTH_METHOD;
	}

	ret = setup_tor_connection(&conn, socks5_method);
	if (ret < 0) {
		goto end_close;
	}

	/* For the user/pass method, send the request before resolve ptr. */
	if (socks5_method == SOCKS5_USER_PASS_METHOD) {
		ret = auth_socks5(&conn);
		if (ret < 0) {
			goto end_close;
		}
	}

	ret = socks5_send_resolve_ptr_request(&conn, addr, af);
	if (ret < 0) {
		goto end_close;
	}

	/* Force IPv4 resolution for now. */
	ret = socks5_recv_resolve_ptr_reply(&conn, ip);
	if (ret < 0) {
		goto end_close;
	}

end_close:
	if (tsocks_libc_close(conn.fd) < 0) {
		PERROR("close");
	}

error:
	return ret;
}
Пример #2
0
/*
 * Resolve a hostname through Tor and set the ip address in the given pointer.
 *
 * Return 0 on success else a negative value and the result addr is untouched.
 */
int tsocks_tor_resolve_ptr(const char *addr, char **ip, int af)
{
	int ret;
	struct connection conn;

	assert(addr);
	assert(ip);

	DBG("Resolving %" PRIu32 " on the Tor network", addr);

	conn.fd = tsocks_libc_socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
	if (conn.fd < 0) {
		PERROR("socket");
		ret = -errno;
		goto error;
	}
	conn.dest_addr.domain = CONNECTION_DOMAIN_INET;

	ret = setup_tor_connection(&conn, SOCKS5_NO_AUTH_METHOD);
	if (ret < 0) {
		goto end_close;
	}

	ret = socks5_send_resolve_ptr_request(&conn, addr, af);
	if (ret < 0) {
		goto end_close;
	}

	/* Force IPv4 resolution for now. */
	ret = socks5_recv_resolve_ptr_reply(&conn, ip);
	if (ret < 0) {
		goto end_close;
	}

end_close:
	if (tsocks_libc_close(conn.fd) < 0) {
		PERROR("close");
	}

error:
	return ret;
}
Пример #3
0
/*
 * Torsocks call for socket(2)
 */
LIBC_SOCKET_RET_TYPE tsocks_socket(LIBC_SOCKET_SIG)
{
	DBG("[socket] Creating socket with domain %d, type %d and protocol %d",
			__domain, __type, __protocol);

	switch (__type) {
	case SOCK_STREAM:
		break;
	default:
		if (__domain == AF_INET || __domain == AF_INET6) {
			WARN("Non TCP inet socket denied. Tor network can't handle it.");
			errno = EINVAL;
			return -1;
		}
		break;
	}

	/* Stream socket for INET/INET6 is good so open it. */
	return tsocks_libc_socket(__domain, __type, __protocol);
}
Пример #4
0
/*
 * Resolve a hostname through Tor and set the ip address in the given pointer.
 *
 * Return 0 on success else a negative value and the result addr is untouched.
 */
int tsocks_tor_resolve_ptr(const char *addr, char **ip, int af)
{
	int ret;
	struct connection conn;

	assert(addr);
	assert(ip);

	DBG("Resolving %" PRIu32 " on the Tor network", addr);

	conn.fd = tsocks_libc_socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
	if (conn.fd < 0) {
		PERROR("socket");
		ret = -errno;
		goto error;
	}

	ret = setup_tor_connection(&conn);
	if (ret < 0) {
		goto error;
	}

	ret = socks5_send_resolve_ptr_request(addr, &conn);
	if (ret < 0) {
		goto error;
	}

	/* Force IPv4 resolution for now. */
	ret = socks5_recv_resolve_ptr_reply(&conn, ip);
	if (ret < 0) {
		goto error;
	}

	ret = close(conn.fd);
	if (ret < 0) {
		PERROR("close");
	}

error:
	return ret;
}
Пример #5
0
/*
 * Resolve a hostname through Tor and set the ip address in the given pointer.
 *
 * Return 0 on success else a negative value and the result addr is untouched.
 */
int tsocks_tor_resolve(const char *hostname, uint32_t *ip_addr)
{
	int ret;
	struct connection conn;

	assert(hostname);
	assert(ip_addr);

	ret = hosts_file_resolve(hostname, ip_addr);
	if (!ret) {
		goto end;
	}

	DBG("Resolving %s on the Tor network", hostname);

	/*
	 * Tor hidden service address have no IP address so we send back an onion
	 * reserved IP address that acts as a cookie that we will use to find the
	 * onion hostname at the connect() stage.
	 */
	if (utils_strcasecmpend(hostname, ".onion") == 0) {
		struct onion_entry *entry;

		entry = get_onion_entry(hostname, &tsocks_onion_pool);
		if (entry) {
			memcpy(ip_addr, &entry->ip, sizeof(entry->ip));
			ret = 0;
			goto end;
		}
	}

	conn.fd = tsocks_libc_socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
	if (conn.fd < 0) {
		PERROR("socket");
		ret = -errno;
		goto error;
	}

	ret = setup_tor_connection(&conn);
	if (ret < 0) {
		goto error;
	}

	ret = socks5_send_resolve_request(hostname, &conn);
	if (ret < 0) {
		goto error;
	}

	/* Force IPv4 resolution for now. */
	ret = socks5_recv_resolve_reply(&conn, ip_addr, sizeof(uint32_t));
	if (ret < 0) {
		goto error;
	}

	ret = close(conn.fd);
	if (ret < 0) {
		PERROR("close");
	}

end:
error:
	return ret;
}
Пример #6
0
/*
 * Resolve a hostname through Tor and set the ip address in the given pointer.
 *
 * Return 0 on success else a negative value and the result addr is untouched.
 */
int tsocks_tor_resolve(int af, const char *hostname, void *ip_addr)
{
	int ret;
	size_t addr_len;
	struct connection conn;

	assert(hostname);
	assert(ip_addr);

	if (af == AF_INET) {
		addr_len = sizeof(uint32_t);
		conn.dest_addr.domain = CONNECTION_DOMAIN_INET;
	} else if (af == AF_INET6) {
		addr_len = 16;
		conn.dest_addr.domain = CONNECTION_DOMAIN_INET6;
		/* Tor daemon does not support IPv6 DNS resolution yet. */
		ret = -ENOSYS;
		goto error;
	} else {
		ret = -EINVAL;
		goto error;
	}

	ret = utils_localhost_resolve(hostname, af, ip_addr, addr_len);
	if (ret) {
		/* Found to be a localhost name. */
		ret = 0;
		goto end;
	}

	DBG("Resolving %s on the Tor network", hostname);

	/*
	 * Tor hidden service address have no IP address so we send back an onion
	 * reserved IP address that acts as a cookie that we will use to find the
	 * onion hostname at the connect() stage.
	 */
	if (utils_strcasecmpend(hostname, ".onion") == 0) {
		struct onion_entry *entry;

		entry = get_onion_entry(hostname, &tsocks_onion_pool);
		if (entry) {
			memcpy(ip_addr, &entry->ip, sizeof(entry->ip));
			ret = 0;
			goto end;
		}
	}

	conn.fd = tsocks_libc_socket(af, SOCK_STREAM, IPPROTO_TCP);
	if (conn.fd < 0) {
		PERROR("socket");
		ret = -errno;
		goto error;
	}

	ret = setup_tor_connection(&conn, SOCKS5_NO_AUTH_METHOD);
	if (ret < 0) {
		goto end_close;
	}

	ret = socks5_send_resolve_request(hostname, &conn);
	if (ret < 0) {
		goto end_close;
	}

	/* Force IPv4 resolution for now. */
	ret = socks5_recv_resolve_reply(&conn, ip_addr, addr_len);
	if (ret < 0) {
		goto end_close;
	}

end_close:
	if (tsocks_libc_close(conn.fd) < 0) {
		PERROR("close");
	}
end:
error:
	return ret;
}