From 00aae4e42cb6ad93960955a6bd9f45e092129a89 Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Sun, 22 Nov 2020 13:32:28 +0100 Subject: document exchange crypto helper design --- design-documents/010-exchange-helpers.rst | 128 ++++++++++++++++++++++++++++++ 1 file changed, 128 insertions(+) create mode 100644 design-documents/010-exchange-helpers.rst (limited to 'design-documents/010-exchange-helpers.rst') diff --git a/design-documents/010-exchange-helpers.rst b/design-documents/010-exchange-helpers.rst new file mode 100644 index 00000000..cf7a4dff --- /dev/null +++ b/design-documents/010-exchange-helpers.rst @@ -0,0 +1,128 @@ +Exchange crypto helper design +############################# + +Summary +======= + +A way to minimize the attack surface for extraction of the private online +signing keys (RSA and EdDSA) from the exchange is described. + + +Motivation +========== + +We want to provide an additional layer of protection for the private online +signing keys used by the exchange. The exchange is network-facing, includes an +HTTP server, Postgres interaction, JSON parser and quite a bit of other logic +which may all be theoretically vulnerable to remote exploitation. Thus, it +would be good from a security perspective to protect the private online +signing keys via an additional layer of protection. + + +Requirements +============ + +* The solution should not result in a dramatic loss of performance. +* An attacker with a successful arbitrary code execution on the exchange + must not be able to extract the private keys. +* Ideally, we should be able to determine the number of signatures + obtained illicitly by the attacker. +* Key management for operators should be simplified to improve usability. +* Both RSA and EdDSA online signing keys need to be protected. + + +Proposed Solution +================= + +The private keys are to be created, used and deleted by two helper processes +running under a different user ID (UID). The exchange's HTTP process will be +required to interact with those helpers via a UNIX domain socket. + +Specific design details: + +* The helpers will process requests from the exchange to sign and revoke keys. +* The helpers will tell the exchange when keys are created or deleted/expired. +* SOCK_DGRAM will be used to avoid needing to parse a data stream. +* The helpers will only know about (private) key lifetime. They will not know about + details like currency, fee structure, master or auditor signatures. + Those will be managed by the HTTP process to keep the helpers minimal. +* The exchange will expose the corresponding public keys via a ``/keys?future`` + endpoint to the auditor and the offline signing process. Auditor and master + signatures will be POSTed to the exchange via the ``/keys`` endpoint. + The exchange will keep those signatures in the Postgres database. +* Each exchange thread will create its own connection to the helpers, and will + block while waiting on the helper to create a signature. This keeps the + exchange logic simple and similar to the existing in-line signing calls. + Suspending and resuming would be difficult as we currently do not have a + way to wait for a UNIX domain socket to resume the MHD logic. + If a signal is received while waiting for the helper, the signature operation + fails. Signature operations can also fail if the helper is not running or + responding with incorrect data. However, signature operations do NOT have a + timeout. +* The helpers will use a single-threaded, GNUnet-scheduler-driven event loop + to process incoming requests from the UNIX domain sockets. However, the + actual signing will be done by a thread pool of workers that only process + signing requests from a work queue. Reference counting is used to avoid + releasing private keys while workers are actively using them to sign requests. +* The work queue is managed via a pthread-style semaphore. +* The master thread is informed about completed work via an ``eventfd()``. +* The master thread is responsible for handling revocations, creating future + private keys and expiring old keys. + + +Alternatives +============ + +* The helpers could have been given the information to validate the signing + request. However, without database access, validating the reserve key + signature (and others) is pretty useless. Thus, this direction would only + complicate the helper (which we want to keep minimal to minimize attack + surface) without real benefits. Even validating revocation requests (checking + signatures by auditor or master public key) makes no sense, as if an attacker + triggers a revocation, we should probably be thankful: That's a white-hat + demonstrating that they got control in the least harmful way. +* Instead of two helpers, we could have just one helper. But there is limited + overlap between the (RSA) denomination key logic and the (EdDSA) signing + key logic. Separation may improve security. +* We could have proposed a helper per denomination. But as the code of all of + these helpers would be identical, this would have no security advantages. +* We could have implemented our own event loop and configuration parser, + instead of relying on libgnunetutil. But this part of GNUnet is very + robust. +* We could have had a thread pool reading requests from the exchange clients, + instead of a master thread doling out the work. But this would become really + complicted with key revocations, and as really only the cryptography should + be the bottleneck, performance advantages should be minimal. If IPC ever + becomes the issue, then the entire idea of moving signatures to another + process would be flawed. +* More portable mechanisms (like a ``pipe()``) could be used for signaling + instead of ``eventfd()``. But, this can always be implemented if we truly + ever have an exchange operator needing support for such a platform. +* We could have left the helper single-threaded, to avoid the complications + arising from the use of threads. However, given that signing is expected to + be a bottleneck of the exchange, this would have had serious performance + implications for the entire system. + + +Drawbacks +========= + +* Additional work to properly setup an exchange and to run + our automated tests. +* Slight (?) performance impact. +* UNIX only. Likely Linux-only for now (but fixable). +* If exchange receives ANY (not ignored) signal during signing + operation, a discrepancy in the number of signatures created + between exchange (DB) and the helper will arise. Thus, + auditors have to allow for small discrepancies (increasing + over time). Note that we only expect the exchange to receive + signals if the software is updated or the process is terminated. +* If helper is stopped (SIGSTOP), exchange HTTP will itself block + (no timeout!). Timeout-based mitigation would additionally increase + discrepancies in the count of the number of signatures created. + + +Discussion / Q&A +================ + +(This should be filled in with results from discussions on mailing lists / personal communication.) -- cgit v1.2.3