Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Emergency Access Takeover not storing password #3196

Closed
rsoftnl opened this issue Jan 29, 2023 · 15 comments · Fixed by #3215
Closed

Emergency Access Takeover not storing password #3196

rsoftnl opened this issue Jan 29, 2023 · 15 comments · Fixed by #3215
Labels
bug Something isn't working

Comments

@rsoftnl
Copy link

rsoftnl commented Jan 29, 2023

Hi,

I'm trying to access a users vault by means of the Emergency Access feature. Everything appears to be setup correctly, but when I'm given the opportunity to takeover the Master Password (after 7 days wait period, E-mail from Vaultwarden received it has granted me rights) I can't change the Master Password. It will allow me to enter the new password, but Save seems to not do anything at all. The window does not close and the LOG shows a 200 message

Your environment (Generated via diagnostics page)

  • Vaultwarden version: v1.27.0
  • Web-vault version: v2022.12.0
  • Running within Docker: true (Base: Debian)
  • Environment settings overridden: true
  • Uses a reverse proxy: true
  • IP Header check: true (X-Real-IP)
  • Internet access: true
  • Internet access via a proxy: false
  • DNS Check: true
  • Time Check: true
  • Domain Configuration Check: true
  • HTTPS Check: true
  • Database type: SQLite
  • Database version: 3.39.2
  • Clients used:
  • Reverse proxy and version:
  • Other relevant information:

Config (Generated via diagnostics page)

Show Running Config

Environment settings which are overridden: ADMIN_TOKEN

{
  "_duo_akey": null,
  "_enable_duo": false,
  "_enable_email_2fa": true,
  "_enable_smtp": true,
  "_enable_yubico": true,
  "_icon_service_csp": "",
  "_icon_service_url": "",
  "_ip_header_enabled": true,
  "_smtp_img_src": "cid:",
  "admin_ratelimit_max_burst": 3,
  "admin_ratelimit_seconds": 300,
  "admin_token": "***",
  "allowed_iframe_ancestors": "",
  "attachments_folder": "data/attachments",
  "authenticator_disable_time_drift": false,
  "data_folder": "data",
  "database_conn_init": "",
  "database_max_conns": 10,
  "database_timeout": 30,
  "database_url": "***************",
  "db_connection_retries": 15,
  "disable_2fa_remember": false,
  "disable_admin_token": false,
  "disable_icon_download": false,
  "domain": "*****://*************************",
  "domain_origin": "*****://*************************",
  "domain_path": "",
  "domain_set": true,
  "duo_host": null,
  "duo_ikey": null,
  "duo_skey": null,
  "email_attempts_limit": 3,
  "email_expiration_time": 600,
  "email_token_size": 6,
  "emergency_access_allowed": true,
  "emergency_notification_reminder_schedule": "0 3 * * * *",
  "emergency_request_timeout_schedule": "0 7 * * * *",
  "enable_db_wal": true,
  "event_cleanup_schedule": "0 10 0 * * *",
  "events_days_retain": null,
  "extended_logging": true,
  "helo_name": "********",
  "hibp_api_key": null,
  "icon_blacklist_non_global_ips": true,
  "icon_blacklist_regex": null,
  "icon_cache_folder": "data/icon_cache",
  "icon_cache_negttl": 259200,
  "icon_cache_ttl": 2592000,
  "icon_download_timeout": 10,
  "icon_redirect_code": 302,
  "icon_service": "internal",
  "incomplete_2fa_schedule": "30 * * * * *",
  "incomplete_2fa_time_limit": 3,
  "invitation_expiration_hours": 120,
  "invitation_org_name": "Vaultwarden",
  "invitations_allowed": true,
  "ip_header": "X-Real-IP",
  "job_poll_interval_ms": 30000,
  "log_file": "/data/vaultwarden.log",
  "log_level": "INFO",
  "log_timestamp_format": "%Y-%m-%d %H:%M:%S.%3f",
  "login_ratelimit_max_burst": 10,
  "login_ratelimit_seconds": 60,
  "org_attachment_limit": null,
  "org_creation_users": "***************************",
  "org_events_enabled": false,
  "org_groups_enabled": false,
  "password_hints_allowed": false,
  "password_iterations": 100000,
  "reload_templates": false,
  "require_device_email": false,
  "rsa_key_filename": "data/rsa_key",
  "send_purge_schedule": "0 5 * * * *",
  "sends_allowed": true,
  "sends_folder": "data/sends",
  "show_password_hint": false,
  "signups_allowed": false,
  "signups_domains_whitelist": "********",
  "signups_verify": true,
  "signups_verify_resend_limit": 6,
  "signups_verify_resend_time": 3600,
  "smtp_accept_invalid_certs": false,
  "smtp_accept_invalid_hostnames": false,
  "smtp_auth_mechanism": "LOGIN",
  "smtp_debug": false,
  "smtp_embed_images": true,
  "smtp_explicit_tls": null,
  "smtp_from": "**********************",
  "smtp_from_name": "Vaultwarden",
  "smtp_host": "*****************",
  "smtp_password": "***",
  "smtp_port": 587,
  "smtp_security": "starttls",
  "smtp_ssl": null,
  "smtp_timeout": 15,
  "smtp_username": "**********************",
  "templates_folder": "data/templates",
  "tmp_folder": "data/tmp",
  "trash_auto_delete_days": 30,
  "trash_purge_schedule": "0 5 0 * * *",
  "use_syslog": false,
  "user_attachment_limit": null,
  "web_vault_enabled": true,
  "web_vault_folder": "web-vault/",
  "websocket_address": "0.0.0.0",
  "websocket_enabled": true,
  "websocket_port": 3012,
  "yubico_client_id": null,
  "yubico_secret_key": null,
  "yubico_server": null
}

