socket_request
This commit is contained in:
parent
9e4aa98c04
commit
9aec4435ec
|
@ -10,13 +10,13 @@ struct wifi_client {
|
|||
struct avl_node avl;
|
||||
u8 addr[ETH_ALEN];
|
||||
time_t time;
|
||||
int try_probe;
|
||||
int try_auth;
|
||||
uint16_t try_probe;
|
||||
uint16_t try_auth;
|
||||
bool connected;
|
||||
bool authed;
|
||||
uint32_t freq_highest;
|
||||
uint32_t signal_lowfreq;
|
||||
uint32_t signal_highfreq;
|
||||
uint16_t freq_highest;
|
||||
uint16_t signal_lowfreq;
|
||||
uint16_t signal_highfreq;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include <libubox/usock.h>
|
||||
#include <libubox/ustream.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/time.h>
|
||||
#include <netinet/in.h>
|
||||
#include <net/if.h>
|
||||
#include <arpa/inet.h>
|
||||
|
|
|
@ -1,8 +1,71 @@
|
|||
#include "include.h"
|
||||
#include "log.h"
|
||||
#include "socket.h"
|
||||
#include "socket_msg.h"
|
||||
|
||||
static struct uloop_fd server;
|
||||
struct in6_addr ownaddr;
|
||||
struct sockaddr_in6 client_addr;
|
||||
|
||||
int socket_request_timeout(struct socket_msg *request, struct socket_msg *answer, struct timeval timeout) {
|
||||
int ret = 0;
|
||||
int sock = 0;
|
||||
char msg[REQUEST_MAXLEN];
|
||||
request->type = (request->type | SOCKET_MSG_TYPE_REQUEST);
|
||||
|
||||
ret = socket_msg_marshal(request, msg);
|
||||
if (ret) {
|
||||
log_error("socket_request: could not marshel message: %d\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
sock = socket(AF_INET6, SOCK_DGRAM, IPPROTO_UDP);
|
||||
if (sock < 0) {
|
||||
log_error("socket_request: could not create socket\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
int loop = 0;
|
||||
if(setsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, &loop, sizeof(loop)) < 0) {
|
||||
log_error("socket_request: unable to disable listen/loop own multicast package: %d\n", errno);
|
||||
return -1;
|
||||
}
|
||||
|
||||
ret = sendto(sock, msg, REQUEST_MAXLEN, 0, (struct sockaddr *)&client_addr, sizeof(client_addr));
|
||||
if (ret < 0) {
|
||||
close(sock);
|
||||
log_error("socket_request: could not send message: %d\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeout,sizeof(timeout));
|
||||
if(ret < 0) {
|
||||
close(sock);
|
||||
log_error("socket_request: unable to set timeout: %d\n", errno);
|
||||
return ret;
|
||||
}
|
||||
ret = recv(sock, msg, REQUEST_MAXLEN, 0);
|
||||
close(sock);
|
||||
if (ret < 0) {
|
||||
if(errno == EWOULDBLOCK)
|
||||
return ret;
|
||||
log_error("socket_request: could not recv message: %d\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = socket_msg_unmarshal(answer, msg);
|
||||
if (ret) {
|
||||
log_error("socket_request: could not unmarshel message: %d\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
log_verbose("socket_request: end %d\n", ret);
|
||||
if(answer->type & SOCKET_MSG_TYPE_RESPONSE) {
|
||||
return -1;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void server_cb(struct uloop_fd *fd, unsigned int events) {
|
||||
struct sockaddr_in6 addr;
|
||||
|
@ -46,28 +109,34 @@ int socket_init(char *ifname) {
|
|||
if (server.fd < 0) {
|
||||
return 1;
|
||||
}
|
||||
struct in6_addr mgroup_addr;
|
||||
|
||||
if (!inet_pton(AF_INET6, SOCKET_MADDR, &mgroup_addr)) {
|
||||
client_addr.sin6_family = AF_INET6;
|
||||
client_addr.sin6_port = htons(atoi(SOCKET_PORT));
|
||||
client_addr.sin6_scope_id = if_nametoindex(ifname);
|
||||
|
||||
// listen multicast
|
||||
if (!inet_pton(AF_INET6, SOCKET_MADDR, &client_addr.sin6_addr)) {
|
||||
log_error("socket: invalid multicast group\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
struct ipv6_mreq mreq;
|
||||
|
||||
mreq.ipv6mr_multiaddr = mgroup_addr;
|
||||
mreq.ipv6mr_interface = if_nametoindex(ifname);
|
||||
struct ipv6_mreq mreq = {
|
||||
.ipv6mr_multiaddr = client_addr.sin6_addr,
|
||||
.ipv6mr_interface = client_addr.sin6_scope_id,
|
||||
};
|
||||
|
||||
if (setsockopt(server.fd, IPPROTO_IPV6, IPV6_JOIN_GROUP, &mreq, sizeof(mreq)) == -1) {
|
||||
log_error("socket: unable to join multicast group\n");
|
||||
log_error("socket: unable to join multicast group: %d\n", errno);
|
||||
return -1;
|
||||
}
|
||||
|
||||
// end listen multicast
|
||||
uloop_fd_add(&server, ULOOP_READ);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void socket_close() {
|
||||
|
||||
uloop_fd_delete(&server);
|
||||
//ustream_free(&(server.fd));
|
||||
close(server.fd);
|
||||
}
|
||||
|
|
|
@ -1,13 +1,25 @@
|
|||
#ifndef __WIFICTLD_SOCKET_H
|
||||
#define __WIFICTLD_SOCKET_H
|
||||
|
||||
#include "include.h"
|
||||
#include "socket_msg.h"
|
||||
|
||||
#define SOCKET_ADDR "::"
|
||||
#define SOCKET_MADDR "ff02::31f1"
|
||||
#define SOCKET_PORT "1000"
|
||||
|
||||
#define REQUEST_MAXLEN 256
|
||||
|
||||
int socket_init();
|
||||
void socket_close();
|
||||
|
||||
int socket_request_timeout(struct socket_msg *request, struct socket_msg *answer, struct timeval timeout);
|
||||
|
||||
static inline int socket_request(struct socket_msg *request, struct socket_msg *answer)
|
||||
{
|
||||
struct timeval tv = {
|
||||
.tv_sec = 0,
|
||||
.tv_usec = 100000,
|
||||
};
|
||||
return socket_request_timeout(request, answer, tv);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -0,0 +1,100 @@
|
|||
#include "include.h"
|
||||
#include "socket_msg.h"
|
||||
|
||||
|
||||
int socket_msg_marshal(struct socket_msg *src, char dest[REQUEST_MAXLEN]) {
|
||||
uint32_t nl = 0;
|
||||
uint16_t ns = 0;
|
||||
int pos = 0;
|
||||
|
||||
memset(dest, 0, REQUEST_MAXLEN);
|
||||
|
||||
nl = htonl(src->type);
|
||||
memcpy(dest + pos, &nl, sizeof(nl));
|
||||
pos += sizeof(nl);
|
||||
|
||||
if (src->type & SOCKET_MSG_TYPE_CLIENT) {
|
||||
memcpy(dest + pos, src->client->addr, sizeof(src->client->addr));
|
||||
pos += sizeof(src->client->addr);
|
||||
|
||||
nl = htonl(src->client->time);
|
||||
memcpy(dest + pos, &nl, sizeof(nl));
|
||||
pos += sizeof(nl);
|
||||
|
||||
ns = htons(src->client->try_probe);
|
||||
memcpy(dest + pos, &ns, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
|
||||
ns = htons(src->client->try_auth);
|
||||
memcpy(dest + pos, &ns, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
|
||||
memcpy(dest + pos, &src->client->connected, sizeof(src->client->connected));
|
||||
pos += sizeof(src->client->connected);
|
||||
|
||||
memcpy(dest + pos, &src->client->authed, sizeof(src->client->authed));
|
||||
pos += sizeof(src->client->authed);
|
||||
|
||||
ns = htons(src->client->freq_highest);
|
||||
memcpy(dest + pos, &ns, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
|
||||
ns = htons(src->client->signal_lowfreq);
|
||||
memcpy(dest + pos, &ns, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
|
||||
ns = htons(src->client->signal_highfreq);
|
||||
memcpy(dest + pos, &ns, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
|
||||
}
|
||||
memset(dest + pos, 0, REQUEST_MAXLEN-pos);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int socket_msg_unmarshal(struct socket_msg *dest, char src[REQUEST_MAXLEN]) {
|
||||
uint32_t nl = 0;
|
||||
uint16_t ns = 0;
|
||||
int pos = 0;
|
||||
|
||||
memcpy(&nl, src + pos, sizeof(nl));
|
||||
pos += sizeof(nl);
|
||||
dest->type = ntohl(nl);
|
||||
|
||||
if (dest->type & SOCKET_MSG_TYPE_CLIENT) {
|
||||
memcpy(dest->client->addr, src + pos, sizeof(dest->client->addr));
|
||||
pos += sizeof(dest->client->addr);
|
||||
|
||||
memcpy(&nl, src + pos, sizeof(nl));
|
||||
pos += sizeof(nl);
|
||||
dest->client->time = ntohl(nl);
|
||||
|
||||
memcpy(&ns, src + pos, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
dest->client->try_probe = ntohs(ns);
|
||||
|
||||
memcpy(&ns, src + pos, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
dest->client->try_auth = ntohs(ns);
|
||||
|
||||
memcpy(&dest->client->connected, src + pos, sizeof(dest->client->connected));
|
||||
pos += sizeof(dest->client->connected);
|
||||
|
||||
memcpy(&dest->client->authed, src + pos, sizeof(dest->client->authed));
|
||||
pos += sizeof(dest->client->authed);
|
||||
|
||||
memcpy(&ns, src + pos, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
dest->client->freq_highest = ntohs(ns);
|
||||
|
||||
memcpy(&ns, src + pos, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
dest->client->signal_lowfreq = ntohs(ns);
|
||||
|
||||
memcpy(&ns, src + pos, sizeof(ns));
|
||||
pos += sizeof(ns);
|
||||
dest->client->signal_highfreq = ntohs(ns);
|
||||
}
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
#ifndef __WIFICTLD_SOCKET_MSG_H
|
||||
#define __WIFICTLD_SOCKET_MSG_H
|
||||
|
||||
#include "include.h"
|
||||
#include "data.h"
|
||||
|
||||
#define REQUEST_MAXLEN 256
|
||||
|
||||
enum socket_msg_type {
|
||||
SOCKET_MSG_TYPE_REQUEST = (1 << 0),
|
||||
SOCKET_MSG_TYPE_RESPONSE = (1 << 1),
|
||||
SOCKET_MSG_TYPE_CLIENT = (1 << 2),
|
||||
SOCKET_MSG_TYPE_STATS = (1 << 3),
|
||||
};
|
||||
|
||||
struct socket_msg {
|
||||
uint32_t type;
|
||||
struct wifi_client *client;
|
||||
};
|
||||
|
||||
int socket_msg_marshal(struct socket_msg *src, char dest[REQUEST_MAXLEN]);
|
||||
int socket_msg_unmarshal(struct socket_msg *dest, char src[REQUEST_MAXLEN]);
|
||||
|
||||
#endif
|
|
@ -142,20 +142,20 @@ static int receive_notify(struct ubus_context *ctx, struct ubus_object *obj, str
|
|||
if (!strcmp(method, "auth")) {
|
||||
hclient.auth = true;
|
||||
if (wifi_clients_try(&hclient)) {
|
||||
log_debug(" -> reject\n");
|
||||
log_verbose(" -> reject\n");
|
||||
return WLAN_STATUS_ASSOC_REJECTED_TEMPORARILY;
|
||||
}
|
||||
log_debug(" -> accept\n");
|
||||
log_verbose(" -> accept\n");
|
||||
return WLAN_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
if (!strcmp(method, "probe")) {
|
||||
if(config_client_probe_steering) {
|
||||
if (wifi_clients_try(&hclient)) {
|
||||
log_debug(" -> reject\n");
|
||||
log_verbose(" -> reject\n");
|
||||
return WLAN_STATUS_UNSPECIFIED_FAILURE;
|
||||
}
|
||||
log_debug(" -> accept\n");
|
||||
log_verbose(" -> accept\n");
|
||||
return WLAN_STATUS_SUCCESS;
|
||||
}
|
||||
if(config_client_probe_learning) {
|
||||
|
|
|
@ -3,6 +3,9 @@
|
|||
#include "log.h"
|
||||
#include "data.h"
|
||||
#include "wifi_clients.h"
|
||||
#ifndef MINI
|
||||
#include "socket.h"
|
||||
#endif
|
||||
|
||||
|
||||
void clean_cbhandler(struct uloop_timeout *t)
|
||||
|
@ -100,6 +103,16 @@ struct wifi_client *__get_client(struct hostapd_client *hclient){
|
|||
client->authed = false;
|
||||
client->freq_highest = 0;
|
||||
__client_setvalues(client, hclient);
|
||||
#ifndef MINI
|
||||
struct socket_msg req = {
|
||||
.type = SOCKET_MSG_TYPE_CLIENT,
|
||||
.client = client,
|
||||
}, resp;
|
||||
if(socket_request(&req, &resp) == 0){
|
||||
log_debug("wifi_clients.__get_client("MACSTR"): get client from neigbour\n", MAC2STR(hclient->address));
|
||||
return resp.client;
|
||||
}
|
||||
#endif
|
||||
client->avl.key = client->addr;
|
||||
log_debug("wifi_clients.__get_client("MACSTR"): add client to mem\n", MAC2STR(hclient->address));
|
||||
avl_insert(&clients_by_addr, &client->avl);
|
||||
|
|
Loading…
Reference in New Issue