My guide to using Yubikeys

Table of Contents


When I received my Yubikeys for the first time, I was pleased to find an existing guide to follow. This guide heavily focuses on setting up the keys for GnuPG.

If I had to set up my keys today, I think the process would be much simpler. I’d prefer to have a guide dedicated to Passkeys, with more details on how to use them, what information to save, and so on. I’d also prefer if the instructions recommended using age rather than GnuPG.

So that is what this guide aims to do.

This guide also works with keys from other manufacturers, as soon as it supports FIDO2[1] and PIV[2].

[1] FIDO2: Fast IDentity Online is a standard to authenticate online without passwords

  • It is based on asymmetric keys stored in a password manager, a hardware key, or in a device secure element.
  • FIDO2 also allows you to log in from another device via a QR code over the Internet and requires Bluetooth connection to prevent phishing. This can be useful for logging in to a TV using your smartphone.

[2] PIV: Personal Identity Verification is a protocol used to authenticate using smartcards

How many keys ?

It's helpful to have at least two keys. A third one, which you leave at home, is really handy.

But, it's possible to own a single security key, and use your phone as a second token — even without the Google Play Services — using Passchain (or a similar app), and a password-protected encryption key stored on a hard drive as a backup solution.

Personally, I have a Nano that’s always plugged into my laptop, a 5C NFC that’s always in my wallet, and another 5C NFC that stays at home. Let’s call them YNano, YWallet, and YHome.

I only had two at first, until I thought I’d lost one — which I later found: YHome.

What for ?

The security keys are mainly used for 2 things: login with FIDO2 operations, and asymmetric encryption with age.

FIDO2 is used to authenticate on different websites, and for some crypto operations, like decrypting a disk, or a home partition. If you have an old key, like a Yubikey 4, it may support the legacy protocol U2F[3] instead.

The asymmetric encryption is mainly used to back up 2FA[4]/Passkeys[5] recovery keys, and some other secrets. It may be used by someone to send you an encrypted file too.

[3] U2F: Universal 2nd Factor, is the predecessor of FIDO2. FIDO2 used for 2FA[4] and U2F are compatible, so you can continue to use your old key.

[4] 2FA: 2 Factors Authentication, to login you need a password and something else, for example a hardware token.

[5] Passkey: is the marketing name for FIDO2. You may encounter Webauthn or CTAP2 too, when talking about FIDO2. They are both parts of FIDO2.

For my part, I use YNano and YWallet every day for FIDO2 authentication and for decryption. I mainly use YWallet on my smartphone — using Passchain as I don't have the Play Services. And YHome stays at home.

Age encryption setup

The asymmetric encryption tasks are done using age encryption. The tool is simple and easy to use, you can't mess everything with config and parameters.

Age uses the PIV feature of your keys. You need to install age-plugin-yubikey to be able to do so.

If you have many Yubikeys, I recommend configuring one differently for recovery tasks.

This age-recovery key may be used as a daily token for FIDO2 operations. It just has a little more lax config to do automated tasks. So you don't use this Yubikey for age decryption unless in trusted environment.

But if you prefer, that's also possible to use a password protected key, stored in a file, for these recovery tasks.

For ease of use, you can rely on passage to manage a directory with your encrypted secrets.

Expect most encrypted secrets to be 2FA/Passkeys recovery keys that web applications provide when you enable 2FA. Many of them will be TOTP[6] secrets as websites often use TOTP as a recovery mechanism for FIDO2 authentication/2FA.

[6] TOTP: Time Based One Time Password is a standard and common 2FA protocol. You need an application that gives you 6 digits code that are valid for 10 seconds. During the setup, you usually scan a QR code to save a secret.

Aegis Android application showing 6-digits codes for 3 different websites

Aegis is an Android application to manage TOTP

Trusted environment

Any secret must be generated, encrypted or decrypted in a trusted environment.

Your daily desktop should be enough for most of them, for example to encrypt 2FA recovery keys.

Depending on your need, you probably want to generate a backup age identity, protected by a password. This is the secret to rule them all.

For this one secret, you may want to use a live USB as a trusted environment, to get something more trusted. You need to install 3 things ykman, age-encryption and age-plugin-yubikey, the name may change depending on your distribution.

Age recovery identity

So, if losing all your Yubikeys at the same time is a possibility, you need a password protected age identity that you can store on a drive you keep in a safe place