Thanks in advance for any suggestions

@rsoftnl
Copy link
Author

rsoftnl commented Jan 29, 2023

The database record in the Emergency Access table is:
Database dump of the record in question
INSERT INTO emergency_access VALUES('','<grantor_uuid>','<grantee_uuid>',NULL,NULL,1,4,7,'2023-01-22 12:20:38.749272006','2023-01-29 13:03:24.861587170','2023-01-29 13:07:24.872023194','2022-07-20 18:00:44.595490964');

@rsoftnl
Copy link
Author

rsoftnl commented Jan 29, 2023

[2023-01-29 16:30:13.214][request][INFO] POST /identity/accounts/prelogin
[2023-01-29 16:30:13.217][response][INFO] (prelogin) POST /identity/accounts/prelogin => 200 OK
[2023-01-29 16:30:13.299][request][INFO] POST /identity/connect/token
[2023-01-29 16:30:13.484][vaultwarden::api::identity][INFO] User logged in successfully. IP:
[2023-01-29 16:30:13.484][response][INFO] (login) POST /identity/connect/token => 200 OK
[2023-01-29 16:30:13.604][request][INFO] POST /identity/connect/token
[2023-01-29 16:30:13.613][response][INFO] (login) POST /identity/connect/token => 200 OK
[2023-01-29 16:30:13.645][request][INFO] GET /api/sync?excludeDomains=true
[2023-01-29 16:30:13.694][vaultwarden::api::notifications][INFO] Accepting WS connection from :41792
[2023-01-29 16:30:13.696][tungstenite::handshake::server][DEBUG] Server handshake done.
[2023-01-29 16:30:13.743][response][INFO] (sync) GET /api/sync?<data..> => 200 OK
[2023-01-29 16:30:18.028][request][INFO] GET /api/accounts/profile
[2023-01-29 16:30:18.030][response][INFO] (profile) GET /api/accounts/profile => 200 OK
[2023-01-29 16:30:18.036][request][INFO] GET /api/two-factor
[2023-01-29 16:30:18.038][response][INFO] (get_twofactor) GET /api/two-factor => 200 OK
[2023-01-29 16:30:19.726][request][INFO] GET /api/emergency-access/trusted
[2023-01-29 16:30:19.730][response][INFO] (get_contacts) GET /api/emergency-access/trusted => 200 OK
[2023-01-29 16:30:19.754][request][INFO] GET /api/emergency-access/granted
[2023-01-29 16:30:19.759][response][INFO] (get_grantees) GET /api/emergency-access/granted => 200 OK
[2023-01-29 16:30:22.396][request][INFO] GET /api/emergency-access/f4861a66-08c5-4d59-8725-a54339e91a1d/policies
[2023-01-29 16:30:22.400][response][INFO] (policies_emergency_access) GET /api/emergency-access/<emer_id>/policies => 200 OK
[2023-01-29 16:30:34.513][request][INFO] POST /api/emergency-access/f4861a66-08c5-4d59-8725-a54339e91a1d/takeover
[2023-01-29 16:30:34.516][response][INFO] (takeover_emergency_access) POST /api/emergency-access/<emer_id>/takeover => 200 OK
[2023-01-29 16:30:59.998][vaultwarden::api::core::two_factor][DEBUG] Sending notifications for incomplete 2FA logins
[2023-01-29 16:31:00.202][request][INFO] GET /alive
[2023-01-29 16:31:00.203][response][INFO] (alive) GET /alive => 200 OK
[2023-01-29 16:31:19.936][request][INFO] POST /identity/accounts/prelogin
[2023-01-29 16:31:19.937][response][INFO] (prelogin) POST /identity/accounts/prelogin => 200 OK
[2023-01-29 16:31:20.036][request][INFO] POST /identity/connect/token
[2023-01-29 16:31:20.217][vaultwarden::api::identity][ERROR] Username or password is incorrect. Try again. IP: . Username: <vault I'm trying to take over>.
[2023-01-29 16:31:20.217][response][INFO] (login) POST /identity/connect/token => 400 Bad Request

