From f12dee199c5f6207ddddafd26c85136daa6842ad Mon Sep 17 00:00:00 2001 From: Vincent Sanders Date: Sat, 3 Nov 2018 17:33:25 +0000 Subject: add 401 login handling to monkey frontend --- docs/using-monkey.md | 33 ++++++-- frontends/monkey/401login.c | 183 +++++++++++++++++++++++++++++++++++++++----- frontends/monkey/401login.h | 40 ++++++++-- frontends/monkey/main.c | 5 ++ 4 files changed, 227 insertions(+), 34 deletions(-) diff --git a/docs/using-monkey.md b/docs/using-monkey.md index d6082bda9..c6298dd04 100644 --- a/docs/using-monkey.md +++ b/docs/using-monkey.md @@ -49,7 +49,7 @@ browser windows are prefixed by `WINDOW`. * `WINDOW`: Anything about browser windows in general -* `DOWNLOAD_WINDOW`: Anything about the download window. +* `DOWNLOAD`: Anything about the download window. * `SSLCERT`: Anything about SSL certificates @@ -124,6 +124,25 @@ Commands Expect responses similar to a GO command. +### Login commands + +* `LOGIN USERNAME` _%id%_ _%str_ + + Set the username for the login + +* `LOGIN PASSWORD` _%id%_ _%str_ + + Set the password for the login + +* `LOGIN GO` _%id%_ + + Cause a login to proceed using the set credentials + +* `LOGIN DESTROY` _%id%_ + + Cause a login to fail + + Responses --------- @@ -304,28 +323,28 @@ Responses ### Download window messages -* `DOWNLOAD_WINDOW CREATE DWIN` _%id%_ `WIN` _%id%_ +* `DOWNLOAD CREATE DWIN` _%id%_ `WIN` _%id%_ The core asked Monkey to create a download window owned by the given browser window. -* `DOWNLOAD_WINDOW DATA DWIN` _%id%_ `SIZE` _%n%_ `DATA` _%str%_ +* `DOWNLOAD DATA DWIN` _%id%_ `SIZE` _%n%_ `DATA` _%str%_ The core asked Monkey to update the named download window with the given byte size and data string. -* `DOWNLOAD_WINDOW ERROR DWIN` _%id%_ `ERROR` _%str%_ +* `DOWNLOAD ERROR DWIN` _%id%_ `ERROR` _%str%_ The core asked Monkey to update the named download window with the given error message. -* `DOWNLOAD_WINDOW DONE DWIN` _%id%_ +* `DOWNLOAD DONE DWIN` _%id%_ The core asked Monkey to destroy the named download window. ### SSL Certificate messages -* `SSLCERT VERIFY CERT` _%id%_ `URL` _%url%_ +* `SSLCERT VERIFY CWIN` _%id%_ `URL` _%url%_ The core asked Monkey to say whether or not a given SSL certificate is OK. @@ -334,7 +353,7 @@ Responses ### 401 Login messages -* `401LOGIN OPEN M4` _%id%_ `URL` _%url%_ `REALM` _%str%_ +* `LOGIN OPEN LWIN` _%id%_ `URL` _%url%_ USER _%str%_ PASSWD _%str%_ `REALM` _%str%_ The core asked Monkey to ask for identification for the named realm at the given URL. diff --git a/frontends/monkey/401login.c b/frontends/monkey/401login.c index 76550d86c..72f663ee4 100644 --- a/frontends/monkey/401login.c +++ b/frontends/monkey/401login.c @@ -16,28 +16,32 @@ * along with this program. If not, see . */ -#include "utils/ring.h" - #include #include +#include +#include + +#include "utils/ring.h" +#include "utils/nsurl.h" #include "monkey/output.h" #include "monkey/401login.h" -typedef struct monkey401 { +struct monkey401 { struct monkey401 *r_next, *r_prev; uint32_t num; - lwc_string *host; /* Ignore */ nserror (*cb)(const char *, const char *, void *); - void *pw; -} monkey401_t; + void *cbpw; + char *username; + char *password; +}; -static monkey401_t *m4_ring = NULL; -static uint32_t m4_ctr = 0; +static struct monkey401 *m401_ring = NULL; +static uint32_t m401_ctr = 0; nserror -gui_401login_open(nsurl *url, +gui_401login_open(struct nsurl *url, const char *realm, const char *username, const char *password, @@ -46,20 +50,161 @@ gui_401login_open(nsurl *url, void *pw), void *cbpw) { - monkey401_t *m4t = calloc(sizeof(*m4t), 1); - if (m4t == NULL) { + struct monkey401 *m401_ctx; + + m401_ctx = calloc(sizeof(*m401_ctx), 1); + if (m401_ctx == NULL) { return NSERROR_NOMEM; } - m4t->cb = cb; - m4t->pw = cbpw; - m4t->num = m4_ctr++; - - RING_INSERT(m4_ring, m4t); - - moutf(MOUT_LOGIN, "OPEN LWIN %u URL %s REALM %s", - m4t->num, nsurl_access(url), realm); + m401_ctx->cb = cb; + m401_ctx->cbpw = cbpw; + m401_ctx->num = m401_ctr++; + + RING_INSERT(m401_ring, m401_ctx); + + if (username == NULL) { + username = ""; + } + + if (password == NULL) { + password = ""; + } + + moutf(MOUT_LOGIN, "OPEN LWIN %u URL %s USER %s PASSWD %s REALM %s", + m401_ctx->num, nsurl_access(url), username, password, realm); return NSERROR_OK; } +static struct monkey401 * +monkey_find_login_by_num(uint32_t login_num) +{ + struct monkey401 *ret = NULL; + + RING_ITERATE_START(struct monkey401, m401_ring, c_ring) { + if (c_ring->num == login_num) { + ret = c_ring; + RING_ITERATE_STOP(m401_ring, c_ring); + } + } RING_ITERATE_END(m401_ring, c_ring); + + return ret; +} +static void free_login_context(struct monkey401 *m401_ctx) { + RING_REMOVE(m401_ring, m401_ctx); + if (m401_ctx->username != NULL) { + free(m401_ctx->username); + } + if (m401_ctx->password != NULL) { + free(m401_ctx->password); + } + free(m401_ctx); +} + +static void +monkey_login_handle_go(int argc, char **argv) +{ + struct monkey401 *m401_ctx; + + if (argc != 3) { + moutf(MOUT_ERROR, "LOGIN GO ARGS BAD"); + return; + } + + m401_ctx = monkey_find_login_by_num(atoi(argv[2])); + if (m401_ctx == NULL) { + moutf(MOUT_ERROR, "LOGIN NUM BAD"); + return; + } + + m401_ctx->cb(m401_ctx->username, m401_ctx->password, m401_ctx->cbpw); + + free_login_context(m401_ctx); +} + +static void +monkey_login_handle_destroy(int argc, char **argv) +{ + struct monkey401 *m401_ctx; + + if (argc != 3) { + moutf(MOUT_ERROR, "LOGIN DESTROY ARGS BAD"); + return; + } + + m401_ctx = monkey_find_login_by_num(atoi(argv[2])); + if (m401_ctx == NULL) { + moutf(MOUT_ERROR, "LOGIN NUM BAD"); + return; + } + + m401_ctx->cb(NULL, NULL, m401_ctx->cbpw); + + free_login_context(m401_ctx); +} + +static void +monkey_login_handle_username(int argc, char **argv) +{ + struct monkey401 *m401_ctx; + + if (argc != 4) { + moutf(MOUT_ERROR, "LOGIN USERNAME ARGS BAD"); + return; + } + + m401_ctx = monkey_find_login_by_num(atoi(argv[2])); + if (m401_ctx == NULL) { + moutf(MOUT_ERROR, "LOGIN NUM BAD"); + return; + } + + if (m401_ctx->username != NULL) { + free(m401_ctx->username); + } + + m401_ctx->username = strdup(argv[3]); +} + +static void +monkey_login_handle_password(int argc, char **argv) +{ + struct monkey401 *m401_ctx; + + if (argc != 4) { + moutf(MOUT_ERROR, "LOGIN PASSWORD ARGS BAD"); + return; + } + + m401_ctx = monkey_find_login_by_num(atoi(argv[2])); + if (m401_ctx == NULL) { + moutf(MOUT_ERROR, "LOGIN NUM BAD"); + return; + } + + if (m401_ctx->password != NULL) { + free(m401_ctx->password); + } + + m401_ctx->password = strdup(argv[3]); +} + +void +monkey_login_handle_command(int argc, char **argv) +{ + if (argc == 1) + return; + + if (strcmp(argv[1], "USERNAME") == 0) { + monkey_login_handle_username(argc, argv); + } else if (strcmp(argv[1], "PASSWORD") == 0) { + monkey_login_handle_password(argc, argv); + } else if (strcmp(argv[1], "DESTROY") == 0) { + monkey_login_handle_destroy(argc, argv); + } else if (strcmp(argv[1], "GO") == 0) { + monkey_login_handle_go(argc, argv); + } else { + moutf(MOUT_ERROR, "LOGIN COMMAND UNKNOWN %s\n", argv[1]); + } +} diff --git a/frontends/monkey/401login.h b/frontends/monkey/401login.h index 93606e5b9..9ebe46a62 100644 --- a/frontends/monkey/401login.h +++ b/frontends/monkey/401login.h @@ -1,13 +1,37 @@ +/* + * Copyright 2018 Vincent Sanders + * + * This file is part of NetSurf, http://www.netsurf-browser.org/ + * + * NetSurf is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * NetSurf is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ -#include +#ifndef NS_MONKEY_401LOGIN_H +#define NS_MONKEY_401LOGIN_H -#include "utils/nsurl.h" #include "utils/errors.h" +struct nsurl; -nserror gui_401login_open(nsurl *url, const char *realm, - const char *username, const char *password, - nserror (*cb)(const char *username, - const char *password, - void *pw), - void *cbpw); +nserror gui_401login_open(struct nsurl *url, + const char *realm, + const char *username, + const char *password, + nserror (*cb)(const char *username, + const char *password, + void *pw), + void *cbpw); + +void monkey_login_handle_command(int argc, char **argv); + +#endif diff --git a/frontends/monkey/main.c b/frontends/monkey/main.c index 7ef4208ca..4fdc5ebc2 100644 --- a/frontends/monkey/main.c +++ b/frontends/monkey/main.c @@ -393,6 +393,11 @@ main(int argc, char **argv) die("options handler failed to register"); } + ret = monkey_register_handler("LOGIN", monkey_login_handle_command); + if (ret != NSERROR_OK) { + die("login handler failed to register"); + } + moutf(MOUT_GENERIC, "STARTED"); monkey_run(); -- cgit v1.2.3