This identity should be generated in a particularly trusted environment, as it can be used to decrypt all the other secrets.

~/.p > mkdir SEEDS  
~/.p > sudo mount -t tmpfs -o size=100M tmpfs SEEDS/  
~/.p > cd SEEDS  
~/.p/SEEDS> age-keygen -o backup_identity  
Public key: age123[...]  
~/.p/SEEDS> age -p -e -a backup_identity > encrypted_backup_identity.txt  
~/.p/SEEDS> echo "# Backup ID" > age-recipients   
~/.p/SEEDS> age-keygen -y < backup_identity >> age-recipients  
~/.p/SEEDS> cat age-recipients   
# Backup ID  
age123[...]  
~/.p/SEEDS> rm backup_identity

You should write the password of the key on a piece of paper and store it safely.

Tip: One of the first secret you can store with passage is this password, you may need it if you lose the paper you wrote the password on.

Configure the Yubikeys

The Yubikeys are configured with ykman, and age needs a plugin to use the keys' PIV: age-plugin-yubikey.

At this point, you're supposed to have your age recovery identity if you want one.

Daily Yubikeys' identity

First, we configure the Yubikeys we want to use on a daily basis, that is, the ones we keep nearby to log in to websites and other services.

We change the key secrets, and PIN, then finish the age setup.

  • (Optional) Change the PIV retries counter. This resets the PIN and PUK to their factory defaults:
> ykman piv access set-retries
  • Change the PIV management key (we generate a key that stays on the hardware, protected by a PIN), the PUK (recovery) and the PIN:
> ykman piv access change-management-key -t -p
> ykman piv change-puk
> ykman piv change-pin
  • Generate an age key for each hardware key, and add to the passage store’s recipients.

Note: Replace 83 with the first retired slot available. You can find this slot with the command ykman piv info, if you haven't used any retired slot yet, it should be the 82nd.

> ykman piv info  
... (Check current slots)  
  
~/.p/SEEDS> ykman piv keys generate --algorithm ECCP256 83 --touch-policy ALWAYS --pin-policy ONCE pub.pem  
~/.p/SEEDS> ykman piv certificates generate --subject "CN=age" 83 pub.pem  
~/.p/SEEDS> ykman piv info  
... (A new slot is used)  
~/.p/SEEDS> echo "# YWallet" >> age-recipients # Change with your key name  
~/.p/SEEDS> age-plugin-yubikey --list-all >> age-recipients

Recovery Yubikey

If you want to keep a Yubikey for recovery tasks, specially if you haven't set an age recovery identity: generate an identity with touch-policy=CACHED.

This policy is a little more lax than the daily key setup, but it allows some automated tasks.

For example it will be used if you get a new Yubikey and want to encrypt the current secret to this key as well.

  • (Optional) Change the PIV retries counter. This resets the PIN and PUK to their factory defaults:
> ykman piv access set-retries
  • Change the PIV management key (we generate a key that stays on the hardware, protected by a PIN), the PUK (recovery) and the PIN:
> ykman piv access change-management-key -t -p
> ykman piv change-puk
> ykman piv change-pin
  • Generate an age key, and add to the passage store’s recipients. This is the step that differs from the other kind of key:

Note: Replace 83 with the first retired slot available. You can find this slot with the command ykman piv info, if you haven't used any retired slot yet, it should be the 82nd.

~/.p/SEEDS> ykman piv keys generate --algorithm ECCP256 83 --touch-policy CACHED --pin-policy ONCE pub.pem  
~/.p/SEEDS> ykman piv certificates generate --subject "CN=age" 83 pub.pem  
~/.p/SEEDS> ykman piv info  
... (A new slot is used)  
~/.p/SEEDS> echo "# YHome" >> age-recipients # Change with your key name  
~/.p/SEEDS> age-plugin-yubikey --list-all >> age-recipients

FIDO2 setup

The main use case of the security keys is to log in on websites or services without a password. As soon as you have access to one of your keys, you can retrieve your access to your accounts.

That's particularly useful to get access to your cloud hosting your password manager file for instance.

