Client and server commnunication now works
We can send our little datagrams over and that works nicely. Need to consolidate the PSK session establishment into one shared function.
This commit is contained in:
parent
983217ffbd
commit
0e8e42d0ea
6
Makefile
6
Makefile
@ -11,7 +11,7 @@ PYPGMOPTS := ../Python/pypgmopts/pypgmopts
|
||||
|
||||
LDFLAGS := `pkg-config --libs openssl`
|
||||
|
||||
OBJS := luksrku.o editor.o util.o log.o keydb.o file_encryption.o uuid.o argparse_edit.o pgmopts.o openssl.o server.o argparse_server.o thread.o argparse_client.o client.o
|
||||
OBJS := luksrku.o editor.o util.o log.o keydb.o file_encryption.o uuid.o argparse_edit.o pgmopts.o openssl.o server.o argparse_server.o thread.o argparse_client.o client.o signals.o
|
||||
|
||||
parsers:
|
||||
$(PYPGMOPTS) -n edit parsers/parser_edit.py
|
||||
@ -27,10 +27,10 @@ clean:
|
||||
rm -f $(OBJS) $(OBJS_CFG) luksrku
|
||||
|
||||
test_s: luksrku
|
||||
./luksrku server -vv base
|
||||
./luksrku server -vv testdata/server.bin
|
||||
|
||||
test_c: luksrku
|
||||
./luksrku client -vv export 127.0.0.1
|
||||
./luksrku client -vv testdata/client.bin 127.0.0.1
|
||||
|
||||
.c.o:
|
||||
$(CC) $(CFLAGS) -c -o $@ $<
|
||||
|
73
client.c
73
client.c
@ -41,6 +41,7 @@
|
||||
#include "client.h"
|
||||
#include "blacklist.h"
|
||||
#include "keydb.h"
|
||||
#include "uuid.h"
|
||||
|
||||
#if 0
|
||||
static const struct keydb_t *client_keydb;
|
||||
@ -216,11 +217,53 @@ struct keyclient_t {
|
||||
const struct pgmopts_client_t *opts;
|
||||
struct keydb_t *keydb;
|
||||
bool volume_unlocked[MAX_VOLUMES_PER_HOST];
|
||||
unsigned char identifier[ASCII_UUID_BUFSIZE];
|
||||
};
|
||||
|
||||
static int psk_client_callback(SSL *ssl, const EVP_MD *md, const unsigned char **id, size_t *idlen, SSL_SESSION **sess) {
|
||||
fprintf(stderr, "CLIENT CALLBACK\n");
|
||||
return 0;
|
||||
static int psk_client_callback(SSL *ssl, const EVP_MD *md, const unsigned char **id, size_t *idlen, SSL_SESSION **sessptr) {
|
||||
struct keyclient_t *key_client = (struct keyclient_t*)SSL_get_app_data(ssl);
|
||||
*id = key_client->identifier;
|
||||
*idlen = ASCII_UUID_CHARACTER_COUNT;
|
||||
|
||||
SSL_SESSION *sess = SSL_SESSION_new();
|
||||
if (!sess) {
|
||||
log_openssl(LLVL_ERROR, "Failed to create SSL_SESSION context for client.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
const uint8_t tls13_aes128gcmsha256_id[] = { 0x13, 0x01 };
|
||||
const SSL_CIPHER *cipher = SSL_CIPHER_find(ssl, tls13_aes128gcmsha256_id);
|
||||
if (!cipher) {
|
||||
log_openssl(LLVL_ERROR, "Unable to look up SSL_CIPHER for TLSv1.3-PSK");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int return_value = 1;
|
||||
do {
|
||||
if (!SSL_SESSION_set1_master_key(sess, key_client->keydb->hosts[0].tls_psk, PSK_SIZE_BYTES)) {
|
||||
log_openssl(LLVL_ERROR, "Failed to set TLSv1.3-PSK master key.");
|
||||
return_value = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!SSL_SESSION_set_cipher(sess, cipher)) {
|
||||
log_openssl(LLVL_ERROR, "Failed to set TLSv1.3-PSK cipher.");
|
||||
return_value = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!SSL_SESSION_set_protocol_version(sess, TLS1_3_VERSION)) {
|
||||
log_openssl(LLVL_ERROR, "Failed to set TLSv1.3-PSK protocol version.");
|
||||
return_value = 0;
|
||||
break;
|
||||
}
|
||||
} while (false);
|
||||
|
||||
if (return_value) {
|
||||
*sessptr = sess;
|
||||
}
|
||||
|
||||
return return_value;
|
||||
}
|
||||
|
||||
static bool contact_keyserver_socket(struct keyclient_t *keyclient, int sd) {
|
||||
@ -237,7 +280,24 @@ static bool contact_keyserver_socket(struct keyclient_t *keyclient, int sd) {
|
||||
SSL_set_app_data(ssl, keyclient);
|
||||
|
||||
if (SSL_connect(ssl) == 1) {
|
||||
fprintf(stderr, "OK\n");
|
||||
struct msg_t msg;
|
||||
while (true) {
|
||||
int bytes_read = SSL_read(ssl, &msg, sizeof(msg));
|
||||
if (bytes_read == 0) {
|
||||
/* Server closed the connection. */
|
||||
break;
|
||||
}
|
||||
if (bytes_read != sizeof(msg)) {
|
||||
log_openssl(LLVL_FATAL, "SSL_read returned %d bytes when we expected to read %d", bytes_read, sizeof(msg));
|
||||
break;
|
||||
}
|
||||
if (should_log(LLVL_TRACE)) {
|
||||
char uuid_str[ASCII_UUID_BUFSIZE];
|
||||
sprintf_uuid(uuid_str, msg.volume_uuid);
|
||||
log_msg(LLVL_TRACE, "Received LUKS key to unlock volume with UUID %s", uuid_str);
|
||||
}
|
||||
}
|
||||
OPENSSL_cleanse(&msg, sizeof(msg));
|
||||
} else {
|
||||
log_openssl(LLVL_FATAL, "SSL_connect failed");
|
||||
}
|
||||
@ -292,7 +352,7 @@ static bool contact_keyserver_hostname(struct keyclient_t *keyclient, const char
|
||||
}
|
||||
|
||||
struct sockaddr_in *sin_address = (struct sockaddr_in*)result->ai_addr;
|
||||
log_msg(LLVL_DEBUG, "Resolved %s to %d.%d.%d.%d", hostname, PRINTF_FORMAT_IP(sin_address));
|
||||
log_msg(LLVL_TRACE, "Resolved %s to %d.%d.%d.%d", hostname, PRINTF_FORMAT_IP(sin_address));
|
||||
|
||||
bool success = contact_keyserver_ipv4(keyclient, sin_address, keyclient->opts->port);
|
||||
|
||||
@ -334,6 +394,9 @@ bool keyclient_start(const struct pgmopts_client_t *opts) {
|
||||
break;
|
||||
}
|
||||
|
||||
/* Transcribe the host UUID to ASCII so we only have to do this once */
|
||||
sprintf_uuid((char*)keyclient.identifier, host->host_uuid);
|
||||
|
||||
log_msg(LLVL_DEBUG, "Attempting to unlock %d volumes of host \"%s\".", host->volume_count, host->host_name);
|
||||
if (opts->hostname) {
|
||||
if (!contact_keyserver_hostname(&keyclient, opts->hostname)) {
|
||||
|
6
keydb.c
6
keydb.c
@ -74,8 +74,10 @@ struct keydb_t* keydb_export_public(struct host_entry_t *host) {
|
||||
}
|
||||
|
||||
void keydb_free(struct keydb_t *keydb) {
|
||||
OPENSSL_cleanse(keydb, keydb_getsize(keydb));
|
||||
free(keydb);
|
||||
if (keydb) {
|
||||
OPENSSL_cleanse(keydb, keydb_getsize(keydb));
|
||||
free(keydb);
|
||||
}
|
||||
}
|
||||
|
||||
static int keydb_get_volume_index_by_name(struct host_entry_t *host, const char *devmapper_name) {
|
||||
|
1
log.c
1
log.c
@ -37,6 +37,7 @@ static const char *loglvl_names[] = {
|
||||
[LLVL_WARNING] = "WARNING",
|
||||
[LLVL_INFO] = "INFO",
|
||||
[LLVL_DEBUG] = "DEBUG",
|
||||
[LLVL_TRACE] = "TRACE",
|
||||
};
|
||||
|
||||
void log_setlvl(enum loglvl_t level) {
|
||||
|
3
log.h
3
log.h
@ -31,7 +31,8 @@ enum loglvl_t {
|
||||
LLVL_ERROR = 1,
|
||||
LLVL_WARNING = 2,
|
||||
LLVL_INFO = 3,
|
||||
LLVL_DEBUG = 4
|
||||
LLVL_DEBUG = 4,
|
||||
LLVL_TRACE = 5,
|
||||
};
|
||||
|
||||
/*************** AUTO GENERATED SECTION FOLLOWS ***************/
|
||||
|
5
server.c
5
server.c
@ -30,6 +30,7 @@
|
||||
#include <sys/select.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/types.h>
|
||||
#include <signal.h>
|
||||
|
||||
#include <openssl/ssl.h>
|
||||
#include <openssl/err.h>
|
||||
@ -45,6 +46,7 @@
|
||||
#include "uuid.h"
|
||||
#include "thread.h"
|
||||
#include "keydb.h"
|
||||
#include "signals.h"
|
||||
|
||||
static int create_tcp_server_socket(int port) {
|
||||
int s;
|
||||
@ -370,6 +372,9 @@ bool keyserver_start(const struct pgmopts_server_t *opts) {
|
||||
struct keydb_t* keydb = NULL;
|
||||
struct generic_tls_ctx_t gctx = { 0 };
|
||||
do {
|
||||
/* We ignore SIGPIPE or the server will die when clients disconnect suddenly */
|
||||
ignore_signal(SIGPIPE);
|
||||
|
||||
/* Load key database first */
|
||||
keydb = keydb_read(opts->filename);
|
||||
if (!keydb) {
|
||||
|
35
signals.c
Normal file
35
signals.c
Normal file
@ -0,0 +1,35 @@
|
||||
/*
|
||||
luksrku - Tool to remotely unlock LUKS disks using TLS.
|
||||
Copyright (C) 2016-2016 Johannes Bauer
|
||||
|
||||
This file is part of luksrku.
|
||||
|
||||
luksrku 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; this program is ONLY licensed under
|
||||
version 3 of the License, later versions are explicitly excluded.
|
||||
|
||||
luksrku 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 luksrku; if not, write to the Free Software
|
||||
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
Johannes Bauer <JohannesBauer@gmx.de>
|
||||
*/
|
||||
|
||||
#include <stddef.h>
|
||||
#include <signal.h>
|
||||
#include "signals.h"
|
||||
|
||||
bool ignore_signal(int signum) {
|
||||
struct sigaction action = {
|
||||
.sa_handler = SIG_IGN,
|
||||
.sa_flags = SA_RESTART,
|
||||
};
|
||||
sigemptyset(&action.sa_mask);
|
||||
return sigaction(signum, &action, NULL) == 0;
|
||||
}
|
33
signals.h
Normal file
33
signals.h
Normal file
@ -0,0 +1,33 @@
|
||||
/*
|
||||
luksrku - Tool to remotely unlock LUKS disks using TLS.
|
||||
Copyright (C) 2016-2016 Johannes Bauer
|
||||
|
||||
This file is part of luksrku.
|
||||
|
||||
luksrku 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; this program is ONLY licensed under
|
||||
version 3 of the License, later versions are explicitly excluded.
|
||||
|
||||
luksrku 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 luksrku; if not, write to the Free Software
|
||||
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
Johannes Bauer <JohannesBauer@gmx.de>
|
||||
*/
|
||||
|
||||
#ifndef __SIGNALS_H__
|
||||
#define __SIGNALS_H__
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
/*************** AUTO GENERATED SECTION FOLLOWS ***************/
|
||||
bool ignore_signal(int signum);
|
||||
/*************** AUTO GENERATED SECTION ENDS ***************/
|
||||
|
||||
#endif
|
BIN
testdata/client.bin
vendored
Normal file
BIN
testdata/client.bin
vendored
Normal file
Binary file not shown.
BIN
testdata/server.bin
vendored
Normal file
BIN
testdata/server.bin
vendored
Normal file
Binary file not shown.
Loading…
Reference in New Issue
Block a user