# Core objects
add_library(libonak STATIC armor.c charfuncs.c cleankey.c cleanup.c decodekey.c
- getcgi.c hash.c hash-helper.c keyarray.c keyid.c keyindex.c ll.c log.c
- marshal.c mem.c merge.c onak-conf.c parsekey.c photoid.c rsa.c
- sigcheck.c sendsync.c sha1x.c wordlist.c)
+ getcgi.c hash.c hash-helper.c key-store.c keyarray.c keyid.c keyindex.c
+ ll.c log.c marshal.c mem.c merge.c onak-conf.c parsekey.c photoid.c
+ rsa.c sigcheck.c sendsync.c sha1x.c wordlist.c)
set(LIBONAK_LIBRARIES "")
# Ideally use Nettle, fall back to our own md5/sha1 routines otherwise
--- /dev/null
+/*
+ * key-store.c - High level routines to load + save OpenPGP packets/keys
+ *
+ * This program 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.
+ *
+ * This program 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 <https://www.gnu.org/licenses/>.
+ */
+
+#include <errno.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+#include "build-config.h"
+
+#include "armor.h"
+#include "charfuncs.h"
+#include "key-store.h"
+#include "keystructs.h"
+#include "onak.h"
+#include "parsekey.h"
+
+/**
+ * onak_read_openpgp_file - Reads a set of OpenPGP packets from a file
+ * @file: The file to open and read
+ * @packets: The returned packet list
+ *
+ * This function opens the supplied file and tries to parse it as a set
+ * of OpenPGP packets. It will attempt to autodetect if the file is ASCII
+ * armored, or binary packets, and adapt accordingly. The packets read are
+ * returned in the packets parameter. It is the callers responsbility to
+ * free the packet memory when it is no longe required, e.g. using
+ * free_packet_list.
+ *
+ * Returns a status code indicating any error.
+ */
+onak_status_t onak_read_openpgp_file(const char *file,
+ struct openpgp_packet_list **packets)
+{
+ onak_status_t res;
+ int fd, ret;
+ char c;
+
+ fd = open(file, O_RDONLY);
+ if (fd < 0) {
+ return (errno == ENOENT) ? ONAK_E_NOT_FOUND : ONAK_E_IO_ERROR;
+ }
+
+ /* Peek at the first byte in the file */
+ ret = read(fd, &c, 1);
+ if (ret != 1) {
+ return ONAK_E_IO_ERROR;
+ }
+ lseek(fd, 0, SEEK_SET);
+
+ /*
+ * A binary OpenPGP packet will have the top bit set on its first byte,
+ * so we use that to determine if we should try to process the stream
+ * as binary or ASCII armored data.
+ */
+ if (c & 0x80) {
+ res = read_openpgp_stream(file_fetchchar, &fd,
+ packets, 0);
+ } else {
+ res = dearmor_openpgp_stream(file_fetchchar, &fd, packets);
+ }
+
+ return res;
+}
--- /dev/null
+/*
+ * key-store.h - High level routines to load + save OpenPGP packets/keys
+ *
+ * This program 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.
+ *
+ * This program 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 <https://www.gnu.org/licenses/>.
+ */
+
+#ifndef __KEY_STORE_H__
+#define __KEY_STORE_H__
+
+#include "build-config.h"
+#include "keystructs.h"
+#include "onak.h"
+
+/**
+ * onak_read_openpgp_file - Reads a set of OpenPGP packets from a file
+ * @file: The file to open and read
+ * @packets: The returned packet list
+ *
+ * This function opens the supplied file and tries to parse it as a set
+ * of OpenPGP packets. It will attempt to autodetect if the file is ASCII
+ * armored, or binary packets, and adapt accordingly. The packets read are
+ * returned in the packets parameter. It is the callers responsbility to
+ * free the packet memory when it is no longe required, e.g. using
+ * free_packet_list.
+ *
+ * Returns a status code indicating any error.
+ */
+onak_status_t onak_read_openpgp_file(const char *file,
+ struct openpgp_packet_list **packets);
+
+#endif /* __KEY_STORE_H__ */
#include <unistd.h>
#include "charfuncs.h"
+#include "key-store.h"
#include "keydb.h"
#include "keyid.h"
#include "keystructs.h"
char *db_dir = (char *) dbctx->priv;
struct openpgp_packet_list *packets = NULL;
char keyfile[1024];
- int fd = -1;
+ onak_status_t res;
snprintf(keyfile, 1023, "%s/0x%" PRIX64, db_dir,
keyid & 0xFFFFFFFF);
- fd = open(keyfile, O_RDONLY); // | O_SHLOCK);
+ res = onak_read_openpgp_file(keyfile, &packets);
- if (fd > -1) {
- read_openpgp_stream(file_fetchchar, &fd, &packets, 0);
+ if (res == ONAK_E_OK) {
parse_keys(packets, publickey);
free_packet_list(packets);
packets = NULL;
- close(fd);
}
- return (fd > -1);
+ return (res == ONAK_E_OK);
}
/**
struct openpgp_publickey *key = NULL;
DIR *dir;
char keyfile[1024];
- int fd = -1;
struct dirent *curfile = NULL;
+ onak_status_t res;
dir = opendir(db_dir);
snprintf(keyfile, 1023, "%s/%s",
db_dir,
curfile->d_name);
- fd = open(keyfile, O_RDONLY);
+ res = onak_read_openpgp_file(keyfile,
+ &packets);
- if (fd > -1) {
- read_openpgp_stream(file_fetchchar,
- &fd,
- &packets,
- 0);
+ if (res == ONAK_E_OK) {
parse_keys(packets, &key);
iterfunc(ctx, key);
key = NULL;
free_packet_list(packets);
packets = NULL;
- close(fd);
}
numkeys++;
}
#include "charfuncs.h"
#include "decodekey.h"
+#include "key-store.h"
#include "keydb.h"
#include "keyid.h"
#include "keystructs.h"
bool intrans)
{
static char buffer[PATH_MAX];
- int ret = 0, fd;
+ int ret = 0;
struct openpgp_packet_list *packets = NULL;
+ onak_status_t res;
if (!intrans)
fs_starttrans(dbctx);
keyid = fs_getfullkeyid(dbctx, keyid);
keypath(buffer, sizeof(buffer), keyid, dbctx->config->location);
- fd = open(buffer, O_RDONLY);
- if (fd == -1 && errno == ENOENT) {
+ res = onak_read_openpgp_file(buffer,
+ &packets);
+ if (res == ONAK_E_NOT_FOUND) {
subkeypath(buffer, sizeof(buffer), keyid,
dbctx->config->location);
- fd = open(buffer, O_RDONLY);
+ res = onak_read_openpgp_file(buffer,
+ &packets);
}
- if (fd != -1) {
+ if (res == ONAK_E_OK) {
/* File is present, load it in... */
- read_openpgp_stream(file_fetchchar, &fd, &packets, 0);
parse_keys(packets, publickey);
free_packet_list(packets);
packets = NULL;
- close(fd);
ret = 1;
}
struct openpgp_publickey **publickey)
{
static char buffer[PATH_MAX];
- int ret = 0, fd;
+ int ret = 0;
struct openpgp_packet_list *packets = NULL;
+ onak_status_t res;
skshashpath(buffer, sizeof(buffer), hash, dbctx->config->location);
- if ((fd = open(buffer, O_RDONLY)) != -1) {
- read_openpgp_stream(file_fetchchar, &fd, &packets, 0);
+ res = onak_read_openpgp_file(buffer, &packets);
+ if (res == ONAK_E_OK) {
parse_keys(packets, publickey);
free_packet_list(packets);
packets = NULL;
- close(fd);
ret = 1;
}
ONAK_E_UNSUPPORTED_FEATURE,
ONAK_E_BAD_SIGNATURE,
ONAK_E_WEAK_SIGNATURE,
+ ONAK_E_IO_ERROR,
} onak_status_t;
#endif /* __ONAK_H__ */