Browse Source

replace fake ICMP echo reply with test_loopback flag, honest error when no raw socket

congestion
Evgeny 5 months ago
parent
commit
edeb83ce89
  1. 11
      src/icmp_proxy.c
  2. 3
      src/icmp_proxy.h
  3. 2
      tests/test_icmp_proxy.c

11
src/icmp_proxy.c

@ -124,8 +124,7 @@ static void exit_handle_request(struct ETCP_CONN* conn, struct ll_entry* entry)
if (g_icmp_ctx->raw_sock != SOCKET_INVALID) {
exit_send_echo(inst, client_node_id, dst_ip, echo_id, echo_seq, payload, payload_len);
} else {
// No raw socket (e.g. no root): send simulated echo reply back to client
} else if (g_icmp_ctx->test_loopback) {
struct ll_entry* e = queue_entry_new(0);
if (e) {
e->dgram = u_malloc(ICMP_PROXY_HDR_SIZE + payload_len);
@ -141,6 +140,8 @@ static void exit_handle_request(struct ETCP_CONN* conn, struct ll_entry* entry)
etcp_route_send(inst, client_node_id, e);
} else queue_entry_free(e);
}
} else {
DEBUG_ERROR(DEBUG_CATEGORY_SOCKET, "icmp_proxy: no raw socket, dropping echo request to 0x%08x", dst_ip);
}
drop:
@ -240,6 +241,11 @@ int icmp_proxy_deliver_reply(struct UTUN_INSTANCE* inst,
return 0;
}
void icmp_proxy_set_test_loopback(struct UTUN_INSTANCE* inst, int enabled) {
(void)inst;
if (g_icmp_ctx) g_icmp_ctx->test_loopback = enabled;
}
static void req_expire(struct icmp_proxy_ctx* ctx) {
uint64_t now = get_time_tb(); struct icmp_request** prev = &ctx->pending;
while (*prev) {
@ -259,6 +265,7 @@ int icmp_proxy_init(struct UTUN_INSTANCE* inst, struct UASYNC* ua) {
ctx->inst = inst; ctx->ua = ua; ctx->raw_sock = SOCKET_INVALID;
ctx->request_timeout_tb = ICMP_TIMEOUT_TB;
ctx->is_exit = inst->remote_proxy.enabled;
ctx->test_loopback = 0;
g_icmp_ctx = ctx;
if (ctx->is_exit) {

3
src/icmp_proxy.h

@ -40,6 +40,7 @@ struct icmp_proxy_ctx {
void* raw_read_id;
struct icmp_request* pending;
uint64_t request_timeout_tb;
int test_loopback; // 1 = virtual loopback when no raw socket (test only)
};
int icmp_proxy_init(struct UTUN_INSTANCE* inst, struct UASYNC* ua);
@ -57,4 +58,6 @@ int icmp_proxy_deliver_reply(struct UTUN_INSTANCE* inst,
uint32_t src_ip, uint16_t echo_id, uint16_t echo_seq,
const uint8_t* payload, size_t payload_len);
void icmp_proxy_set_test_loopback(struct UTUN_INSTANCE* inst, int enabled);
#endif // ICMP_PROXY_H

2
tests/test_icmp_proxy.c

@ -154,6 +154,8 @@ int main(void) {
if (utun_instance_init(cli) < 0) { printf("[FAIL] client init\n"); goto done; }
if (utun_instance_init(exit_node) < 0) { printf("[FAIL] exit init\n"); goto done; }
icmp_proxy_set_test_loopback(exit_node, 1);
g_to_id = uasync_set_timeout(ua, 100, NULL, monitor, "mon");
void* to_id = uasync_set_timeout(ua, TEST_TIMEOUT_MS * 10, NULL, test_timeout, "to");

Loading…
Cancel
Save