128
wpa_supplicant_ctrl_iface_get_cookie(struct ctrl_iface_priv *priv,
132
reply = malloc(7 + 2 * COOKIE_LEN + 1);
138
memcpy(reply, "COOKIE=", 7);
139
wpa_snprintf_hex(reply + 7, 2 * COOKIE_LEN + 1,
140
priv->cookie, COOKIE_LEN);
142
*reply_len = 7 + 2 * COOKIE_LEN;
123
147
static void wpa_supplicant_ctrl_iface_receive(int sock, void *eloop_ctx,
126
150
struct wpa_supplicant *wpa_s = eloop_ctx;
127
151
struct ctrl_iface_priv *priv = sock_ctx;
130
154
struct sockaddr_in from;
131
155
socklen_t fromlen = sizeof(from);
132
156
char *reply = NULL;
133
157
size_t reply_len = 0;
134
158
int new_attached = 0;
159
u8 cookie[COOKIE_LEN];
136
161
res = recvfrom(sock, buf, sizeof(buf) - 1, 0,
137
162
(struct sockaddr *) &from, &fromlen);
139
164
perror("recvfrom(ctrl_iface)");
167
if (from.sin_addr.s_addr != htonl((127 << 24) | 1)) {
169
* The OS networking stack is expected to drop this kind of
170
* frames since the socket is bound to only localhost address.
171
* Just in case, drop the frame if it is coming from any other
174
wpa_printf(MSG_DEBUG, "CTRL: Drop packet from unexpected "
175
"source %s", inet_ntoa(from.sin_addr));
144
if (strcmp(buf, "ATTACH") == 0) {
180
if (strcmp(buf, "GET_COOKIE") == 0) {
181
reply = wpa_supplicant_ctrl_iface_get_cookie(priv, &reply_len);
186
* Require that the client includes a prefix with the 'cookie' value
187
* fetched with GET_COOKIE command. This is used to verify that the
188
* client has access to a bidirectional link over UDP in order to
189
* avoid attacks using forged localhost IP address even if the OS does
190
* not block such frames from remote destinations.
192
if (strncmp(buf, "COOKIE=", 7) != 0) {
193
wpa_printf(MSG_DEBUG, "CTLR: No cookie in the request - "
198
if (hexstr2bin(buf + 7, cookie, COOKIE_LEN) < 0) {
199
wpa_printf(MSG_DEBUG, "CTLR: Invalid cookie format in the "
200
"request - drop request");
204
if (memcmp(cookie, priv->cookie, COOKIE_LEN) != 0) {
205
wpa_printf(MSG_DEBUG, "CTLR: Invalid cookie in the request - "
210
pos = buf + 7 + 2 * COOKIE_LEN;
214
if (strcmp(pos, "ATTACH") == 0) {
145
215
if (wpa_supplicant_ctrl_iface_attach(priv, &from, fromlen))
148
218
new_attached = 1;
151
} else if (strcmp(buf, "DETACH") == 0) {
221
} else if (strcmp(pos, "DETACH") == 0) {
152
222
if (wpa_supplicant_ctrl_iface_detach(priv, &from, fromlen))
156
} else if (strncmp(buf, "LEVEL ", 6) == 0) {
226
} else if (strncmp(pos, "LEVEL ", 6) == 0) {
157
227
if (wpa_supplicant_ctrl_iface_level(priv, &from, fromlen,
163
reply = wpa_supplicant_ctrl_iface_process(wpa_s, buf,
233
reply = wpa_supplicant_ctrl_iface_process(wpa_s, pos,
168
239
sendto(sock, reply, reply_len, 0, (struct sockaddr *) &from,
316
389
struct ctrl_iface_global_priv {
391
u8 cookie[COOKIE_LEN];
396
wpa_supplicant_global_get_cookie(struct ctrl_iface_global_priv *priv,
400
reply = malloc(7 + 2 * COOKIE_LEN + 1);
406
memcpy(reply, "COOKIE=", 7);
407
wpa_snprintf_hex(reply + 7, 2 * COOKIE_LEN + 1,
408
priv->cookie, COOKIE_LEN);
410
*reply_len = 7 + 2 * COOKIE_LEN;
321
415
static void wpa_supplicant_global_ctrl_iface_receive(int sock, void *eloop_ctx,
324
418
struct wpa_global *global = eloop_ctx;
419
struct ctrl_iface_global_priv *priv = sock_ctx;
327
422
struct sockaddr_in from;
328
423
socklen_t fromlen = sizeof(from);
330
425
size_t reply_len;
426
u8 cookie[COOKIE_LEN];
332
428
res = recvfrom(sock, buf, sizeof(buf) - 1, 0,
333
429
(struct sockaddr *) &from, &fromlen);
335
431
perror("recvfrom(ctrl_iface)");
434
if (from.sin_addr.s_addr != htonl((127 << 24) | 1)) {
436
* The OS networking stack is expected to drop this kind of
437
* frames since the socket is bound to only localhost address.
438
* Just in case, drop the frame if it is coming from any other
441
wpa_printf(MSG_DEBUG, "CTRL: Drop packet from unexpected "
442
"source %s", inet_ntoa(from.sin_addr));
340
reply = wpa_supplicant_global_ctrl_iface_process(global, buf,
447
if (strcmp(buf, "GET_COOKIE") == 0) {
448
reply = wpa_supplicant_global_get_cookie(priv, &reply_len);
452
if (strncmp(buf, "COOKIE=", 7) != 0) {
453
wpa_printf(MSG_DEBUG, "CTLR: No cookie in the request - "
458
if (hexstr2bin(buf + 7, cookie, COOKIE_LEN) < 0) {
459
wpa_printf(MSG_DEBUG, "CTLR: Invalid cookie format in the "
460
"request - drop request");
464
if (memcmp(cookie, priv->cookie, COOKIE_LEN) != 0) {
465
wpa_printf(MSG_DEBUG, "CTLR: Invalid cookie in the request - "
470
pos = buf + 7 + 2 * COOKIE_LEN;
474
reply = wpa_supplicant_global_ctrl_iface_process(global, pos,
344
479
sendto(sock, reply, reply_len, 0, (struct sockaddr *) &from,