I wanted to get DKIM working on an Debian box I have that runs Exim. The first thing to do is to create the keys:
$ openssl genrsa -out diamonds.key 4096 $ openssl rsa -in diamonds.key -pubout > diamonds.pub
I was following these instructions and noticed that Exim supports ed25519 DKIM signatures. Neat! I decided I may as well create those keys, too:
$ openssl genpkey -algorithm ed25519 -out hearts.key $ openssl pkey -outform DER -pubout -in hearts.key | tail -c +13 | base64 > hearts.pub
From there I stuck the public keys in DNS:
diamonds._domainkey.example.com. 3600 IN TXT "v=DKIM1; k=rsa; t=s; p=MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAxDMS3KRFCU4PEtygOUdALBt7jmz5IIX2+KHoV4fd0CLjXRvOqA5H8rU3e+y1lNese9yjPLksPqiOh5vtx8Tysjv2MSTXB1Kgr0tl+1IlJL4ihdpUgR1veKB5X4wK3Ppkr5Oy42H7xNHf/yj6aC1E+alZ8TdssuHY3ReqO6YvGa72UqTMmL1gBl9SXBUl" "vD+FqvfFtkQFFMU9QSTtrIuzcup6NC6z3a4I4UGz4YOZSxeUARKzySGFzPd7vwmrKEZVhlA0HzmJm9eGrjq6IiLVdgTJhSZ8Ecn9h65x9EjhNYYhsufTbcPDljlZYpA4b+dkTEs35a4KjOM2wY7gUdY9ydOqOCfz2BpzJ25Mn3K8nTV8a7fInWCnKg0sm6Fuiwe0DrQjrTe7xGC3Y03CU8eziynOukyWnfsCAnpWcUGa15bp1/O0Le+ZYsKOWxA" "CL5cKlYPw1VJrqz7ZQ1i+s+twOLgEKWm8gwKMsDysgpM1WvE+IhlJkkZLkWavF9pAKeSD6akkHcbkB3QsDKgNugDC4EEm6XV/+hPcTS9Gmd2PYPswxg8nlEdUDjxLul6UbKzWwkYihzKxhMSqCEXTUkt6eHjT+KAIHXVm86elFEmOcuadUWwr+74fgnTpv1XbWIs5qqqh/zROhvUUR8EXZbjOchFEX3YjLO8NDPqHdW4zHt0CAwEAAQ==" hearts._domainkey.example.com. 3600 IN TXT "v=DKIM1; t=s; k=ed25519; p=MTGVeSXmIzviF/B+ANc/bLqP2zEWhO/rw6o8HxIl5+8="
Ed25519 is quite compact!
t=s:y is found in the DKIM RFC (section 3.6.1).
t is for various flags.
s is for strict (I’m just guessing the mnemonic)—it means all the domain names have to match. Apparently you don’t want this if you use subdomains in your email addresses (I don’t).
y means “This domain is testing DKIM”—ie, don’t worry if it fails. It seemed reasonable to set that while I was playing around.
Next, I had to set up Exim in Debian. This was kind of a pain because there’s the Exim config, then the Debian wrapper around that config. This is made more complicated by the fact that Debian has a debconf option named
dc_use_split_config. You can see which way yours is set in
/etc/exim4/update-exim4.conf.conf (the double
.conf is not a typo!). If it’s
false then when you update
/etc/exim4/conf.d you first have run
/usr/sbin/update-exim4.conf.template which cats everything in the
conf.d dir into
/etc/exim4/exim4.conf.template. Then you have to run
/usr/sbin/update-exim4.conf which combines
/etc/exim4/exim4.conf.template and puts the resulting final config file in
The basic DKIM config is in
/etc/exim4/exim4.conf.localmacros. I added these lines:
DKIM_CANON = relaxed DKIM_SELECTOR = diamonds : hearts DKIM_DOMAIN = example.com DKIM_PRIVATE_KEY = /etc/exim4/dkim/$dkim_selector.key
For my setup this wasn’t enough. The
DKIM_* macros are only used by the “remote_smtp” transport (found in
/etc/exim4/conf.d/transport/30_exim4-config_remote_smtp). I was using a “satellite” configuration with a smarthost. This means it uses the “remote_smtp_smarthost” transport (found in
/etc/exim4/conf.d/transport/30_exim4-config_remote_smtp_smarthost). You can tell what transport is being used by looking for
I copied all the DKIM related stuff from
/etc/exim4/conf.d/transport/30_exim4-config_remote_smtp_smarthost, namely these lines:
# 2019-08-26: David added these: .ifdef DKIM_DOMAIN dkim_domain = DKIM_DOMAIN .endif .ifdef DKIM_SELECTOR dkim_selector = DKIM_SELECTOR .endif .ifdef DKIM_PRIVATE_KEY dkim_private_key = DKIM_PRIVATE_KEY .endif .ifdef DKIM_CANON dkim_canon = DKIM_CANON .endif .ifdef DKIM_STRICT dkim_strict = DKIM_STRICT .endif .ifdef DKIM_SIGN_HEADERS dkim_sign_headers = DKIM_SIGN_HEADERS .endif
Then I ran
update-exim4.conf and finally
systemctl restart exim4.
At this point I could send emails through and the DKIM headers were added.
Next I removed the
y flag from the
t flags in the DNS since everything appeared correct. I also added the ADSP DNS record:
_adsp._domainkey.example.com. 3600 IN TXT "dkim=all"
Then I wrote this post and called it a night!