There are 2 kinds of keys:

  • Discoverable keys, also named resident keys, that are stored on the key.

    • You usually don't need to enter any username to login.
    • Authentication with a key protected with a PIN is an authentication with 2 factors as you need the PIN and the hardware key.
  • Non-discoverable keys, who require a challenge from the server.

    • This kind of key require the user to enter their username, and is often used as a 2nd factor to authenticate (so username+password+key).
    • When it is used as a 2FA, website usually don't require the key PIN.
    • This kind of key is compatible with U2F.
Screenshot of a Discourse instance, with the different options to login, including "Sign in with a passkey"

Discourse, a FOSS forum solution, offers an option to log in with a discoverable key

Screenshot of Codeberg login interface, without any option to "login with passkey"

Codeberg doesn't offer an option to log in with a discoverable key. But security keys can be used as a 2FA.

Configure the Yubikeys

Again, the Yubikeys are configured with ykman.

The setup is pretty straightforward. All you have to do is to change the PIN of the keys:

> ykman fido access force-change

slots.md

While it is always possible to list resident keys (ykman fido credentials list), it isn't possible to list where we registered with non-discoverable keys. Keeping a list of these websites is particularly useful the day you will receive a new Yubikey.

For that, I have a slots.md file in my passage store that I update whenever I register a new key. It also contains other information like the key serial number, or PIV slots used for age.

~/.passage/store/slots.md:

# Yubikey - slots  
  
YNano:   21 235 311  
YWallet: 21 235 312  
YHome:   21 235 313  
  
## FIDO2  
  
### Discoverable  
  
| Service                   | YNa   | YWa  | Backup |  
|---------------------------|-------|------|--------|  
| github                    | OK    | OK   | OK     |  
| ssh_ed25519-sk            | OK    | OK   | OK     |  
| google unifiedpush.org    | OK    | OK   | OK     |  
  
### Non-Discoverable  
  
| Service               | YNa   | YWa  | Backup |  
|-----------------------|-------|------|--------|  
| Gitlab                | OK    | OK   | OK     |  
| Strip                 | OK    | OK   | OK     |  
| Nextcloud (s1m)       | OK    | OK   | OK     |  
| Nextcloud (admin)     | OK    | OK   | OK     |  
[...]  
  
### SSH  
  
| Service                       | YNa   | YWa  | Backup |  
|-------------------------------|-------|------|--------|  
| home                          | OK    | OK   | OK     |  
| back                          | OK    | OK   | OK     |  
| github                        | OK    | OK   | OK     |  
| codeberg                      | OK    | OK   | OK     |  
[...]  
  
### PIV  
  
82 -> 95 are free  
  
| Service      | Slot | YNa | YWa | YBa | Backup | Policy |  
|--------------|------|-----|-----|-----|--------|--------|  
| Management   | -    | OK  | OK  | OK  | \*     |        |  
| Age          | 82   | OK  | OK  | +TC | OK     | PO+TA  |  
  
\* The management key is stored in the key, protected with PIN+UV.  
  
Policy: Px=PIN, Tx=Touch  
xD=Default, xN=Never, xA=Always, xO=Once, xC=Cached  
  
Note: PO ~= Cached, because the key is powered off after 5 secs

Websites

All websites don't have the same flow to enroll new passkeys.

  1. Some of them require to enable 2FA first.
Screenshot of Mastodon "Two-factor Auth" settings. 2FA is enabled, and 2 methods are listed: "Authenticator app" and "Security keys"

Mastodon requires to set a TOTP to use Passkeys

In this case, I use pass/passage's OTP extension:

  • I take a screenshot of the QR code
  • Add the OTP to passage wl-paste | zbarimg -q --raw - | passage otp insert gitlab/otp # QR
  • Validate the OTP passage otp gitlab/otp
  • Then register the keys
  1. Most website also give a backup key, which I add to passage: passage add -m gitlab/backup

  2. Some websites use FIDO2 only for 2FA (non-resident keys), others offer only resident keys, and still others offer both.

  3. Finally, only a few websites offer passwordless FIDO2 authentication using non-resident keys. In this case, the user simply needs to enter their username.

Screenshot of Nextcloud "log in with a device" interface. The interface as one single field to fill: "login or email".

Nextcloud offers passwordless authentication using non-resident keys.

And every time I enroll passkeys, I enroll the 2 Yubikeys (YNa, and YWa), and add it to my slots.md file.

Screenshot of Nextcloud settings. The section is named "Passwordless Authentication". 2 devices are listed as registered: YWa and YNa.

