More consistently reset EVP_PKEYs in free_it

free_it forgets to reset pkey->ameth and also doesn't reset things if
there's no free function defined (but there's always a free function
defined).

It is almost the case that pkey->ameth gets reset or destroyed
immediately after free_it... except when EVP_PKEY_set_type fails. Fix
that up.

Change-Id: Ib3fe5848fa2ed9cd8723452519b678c4c5ce5ea8
Reviewed-on: https://boringssl-review.googlesource.com/c/boringssl/+/81307
Reviewed-by: Lily Chen <chlily@google.com>
Commit-Queue: Lily Chen <chlily@google.com>
Auto-Submit: David Benjamin <davidben@google.com>
diff --git a/crypto/evp/evp.cc b/crypto/evp/evp.cc
index 806c34c..a3b8e86 100644
--- a/crypto/evp/evp.cc
+++ b/crypto/evp/evp.cc
@@ -49,9 +49,10 @@
 static void free_it(EVP_PKEY *pkey) {
   if (pkey->ameth && pkey->ameth->pkey_free) {
     pkey->ameth->pkey_free(pkey);
-    pkey->pkey = NULL;
-    pkey->type = EVP_PKEY_NONE;
   }
+  pkey->pkey = nullptr;
+  pkey->type = EVP_PKEY_NONE;
+  pkey->ameth = nullptr;
 }
 
 void EVP_PKEY_free(EVP_PKEY *pkey) {
diff --git a/crypto/evp/evp_extra_test.cc b/crypto/evp/evp_extra_test.cc
index f39f493..be91bc8 100644
--- a/crypto/evp/evp_extra_test.cc
+++ b/crypto/evp/evp_extra_test.cc
@@ -1337,4 +1337,6 @@
   EXPECT_FALSE(EVP_PKEY_set_type(pkey.get(), EVP_PKEY_NONE));
   // However, it still resets the key to the initial state.
   EXPECT_EQ(EVP_PKEY_id(pkey.get()), EVP_PKEY_NONE);
+  // Calling operations on the |EVP_PKEY| should cleanly fail.
+  EXPECT_EQ(EVP_PKEY_bits(pkey.get()), 0);
 }