first complete network stack version

This commit is contained in:
Martin/Geno 2018-08-05 19:35:16 +02:00
parent a4961cc6f2
commit 2349afd777
No known key found for this signature in database
GPG Key ID: 9D7D3C6BFF600C6A
10 changed files with 234 additions and 71 deletions

View File

@ -16,5 +16,6 @@ bool config_client_probe_steering = true;
bool config_client_probe_learning = false; bool config_client_probe_learning = false;
#ifndef MINI #ifndef MINI
bool config_client_socket_learning = true;
bool config_socket_always_answer = false;
#endif #endif

View File

@ -28,7 +28,8 @@ extern bool config_client_probe_steering;
extern bool config_client_probe_learning; extern bool config_client_probe_learning;
#ifndef MINI #ifndef MINI
extern bool config_client_socket_learning;
extern bool config_socket_always_answer;
#endif #endif
#endif #endif

View File

@ -27,11 +27,16 @@ struct option longopts[] = {
{"clean-every", required_argument, 0, 3}, {"clean-every", required_argument, 0, 3},
{"clean-older-then", required_argument, 0, 4}, {"clean-older-then", required_argument, 0, 4},
{"clean-authed", optional_argument, 0, 5}, {"clean-authed", optional_argument, 0, 5},
#ifndef MINI
// network options // network options
{"addr", required_argument, 0, 6}, {"addr", required_argument, 0, 6},
{"maddr", required_argument, 0, 7}, {"maddr", required_argument, 0, 7},
{"port", required_argument, 0, 8}, {"port", required_argument, 0, 8},
{"ifname", required_argument, 0, 9}, {"ifname", required_argument, 0, 9},
// other extended option
{"socket-learning", optional_argument, 0, 10},
{"socket-always-answer", optional_argument, 0, 11},
#endif
}; };
void usage(int c) { void usage(int c) {
@ -54,11 +59,16 @@ void usage(int c) {
printf(" --clean-every run cleaning every (current: %ds)\n", config_client_clean_every); printf(" --clean-every run cleaning every (current: %ds)\n", config_client_clean_every);
printf(" --clean-older-then clean unseen for secound (current: %ds)\n", config_client_clean_older_then); printf(" --clean-older-then clean unseen for secound (current: %ds)\n", config_client_clean_older_then);
printf(" --clean-authed clean already authed also (not only learned by probes) (current: %s)\n", BOOL2STR(config_client_clean_authed)); printf(" --clean-authed clean already authed also (not only learned by probes) (current: %s)\n", BOOL2STR(config_client_clean_authed));
#ifndef MINI
printf("\nnetwork options:\n"); printf("\nnetwork options:\n");
printf(" --addr listen on ip address (current: %s)\n", addr); printf(" --addr listen on ip address (current: %s)\n", addr);
printf(" --maddr listen and request on multcast address (current: %s)\n", maddr); printf(" --maddr listen and request on multcast address (current: %s)\n", maddr);
printf(" --port listen on port (current: %s)\n", port); printf(" --port listen on port (current: %s)\n", port);
printf(" --ifname listen on interface for multicast (current: %s)\n", ifname); printf(" --ifname listen on interface for multicast (current: %s)\n", ifname);
printf("\nother extended options:\n");
printf(" --socket-learning learn clients during listen on socket (current: %s)\n", BOOL2STR(config_client_socket_learning));
printf(" --socket-always-answer answer on socket only with useful information (current: %s)\n", BOOL2STR(config_socket_always_answer));
#endif
printf("\nSome config could be changed by ubus, see `ubus -v list wifictld`\n"); printf("\nSome config could be changed by ubus, see `ubus -v list wifictld`\n");
if(c) if(c)
printf("Invalid parameter %c ignored.\n", c); printf("Invalid parameter %c ignored.\n", c);
@ -143,6 +153,7 @@ int main(int argc, char *argv[])
else else
config_client_clean_authed = !config_client_clean_authed; config_client_clean_authed = !config_client_clean_authed;
break; break;
#ifndef MINI
// network options // network options
case 6: case 6:
addr = optarg; addr = optarg;
@ -156,6 +167,20 @@ int main(int argc, char *argv[])
case 9: case 9:
ifname = optarg; ifname = optarg;
break; break;
// other extended option
case 10:
if(optarg)
config_client_socket_learning = atoi(optarg);
else
config_client_socket_learning = !config_client_socket_learning;
break;
case 11:
if(optarg)
config_socket_always_answer = atoi(optarg);
else
config_socket_always_answer = !config_socket_always_answer;
break;
#endif
default: default:
usage(c); usage(c);
return 1; return 1;

View File

@ -1,10 +1,12 @@
#include "include.h" #include "include.h"
#include "log.h" #include "log.h"
#include "data.h"
#include "socket.h" #include "socket.h"
#include "socket_msg.h" #include "socket_msg.h"
#include "socket_handler.h"
static struct uloop_fd server; static struct uloop_fd server;
struct in6_addr ownaddr; struct sockaddr_in6 ownaddr;
struct sockaddr_in6 client_addr; struct sockaddr_in6 client_addr;
int socket_info(struct socket_msg *info) { int socket_info(struct socket_msg *info) {
@ -13,14 +15,16 @@ int socket_info(struct socket_msg *info) {
ret = socket_msg_marshal(info, msg); ret = socket_msg_marshal(info, msg);
if (ret) { if (ret) {
log_error("socket_request: could not marshel message: %d\n", ret); log_error("socket_info: could not marshel message: %d\n", ret);
return ret; return ret;
} }
ret = sendto(server.fd, msg, REQUEST_MAXLEN, 0, (struct sockaddr *)&client_addr, sizeof(client_addr)); ret = sendto(server.fd, msg, REQUEST_MAXLEN, 0, (struct sockaddr *)&client_addr, sizeof(client_addr));
if (ret < 0) { if (ret < 0) {
log_error("socket_request: could not send message: %d\n", ret); log_error("socket_info: could not send message: %d\n", ret);
} }
if(info->type & SOCKET_MSG_TYPE_CLIENT)
log_verbose("net-send(type=client mac="MACSTR" freq=%d ssi_l=%d ssi_h=%d tprobe=%d tauth=%d authed=%s time=%d)\n", MAC2STR(info->client->addr), info->client->freq_highest, info->client->signal_lowfreq, info->client->signal_highfreq, info->client->try_probe, info->client->try_auth, BOOL2STR(info->client->authed), info->client->time);
return ret; return ret;
} }
@ -42,6 +46,11 @@ int socket_request_timeout(struct socket_msg *request, struct socket_msg *answer
return -1; return -1;
} }
if(bind(sock, (struct sockaddr*)&ownaddr, sizeof(ownaddr))) {
log_error("socket_request: could not bind to addr\n");
return -1;
}
int loop = 0; int loop = 0;
if(setsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, &loop, sizeof(loop)) < 0) { if(setsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, &loop, sizeof(loop)) < 0) {
@ -55,7 +64,10 @@ int socket_request_timeout(struct socket_msg *request, struct socket_msg *answer
log_error("socket_request: could not send message: %d\n", ret); log_error("socket_request: could not send message: %d\n", ret);
return ret; return ret;
} }
if(request->type & SOCKET_MSG_TYPE_CLIENT)
log_verbose("net-send(type=request,client mac="MACSTR" freq=%d ssi_l=%d ssi_h=%d tprobe=%d tauth=%d authed=%s time=%d)\n", MAC2STR(request->client->addr), request->client->freq_highest, request->client->signal_lowfreq, request->client->signal_highfreq, request->client->try_probe, request->client->try_auth, BOOL2STR(request->client->authed), request->client->time);
// repeat to recieve best answer till timeout
ret = setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeout,sizeof(timeout)); ret = setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeout,sizeof(timeout));
if(ret < 0) { if(ret < 0) {
close(sock); close(sock);
@ -78,22 +90,30 @@ int socket_request_timeout(struct socket_msg *request, struct socket_msg *answer
return ret; return ret;
} }
log_verbose("socket_request: end %d\n", ret);
if (answer->type & SOCKET_MSG_TYPE_RESPONSE) { if (answer->type & SOCKET_MSG_TYPE_RESPONSE) {
if(answer->type & SOCKET_MSG_TYPE_CLIENT)
log_verbose("net-recv(type=response,client mac="MACSTR" freq=%d ssi_l=%d ssi_h=%d tprobe=%d tauth=%d authed=%s time=%d)\n", MAC2STR(answer->client->addr), answer->client->freq_highest, answer->client->signal_lowfreq, answer->client->signal_highfreq, answer->client->try_probe, answer->client->try_auth, BOOL2STR(answer->client->authed), answer->client->time);
return 0; return 0;
} }
log_verbose("socket_request: end %d\n", ret);
return -1; return -1;
} }
static void server_cb(struct uloop_fd *fd, unsigned int events) { static void server_cb(struct uloop_fd *fd, unsigned int events) {
int ret;
struct sockaddr_in6 addr; struct sockaddr_in6 addr;
char buf[REQUEST_MAXLEN];
char control[256]; char control[256];
char buf[REQUEST_MAXLEN];
struct socket_msg msg = {
.type = 0,
.client = malloc(sizeof(struct wifi_client)),
};
struct iovec iv = { struct iovec iv = {
.iov_base = buf, .iov_base = buf,
.iov_len = sizeof(buf) - 1 .iov_len = sizeof(buf)
}; };
struct msghdr mh = { struct msghdr mh = {
@ -110,15 +130,38 @@ static void server_cb(struct uloop_fd *fd, unsigned int events) {
return; return;
} }
char addr_str[INET6_ADDRSTRLEN]; ret = socket_msg_unmarshal(&msg, buf);
inet_ntop(AF_INET6, &(addr.sin6_addr), addr_str, INET6_ADDRSTRLEN); if (ret) {
log_info("socket:recv [%s]:%d - %s\n", addr_str, ntohs(addr.sin6_port), buf); log_error("socket: could not unmarshel message: %d\n", ret);
return;
}
log_verbose("net-recv(type=");
if(msg.type & SOCKET_MSG_TYPE_REQUEST)
log_verbose("request,");
if(msg.type & SOCKET_MSG_TYPE_RESPONSE)
log_verbose("response,");
if(msg.type & SOCKET_MSG_TYPE_CLIENT)
log_verbose("client mac="MACSTR" freq=%d ssi_l=%d ssi_h=%d tprobe=%d tauth=%d authed=%s time=%d)\n", MAC2STR(msg.client->addr), msg.client->freq_highest, msg.client->signal_lowfreq, msg.client->signal_highfreq, msg.client->try_probe, msg.client->try_auth, BOOL2STR(msg.client->authed), msg.client->time);
// response only if message are recieve
ret = socket_handler(&msg);
if (ret != SOCKET_HANDLER_RESPONSE) {
if(ret == SOCKET_HANDLER_ERROR)
log_error("socket_handler: returned with %d\n", ret);
return;
}
if (sendto(server.fd, addr_str, sizeof(addr_str) - 1, 0, (struct sockaddr *) &addr, sizeof(addr)) < 0) { ret = socket_msg_marshal(&msg, buf);
if (ret) {
log_error("socket: could not unmarshel message: %d\n", ret);
return;
}
if (sendto(server.fd, buf, sizeof(buf), 0, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
log_error("socket: could not send answer\n"); log_error("socket: could not send answer\n");
} }
log_info("socket: send answer\n"); if(msg.type & SOCKET_MSG_TYPE_CLIENT)
log_verbose("net-send(type=response,client mac="MACSTR" freq=%d ssi_l=%d ssi_h=%d tprobe=%d tauth=%d authed=%s time=%d)\n", MAC2STR(msg.client->addr), msg.client->freq_highest, msg.client->signal_lowfreq, msg.client->signal_highfreq, msg.client->try_probe, msg.client->try_auth, BOOL2STR(msg.client->authed), msg.client->time);
} }
int socket_init(char *ifname, char *socket_bind, char *socket_maddr, char *socket_port) { int socket_init(char *ifname, char *socket_bind, char *socket_maddr, char *socket_port) {
@ -132,6 +175,14 @@ int socket_init(char *ifname, char *socket_bind, char *socket_maddr, char *socke
client_addr.sin6_port = htons(atoi(socket_port)); client_addr.sin6_port = htons(atoi(socket_port));
client_addr.sin6_scope_id = if_nametoindex(ifname); client_addr.sin6_scope_id = if_nametoindex(ifname);
ownaddr.sin6_family = AF_INET6;
ownaddr.sin6_scope_id = client_addr.sin6_scope_id;
if(!inet_pton(AF_INET6, socket_bind, &ownaddr.sin6_addr)) {
log_error("socket: could not parse address for socket_request\n");
return -1;
}
// listen multicast // listen multicast
if (!inet_pton(AF_INET6, socket_maddr, &client_addr.sin6_addr)) { if (!inet_pton(AF_INET6, socket_maddr, &client_addr.sin6_addr)) {
log_error("socket: invalid multicast group\n"); log_error("socket: invalid multicast group\n");

View File

@ -0,0 +1,59 @@
#include "config.h"
#include "include.h"
#include "data.h"
#include "socket_msg.h"
#include "socket_handler.h"
static int handle_client(struct socket_msg *msg, int response) {
struct wifi_client *own_client;
own_client = avl_find_element(&clients_by_addr, msg->client->addr, own_client, avl);
if (own_client) {
// know client with higher freq
if (own_client->freq_highest < msg->client->freq_highest) {
return SOCKET_HANDLER_RESPONSE;
}
// learn freq
if (own_client->freq_highest < msg->client->freq_highest) {
own_client->freq_highest = msg->client->freq_highest;
}
if (!own_client->authed) {
own_client->authed = msg->client->authed;
}
if (own_client->time < msg->client->time) {
own_client->time = msg->client->time;
}
return response;
}
if(!config_client_socket_learning)
return SOCKET_HANDLER_SILENCE;
// learn client
msg->client->try_probe = 0;
msg->client->try_auth = 0;
msg->client->connected = false;
msg->client->avl.key = msg->client->addr;
avl_insert(&clients_by_addr, &msg->client->avl);
return SOCKET_HANDLER_SILENCE;
}
int socket_handler(struct socket_msg *msg) {
if(msg->type & SOCKET_MSG_TYPE_RESPONSE) {
return SOCKET_HANDLER_ERROR;
}
int ret = SOCKET_HANDLER_RESPONSE;
if(msg->type & SOCKET_MSG_TYPE_REQUEST) {
msg->type = (msg->type ^ SOCKET_MSG_TYPE_REQUEST) | SOCKET_MSG_TYPE_RESPONSE;
// single handlers
if(msg->type & SOCKET_MSG_TYPE_CLIENT) ret = handle_client(msg, SOCKET_HANDLER_RESPONSE);
return ret;
}
// single handlers
if(msg->type & SOCKET_MSG_TYPE_CLIENT) ret = handle_client(msg, SOCKET_HANDLER_SILENCE);
return ret;
}

View File

@ -0,0 +1,12 @@
#ifndef __WIFICTLD_SOCKET_HANDLER_H
#define __WIFICTLD_SOCKET_HANDLER_H
#include "socket_msg.h"
#define SOCKET_HANDLER_ERROR 2
#define SOCKET_HANDLER_SILENCE 1
#define SOCKET_HANDLER_RESPONSE 0
int socket_handler(struct socket_msg *info);
#endif

View File

@ -21,7 +21,7 @@ int wifictld_ubus_init()
// connect to ubus // connect to ubus
ctx = ubus_connect(UBUS_SOCKET); ctx = ubus_connect(UBUS_SOCKET);
if (!ctx) { if (!ctx) {
log_error("Failed to connect to ubus"); log_error("failed to connect to ubus\n");
return 1; return 1;
} }
@ -31,14 +31,14 @@ int wifictld_ubus_init()
// add bbs // add bbs
ret = wifictld_ubus_add_bss(ctx); ret = wifictld_ubus_add_bss(ctx);
if (ret) { if (ret) {
log_error("Failed to add ubus service"); log_error("failed to add ubus service\n");
return 1; return 1;
} }
// bind events // bind events
ret = wifictld_ubus_bind_events(ctx); ret = wifictld_ubus_bind_events(ctx);
if (ret) { if (ret) {
log_error("Failed to bind for ubus events"); log_error("failed to bind for ubus events\n");
return 2; return 2;
} }

View File

@ -32,7 +32,7 @@ int wifictld_ubus_bind_events(struct ubus_context *ctx)
// register subscriber on ubus // register subscriber on ubus
int ret = ubus_register_subscriber(ctx, &sub); int ret = ubus_register_subscriber(ctx, &sub);
if (ret) { if (ret) {
log_error("Error while registering subscriber: %s", ubus_strerror(ret)); log_error("error while registering subscriber: %s\n", ubus_strerror(ret));
ubus_free(ctx); ubus_free(ctx);
return 2; return 2;
} }
@ -138,38 +138,33 @@ static int receive_notify(struct ubus_context *ctx, struct ubus_object *obj, str
// handle // handle
log_verbose("%s["MACSTR"] freq: %d signal %d", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
if (!strcmp(method, "auth")) { if (!strcmp(method, "auth")) {
hclient.auth = true; hclient.auth = true;
if (wifi_clients_try(&hclient)) { if (wifi_clients_try(&hclient)) {
log_verbose(" -> reject\n"); log_verbose("%s["MACSTR"] freq: %d signal %d -> reject\n", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
return WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY; return WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY;
} }
log_verbose(" -> accept\n"); log_verbose("%s["MACSTR"] freq: %d signal %d -> accept\n", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
return WLAN_STATUS_SUCCESS; return WLAN_STATUS_SUCCESS;
} }
if (!strcmp(method, "probe")) { if (!strcmp(method, "probe")) {
if(config_client_probe_steering) { if(config_client_probe_steering) {
if (wifi_clients_try(&hclient)) { if (wifi_clients_try(&hclient)) {
log_verbose(" -> reject\n"); log_verbose("%s["MACSTR"] freq: %d signal %d -> reject\n", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
return WLAN_STATUS_UNSPECIFIED_FAILURE; return WLAN_STATUS_UNSPECIFIED_FAILURE;
} }
log_verbose(" -> accept\n"); log_verbose("%s["MACSTR"] freq: %d signal %d -> accept\n", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
return WLAN_STATUS_SUCCESS; return WLAN_STATUS_SUCCESS;
} }
if(config_client_probe_learning) { if(config_client_probe_learning) {
log_verbose(" learn"); log_verbose("%s["MACSTR"] freq: %d signal %d -> learn\n", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
wifi_clients_learn(&hclient); wifi_clients_learn(&hclient);
} }
} } else {
if (!strcmp(method, "deauth")) {
wifi_clients_disconnect(&hclient); wifi_clients_disconnect(&hclient);
log_verbose(" -> disconnect\n"); log_verbose("%s["MACSTR"] freq: %d signal %d -> disconnect\n", method, MAC2STR(addr), hclient.freq, hclient.ssi_signal);
return WLAN_STATUS_SUCCESS;
} }
log_verbose("\n");
return WLAN_STATUS_SUCCESS; return WLAN_STATUS_SUCCESS;
} }

View File

@ -88,6 +88,8 @@ static int ubus_get_config(struct ubus_context *ctx, struct ubus_object *obj,
blobmsg_add_bool(&b, "client_probe_steering", config_client_probe_steering); blobmsg_add_bool(&b, "client_probe_steering", config_client_probe_steering);
blobmsg_add_bool(&b, "client_probe_learning", config_client_probe_learning); blobmsg_add_bool(&b, "client_probe_learning", config_client_probe_learning);
#ifndef MINI #ifndef MINI
blobmsg_add_bool(&b, "client_socket_learning", config_client_socket_learning);
blobmsg_add_bool(&b, "socket_always_answer", config_socket_always_answer);
#endif #endif
blobmsg_close_table(&b, list); blobmsg_close_table(&b, list);
@ -110,6 +112,8 @@ enum {
SET_CONFIG_CLIENT_PROBE_STEERING, SET_CONFIG_CLIENT_PROBE_STEERING,
SET_CONFIG_CLIENT_PROBE_LEARNING, SET_CONFIG_CLIENT_PROBE_LEARNING,
#ifndef MINI #ifndef MINI
SET_CONFIG_CLIENT_SOCKET_LEARNING,
SET_CONFIG_SOCKET_ALWAYS_ANSWER,
#endif #endif
__SET_CONFIG_MAX __SET_CONFIG_MAX
}; };
@ -126,6 +130,8 @@ static const struct blobmsg_policy ubus_set_config_policy[__SET_CONFIG_MAX] = {
[SET_CONFIG_CLIENT_PROBE_STEERING] = { "client_probe_steering", BLOBMSG_TYPE_BOOL }, [SET_CONFIG_CLIENT_PROBE_STEERING] = { "client_probe_steering", BLOBMSG_TYPE_BOOL },
[SET_CONFIG_CLIENT_PROBE_LEARNING] = { "client_probe_learning", BLOBMSG_TYPE_BOOL }, [SET_CONFIG_CLIENT_PROBE_LEARNING] = { "client_probe_learning", BLOBMSG_TYPE_BOOL },
#ifndef MINI #ifndef MINI
[SET_CONFIG_CLIENT_SOCKET_LEARNING] = { "client_socket_learning", BLOBMSG_TYPE_BOOL },
[SET_CONFIG_SOCKET_ALWAYS_ANSWER] = { "socket_always_answer", BLOBMSG_TYPE_BOOL },
#endif #endif
}; };
@ -147,7 +153,9 @@ static int ubus_set_config(struct ubus_context *ctx, struct ubus_object *obj,
!tb[SET_CONFIG_CLIENT_PROBE_STEERING] && !tb[SET_CONFIG_CLIENT_PROBE_STEERING] &&
!tb[SET_CONFIG_CLIENT_PROBE_LEARNING] !tb[SET_CONFIG_CLIENT_PROBE_LEARNING]
#ifndef MINI #ifndef MINI
// && &&
!tb[SET_CONFIG_CLIENT_SOCKET_LEARNING] &&
!tb[SET_CONFIG_SOCKET_ALWAYS_ANSWER]
#endif #endif
) )
return UBUS_STATUS_INVALID_ARGUMENT; return UBUS_STATUS_INVALID_ARGUMENT;
@ -172,6 +180,10 @@ static int ubus_set_config(struct ubus_context *ctx, struct ubus_object *obj,
if (tb[SET_CONFIG_CLIENT_PROBE_LEARNING]) if (tb[SET_CONFIG_CLIENT_PROBE_LEARNING])
config_client_probe_learning = blobmsg_get_bool(tb[SET_CONFIG_CLIENT_PROBE_LEARNING]); config_client_probe_learning = blobmsg_get_bool(tb[SET_CONFIG_CLIENT_PROBE_LEARNING]);
#ifndef MINI #ifndef MINI
if (tb[SET_CONFIG_CLIENT_SOCKET_LEARNING])
config_client_socket_learning = blobmsg_get_bool(tb[SET_CONFIG_CLIENT_SOCKET_LEARNING]);
if (tb[SET_CONFIG_SOCKET_ALWAYS_ANSWER])
config_socket_always_answer = blobmsg_get_bool(tb[SET_CONFIG_SOCKET_ALWAYS_ANSWER]);
#endif #endif
return 0; return 0;

View File

@ -32,17 +32,20 @@ void clean_cbhandler(struct uloop_timeout *t)
} }
uloop_timeout_set(t, config_client_clean_every * 1000); uloop_timeout_set(t, config_client_clean_every * 1000);
if (count > 0) { if (count == 0) {
log_info("remove %d of %d clients", count, all);
if(!config_client_clean_authed)
log_info(" (skipped %d authed clients)", auth);
log_info(" from memory\n");
}else{
log_verbose("remove %d of %d clients", count, all); log_verbose("remove %d of %d clients", count, all);
if(!config_client_clean_authed) if(!config_client_clean_authed)
log_verbose(" (skipped %d authed clients)", auth); log_verbose(" (skipped %d authed clients)", auth);
log_verbose(" from memory\n"); log_verbose(" from memory\n");
return;
} }
log_info("remove %d of %d clients", count, all);
if(!config_client_clean_authed)
log_info(" (skipped %d authed clients)", auth);
log_info(" from memory\n");
return;
} }
struct uloop_timeout clean = { struct uloop_timeout clean = {
@ -65,7 +68,8 @@ void wifi_clients_close() {
} }
void __client_setvalues(struct wifi_client *client, struct hostapd_client *hclient) { bool __client_setvalues(struct wifi_client *client, struct hostapd_client *hclient) {
bool updated = false;
log_debug("wifi_clients.__client_setvalues(., %d):", hclient->freq); log_debug("wifi_clients.__client_setvalues(., %d):", hclient->freq);
if (client->freq_highest < hclient->freq) { if (client->freq_highest < hclient->freq) {
client->freq_highest = hclient->freq; client->freq_highest = hclient->freq;
@ -74,15 +78,18 @@ void __client_setvalues(struct wifi_client *client, struct hostapd_client *hclie
if (hclient->freq > WIFI_CLIENT_FREQ_THREASHOLD) { if (hclient->freq > WIFI_CLIENT_FREQ_THREASHOLD) {
client->signal_highfreq = hclient->ssi_signal; client->signal_highfreq = hclient->ssi_signal;
client->signal_lowfreq = 0; client->signal_lowfreq = 0;
//here to skip socket_request
updated = true;
}else{ }else{
client->signal_highfreq = 0; client->signal_highfreq = 0;
client->signal_lowfreq = hclient->ssi_signal; client->signal_lowfreq = hclient->ssi_signal;
} }
log_debug("\n");
time(&client->time); time(&client->time);
if(!client->authed) { if(!client->authed) {
client->authed = hclient->auth; client->authed = hclient->auth;
} }
log_debug("\n");
return updated;
} }
struct wifi_client *__get_client(struct hostapd_client *hclient){ struct wifi_client *__get_client(struct hostapd_client *hclient){
@ -90,7 +97,17 @@ struct wifi_client *__get_client(struct hostapd_client *hclient){
client = avl_find_element(&clients_by_addr, hclient->address, client, avl); client = avl_find_element(&clients_by_addr, hclient->address, client, avl);
if (client) { if (client) {
#ifdef MINI
__client_setvalues(client, hclient); __client_setvalues(client, hclient);
#else
if (__client_setvalues(client, hclient)) {
struct socket_msg msg = {
.type = SOCKET_MSG_TYPE_CLIENT,
.client = client,
};
socket_info(&msg);
}
#endif
log_debug("wifi_clients.__get_client("MACSTR"): found existing client\n", MAC2STR(hclient->address)); log_debug("wifi_clients.__get_client("MACSTR"): found existing client\n", MAC2STR(hclient->address));
return client; return client;
} }
@ -104,21 +121,24 @@ struct wifi_client *__get_client(struct hostapd_client *hclient){
client->freq_highest = 0; client->freq_highest = 0;
__client_setvalues(client, hclient); __client_setvalues(client, hclient);
#ifndef MINI #ifdef MINI
struct socket_msg req = { __client_setvalues(client, hclient);
.type = SOCKET_MSG_TYPE_CLIENT, #else
.client = client, if(__client_setvalues(client, hclient)) {
}, resp = { struct socket_msg req = {
.client = malloc(sizeof(*client)), .type = SOCKET_MSG_TYPE_CLIENT,
}; .client = client,
}, resp = {
.client = malloc(sizeof(struct wifi_client)),
};
if(socket_request(&req, &resp) == 0){ if(socket_request(&req, &resp) == 0){
log_debug("wifi_clients.__get_client("MACSTR"): get client from neigbour\n", MAC2STR(hclient->address)); if (client->freq_highest < resp.client->freq_highest) {
if (client->freq_highest < resp.client->freq_highest) { client->freq_highest = resp.client->freq_highest;
client->freq_highest = resp.client->freq_highest; }
} if(!client->authed) {
if(!client->authed) { client->authed = resp.client->authed;
client->authed = resp.client->authed; }
} }
} }
#endif #endif
@ -133,23 +153,10 @@ void wifi_clients_learn(struct hostapd_client *hclient) {
__get_client(hclient); __get_client(hclient);
} }
#ifdef MINI
#define returnINFO_CLIENT return
#else
#define returnINFO_CLIENT if(config_client_force_probe && !hclient->auth) socket_info(&msg); return
#endif
int wifi_clients_try(struct hostapd_client *hclient) { int wifi_clients_try(struct hostapd_client *hclient) {
struct wifi_client *client; struct wifi_client *client;
client = __get_client(hclient); client = __get_client(hclient);
#ifndef MINI
struct socket_msg msg = {
.type = SOCKET_MSG_TYPE_CLIENT,
.client = client,
};
#endif
if (hclient->auth) { if (hclient->auth) {
log_info("auth(try=%d mac="MACSTR" freq=%d ssi=%d): ", client->try_auth, MAC2STR(hclient->address), hclient->freq, hclient->ssi_signal); log_info("auth(try=%d mac="MACSTR" freq=%d ssi=%d): ", client->try_auth, MAC2STR(hclient->address), hclient->freq, hclient->ssi_signal);
@ -167,12 +174,12 @@ int wifi_clients_try(struct hostapd_client *hclient) {
if(!hclient->auth){ if(!hclient->auth){
client->try_probe = 0; client->try_probe = 0;
log_verbose("accept\n"); log_verbose("accept\n");
returnINFO_CLIENT 0; return 0;
} }
log_info("accept\n"); log_info("accept\n");
client->try_auth = 0; client->try_auth = 0;
client->connected = 1; client->connected = 1;
returnINFO_CLIENT 0; return 0;
} }
if (client->freq_highest > WIFI_CLIENT_FREQ_THREASHOLD) { if (client->freq_highest > WIFI_CLIENT_FREQ_THREASHOLD) {
if (config_client_force || config_client_force_probe && !hclient->auth) { if (config_client_force || config_client_force_probe && !hclient->auth) {