Repository: randombit/botan
Pull request #3185 (2023-01-17 10:24:50)

Backport fix overwriting an attribute in an AttributeContainer
Backport of #3138.


Patch:
diff --git a/src/lib/prov/pkcs11/p11_object.cpp b/src/lib/prov/pkcs11/p11_object.cpp
index 0b92d9bf8..edda423f6 100644
--- a/src/lib/prov/pkcs11/p11_object.cpp
+++ b/src/lib/prov/pkcs11/p11_object.cpp
@@ -59,21 +59,20 @@ void AttributeContainer::add_attribute(AttributeType attribute, const uint8_t* v
       if(existing_attribute.type == static_cast< CK_ATTRIBUTE_TYPE >(attribute))
          {
          // remove old entries
-         m_strings.erase(std::remove_if(m_strings.begin(), m_strings.end(), [ &existing_attribute ](const std::string& data)
+         m_strings.remove_if([ &existing_attribute ](const std::string& data)
             {
             return data.data() == existing_attribute.pValue;
-            }), m_strings.end());
+            });
 
-         m_numerics.erase(std::remove_if(m_numerics.begin(), m_numerics.end(), [ &existing_attribute ](const uint64_t& data)
+         m_numerics.remove_if([ &existing_attribute ](const uint64_t& data)
             {
             return &data == existing_attribute.pValue;
-            }), m_numerics.end());
+            });
 
-         m_vectors.erase(std::remove_if(m_vectors.begin(),
-                                        m_vectors.end(), [ &existing_attribute ](const secure_vector<uint8_t>& data)
+         m_vectors.remove_if([ &existing_attribute ](const secure_vector<uint8_t>& data)
             {
             return data.data() == existing_attribute.pValue;
-            }), m_vectors.end());
+            });
 
          existing_attribute.pValue = const_cast< uint8_t* >(value);
          existing_attribute.ulValueLen = size;


Test patch:
diff --git a/src/tests/test_pkcs11_high_level.cpp b/src/tests/test_pkcs11_high_level.cpp
index 84c2c62c3..7acb7e4b7 100644
--- a/src/tests/test_pkcs11_high_level.cpp
+++ b/src/tests/test_pkcs11_high_level.cpp
@@ -489,9 +489,24 @@ Test::Result test_attribute_container()
    attributes.add_binary(AttributeType::Value, bin);
 
    attributes.add_bool(AttributeType::Sensitive, true);
-   attributes.add_numeric(AttributeType::ObjectId, 12);
-
-   result.test_eq("Five elements in attribute container", attributes.count(), 5);
+   attributes.add_numeric(AttributeType::ObjectId, 10);
+   attributes.add_numeric(AttributeType::Id, 20);
+   attributes.add_numeric(AttributeType::PixelX, 30);
+   // Test that overwriting the existing Id attribute works. The numeric attributes above should not be affected by this.
+   attributes.add_numeric(AttributeType::Id, 21);
+   attributes.add_numeric(AttributeType::PixelY, 40);
+
+   result.test_eq("8 elements in attribute container", attributes.count(), 8);
+
+   const std::vector<Botan::PKCS11::Attribute>& storedAttributes = attributes.attributes();
+   result.test_int_eq("ObjectId type", storedAttributes.at(4).type, AttributeType::ObjectId);
+   result.test_int_eq("ObjectId value", *reinterpret_cast< uint64_t* >(storedAttributes.at(4).pValue), 10);
+   result.test_int_eq("Id type", storedAttributes.at(5).type, AttributeType::Id);
+   result.test_int_eq("Id value", *reinterpret_cast< uint64_t* >(storedAttributes.at(5).pValue), 21);
+   result.test_int_eq("PixelX type", storedAttributes.at(6).type, AttributeType::PixelX);
+   result.test_int_eq("PixelX value", *reinterpret_cast< uint64_t* >(storedAttributes.at(6).pValue), 30);
+   result.test_int_eq("PixelY type", storedAttributes.at(7).type, AttributeType::PixelY);
+   result.test_int_eq("PixelY value", *reinterpret_cast< uint64_t* >(storedAttributes.at(7).pValue), 40);
 
    return result;
    }