@rsoftnl
Copy link
Author

rsoftnl commented Jan 29, 2023

image

image

@BlackDex
Copy link
Collaborator

Seems to work fine for me.
It doesn't log you out from your own account. It just updates/changes the password and keys for the takeover account.

@rsoftnl
Copy link
Author

rsoftnl commented Jan 29, 2023

I know and I did try to login with the username of the grantor with the new password, but failed. The thing is: if I click on save as grantee, nothing seems to happen. Window doesn't close, no message saying that the new password is save/applied, ... (I do see a message if the 2nd password doesn't match the first. So that works...)

@BlackDex
Copy link
Collaborator

Again, it does work for me. Just tested it without any issues.

Maybe something else on your side is blocking the request? Try to set it via a different browser, or use a Private/incognito window.
Some browser extensions (AdGuard), or Firewall/Anti-Virus software tend to block some headers.

Also, on the reverse proxy side, i suggest to check the logs there. because i'm missing the POST that tells it to change the password.

It should look like this, but i only see the POST to the /takeover in your example.

[2023-01-29 18:15:44.798][request][INFO] POST /api/emergency-access/f3891612-1c27-49f8-8641-1ab4b7601941/takeover
[2023-01-29 18:15:44.799][response][INFO] (takeover_emergency_access) POST /api/emergency-access/<emer_id>/takeover => 200 OK
[2023-01-29 18:15:45.114][request][INFO] POST /api/emergency-access/f3891612-1c27-49f8-8641-1ab4b7601941/password
[2023-01-29 18:15:46.698][response][INFO] (password_emergency_access) POST /api/emergency-access/<emer_id>/password => 200 OK

@stefan0xC
Copy link
Contributor

stefan0xC commented Jan 29, 2023

I think I can reproduce this by adding (and confirming) someone as an emergency contact with only view access and then later changing their role to takeover. Afterwards I can attempt an takeover but even if I approve it, it will not work (i.e. do nothing as described above) because the field emergency_access.key_encrypted will be empty (or NULL as above).

On the other hand, if I add and confirm someone with takeover permissions from the beginning, this field will not be empty.

@BlackDex
Copy link
Collaborator

BlackDex commented Jan 30, 2023

@stefan0xC But, as far as i know, you can't change it from takeover to view without removing/rejecting the previous approved one. So, that is probably not the issue here.

Update: Ah, wait, you can indeed. That does cause issues.
Not sure if that is also the same with Bitwarden Self-Hosted.

@BlackDex
Copy link
Collaborator

We probably need to prevent updating the key if it is not set.
It looks like that it doesn't send the key on a PUT.

@BlackDex BlackDex added the bug Something isn't working label Jan 30, 2023
@rsoftnl
Copy link
Author

rsoftnl commented Jan 30, 2023

As far as I can remember, this was a straight TakeOver config, not first a View Only. Is there any digging I can do on my side to verify this situation? I'm also trying to rule out my nginx reverse proxy, but Vaultwarden (understandably) does not allow me to log in over HTTP. I need some more time to figure out the best way to access Vaultwarden directly in my network. I do get an additional POST logline if I click on Save, but that was a /takeover/ URL and not a /password/ URL if I recall correctly (not at home right now and therefor not able to debug at the moment).