My 2 daily Yubikeys are registered on Nextcloud

SSH

OpenSSH has a built-in support for FIDO2 authentication, with both discoverable or non-discoverable key.

Personally this is exactly the kind of service I want to keep access to, even if I lose my KeePass(.kdbx) file, therefore I prefer to use discoverable ones.

So I have 3 keys:

  • 2 discoverable keys, one with YNano and the other with YWallet
  • A password protected ssh-key file. The password is stored in my passage store.

Generate

To generate a resident key, insert your Yubikey and run:

> ssh-keygen -t ed25519-sk -O resident -O verify-required -C "your_email@example.com"

Add to authorized_keys

Whenever I add my public keys on a machine, I add these lines to /.ssh/authorized_keys:

sk-ssh-ed25519@openssh.com AAAAGn[...]A1= sim@ykn  
sk-ssh-ed25519@openssh.com AAAAGn[...]B2= sim@ykr  
ssh-ed25519 AAAAC[...]C sim@back

Using resident keys on a new machine

Insert your Yubikey and run:

> ssh-keygen -K

Resources

GnuPG operations

GnuPG (Gnu Privacy Guard) is an historical cryptographic tool, to encrypt and sign stuff. This tool contains tons of options and parameters and is easy to mess with.

I try to avoid using GPG now, but it happens that I need it, to sign libraries for instance. In this case I use openpgp-card-tools (oct). Its interface is simple, it works well, and it doesn't require a daemon that could interfere with other uses of the key.

Resources to generate and manager GnuPG keys:

Receiving a new Yubikey

At some point, you will likely buy a new key, maybe because you lose or break the previous one, or any other impredictable reason.

