382 lines
10 KiB
C
382 lines
10 KiB
C
#include <kore/kore.h>
|
|
#include <kore/http.h>
|
|
#include <fcntl.h>
|
|
#include <stdlib.h>
|
|
#include <unistd.h>
|
|
#include <sqlite3.h>
|
|
#include <unistd.h>
|
|
#include "assets.h"
|
|
#include "sessions.h"
|
|
#include "sqlite_utils.h"
|
|
#include <pwd.h>
|
|
|
|
#define SESSION_LEN 30
|
|
#define DB_NAME "portal_user.db"
|
|
|
|
#if defined(__linux__)
|
|
|
|
#include <kore/seccomp.h>
|
|
#include <crypt.h>
|
|
|
|
KORE_SECCOMP_FILTER("sqlite3",
|
|
KORE_SYSCALL_ALLOW(newfstatat),
|
|
KORE_SYSCALL_ALLOW(pread64),
|
|
KORE_SYSCALL_ALLOW(pwrite64),
|
|
KORE_SYSCALL_ALLOW(fdatasync),
|
|
KORE_SYSCALL_ALLOW_ARG(write, 0, STDOUT_FILENO)
|
|
);
|
|
#endif
|
|
|
|
|
|
int init(int state);
|
|
int portal_user_load(struct http_request *);
|
|
int v_password_func(struct http_request *, char *);
|
|
int create_user(struct http_request *);
|
|
int v_session_validate(struct http_request *, char *);
|
|
int v_session_remove(struct http_request *);
|
|
int private_portal(struct http_request *);
|
|
|
|
hashtable_t *hashtable = NULL;
|
|
|
|
int
|
|
init(int state)
|
|
{
|
|
hashtable = ht_create( 65536 );
|
|
int err=0;
|
|
if( hashtable == NULL )
|
|
{
|
|
kore_log(LOG_ERR, "Can't create hastable sessions");
|
|
err = 1;
|
|
}
|
|
|
|
if ( access( DB_NAME, F_OK ) == 0 && err == 0 )
|
|
{ kore_log(LOG_NOTICE, "Execute check_db()");
|
|
err = check_db(DB_NAME);}
|
|
else
|
|
{
|
|
kore_log(LOG_NOTICE, "Create Sqlite Base");
|
|
err = init_db(DB_NAME);
|
|
}
|
|
if (err)
|
|
return (KORE_RESULT_ERROR);
|
|
else
|
|
return (KORE_RESULT_OK);
|
|
}
|
|
|
|
int
|
|
create_user(struct http_request *req)
|
|
{
|
|
struct kore_buf *b = NULL;
|
|
u_int8_t *d = NULL;
|
|
size_t len = 0;
|
|
char *salt = NULL, *cryptpwd = NULL;
|
|
char *zErrMsg = NULL;
|
|
char *user = NULL, *pwd = NULL, name[50];
|
|
sqlite3 *db = NULL;
|
|
char sql[512];
|
|
|
|
if (req->method == HTTP_METHOD_GET)
|
|
http_populate_get(req);
|
|
else if (req->method == HTTP_METHOD_POST)
|
|
http_populate_post(req);
|
|
|
|
b = kore_buf_alloc(asset_len_signup_html);
|
|
kore_buf_append(b, asset_signup_html, asset_len_signup_html);
|
|
|
|
|
|
if (req->method == HTTP_METHOD_GET) {
|
|
kore_buf_replace_string(b, "$msg$", "GO", 4);
|
|
|
|
http_response_header(req, "content-type", "text/html");
|
|
d = kore_buf_release(b, &len);
|
|
http_response(req, 200, d, len);
|
|
kore_free(d);
|
|
|
|
return (KORE_RESULT_OK);
|
|
}
|
|
|
|
if (req->method == HTTP_METHOD_POST)
|
|
{
|
|
int rc = sqlite3_open(DB_NAME, &db);
|
|
|
|
if (rc != SQLITE_OK) {
|
|
|
|
kore_log(LOG_ERR, "Cannot open database: %s\n", sqlite3_errmsg(db));
|
|
sqlite3_close(db);
|
|
|
|
return (KORE_RESULT_ERROR);
|
|
}
|
|
#if defined(__linux__)
|
|
salt = crypt_gensalt("$2b$", 15, NULL, 0); //-> linux
|
|
#elif defined(__OpenBSD__)
|
|
salt = bcrypt_gensalt(15);
|
|
#endif
|
|
if (salt == NULL) {
|
|
kore_log(LOG_ERR, "crypt_gensalt");
|
|
exit(EXIT_FAILURE);
|
|
}
|
|
kore_log(LOG_NOTICE, "bcrypt_salt réussi");
|
|
|
|
(void)snprintf(name, sizeof(name), "login");
|
|
http_argument_get_string(req, name, &user);
|
|
|
|
(void)snprintf(name, sizeof(name), "password");
|
|
http_argument_get_string(req, name, &pwd);
|
|
|
|
cryptpwd = crypt(pwd, salt);
|
|
if (cryptpwd == NULL) {
|
|
kore_log(LOG_PERROR, "Can't encrypt password");
|
|
exit(EXIT_FAILURE);
|
|
}
|
|
|
|
|
|
kore_log(LOG_NOTICE, "Encrypted called %s", cryptpwd );
|
|
|
|
(void)sprintf(sql,
|
|
"INSERT INTO Users (Email, Password, Active) VALUES(\"%s\",\"%s\",\"yes\");",
|
|
user, cryptpwd);
|
|
|
|
|
|
printf ( "%s",sql);
|
|
rc = sqlite3_exec(db, sql, 0, 0, &zErrMsg);
|
|
|
|
if( rc != SQLITE_OK ){
|
|
kore_log(LOG_ERR, "SQL error: %s", zErrMsg);
|
|
sqlite3_free(zErrMsg);
|
|
} else {
|
|
kore_log(LOG_NOTICE, "Database successfully created !");
|
|
}
|
|
|
|
sqlite3_close(db);
|
|
http_response_header(req, "location", "/");
|
|
http_response_header(req, "content-type", "text/html");
|
|
d = kore_buf_release(b, &len);
|
|
http_response(req, HTTP_STATUS_FOUND, NULL, 0);
|
|
kore_free(d);
|
|
|
|
return (KORE_RESULT_OK);
|
|
}
|
|
|
|
return (KORE_RESULT_ERROR);
|
|
|
|
}
|
|
|
|
int
|
|
portal_user_load(struct http_request *req)
|
|
{
|
|
struct kore_buf *b = NULL;
|
|
u_int8_t *d = NULL;
|
|
size_t len = 0;
|
|
char *login = NULL, *pwd = NULL, name[70];
|
|
char *err_msg = 0;
|
|
char salt[29], *cryptpwd = NULL;
|
|
int rc = 0;
|
|
sqlite3_stmt *res= NULL;
|
|
sqlite3 *db = NULL;
|
|
char *cookie_session = NULL;
|
|
char *cookie_samesite = NULL;
|
|
char *cookie = NULL;
|
|
char *session_id = NULL;
|
|
|
|
if (req->method == HTTP_METHOD_GET)
|
|
http_populate_get(req);
|
|
else if (req->method == HTTP_METHOD_POST)
|
|
http_populate_post(req);
|
|
|
|
b = kore_buf_alloc(asset_len_index_html);
|
|
kore_buf_append(b, asset_index_html, asset_len_index_html);
|
|
|
|
if (req->method == HTTP_METHOD_GET) {
|
|
kore_buf_replace_string(b, "$login$", NULL, 0);
|
|
kore_buf_replace_string(b, "$password$", NULL, 0);
|
|
kore_buf_replace_string(b, "$msg$", "Toto", 4);
|
|
|
|
http_response_header(req, "content-type", "text/html");
|
|
d = kore_buf_release(b, &len);
|
|
http_response(req, 200, d, len);
|
|
kore_free(d);
|
|
|
|
return (KORE_RESULT_OK);
|
|
}
|
|
|
|
if (req->method == HTTP_METHOD_POST)
|
|
{
|
|
rc = sqlite3_open(DB_NAME, &db);
|
|
|
|
if (rc != SQLITE_OK)
|
|
{
|
|
kore_log(LOG_ERR, "Cannot open database: %s\n", sqlite3_errmsg(db));
|
|
sqlite3_close(db);
|
|
|
|
return (KORE_RESULT_ERROR);
|
|
}
|
|
|
|
char *sql = "SELECT Email, Password FROM Users WHERE Email = ?";
|
|
|
|
rc = sqlite3_prepare_v2(db, sql, -1, &res, 0);
|
|
|
|
if (rc == SQLITE_OK)
|
|
{
|
|
(void)snprintf(name, sizeof(name), "login");
|
|
http_argument_get_string(req, name, &login);
|
|
sqlite3_bind_text(res, 1, login , -1, NULL);
|
|
}
|
|
else
|
|
{
|
|
kore_log(LOG_ERR, "Failed to execute statement: %s\n", sqlite3_errmsg(db));
|
|
}
|
|
|
|
sqlite3_step(res);
|
|
if (rc != SQLITE_OK ) {
|
|
kore_log(LOG_ERR, "SQL error: %s\n", err_msg);
|
|
sqlite3_finalize(res);
|
|
sqlite3_free(err_msg);
|
|
sqlite3_close(db);
|
|
return (KORE_RESULT_ERROR);
|
|
}
|
|
|
|
(void)snprintf(name, sizeof(name), "password");
|
|
http_argument_get_string(req, name, &pwd);
|
|
|
|
|
|
strncpy (salt,(const char *)sqlite3_column_text(res, 1),29);
|
|
|
|
|
|
cryptpwd = crypt(pwd, salt);
|
|
if (cryptpwd == NULL) {
|
|
kore_log(LOG_PERROR, "Can't encrypt password");
|
|
exit(EXIT_FAILURE);
|
|
}
|
|
|
|
|
|
if ( strcmp( (const char *)sqlite3_column_text(res, 1), cryptpwd) )
|
|
{
|
|
kore_buf_replace_string(b, "$msg$", "Erreur de login ou mot de passe ", 17);
|
|
}
|
|
else
|
|
{
|
|
kore_log(LOG_NOTICE, "on va faire le set cookie");
|
|
session_id = gen_session_id(SESSION_LEN);
|
|
ht_set(hashtable, session_id, login);
|
|
|
|
kore_log(LOG_NOTICE, "on a ajouté le sessions dans la hastable");
|
|
cookie_session = set_cookie_header("session_id", '=', session_id);
|
|
cookie_samesite = set_cookie_header("SameSite", '=', "Strict");
|
|
cookie = set_cookie_header(cookie_session, ';', cookie_samesite);
|
|
kore_log(LOG_NOTICE, "on a set le cookie dans les headers");
|
|
kore_buf_replace_string(b, "$msg$", "BRAVO !!!", 13);
|
|
free(session_id);
|
|
free(cookie_session);
|
|
free(cookie_samesite);
|
|
kore_log(LOG_NOTICE, "set cookie OK");
|
|
}
|
|
|
|
sqlite3_finalize(res);
|
|
sqlite3_close(db);
|
|
|
|
|
|
http_response_header(req, "content-type", "text/html");
|
|
if (cookie != NULL)
|
|
{
|
|
http_response_header(req, "set-cookie", cookie);
|
|
free(cookie);
|
|
}
|
|
d = kore_buf_release(b, &len);
|
|
|
|
http_response_header(req, "location", "/portal/bienvenue");
|
|
http_response(req, HTTP_STATUS_FOUND, NULL, 0);
|
|
kore_free(d);
|
|
return (KORE_RESULT_OK);
|
|
}
|
|
|
|
return (KORE_RESULT_ERROR);
|
|
|
|
}
|
|
|
|
int
|
|
v_password_func(struct http_request *req, char *data)
|
|
{
|
|
kore_log(LOG_NOTICE, "v_password_func called %s", data);
|
|
|
|
if ( strlen(data) < 128 )
|
|
return (KORE_RESULT_OK);
|
|
|
|
return (KORE_RESULT_ERROR);
|
|
|
|
}
|
|
|
|
int
|
|
v_session_remove (struct http_request *req)
|
|
{
|
|
char *buffer;
|
|
|
|
http_populate_cookies(req);
|
|
if (http_request_cookie(req, "session_id", &buffer))
|
|
kore_log(LOG_DEBUG, "Got session_id: %s", buffer);
|
|
|
|
if (ht_get(hashtable, buffer) != NULL)
|
|
ht_delete(hashtable, buffer);
|
|
http_response_header(req, "location", "/");
|
|
http_response_header(req, "content-type", "text/html");
|
|
http_response_header(req, "set-cookie", "session_id=""");
|
|
http_response(req, HTTP_STATUS_FOUND, NULL, 0);
|
|
|
|
return (KORE_RESULT_OK);
|
|
}
|
|
|
|
int
|
|
v_session_validate(struct http_request *req, char *data)
|
|
{
|
|
|
|
|
|
kore_log(LOG_NOTICE, "v_session_validate: %s", data);
|
|
|
|
if ( ht_get(hashtable, data) != NULL )
|
|
return (KORE_RESULT_OK);
|
|
else
|
|
{
|
|
kore_log(LOG_NOTICE, "Session Inexistante");
|
|
}
|
|
return (KORE_RESULT_ERROR);
|
|
}
|
|
|
|
int
|
|
private_portal(struct http_request *req)
|
|
{
|
|
struct kore_buf *b = NULL;
|
|
u_int8_t *d = NULL;
|
|
size_t len = 0;
|
|
char *buffer =NULL ;
|
|
session_t *account = NULL;
|
|
|
|
if (req->method == HTTP_METHOD_GET)
|
|
http_populate_get(req);
|
|
|
|
|
|
http_populate_cookies(req);
|
|
|
|
if (http_request_cookie(req, "session_id", &buffer))
|
|
kore_log(LOG_DEBUG, "Got session_id: %s", buffer);
|
|
|
|
|
|
b = kore_buf_alloc(asset_len_signup_html);
|
|
kore_buf_append(b, asset_private_html, asset_len_private_html);
|
|
|
|
account = ht_get(hashtable, buffer);
|
|
if (req->method == HTTP_METHOD_GET) {
|
|
|
|
kore_buf_replace_string(b, "$msg$", "GO", 4);
|
|
|
|
if (account != NULL)
|
|
{
|
|
kore_log(LOG_NOTICE, "account trouvé: %s", account->user);
|
|
kore_buf_replace_string(b, "$login$", account->user, sizeof(account->user)+1);
|
|
}
|
|
http_response_header(req, "content-type", "text/html");
|
|
d = kore_buf_release(b, &len);
|
|
http_response(req, 200, d, len);
|
|
kore_free(d);
|
|
}
|
|
return (KORE_RESULT_OK);
|
|
}
|