summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2012-08-20 22:02:19 +0200
committerLennart Poettering <lennart@poettering.net>2012-08-20 22:02:19 +0200
commitf6a971bc0bf1252e9614919ccca0d53db5fc53d9 (patch)
tree9bd5bd2df95eb4ff419f5bde84998f2a62ff9012
parent3e4b9b506d676d1cb8692306b38c05f8529e5cdb (diff)
journalctl: output FSS key as QR code on generating
-rw-r--r--Makefile.am12
-rw-r--r--configure.ac13
-rw-r--r--src/journal/journal-qrcode.c127
-rw-r--r--src/journal/journal-qrcode.h30
-rw-r--r--src/journal/journalctl.c17
-rw-r--r--src/shared/util.c1
6 files changed, 198 insertions, 2 deletions
diff --git a/Makefile.am b/Makefile.am
index 166c357db2..69cdeb7145 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -2353,6 +2353,18 @@ journalctl_LDADD = \
libsystemd-id128-internal.la \
libsystemd-logs.la
+if HAVE_QRENCODE
+journalctl_SOURCES += \
+ src/journal/journal-qrcode.c \
+ src/journal/journal-qrcode.h
+
+journalctl_CFLAGS += \
+ $(QRENCODE_CFLAGS)
+
+journalctl_LDADD += \
+ $(QRENCODE_LIBS)
+endif
+
test_journal_SOURCES = \
src/journal/test-journal.c
diff --git a/configure.ac b/configure.ac
index 3df43b91fd..52adb20e0b 100644
--- a/configure.ac
+++ b/configure.ac
@@ -384,6 +384,18 @@ fi
AM_CONDITIONAL(HAVE_LIBCRYPTSETUP, [test "$have_libcryptsetup" = "yes"])
# ------------------------------------------------------------------------------
+have_qrencode=no
+AC_ARG_ENABLE(qrencode, AS_HELP_STRING([--disable-qrencode], [disable qrencode support]))
+if test "x$enable_qrencode" != "xno"; then
+ PKG_CHECK_MODULES(QRENCODE, [ libqrencode ],
+ [AC_DEFINE(HAVE_QRENCODE, 1, [Define if qrencode is available]) have_qrencode=yes], have_qrencode=no)
+ if test "x$have_qrencode" = xno -a "x$enable_qrencode" = xyes; then
+ AC_MSG_ERROR([*** qrencode support requested but libraries not found])
+ fi
+fi
+AM_CONDITIONAL(HAVE_QRENCODE, [test "$have_qrencode" = "yes"])
+
+# ------------------------------------------------------------------------------
have_binfmt=no
AC_ARG_ENABLE(binfmt, AS_HELP_STRING([--disable-binfmt], [disable binfmt tool]))
if test "x$enable_binfmt" != "xno"; then
@@ -760,6 +772,7 @@ AC_MSG_RESULT([
XZ: ${have_xz}
ACL: ${have_acl}
GCRYPT: ${have_gcrypt}
+ QRENCODE: ${have_qrencode}
binfmt: ${have_binfmt}
vconsole: ${have_vconsole}
readahead: ${have_readahead}
diff --git a/src/journal/journal-qrcode.c b/src/journal/journal-qrcode.c
new file mode 100644
index 0000000000..b4dab8e86a
--- /dev/null
+++ b/src/journal/journal-qrcode.c
@@ -0,0 +1,127 @@
+/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
+
+/***
+ This file is part of systemd.
+
+ Copyright 2012 Lennart Poettering
+
+ systemd is free software; you can redistribute it and/or modify it
+ under the terms of the GNU Lesser General Public License as published by
+ the Free Software Foundation; either version 2.1 of the License, or
+ (at your option) any later version.
+
+ systemd 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
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public License
+ along with systemd; If not, see <http://www.gnu.org/licenses/>.
+***/
+
+#include <assert.h>
+#include <stdio.h>
+#include <errno.h>
+#include <stdlib.h>
+#include <stdbool.h>
+
+#include <qrencode.h>
+
+#include "journal-qrcode.h"
+
+#define WHITE_ON_BLACK "\033[40;37;1m"
+#define NORMAL "\033[0m"
+
+static void print_border(FILE *output, unsigned width) {
+ unsigned x, y;
+
+ /* Four rows of border */
+ for (y = 0; y < 4; y += 2) {
+ fputs(WHITE_ON_BLACK, output);
+
+ for (x = 0; x < 4 + width + 4; x++)
+ fputs("\342\226\210", output);
+
+ fputs(NORMAL "\n", output);
+ }
+}
+
+int print_qr_code(FILE *output, const void *seed, size_t seed_size, uint64_t start, uint64_t interval, const char *hn, sd_id128_t mahcine) {
+ FILE *f;
+ char *url = NULL;
+ size_t url_size = 0, i;
+ QRcode* qr;
+ unsigned x, y;
+
+ assert(seed);
+ assert(seed_size > 0);
+
+ f = open_memstream(&url, &url_size);
+ if (!f)
+ return -ENOMEM;
+
+ fputs("fss://", f);
+
+ for (i = 0; i < seed_size; i++) {
+ if (i > 0 && i % 3 == 0)
+ fputc('-', f);
+ fprintf(f, "%02x", ((uint8_t*) seed)[i]);
+ }
+
+ fprintf(f, "/%llx-%llx\n", (unsigned long long) start, (unsigned long long) interval);
+
+ if (hn)
+ fprintf(f, "?hostname=%s", hn);
+
+ if (ferror(f)) {
+ fclose(f);
+ free(url);
+ return -ENOMEM;
+ }
+
+ fclose(f);
+
+ qr = QRcode_encodeString(url, 0, QR_ECLEVEL_L, QR_MODE_8, 1);
+ free(url);
+
+ if (!qr)
+ return -ENOMEM;
+
+ print_border(output, qr->width);
+
+ for (y = 0; y < (unsigned) qr->width; y += 2) {
+ const uint8_t *row1, *row2;
+
+ row1 = qr->data + qr->width * y;
+ row2 = row1 + qr->width;
+
+ fputs(WHITE_ON_BLACK, output);
+ for (x = 0; x < 4; x++)
+ fputs("\342\226\210", output);
+
+ for (x = 0; x < (unsigned) qr->width; x ++) {
+ bool a, b;
+
+ a = row1[x] & 1;
+ b = (y+1) < (unsigned) qr->width ? (row2[x] & 1) : false;
+
+ if (a && b)
+ fputc(' ', output);
+ else if (a)
+ fputs("\342\226\204", output);
+ else if (b)
+ fputs("\342\226\200", output);
+ else
+ fputs("\342\226\210", output);
+ }
+
+ for (x = 0; x < 4; x++)
+ fputs("\342\226\210", output);
+ fputs(NORMAL "\n", output);
+ }
+
+ print_border(output, qr->width);
+
+ QRcode_free(qr);
+ return 0;
+}
diff --git a/src/journal/journal-qrcode.h b/src/journal/journal-qrcode.h
new file mode 100644
index 0000000000..da6244c160
--- /dev/null
+++ b/src/journal/journal-qrcode.h
@@ -0,0 +1,30 @@
+/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
+
+#pragma once
+
+/***
+ This file is part of systemd.
+
+ Copyright 2012 Lennart Poettering
+
+ systemd is free software; you can redistribute it and/or modify it
+ under the terms of the GNU Lesser General Public License as published by
+ the Free Software Foundation; either version 2.1 of the License, or
+ (at your option) any later version.
+
+ systemd 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
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public License
+ along with systemd; If not, see <http://www.gnu.org/licenses/>.
+***/
+
+#include <inttypes.h>
+#include <sys/types.h>
+#include <stdio.h>
+
+#include <systemd/sd-id128.h>
+
+int print_qr_code(FILE *f, const void *seed, size_t seed_size, uint64_t start, uint64_t interval, const char *hn, sd_id128_t machine);
diff --git a/src/journal/journalctl.c b/src/journal/journalctl.c
index 551cb311b5..b0d8258dd2 100644
--- a/src/journal/journalctl.c
+++ b/src/journal/journalctl.c
@@ -46,6 +46,7 @@
#include "journal-def.h"
#include "journal-verify.h"
#include "journal-authenticate.h"
+#include "journal-qrcode.h"
#include "fsprg.h"
#define DEFAULT_FSS_INTERVAL_USEC (15*USEC_PER_MINUTE)
@@ -607,12 +608,26 @@ static int setup_keys(void) {
printf("/%llx-%llx\n", (unsigned long long) n, (unsigned long long) arg_interval);
if (isatty(STDOUT_FILENO)) {
- char tsb[FORMAT_TIMESPAN_MAX];
+ char tsb[FORMAT_TIMESPAN_MAX], *hn;
fprintf(stderr,
ANSI_HIGHLIGHT_OFF "\n"
"The sealing key is automatically changed every %s.\n",
format_timespan(tsb, sizeof(tsb), arg_interval));
+
+ hn = gethostname_malloc();
+
+ if (hn) {
+ hostname_cleanup(hn);
+ fprintf(stderr, "The keys have been generated for host %s (" SD_ID128_FORMAT_STR ").\n", hn, SD_ID128_FORMAT_VAL(machine));
+ } else
+ fprintf(stderr, "The keys have been generated for host " SD_ID128_FORMAT_STR ".\n", SD_ID128_FORMAT_VAL(machine));
+
+#ifdef HAVE_QRENCODE
+ fputc('\n', stderr);
+ print_qr_code(stderr, seed, seed_size, n, arg_interval, hn, machine);
+#endif
+ free(hn);
}
r = 0;
diff --git a/src/shared/util.c b/src/shared/util.c
index cbf44ebdfd..041b759287 100644
--- a/src/shared/util.c
+++ b/src/shared/util.c
@@ -3089,7 +3089,6 @@ bool hostname_is_set(void) {
return !isempty(u.nodename) && !streq(u.nodename, "(none)");
}
-
static char *lookup_uid(uid_t uid) {
long bufsize;
char *buf, *name;