summaryrefslogtreecommitdiff
path: root/TLS.md
diff options
context:
space:
mode:
authorYossi Gottlieb <yossigo@gmail.com>2019-09-12 10:56:54 +0300
committerYossi Gottlieb <yossigo@gmail.com>2019-10-07 21:06:13 +0300
commitb087dd1db60ed23d9e59304deb0b1599437f6e23 (patch)
tree0533b9d4d626af5ab4b5fdb5d4a2eb500b12c163 /TLS.md
parentf4d37173fef8a020fe99a7b98e32a9201113cc09 (diff)
downloadredis-b087dd1db60ed23d9e59304deb0b1599437f6e23.tar.gz
TLS: Connections refactoring and TLS support.
* Introduce a connection abstraction layer for all socket operations and integrate it across the code base. * Provide an optional TLS connections implementation based on OpenSSL. * Pull a newer version of hiredis with TLS support. * Tests, redis-cli updates for TLS support.
Diffstat (limited to 'TLS.md')
-rw-r--r--TLS.md133
1 files changed, 133 insertions, 0 deletions
diff --git a/TLS.md b/TLS.md
new file mode 100644
index 000000000..ee24a8df5
--- /dev/null
+++ b/TLS.md
@@ -0,0 +1,133 @@
+TLS Support -- Work In Progress
+===============================
+
+This is a brief note to capture current thoughts/ideas and track pending action
+items.
+
+Getting Started
+---------------
+
+### Building
+
+To build with TLS support you'll need OpenSSL development libraries (e.g.
+libssl-dev on Debian/Ubuntu).
+
+Run `make BUILD_TLS=yes`.
+
+### Tests
+
+To run Redis test suite with TLS, you'll need TLS support for TCL (i.e.
+`tcl-tls` package on Debian/Ubuntu).
+
+1. Run `./utils/gen-test-certs.sh` to generate a root CA and a server
+ certificate.
+
+2. Run `./runtest --tls` or `./runtest-cluster --tls` to run Redis and Redis
+ Cluster tests in TLS mode.
+
+### Running manually
+
+To manually run a Redis server with TLS mode (assuming `gen-test-certs.sh` was
+invoked so sample certificates/keys are available):
+
+ ./src/redis-server --tls-port 6379 --port 0 \
+ --tls-cert-file ./tests/tls/redis.crt \
+ --tls-key-file ./tests/tls/redis.key \
+ --tls-ca-cert-file ./tests/tls/ca.crt
+
+To connect to this Redis server with `redis-cli`:
+
+ ./src/redis-cli --tls \
+ --cert ./tests/tls/redis.crt \
+ --key ./tests/tls/redis.key \
+ --cacert ./tests/tls/ca.crt
+
+This will disable TCP and enable TLS on port 6379. It's also possible to have
+both TCP and TLS available, but you'll need to assign different ports.
+
+To make a Replica connect to the master using TLS, use `--tls-replication yes`,
+and to make Redis Cluster use TLS across nodes use `--tls-cluster yes`.
+
+**NOTE: This is still very much work in progress and some configuration is still
+missing or may change.**
+
+Connections
+-----------
+
+Connection abstraction API is mostly done and seems to hold well for hiding
+implementation details between TLS and TCP.
+
+1. Still need to implement the equivalent of AE_BARRIER. Because TLS
+ socket-level read/write events don't correspond to logical operations, this
+ should probably be done at the Read/Write handler level.
+
+2. Multi-threading I/O is not supported. The main issue to address is the need
+ to manipulate AE based on OpenSSL return codes. We can either propagate this
+ out of the thread, or explore ways of further optimizing MT I/O by having
+ event loops that live inside the thread and borrow connections in/out.
+
+3. Finish cleaning up the implementation. Make sure all error cases are handled
+ and reflected into connection state, connection state validated before
+ certain operations, etc.
+ - Clean (non-errno) interface to report would-block.
+ - Consistent error reporting.
+
+4. Sync IO for TLS is currently implemented in a hackish way, i.e. making the
+ socket blocking and configuring socket-level timeout. This means the timeout
+ value may not be so accurate, and there would be a lot of syscall overhead.
+ However I believe that getting rid of syncio completely in favor of pure
+ async work is probably a better move than trying to fix that. For replication
+ it would probably not be so hard. For cluster keys migration it might be more
+ difficult, but there are probably other good reasons to improve that part
+ anyway.
+
+5. A mechanism to re-trigger read callbacks for connections with unread buffers
+ (the case of reading partial TLS frames):
+
+ a) Before sleep should iterate connections looking for those with a read handler,
+ SSL_pending() != 0 and no read event.
+ b) If found, trigger read handler for these conns.
+ c) After iteration if this state persists, epoll should be called in a way
+ that won't block so the process continues and this behave the same as a
+ level trigerred epoll.
+
+Replication
+-----------
+
+Diskless master replication is broken, until child/parent connection proxying is
+implemented.
+
+
+TLS Features
+------------
+
+1. Add metrics to INFO.
+2. Add certificate authentication configuration (i.e. option to skip client
+auth, master auth, etc.).
+3. Add TLS cipher configuration options.
+4. [Optional] Add session caching support. Check if/how it's handled by clients
+ to assess how useful/important it is.
+
+
+redis-benchmark
+---------------
+
+The current implementation is a mix of using hiredis for parsing and basic
+networking (establishing connections), but directly manipulating sockets for
+most actions.
+
+This will need to be cleaned up for proper TLS support. The best approach is
+probably to migrate to hiredis async mode.
+
+
+Others
+------
+
+Consider the implications of allowing TLS to be configured on a separate port,
+making Redis listening on multiple ports.
+
+This impacts many things, like
+1. Startup banner port notification
+2. Proctitle
+3. How slaves announce themselves
+4. Cluster bus port calculation