0
0
mirror of https://github.com/hufrea/byedpi.git synced 2025-06-29 18:21:14 +00:00

Dump cache, save hostname

This commit is contained in:
ruti 2025-06-11 21:00:42 +03:00
parent 110ad77ee4
commit f711eebb69
7 changed files with 143 additions and 54 deletions

View File

@ -106,6 +106,10 @@ void del_event(struct poolhd *pool, struct eval *val)
val->restore_fake = 0;
}
#endif
if (val->host) {
free(val->host);
val->host = 0;
}
close(val->fd);
val->fd = -1;
val->mod_iter = pool->iters;

View File

@ -75,6 +75,8 @@ struct eval {
struct buffer *buff, *sq_buff;
int flag;
union sockaddr_u addr;
char *host;
int host_len;
ssize_t recv_count;
ssize_t round_sent;

115
extend.c
View File

@ -23,8 +23,6 @@
#include "desync.h"
#include "packets.h"
#define KEY_SIZE sizeof(union sockaddr_u)
static int set_timeout(int fd, unsigned int s)
{
@ -48,79 +46,63 @@ static int set_timeout(int fd, unsigned int s)
static ssize_t serialize_addr(const union sockaddr_u *dst,
uint8_t *const out, const size_t out_len)
struct cache_key *out)
{
#define serialize(raw, field, len, counter){ \
const size_t size = sizeof(field); \
if ((counter + size) <= len) { \
memcpy(raw + counter, &(field), size); \
counter += size; \
} else return 0; \
}
size_t c = 0;
serialize(out, dst->in.sin_port, out_len, c);
serialize(out, dst->sa.sa_family, out_len, c);
out->port = dst->in.sin_port;
out->family = dst->sa.sa_family;
static const ssize_t c = offsetof(struct cache_key, ip.v4);
if (dst->sa.sa_family == AF_INET) {
serialize(out, dst->in.sin_addr, out_len, c);
} else {
serialize(out, dst->in6.sin6_addr, out_len, c);
out->ip.v4 = dst->in.sin_addr;
return c + sizeof(out->ip.v4);
}
else {
out->ip.v6 = dst->in6.sin6_addr;
return c + sizeof(out->ip.v6);
}
#undef serialize
return c;
}
static void cache_del(const union sockaddr_u *dst)
{
uint8_t key[KEY_SIZE] = { 0 };
int len = serialize_addr(dst, key, sizeof(key));
INIT_ADDR_STR((*dst));
LOG(LOG_S, "delete ip: %s\n", ADDR_STR);
mem_delete(params.mempool, (char *)key, len);
}
static struct elem_i *cache_get(const union sockaddr_u *dst)
{
uint8_t key[KEY_SIZE] = { 0 };
int len = serialize_addr(dst, key, sizeof(key));
struct cache_key key = { 0 };
int len = serialize_addr(dst, &key);
struct elem_i *val = (struct elem_i *)mem_get(params.mempool, (char *)key, len);
struct elem_i *val = (struct elem_i *)mem_get(params.mempool, (char *)&key, len);
if (!val) {
return 0;
}
time_t t = time(0);
if (t > val->time + params.cache_ttl) {
if (t > val->time + params.cache_ttl || val->dp == params.dp) {
LOG(LOG_S, "time=%jd, now=%jd, ignore\n", (intmax_t)val->time, (intmax_t)t);
mem_delete(params.mempool, (char *)key, len);
mem_delete(params.mempool, (char *)&key, len);
return 0;
}
return val;
}
static struct elem_i *cache_add(const union sockaddr_u *dst)
static struct elem_i *cache_add(
const union sockaddr_u *dst, const char *host, int host_len)
{
uint8_t key[KEY_SIZE] = { 0 };
int len = serialize_addr(dst, key, sizeof(key));
INIT_ADDR_STR((*dst));
LOG(LOG_S, "save ip: %s\n", ADDR_STR);
struct cache_key key = { 0 };
int cmp_len = serialize_addr(dst, &key);
time_t t = time(0);
char *key_d = malloc(len);
if (!key_d) {
size_t total = sizeof(struct cache_data) + host_len;
struct cache_data *data = malloc(total);
if (!data) {
return 0;
}
memcpy(key_d, key, len);
memcpy(data, &key, cmp_len);
struct elem_i *val = (struct elem_i *)mem_add(params.mempool, key_d, len, sizeof(struct elem_i));
data->host_len = host_len;
memcpy(data->host, host, host_len);
struct elem_i *val = (struct elem_i *)mem_add(params.mempool, (char *)data, cmp_len, sizeof(struct elem_i));
if (!val) {
uniperror("mem_add");
free(key_d);
free(data);
return 0;
}
val->time = t;
@ -287,7 +269,8 @@ static bool check_round(const int *nr, int r)
static int on_trigger(int type, struct poolhd *pool, struct eval *val)
{
struct desync_params *dp = val->pair->dp->next;
struct desync_params *dp = val->pair->dp;
dp->fail_count++;
struct buffer *pair_buff = val->pair->sq_buff;
bool can_reconn = (
@ -298,14 +281,18 @@ static int on_trigger(int type, struct poolhd *pool, struct eval *val)
if (!can_reconn && params.auto_level <= AUTO_NOSAVE) {
return -1;
}
for (; dp; dp = dp->next) {
INIT_ADDR_STR((val->addr));
for (dp = dp->next; dp; dp = dp->next) {
if (!dp->detect) {
break;
}
if (!(dp->detect & type)) {
continue;
}
struct elem_i *e = cache_add(&val->addr);
LOG(LOG_S, "save: ip=%s, id=%d\n", ADDR_STR, dp->id);
struct elem_i *e = cache_add(&val->addr, val->pair->host, val->pair->host_len);
if (e) {
e->dp = dp;
}
@ -314,7 +301,12 @@ static int on_trigger(int type, struct poolhd *pool, struct eval *val)
}
return -1;
}
cache_del(&val->addr);
LOG(LOG_S, "unreach ip: %s\n", ADDR_STR);
struct elem_i *e = cache_add(&val->addr, val->pair->host, val->pair->host_len);
if (e) {
e->dp = params.dp;
}
return -1;
}
@ -381,8 +373,31 @@ static inline void free_first_req(struct poolhd *pool, struct eval *client)
}
static void save_hostname(struct eval *client, const char *buffer, ssize_t n)
{
if (client->host) {
return;
}
char *host = 0;
int len = parse_tls(buffer, n, &host);
if (!len) {
if (!(len = parse_http(buffer, n, &host, 0))) {
return;
}
}
if (!(client->host = malloc(len))) {
return;
}
memcpy(client->host, host, len);
client->host_len = len;
}
static int setup_conn(struct eval *client, const char *buffer, ssize_t n)
{
if (params.cache_file) {
save_hostname(client, buffer, n);
}
struct desync_params *dp = client->dp, *init_dp = dp;
for (; dp; dp = dp->next) {

23
main.c
View File

@ -88,6 +88,7 @@ static const char help_text[] = {
" Detect: torst,redirect,ssl_err,none\n"
" -L, --auto-mode <0|1> 1 - handle trigger after several packets\n"
" -u, --cache-ttl <sec> Lifetime of cached desync params for IP\n"
" -y, --cache-dump <file|-> Dump cache to file or stdout\n"
#ifdef TIMEOUT_SUPPORT
" -T, --timeout <sec> Timeout waiting for response, after which trigger auto\n"
#endif
@ -155,6 +156,7 @@ const struct option options[] = {
{"timeout", 1, 0, 'T'},
#endif
{"copy", 1, 0, 'B'},
{"cache-dump", 1, 0, 'y'},
{"proto", 1, 0, 'K'},
{"hosts", 1, 0, 'H'},
{"pf", 1, 0, 'V'},
@ -666,7 +668,7 @@ int main(int argc, char **argv)
params.baddr.sa.sa_family = AF_INET;
}
char *pid_file = 0;
const char *pid_file = 0;
bool daemonize = 0;
int rez;
@ -765,6 +767,10 @@ int main(int argc, char **argv)
invalid = 1;
break;
case 'y': //
params.cache_file = optarg;
break;
// desync options
case 'F':
@ -1190,6 +1196,21 @@ int main(int argc, char **argv)
}
#endif
int status = run(&params.laddr);
for (dp = params.dp; dp; dp = dp->next) {
LOG(LOG_S, "group: %d, triggered: %d\n", dp->id, dp->fail_count);
}
if (params.cache_file) {
FILE *f;
if (!strcmp(params.cache_file, "-"))
f = stdout;
else
f = fopen(params.cache_file, "w");
if (!f)
perror("fopen");
else
dump_cache(params.mempool, f);
}
clear_params();
return status;
}

23
mpool.c
View File

@ -147,3 +147,26 @@ void mem_destroy(struct mphdr *hdr)
}
free(hdr);
}
void dump_cache(struct mphdr *hdr, FILE *out)
{
if (!hdr->root) {
return;
}
kavl_itr_t(my) itr;
kavl_itr_first(my, hdr->root, &itr);
do {
const struct elem_i *p = (const struct elem_i *)kavl_at(&itr);
struct cache_data *value = (struct cache_data *)p->i.data;
char ADDR_STR[INET6_ADDRSTRLEN];
if (value->key.family == AF_INET)
inet_ntop(AF_INET, &value->key.ip.v4, ADDR_STR, sizeof(ADDR_STR));
else
inet_ntop(AF_INET6, &value->key.ip.v6, ADDR_STR, sizeof(ADDR_STR));
fprintf(out, "%s %d %d %jd %.*s\n",
ADDR_STR, ntohs(value->key.port), p->dp->id, (intmax_t)p->time, value->host_len, value->host);
} while (kavl_itr_next(my, &itr));
}

25
mpool.h
View File

@ -3,12 +3,33 @@
#include <stdbool.h>
#include <time.h>
#include "kavl.h"
#include "params.h"
#define CMP_BYTES 0
#define CMP_BITS 1
#define CMP_HOST 2
#pragma pack(push, 1)
struct cache_key {
uint16_t family;
uint16_t port;
union {
struct in_addr v4;
struct in6_addr v6;
} ip;
};
struct cache_data {
struct cache_key key;
int host_len;
char host[];
};
#pragma pack(pop)
struct elem {
int len;
char *data;
@ -18,7 +39,7 @@ struct elem {
struct elem_i {
struct elem i;
void *dp;
struct desync_params *dp;
time_t time;
};
@ -39,4 +60,6 @@ void mem_delete(struct mphdr *hdr, const char *str, int len);
void mem_destroy(struct mphdr *hdr);
void dump_cache(struct mphdr *hdr, FILE *out);
#endif

View File

@ -6,8 +6,6 @@
#include <stdbool.h>
#include <assert.h>
#include "mpool.h"
#ifdef _WIN32
#include <ws2tcpip.h>
#else
@ -17,6 +15,8 @@
#include <sys/socket.h>
#endif
#include "mpool.h"
#if defined(__linux__) || defined(_WIN32)
#define FAKE_SUPPORT 1
#define TIMEOUT_SUPPORT 1
@ -145,6 +145,7 @@ struct params {
const char *protect_path;
const char *pid_file;
int pid_fd;
const char *cache_file;
};
extern struct params params;