When you get a new key:

  • Setup a trusted environment again (cf. Trusted environment)
  • Generate age identity for the key (cf. Daily Yubikeys' identity)
  • Reencrypt your passage store:
    • For the following command, you should use your recovery Yubikey (the one configured with touch-policy=CACHED), or the age recovery identity (the one stored in a file protected with a password), else you will have to touch the Yubikey for every passage entry.
    • Once ready run: passage reencrypt

The age-recipients can then be used with your passage store.

Note about post-quantum

Age is currently working on a solution to get Quantum-resistent encryption with our keys. The setup will likely have to be updated once released.

5 years of UnifiedPush

Table of Contents


It has already been 5 years since UnifiedPush started! It also means I don't have any Play Services, the official or microG reimplementation, for 5 years now. It is a good moment to do a recap, and think about what can be UnifiedPush in 5 years.

It turns out I don't remember in details how all started, I need to read some historical pull requests and chats.

Why do I need push notifications?

I think I've installed my first alternative ROM, LineageOS, around 2013, and never went back to stock ROMs since then. At this time, I didn't really care about the apps I was installing, it was mainly to take control of my devices and get rid of the bloatwares.

I understood that I needed the Play Services, or a reimplementation, for some applications to properly work, and I was vaguely knowing why. So, every time I updated my phone, I had to boot into the custom recovery (TWRP), to flash a zip, to get microG. It was, well .. not the best user experience.

Then, I tried to stay without the Play Services, it was even worse, messages weren't reliable, the battery drained and there were many foreground notifications, which I understood were required to keep a service running.

So I decided to go with a fork of LineageOS that includes microG by default, and distributed by microG team: LineageOS for microG.

Even after using this new system, the experience was nearly the same. Why? Because most of my apps were from F-Droid. Push notifications with Google (via microG) require the use of a proprietary library *, which comes with telemetry, unless explicitly configured to exclude them. F-Droid deny this library, which is fair given that their purpose is to promote free software.

* That's actually possible to use FCM (Google notifs) without Google lib, but I didn't know that at this moment. Cf. UnifiedPush blog post about push notifications for decentralized applications, or Molly issue regarding FOSS FCM implementation.

Gotify (2020)

So, we're in 2020, and I finally want to look why I can't use microG with Fedilab and Element from F-Droid, and if we can replace microG with another notification app.

It turns out among others notification applications, F-Droid distributes Gotify. It isn't able to forward notifications to other apps, but there is an issue opened for that feature, and jmattheis, the developer seems open to the idea.

I didn't touch any Android dev at this moment, but I tried to hack something. Fortunately, jmattheis review helped a lot to make things less hacky. So here came gotify-connector.

It looks like from the pull request history that "connector" comes from jmattheis, for which I added "distributor" later.

At this moment, the feature has picked the interest of some persons, including sorunome, karmanyaahm and sparchatus. Sorunome, contributor to FluffyChat, told me that the feature may interest people in OpenPush matrix room.

First UnifiedPush version (2020)

Late 2020, looking at some p2p projects, I thought it would be cool having a p2p based solution too. So came the questions about ecosystem lock-in of a gotify only solution, adoption, and fragmentation. If we have multiple applications able to provide push notifications, we should have a library that is compatible with all of them. When a new application providing push notifications is published, then all existing applications supporting the thing would be directly compatible. Going that way, we needed to specify how it should work first.

I shared the idea in OpenPush room, and it picked the interest of someone in particular, sparchatus, who helped me to write the specifications. We discussed many edge cases to see how things could be.

I published a first version of the specifications, a library, and a fork of gotify until the support was merged *.

Sorunome was interested in implementing the support in Fluffychat. It required a flutter lib, karmanyaahm wrote a lib porting the already published library to the framework. We also needed something to translate matrix push protocol, and make gotify server compatible: karmanyaahm wrote common-proxies for this.

* Which actually never happened 🤷

FluffyChat, Fedilab, and more (2021)

Early 2021, FluffyChat was supporting UnifiedPush. And soon came Fedilab too, as the dev, Thomas, was directly interested.

Starting with these 2 applications was a chance for the project: we had support for matrix, and many other chats using matrix bridges, and for the fediverse. This covered enough applications for some FOSS enthusiasts. Retrospectively, UnifiedPush may never have started without these 2 applications.

After that, some applications started to implement the feature, such as a Tox application, or FMD, a FOSS solution to find your device.

Mid 2021, I implemented UnifiedPush support for Element, which was soon merged by SchildiChat, a fork. I think the experience from SchildiChat helped for it being merged into Element mid 2022.

UnifiedPush for Linux (mid 2021)

At this moment, vurpo came to UnifiedPush matrix room to talk about push notifications for Linux devices. So we had UnifiedPush for Linux by mirroring the specifications for Android to D-Bus IPC.

ntfy, NextPush (2021)

During 2021, a new project appeared on the Internet: ntfy. A project like Gotify, that can work without any account, with a public server. The app is extremely easy to use, as you have nothing to set up. And the developer, binwiederhier, was directly interested in supporting UnifiedPush, to make ntfy a distributor.

Merged early 2022, it was an important step for UnifiedPush: we have a distributor to recommend by default.

I have also implemented NextPush at the same period, giving an easy opportunity to self-host a push server, if you already host a Nextcloud server

In the same time, Gotify developer informed us that they finally prefer not to merge the support, as they don't use it and prefer to avoid adding maintenance to their project, which is perfectly understandable. With this new position, the official support of UnifiedPush by ntfy, and the new NextPush app, I preferred to discontinued Gotify forks as well.

KUnifiedPush (mid 2022)

Mid 2022, the KDE team, and particularly vkrause, published KUnifiedPush: a distributor for Linux, compatible with different push server, like ntfy or NextPush. Until then, we only had POC implementations of distributors for Linux. KUnifiedPush also provide libraries for KDE applications.

This allowed Linux applications to finally support the protocol.

Full-time on UnifiedPush (2024 - 2025)

At the end of 2023, we have more than 20 applications supporting UnifiedPush, and another distributor: Conversations. Element being probably the one with the larger user base at this moment. Someone advised me to apply for a grant with NLnet, as it would boost development of the project.

During the application process with NLnet, COVESA reached me because they wanted to support the project, but needed a few features that weren't present, to get a more robust authorization mechanism and avoid registration spamming.

UnifiedPush has always been compatible with web push (RFC8030 and RFC8291 but RFC8292, aka VAPID, wasn't). Embracing the standard to require web push was a potential step to take. The specifications needed to be updated in that direction, to require encryption (RFC8291) and to handle authorizations with VAPID (RFC8292). Relying on standard will hopefully help for the adoption, as the server side implementation may be used for web applications in the same time.

At the end of 2024, I've started working full-time on UnifiedPush.

Working with COVESA also allowed to get Sunup, a distributor using Mozilla's push server, autopush, and to add a self-hostable backend for autopush. This feature is currently being merged.

NLnet gave the opportunity to polish many things that were pending, to add a migration feature to the protocol, which can be used to get a fallback service when your self-hosted server is down, to implement the actual web push specifications on Mastodon, and to add web push/UnifiedPush to some applications. It includes Fennec/IronFox, forks of Firefox, so we can now get push notifications with web applications. It also includes SimpleX (being merged), Nextcloud (being merged), DeltaChat (TODO), and flatline (TODO), a self-hostable version of Signal server, hopefully upstreamed to Signal servers.

The idea is to increase the network effect: the more applications support UnifiedPush, the more UnifiedPush can be relevant for users, and the more users will use UnifiedPush. If the number of UnifiedPush users increases, it pushes applications' developers to support the protocol. At the end, we can use our phone with the push service we want, to get an expected user experience even without the Play Services.

Retrospective

It was by chance that I started UnifiedPush and the project would never have existed without other projects like F-Droid, gotify, matrix, Fluffychat or Fedilab, and many more, without the help of many people.

I think it shows how the FOSS ecosystem can be beneficial for everyone. I develop Sunup, but often contribute to ntfy. The projects could be seen as "concurrent", but aren't: the applications answer different needs. We don't have anything to win or lose if a user chose one app over the other. But we all win if a user chose to use one, no matter which, as it increases the network effect.

If UnifiedPush wasn't started 5 years ago, I'm sure an equivalent project would have started since then. This is something that was awaited in the mobile FOSS community, and there were already some research work on the subject.

I wasn't aware how many things were implied with push notifications. It is understandable that giving a single entity the capacity to provide such an important feature give them incredible power. This is concerning when their solution doesn't follow least-privilege policies, come with system rights, has access to the full system, and with "features" we don't want, such as advertisement and telemetry.

I now understand why push servers may be a tool for mass surveillance and how an open solution is important for resilience. Some networks exist outside the Internet, some regions in the world suffer from services block, some users may be banned from these services. When a service is controlled by a single entity, nothing can be done when they consider your device too old to be supported. Offering an open alternative is a response to all these problems.

The idea is not to move everyone to an open solution, but to give the freedom to. Supporting these alternatives also reduces risks of power abuse from Google. If you develop an application, ask yourself how fast could you recover from being banned by Google?

Working full-time on UnifiedPush is incredible. I'm extremely happy a foundation like NLnet exists. I hope my work is beneficial for the project and for most of the users. When it all started, I didn't imagine a second I could work on this, I just wanted my matrix and mastodon notifications without the Play Services.

I would love to continue working daily on UnifiedPush, and there are probably tons of things to do, specially for Linux devices, and many apps to port the feature to. But NLnet funds aren’t unlimited, our main goals are reached - improving the protocol, improving the existing code and documentation, boosting the network effect on Android -, and I don’t want to take the potential place of another project.

Among other things, we still need to improve libraries for UnifiedPush on Linux, and it’d be great to have a UI for KUnifiedPush to publish it on Flatpak. There are some important applications, such as Mozilla sync service, that use an allow-list of authorized push servers, defeating the purpose of self-hosting: it would be great implementing a better anti-SSRF mechanism. We will probably have to build these blocks and others together. If you want to contribute, do not hesitate to PM on Mastodon or join UnifiedPush matrix room.

UnifiedPush in 5 years

The best thing that could happen to UnifiedPush on Android in 5 years would be for it to no longer exist.

If Android gives us a system API to let the user define their push service we wouldn't need UnifedPush anymore. Passkeys (API to login without passwords), used to be provided by the Play Services only. Today, probably to increase the adoption, Android has migrated to a system API (Credential Provider), to allow any password manager to provide the service. With a Push Service API, UnifiedPush would have kind of been integrated into the OS. The applications would receive push endpoints like we do, and they would send web push requests, following standards, like web applications does, like UnifiedPush does. Migration from UnifiedPush would be minimal.

If we manage to have such a Push Service API, we can expect many more apps supporting the feature. And we will finally be able to choose the services we want to trust.

Hopefully, working on UnifiedPush can push in that direction by increasing the demand, and highlighting the need.

On Linux, I think the adoption depends a lot on how the mobile Linux ecosystem evolves. I personally think and wishes that it goes in the right direction. And I think a lot of things can happen in 5 years on the matter.