Is there a way to verify the user has no items in it's personal vault? I have this disabled in the policy, but I'm unsure whether this was prior to this user being created. Currently this is the view in the Admin Panel for this specific user:
image
(being very curious at the "Never" for Last Active as I'm quite sure I had this active on the users smartphone and I'm 100% sure I have logged into the users account via web to help create the emergency contact)

@BlackDex
Copy link
Collaborator

That value is derived from the device table. If for some reason all sessions are deauthorized for that user, that table will have no records for that user, and thus will show up as never.

If you are sure that you did not switched anything, not even the amount of days for example, then i suggest to check (as mentioned before) your reverse proxy log and anything else infront of Vaultwarden which could have blocked calls. Because i'm missing the POST call to update the password as mentioned earlier.

@rsoftnl
Copy link
Author

rsoftnl commented Jan 30, 2023

OK, the deauthorized sessions will indeed be the cause of Never. I did try that to force a full login for the user. I will have a look at the proxy logs tonight.

@stefan0xC
Copy link
Contributor

We probably need to prevent updating the key if it is not set. It looks like that it doesn't send the key on a PUT.

Can confirm that this is the case.

If I replace

emergency_access.key_encrypted = data.KeyEncrypted;
with

    if data.KeyEncrypted.is_some() {
        emergency_access.key_encrypted = data.KeyEncrypted;
     }

the field will not be emptied when changing the user level from view to takeover (or the number of days).

@rsoftnl
Copy link
Author

rsoftnl commented Jan 30, 2023

I tried my best to get a self signed certificate setup using https://github.com/dani-garcia/vaultwarden/wiki/Private-CA-and-self-signed-certs-that-work-with-Chrome but could not get it to work. As it explicitely states no support will be provided, I will not ask any ;-)
I did however establish that the user has no personal passwords in their vault, just in collections (by checking in the ciphers table in the database, no records have a user_uuid). So I'll create a new account and attach it to the right collections.

The logging from my nginx is below:
[30/Jan/2023:21:33:11 +0000] - 200 200 - GET https "/api/emergency-access/f4861a66-08c5-4d59-8725-a54339e91a1d/policies" [Client 192.168.1.175] [Length 1047] [Gzip -] [Sent-to 192.168.5.42] "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61" "https:///"
[30/Jan/2023:21:33:29 +0000] - 200 200 - POST https "/api/emergency-access/f4861a66-08c5-4d59-8725-a54339e91a1d/takeover" [Client 192.168.1.175] [Length 87] [Gzip -] [Sent-to 192.168.5.42] "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61" "https:///"

This seems to correspond to the following lines in the VaultWarden log:
[2023-01-30 21:33:11.554][request][INFO] GET /api/emergency-access/f4861a66-08c5-4d59-8725-a54339e91a1d/policies
[2023-01-30 21:33:11.559][response][INFO] (policies_emergency_access) GET /api/emergency-access/<emer_id>/policies => 200 OK
[2023-01-30 21:33:29.833][request][INFO] POST /api/emergency-access/f4861a66-08c5-4d59-8725-a54339e91a1d/takeover
[2023-01-30 21:33:29.836][response][INFO] (takeover_emergency_access) POST /api/emergency-access/<emer_id>/takeover => 200 OK

I've tried this in both Chrome and Edge (although I'm not sure there's too much difference as both are Chromium based), in private modes and with UBlock Origin disabled for the VaultWarden site. I'm not sure where things are going wrong and why the /password POST is not even reaching my nginx, but for now I'm not sure I can do any additional debugging.

For me it's fine to close this issue, but I'm not sure you already want it closed as you may have identified a bug (although it may be unrelated to this issue). So I'll leave the honours to close it to you :-D Thanks for your help!

@stefan0xC
Copy link
Contributor

@rsoftnl given that the table did not have the encrypted_key field set, I don't think this was a problem with your setup.

If you did check the developer console of your browser while trying to save a new password for the grantor and nothing happens you would have seen that what actually happens is that the web-vault will throw an error Error: Uncaught (in promise): TypeError: e is null as it is getting the following JSON as a response to the POST:

{"Kdf":0,"KdfIterations":100000,"KeyEncrypted":null,"Object":"emergencyAccessTakeover"}

Since this is happening on the client side it's not something you can check (or even notice) in the server logs aside from not seeing the call you expect. And because the database entry has been corrupted somehow (maybe you just opened and saved the grantee again without changing anything?) there's not really anything you could do except removing the grantee and adding them again.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants