)]}'
{"id":"openvpn~1289","triplet_id":"openvpn~master~I31ac2a763209114267c35c4a9182a12d8d82f6fe","project":"openvpn","branch":"master","topic":"ossl40","attention_set":{},"removed_from_attention_set":{"1000003":{"account":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"last_update":"2026-03-31 22:50:08.000000000","reason":"removed on reply"},"1000001":{"account":{"_account_id":1000001,"name":"flichtenheld","display_name":"Frank Lichtenheld","email":"frank@lichtenheld.com","username":"flichtenheld","status":"OpenVPN Inc."},"last_update":"2026-04-17 10:21:25.000000000","reason":"Change was submitted"},"1000047":{"account":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"last_update":"2026-04-17 10:21:25.000000000","reason":"Change was submitted"},"1000030":{"account":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"last_update":"2026-04-15 20:31:46.000000000","reason":"\u003cGERRIT_ACCOUNT_1000030\u003e replied on the change","reason_account":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"}}},"hashtags":[],"change_id":"I31ac2a763209114267c35c4a9182a12d8d82f6fe","subject":"ssl_openssl: Fix some CRL mixups","status":"MERGED","created":"2025-10-20 21:25:53.000000000","updated":"2026-04-17 10:21:25.000000000","submitted":"2026-04-17 10:21:25.000000000","submitter":{"_account_id":1000002,"name":"cron2","display_name":"Gert Doering","email":"gert@greenie.muc.de","username":"cron2"},"total_comment_count":11,"unresolved_comment_count":0,"has_review_started":true,"submission_id":"1289-ossl40","meta_rev_id":"250b31b135eb0f7167171361fbbb6f8f2969a6cc","_number":1289,"virtual_id_number":1289,"owner":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"actions":{},"labels":{"Code-Review":{"all":[{"value":0,"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},{"value":0,"_account_id":1000002,"name":"cron2","display_name":"Gert Doering","email":"gert@greenie.muc.de","username":"cron2"},{"value":0,"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"}],"values":{"-2":"This shall not be submitted","-1":"I would prefer this is not submitted as is"," 0":"No score","+1":"Looks good to me, but someone else must approve","+2":"Looks good to me, approved"},"description":"","default_value":0}},"removable_reviewers":[{"_account_id":1000001,"name":"flichtenheld","display_name":"Frank Lichtenheld","email":"frank@lichtenheld.com","username":"flichtenheld","status":"OpenVPN Inc."}],"reviewers":{"CC":[{"_account_id":1000026,"name":"openvpn-devel","email":"openvpn-devel@lists.sourceforge.net","username":"openvpn-devel"}],"REVIEWER":[{"_account_id":1000001,"name":"flichtenheld","display_name":"Frank Lichtenheld","email":"frank@lichtenheld.com","username":"flichtenheld","status":"OpenVPN Inc."},{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"}]},"pending_reviewers":{},"reviewer_updates":[{"updated":"2025-10-20 21:25:54.000000000","updated_by":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"reviewer":{"_account_id":1000026,"name":"openvpn-devel","email":"openvpn-devel@lists.sourceforge.net","username":"openvpn-devel"},"state":"CC"},{"updated":"2025-10-20 21:25:54.000000000","updated_by":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"reviewer":{"_account_id":1000001,"name":"flichtenheld","display_name":"Frank Lichtenheld","email":"frank@lichtenheld.com","username":"flichtenheld","status":"OpenVPN Inc."},"state":"REVIEWER"},{"updated":"2025-10-20 21:25:54.000000000","updated_by":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"reviewer":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"state":"REVIEWER"},{"updated":"2026-04-15 16:39:29.000000000","updated_by":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"reviewer":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"state":"CC"},{"updated":"2026-04-15 20:31:46.000000000","updated_by":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"reviewer":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"state":"REVIEWER"}],"messages":[{"id":"27bec0cf17b8cbb2e202b5678bdd5d24d08fbfae","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"date":"2025-10-20 21:25:53.000000000","message":"Uploaded patch set 1.","accounts_in_message":[],"_revision_number":1},{"id":"edd6b0610d417a8c64ab9f2f107ca02fea05fb2f","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-09 14:04:32.000000000","message":"Uploaded patch set 2: Patch Set 1 was rebased.","accounts_in_message":[],"_revision_number":2},{"id":"a1e2d867bd2321656daec4006647cdd03419688b","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-09 14:05:42.000000000","message":"Patch Set 2:\n\n(1 comment)","accounts_in_message":[],"_revision_number":2},{"id":"6b86e37f493d61863eb503cfcaea3e7a8f849d2c","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-09 14:47:47.000000000","message":"Patch Set 2: Code-Review-2\n\n(1 comment)","accounts_in_message":[],"_revision_number":2},{"id":"922313d1038bf5c7297b23f24a74b10b9c22fc8d","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-10 13:53:32.000000000","message":"Patch Set 2:\n\n(1 comment)","accounts_in_message":[],"_revision_number":2},{"id":"fc8e6231e3843d6f6e00eb670b811bf798913a8a","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-10 13:56:15.000000000","message":"Patch Set 2:\n\n(1 comment)","accounts_in_message":[],"_revision_number":2},{"id":"64dbcb000ef1eba4f68418bf9e47cdcdcdb72241","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-10 15:42:04.000000000","message":"Uploaded patch set 3.\n\nCopied Votes:\n* Code-Review-2 (copy condition: \"changekind:NO_CHANGE OR changekind:TRIVIAL_REBASE OR **is:MIN**\")\n","accounts_in_message":[],"_revision_number":3},{"id":"2d535cbd7bbefcc07e2796603947f30a22da9bc4","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-10 15:42:56.000000000","message":"Patch Set 3: -Code-Review\n\n(1 comment)","accounts_in_message":[],"_revision_number":3},{"id":"9a202aeb9b3863c58aebf59caaf61d769d5f4553","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-10 15:48:59.000000000","message":"Uploaded patch set 4: Patch Set 3 was rebased.","accounts_in_message":[],"_revision_number":4},{"id":"d8da5e48b5cef3177b75b89881d17aee26d83465","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-10 16:12:01.000000000","message":"Uploaded patch set 5: Patch Set 4 was rebased.","accounts_in_message":[],"_revision_number":5},{"id":"ac30e1a728005399c33319c00f42415302f2834e","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-11 11:36:39.000000000","message":"Uploaded patch set 6: Patch Set 5 was rebased.","accounts_in_message":[],"_revision_number":6},{"id":"be7c9ea69ef81b497d733be2a383e336417f663d","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-15 16:03:59.000000000","message":"Uploaded patch set 7: Patch Set 6 was rebased.","accounts_in_message":[],"_revision_number":7},{"id":"3e87f55253d4e234d83f7df87fc7f322f9ad859d","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2025-12-15 16:13:54.000000000","message":"Uploaded patch set 8: Patch Set 7 was rebased.","accounts_in_message":[],"_revision_number":8},{"id":"59bc7c1e57c597715977bc0f91d559c013c37fda","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-03-31 16:24:02.000000000","message":"Uploaded patch set 9: Patch Set 8 was rebased.","accounts_in_message":[],"_revision_number":9},{"id":"47a02598d38d9b7907ff83f4cb3380ecc9991f1e","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-03-31 16:30:05.000000000","message":"Patch Set 9: Code-Review+2","accounts_in_message":[],"_revision_number":9},{"id":"fc66d2b8e353c399b7201d6dda6f87e99ff9062c","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-03-31 16:30:38.000000000","message":"Patch Set 9:\n\n(1 comment)","accounts_in_message":[],"_revision_number":9},{"id":"ceb89b585c66a50279fc022fbe83a04c113c2622","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-03-31 22:49:56.000000000","message":"Uploaded patch set 10.\n\nOutdated Votes:\n* Code-Review+2 (copy condition: \"changekind:NO_CHANGE OR changekind:TRIVIAL_REBASE OR is:MIN\")\n","accounts_in_message":[],"_revision_number":10},{"id":"d43f842b3fec0be475bb86f14fc949c963671828","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-03-31 22:50:08.000000000","message":"Patch Set 10: Code-Review+2","accounts_in_message":[],"_revision_number":10},{"id":"5119223f08f9c12f4ef7f71ab53fa3544c6b83e7","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-04-01 11:56:52.000000000","message":"Uploaded patch set 11: Patch Set 10 was rebased.\n\nCopied Votes:\n* Code-Review+2 (copy condition: \"changekind:NO_CHANGE OR **changekind:TRIVIAL_REBASE** OR is:MIN\")\n","accounts_in_message":[],"_revision_number":11},{"id":"7640e3688ac60baffdd1179f0afde0599c8e55e2","tag":"autogenerated:gerrit:newPatchSet","author":{"_account_id":1000001,"name":"flichtenheld","display_name":"Frank Lichtenheld","email":"frank@lichtenheld.com","username":"flichtenheld","status":"OpenVPN Inc."},"date":"2026-04-04 18:35:49.000000000","message":"Uploaded patch set 12: Patch Set 11 was rebased.\n\nCopied Votes:\n* Code-Review+2 (copy condition: \"changekind:NO_CHANGE OR **changekind:TRIVIAL_REBASE** OR is:MIN\")\n","accounts_in_message":[],"_revision_number":12},{"id":"3403b3ac0c3f7122adce2cc066b87ae69fa81609","author":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"date":"2026-04-15 16:39:29.000000000","message":"Patch Set 12:\n\n(2 comments)","accounts_in_message":[],"_revision_number":12},{"id":"11768229532ab3281f39684165b0a9c2a19b02b0","author":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"date":"2026-04-15 17:27:38.000000000","message":"Patch Set 12:\n\n(1 comment)","accounts_in_message":[],"_revision_number":12},{"id":"22df74b257cac363ef7e83d9406be4c474422b94","author":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"date":"2026-04-15 18:16:05.000000000","message":"Patch Set 12: Code-Review+2\n\n(1 comment)","accounts_in_message":[],"_revision_number":12},{"id":"3be1071bf9597faa47fa910010850f46013a4f0a","author":{"_account_id":1000030,"name":"MaxF","email":"max@max-fillinger.net","username":"MaxF"},"date":"2026-04-15 20:31:46.000000000","message":"Patch Set 12: Code-Review+2\n\n(1 comment)","accounts_in_message":[],"_revision_number":12},{"id":"250b31b135eb0f7167171361fbbb6f8f2969a6cc","tag":"autogenerated:gerrit:merged","author":{"_account_id":1000002,"name":"cron2","display_name":"Gert Doering","email":"gert@greenie.muc.de","username":"cron2"},"date":"2026-04-17 10:21:25.000000000","message":"Change has been successfully pushed.","accounts_in_message":[],"_revision_number":13}],"current_revision_number":13,"current_revision":"2befad4de1b4da3c06c5fb3537a767ac1d058eb3","revisions":{"152a6f96203e1ef1223f34ac5f20aaaf1cab2a80":{"kind":"REWORK","_number":1,"created":"2025-10-20 21:25:53.000000000","uploader":{"_account_id":1000047,"name":"davidben","email":"davidben@google.com","username":"davidben"},"ref":"refs/changes/89/1289/1","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/1","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/1 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/1 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/1 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/1 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/1","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/1 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"3e76d8f8a475d08bcb50321e742a06c53e19d45d","subject":"dco: remove dco_read/write_bytes from dco_context_t"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-10-20 21:25:38.000000000","tz":-240},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\n"},"branch":"refs/heads/master"},"0ac6b4766490c6ab33ee81b13983308bc9da4be6":{"kind":"TRIVIAL_REBASE","_number":2,"created":"2025-12-09 14:04:32.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/2","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/2","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/2 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/2 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/2 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/2 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/2","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/2 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"f90a0d87a53759dad9c20e9731f3af5f237ece28","subject":"multipeer: introduce asymmetric peer-id"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-09 14:03:53.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\n"},"branch":"refs/heads/master"},"f749dedbbd62f68ea578442f6dd577c339b75d42":{"kind":"REWORK","_number":3,"created":"2025-12-10 15:42:04.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/3","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/3","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/3 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/3 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/3 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/3 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/3","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/3 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"65af575a17fded02eb9bf72b4e4e48e63903dbe2","subject":"Change ssl_ctx in struct tls_options to be a pointer"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-10 15:41:58.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"22d8a8a6b0a28d396913e8cf3e6617d99c11bde3":{"kind":"TRIVIAL_REBASE","_number":4,"created":"2025-12-10 15:48:59.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/4","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/4","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/4 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/4 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/4 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/4 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/4","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/4 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"f8df55e52c21358b37b81b99d99572fce7ebecf2","subject":"Change ssl_ctx in struct tls_options to be a pointer"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-10 15:46:34.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"001d041dd55819fc9f2aea0265d6bc3d1865fce8":{"kind":"TRIVIAL_REBASE","_number":5,"created":"2025-12-10 16:12:01.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/5","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/5","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/5 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/5 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/5 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/5 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/5","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/5 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"2a0fd3bd79c94631fc5e155ac629f72fc88b6140","subject":"Change ssl_ctx in struct tls_options to be a pointer"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-10 16:11:55.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"0d2c140e3104e2c6926fc7441819971c31add5e6":{"kind":"TRIVIAL_REBASE","_number":6,"created":"2025-12-11 11:36:39.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/6","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/6","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/6 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/6 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/6 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/6 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/6","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/6 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"6331c44bef30adef338e10001d9502f5c7a51a30","subject":"Change ssl_ctx in struct tls_options to be a pointer"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-11 11:36:33.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"df4eef593c0562cdfd04d9ded60b444b66c8641c":{"kind":"TRIVIAL_REBASE","_number":7,"created":"2025-12-15 16:03:59.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/7","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/7","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/7 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/7 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/7 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/7 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/7","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/7 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"d5a425f2723d47c8868ab71a7ccae23aebdd66ea","subject":"Change ssl_ctx in struct tls_options to be a pointer"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-15 16:03:52.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"ffeff473a8de34058d0b8da8151cad75284cd936":{"kind":"TRIVIAL_REBASE","_number":8,"created":"2025-12-15 16:13:54.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/8","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/8","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/8 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/8 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/8 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/8 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/8","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/8 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"b147da313883af0a4d803583c12e993b807b0cd7","subject":"Change ssl_ctx in struct tls_options to be a pointer"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2025-12-15 16:13:48.000000000","tz":60},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"9438baa6be79a4661b118b028639d5e951575649":{"kind":"TRIVIAL_REBASE","_number":9,"created":"2026-03-31 16:24:02.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/9","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/9","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/9 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/9 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/9 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/9 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/9","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/9 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"5a8e4bc53107583526a281e6c195f626221c67fc","subject":"Use ASN1_BIT_STRING_get_bit to check for netscape certificate usage"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2026-03-31 15:23:30.000000000","tz":120},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"f890b726f40bbec2f84a4c5f4bbb464fa0092011":{"kind":"REWORK","_number":10,"created":"2026-03-31 22:49:56.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/10","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/10","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/10 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/10 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/10 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/10 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/10","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/10 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"574cd86d570b0e9b7fce99cbe1a63111b1059147","subject":"Use ASN1_BIT_STRING_get_bit to check for netscape certificate usage"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2026-03-31 22:02:45.000000000","tz":120},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nAdd .clang-format section for STACK_OF since we otherwise format the\nline as STACK_OF(X509_CRL) * crls\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"e5ae7ceaf7cd7bc58dcf9ea733197b43f910cb15":{"kind":"TRIVIAL_REBASE","_number":11,"created":"2026-04-01 11:56:52.000000000","uploader":{"_account_id":1000003,"name":"plaisthos","display_name":"Arne Schwabe","email":"arne-openvpn@rfc2549.org","username":"plaisthos"},"ref":"refs/changes/89/1289/11","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/11","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/11 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/11 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/11 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/11 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/11","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/11 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"eb5c944ddaab5c9b3240c7853b93863b2180dd55","subject":"OpenSSL 4.0: Use X509_check_certificate_times instead of X509_cmp_time"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Arne Schwabe","email":"arne@rfc2549.org","date":"2026-04-01 11:33:55.000000000","tz":120},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nAdd .clang-format section for STACK_OF since we otherwise format the\nline as STACK_OF(X509_CRL) * crls\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"615d0dee8480f28a07c2b6846e0c4dc2fd96956a":{"kind":"TRIVIAL_REBASE","_number":12,"created":"2026-04-04 18:35:49.000000000","uploader":{"_account_id":1000001,"name":"flichtenheld","display_name":"Frank Lichtenheld","email":"frank@lichtenheld.com","username":"flichtenheld","status":"OpenVPN Inc."},"ref":"refs/changes/89/1289/12","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/12","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/12 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/12 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/12 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/12 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/12","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/12 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"8452125a387d17e6a7312592476011a75035a76c","subject":"OpenSSL 4.0: Use X509_check_certificate_times instead of X509_cmp_time"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2025-09-18 14:00:41.000000000","tz":-240},"committer":{"name":"Frank Lichtenheld","email":"frank@lichtenheld.com","date":"2026-04-04 18:35:02.000000000","tz":120},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nAdd .clang-format section for STACK_OF since we otherwise format the\nline as STACK_OF(X509_CRL) * crls\n\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\n"},"branch":"refs/heads/master"},"2befad4de1b4da3c06c5fb3537a767ac1d058eb3":{"kind":"TRIVIAL_REBASE_WITH_MESSAGE_UPDATE","_number":13,"created":"2026-04-17 10:21:25.000000000","uploader":{"_account_id":1000002,"name":"cron2","display_name":"Gert Doering","email":"gert@greenie.muc.de","username":"cron2"},"ref":"refs/changes/89/1289/13","fetch":{"anonymous http":{"url":"http://gerrit.openvpn.net/openvpn","ref":"refs/changes/89/1289/13","commands":{"Branch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/13 \u0026\u0026 git checkout -b change-1289 FETCH_HEAD","Checkout":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/13 \u0026\u0026 git checkout FETCH_HEAD","Cherry Pick":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/13 \u0026\u0026 git cherry-pick FETCH_HEAD","Format Patch":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/13 \u0026\u0026 git format-patch -1 --stdout FETCH_HEAD","Pull":"git pull http://gerrit.openvpn.net/openvpn refs/changes/89/1289/13","Reset To":"git fetch http://gerrit.openvpn.net/openvpn refs/changes/89/1289/13 \u0026\u0026 git reset --hard FETCH_HEAD"}}},"commit":{"parents":[{"commit":"25c5c42ac265c4731c0e44c0afd773dc89bf22da","subject":"Add unit tests for \u0027auth-user-pass username-only\u0027"}],"author":{"name":"David Benjamin","email":"davidben@google.com","date":"2026-04-16 17:41:35.000000000","tz":120},"committer":{"name":"Gert Doering","email":"gert@greenie.muc.de","date":"2026-04-17 09:30:24.000000000","tz":120},"subject":"ssl_openssl: Fix some CRL mixups","message":"ssl_openssl: Fix some CRL mixups\n\nThere are two ways to load CRLs in OpenSSL. They can be loaded at the\nX509_STORE, shared across verifications, or loaded per verification at\nthe X509_STORE_CTX.\n\nOpenVPN currently does the former. However, it also supports CRL\nreloading, and tries to reload the CRL file before each connection.\nOpenSSL does not really have a good way to unload objects from an\nX509_STORE. OpenVPN currently does it by grabbing the\nSTACK_OF(X509_OBJECT) out of the X509_STORE and manually deleting all\nthe CRLs from it.\n\nThis mutates an OpenSSL internal object which bumps into problems if\nOpenSSL ever switches to a more efficient representation. See\nhttps://github.com/openssl/openssl/pull/28599\n\n(It\u0027s also not thread-safe, though it doesn\u0027t look like that impacts\nOpenVPN? Actually even reading that list doesn\u0027t work. See\nCVE-2024-0397. This OpenSSL API was simply broken.)\n\nAdditionally, this seems to cause two OpenVPN features to not work\ntogether. I gather backend_tls_ctx_reload_crl is trying to clear the\nCRLs loaded from last time it ran. But tls_ctx_load_ca with a ca_file\ncan also load CRLs. tls_ctx_load_ca with ca_path will also pick up CRLs\nand backend_tls_ctx_reload_crl actually ends up clobbering some state\nX509_LOOKUP_hash_dir internally maintains on the X509_STORE. Likewise,\ntls_verify_crl_missing can get confused between\nbackend_tls_ctx_reload_crl\u0027s crl_file-based CRLs and CRLs from\ntls_ctx_load_ca.\n\nAvoid all this by tracking the two CRLs separately. crl_file-based CRLs\nnow go onto a STACK_OF(X509_CRL) tracked on the tls_root_ctx. Now this\nfield can be freely reloaded by OpenVPN without reconfiguring OpenSSL.\nInstead, pass the current value into OpenSSL at verification time.  To\ndo so, we need to use the SSL_CTX_set_cert_verify_callback, which allows\nswapping out the X509_verify_cert call, and also tweaking the\nX509_STORE_CTX configuration before starting certificate verification.\n\nContext: SSL_CTX_set_cert_verify_callback and the existing\nverify_callback are not the same. SSL_CTX_set_cert_verify_callback wraps\nthe verification while verify_callback is called multiple times\nthroughout verification. It\u0027s too late to reconfigure X509_STORE_CTX in\nverify_callback. verify_callback is usually not what you want.\nSometimes current_cert and error_depth don\u0027t quite line up, and\ncert_hash_remember may end up called multiple times for a single\ncertificate.\n\nI suspect some of the other verify_callback logic would also be better\ndone in the new callback, but I\u0027ve left it alone to keep this change\nminimal. verify_callback is really only usable for suppressing errors.\nApplication bookkeeping is better down elsewhere.\n\nAdd .clang-format section for STACK_OF since we otherwise format the\nline as STACK_OF(X509_CRL) * crls\n\nGithub: see also openssl/openssl#28599\nSigned-off-by: David Benjamin \u003cdavidben@google.com\u003e\nChange-Id: I31ac2a763209114267c35c4a9182a12d8d82f6fe\nSigned-off-by: Arne Schwabe \u003carne@rfc2549.org\u003e\nAcked-by: Arne Schwabe \u003carne-openvpn@rfc2549.org\u003e\nAcked-by: MaxF \u003cmax@max-fillinger.net\u003e\nGerrit URL: https://gerrit.openvpn.net/c/openvpn/+/1289\nMessage-Id: \u003c20260416174142.28918-1-gert@greenie.muc.de\u003e\nURL: https://www.mail-archive.com/openvpn-devel@lists.sourceforge.net/msg36641.html\nSigned-off-by: Gert Doering \u003cgert@greenie.muc.de\u003e\n"},"branch":"refs/heads/master"}},"requirements":[],"submit_records":[],"submit_requirements":[]}
