--- /dev/null
+// Copyright (C) 2024 Internet Systems Consortium, Inc. ("ISC")
+//
+// This Source Code Form is subject to the terms of the Mozilla Public
+// License, v. 2.0. If a copy of the MPL was not distributed with this
+// file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+#include <config.h>
+
+#include <exceptions/exceptions.h>
+#include <alarm_store.h>
+#include <util/multi_threading_mgr.h>
+
+using namespace isc;
+using namespace isc::util;
+
+namespace isc {
+namespace perfmon {
+
+AlarmStore::AlarmStore(uint16_t family)
+ : family_(family),
+ alarms_(),
+ mutex_(new std::mutex) {
+ if (family_ != AF_INET && family_ != AF_INET6) {
+ isc_throw(BadValue, "AlarmStore - invalid family "
+ << family_ << ", must be AF_INET or AF_INET6");
+ }
+}
+
+void
+AlarmStore::validateKey(const std::string& label, DurationKeyPtr key) const {
+ if (!key) {
+ isc_throw(BadValue, "AlarmStore::" << label << " - key is empty");
+ }
+
+ if (key->getFamily() != family_) {
+ isc_throw(BadValue, "AlarmStore::" << label
+ << " - family mismatch, key is " << (family_ == AF_INET ?
+ "v6, store is v4" : "v4, store is v6"));
+ }
+}
+
+AlarmPtr
+AlarmStore::addAlarm(AlarmPtr alarm) {
+ {
+ MultiThreadingLock lock(*mutex_);
+ auto ret = alarms_.insert(alarm);
+ if (ret.second == false) {
+ isc_throw(DuplicateAlarm,
+ "AlarmStore::addAlarm: alarm already exists for: "
+ << alarm->getLabel());
+ }
+ }
+
+ // Return a copy of what we inserted.
+ return (AlarmPtr(new Alarm(*alarm)));
+}
+
+AlarmPtr
+AlarmStore::addAlarm(DurationKeyPtr key, const Duration& low_water,
+ const Duration& high_water, bool enabled /* = true */) {
+ validateKey("addAlarm", key);
+
+ // Create the alarm instance.
+ AlarmPtr alarm;
+ try {
+ alarm.reset(new Alarm(*key, low_water, high_water, enabled));
+ } catch (const std::exception& ex) {
+ isc_throw(BadValue, "AlarmStore::addAlarm failed: " << ex.what());
+ }
+
+ return(addAlarm(alarm));
+}
+
+AlarmPtr
+AlarmStore::getAlarm(DurationKeyPtr key) {
+ validateKey("getAlarm", key);
+
+ MultiThreadingLock lock(*mutex_);
+ const auto& index = alarms_.get<AlarmPrimaryKeyTag>();
+ auto alarm_iter = index.find(*key);
+ return (alarm_iter == index.end() ? AlarmPtr()
+ : AlarmPtr(new Alarm(**alarm_iter)));
+}
+
+void
+AlarmStore::updateAlarm(AlarmPtr& alarm) {
+ validateKey("updateAlarm", alarm);
+
+ MultiThreadingLock lock(*mutex_);
+ auto& index = alarms_.get<AlarmPrimaryKeyTag>();
+ auto alarm_iter = index.find(*alarm);
+ if (alarm_iter == index.end()) {
+ isc_throw(InvalidOperation, "AlarmStore::updateAlarm alarm not found: "
+ << alarm->getLabel());
+ }
+
+ // Use replace() which only re-indexes if keys change.
+ index.replace(alarm_iter, AlarmPtr(new Alarm(*alarm)));
+}
+
+void
+AlarmStore::deleteAlarm(DurationKeyPtr key) {
+ validateKey("deleteAlarm", key);
+
+ MultiThreadingLock lock(*mutex_);
+ auto& index = alarms_.get<AlarmPrimaryKeyTag>();
+ auto alarm_iter = index.find(*key);
+ if (alarm_iter == index.end()) {
+ // Not there, just return.
+ return;
+ }
+
+ // Remove the alarm from the store.
+ alarms_.erase(alarm_iter);
+}
+
+AlarmCollectionPtr
+AlarmStore::getAll() {
+ MultiThreadingLock lock(*mutex_);
+ const auto& index = alarms_.get<AlarmPrimaryKeyTag>();
+ AlarmCollectionPtr collection(new AlarmCollection());
+ for (auto alarm_iter = index.begin(); alarm_iter != index.end(); ++alarm_iter) {
+ collection->push_back(AlarmPtr(new Alarm(**alarm_iter)));
+ }
+
+ return (collection);
+}
+
+void
+AlarmStore::clear() {
+ MultiThreadingLock lock(*mutex_);
+ alarms_.clear();
+}
+
+} // end of namespace perfmon
+} // end of namespace isc
+
--- /dev/null
+// Copyright (C) 2024 Internet Systems Consortium, Inc. ("ISC")
+//
+// This Source Code Form is subject to the terms of the Mozilla Public
+// License, v. 2.0. If a copy of the MPL was not distributed with this
+// file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+#ifndef ALARM_STORE_H
+#define ALARM_STORE_H
+
+#include <exceptions/exceptions.h>
+#include <alarm.h>
+
+#include <boost/multi_index/indexed_by.hpp>
+#include <boost/multi_index/member.hpp>
+#include <boost/multi_index/mem_fun.hpp>
+#include <boost/multi_index/ordered_index.hpp>
+#include <boost/multi_index_container.hpp>
+#include <boost/multi_index/composite_key.hpp>
+#include <boost/multi_index/sequenced_index.hpp>
+#include <boost/multi_index/identity.hpp>
+#include <boost/scoped_ptr.hpp>
+
+#include <string>
+
+namespace isc {
+namespace perfmon {
+
+/// @brief Exception thrown when an attempt was made to add a duplicate key
+/// to either the duration or alarm stores.
+class DuplicateAlarm : public Exception {
+public:
+ DuplicateAlarm(const char* file, size_t line, const char* what) :
+ isc::Exception(file, line, what) {}
+};
+
+/// @brief Tag for index by primary key (DurationKey).
+struct AlarmPrimaryKeyTag { };
+
+/// @brief A multi index container holding pointers to Alarms.
+///
+/// The durations in the container may be accessed using different indexes:
+/// - using the full key index
+/// <TBD>
+///
+/// Indexes can be accessed using the index number (from 0 to n) or a
+/// name tag. It is recommended to use the tags to access indexes as
+/// they do not depend on the order of indexes in the container.
+typedef boost::multi_index_container<
+ // It holds pointers to Lease6 objects.
+ AlarmPtr,
+ boost::multi_index::indexed_by<
+ // Specification of the first index starts here.
+ // This index sorts using DurationKey::operators
+ boost::multi_index::ordered_unique<
+ boost::multi_index::tag<AlarmPrimaryKeyTag>,
+ boost::multi_index::identity<DurationKey>
+ >
+ >
+> AlarmContainer;
+
+/// @brief Type for a collection of AlarmPtrs.
+typedef std::vector<AlarmPtr> AlarmCollection;
+
+/// @brief Type for a pointer to a collection of AlarmPtrs.
+typedef boost::shared_ptr<AlarmCollection> AlarmCollectionPtr;
+
+/// @brief Maintains an in-memory store of Alarms
+///
+/// Provides essential CRUD functions for managing a collection of
+/// Alarms. Additionally there are finders that can return
+/// durations by DurationKey <TBD>
+/// All finders return copies of the durations found, rather than the
+/// stored duration itself.
+class AlarmStore {
+public:
+ /// @brief Constructor
+ ///
+ /// @param family protocol family AF_INET or AF_INET6
+ explicit AlarmStore(uint16_t family);
+
+ /// @brief Destructor
+ ~AlarmStore() = default;
+
+ /// @brief Creates a new Alarm and adds it to the store
+ ///
+ /// @param key key value of the Alarm to create.
+ /// @param low_water threshold below which the average duration must fall to clear the alarm
+ /// @brief high_water threshold above which the average duration must rise to trigger the alarm.
+ /// @brief enabled true sets state to CLEAR, otherwise DISABLED, defaults to true.
+ ///
+ /// @return pointer to the newly created Alarm.
+ /// @throw DuplicateAlarm if a duration for the given key already exists in
+ /// the store.
+ AlarmPtr addAlarm(DurationKeyPtr key, const Duration& low_water,
+ const Duration& high_water, bool enabled = true);
+
+ /// @brief Adds an Alarm to the store.
+ ///
+ /// @return pointer to a copy of the Alarm added.
+ AlarmPtr addAlarm(AlarmPtr alarm);
+
+ /// @brief Fetches a duration from the store for a given key.
+ ///
+ /// @param key key value of the alarm to fetch.
+ ///
+ /// @return Pointer the desired alarm or an empty pointer.
+ AlarmPtr getAlarm(DurationKeyPtr key);
+
+ /// @brief Updates an alarm in the store.
+ ///
+ /// The alarm is assumed to already exist in the store.
+ ///
+ /// @param alarm alarm to update.
+ ///
+ /// @throw InvalidOperation if the alarm does not exist in the store.
+ void updateAlarm(AlarmPtr& alarm);
+
+ /// @brief Removes the alarm from the store.
+ ///
+ /// If the alarm does not exist in the store, it simply returns.
+ ///
+ /// @param key key value of the alarm to delete.
+ void deleteAlarm(DurationKeyPtr key);
+
+ /// @brief Fetches all of the alarms (in order by target)
+ ///
+ /// @return a collection of all alarms in the store.
+ AlarmCollectionPtr getAll();
+
+ /// @brief Removes all alarms from the store.
+ void clear();
+
+ /// @brief Get protocol family
+ ///
+ /// @return uint16_t containing the family (AF_INET or AF_INET6)
+ uint16_t getFamily() {
+ return (family_);
+ }
+
+private:
+ /// @brief Convenience method to verify a key is valid for an operation.
+ ///
+ /// @param label description of where the check is being made, appears in exception text.
+ /// @param key key to validate
+ ///
+ /// @throw BadValue if the key is either empty or its family does not
+ /// match the store.
+ void validateKey(const std::string& label, DurationKeyPtr key) const;
+
+ /// @brief Protocol family AF_INET or AF_INET6.
+ uint16_t family_;
+
+ /// @brief Container instance.
+ AlarmContainer alarms_;
+
+ /// @brief The mutex used to protect internal state.
+ const boost::scoped_ptr<std::mutex> mutex_;
+};
+
+typedef boost::shared_ptr<AlarmStore> AlarmStorePtr;
+
+} // end of namespace perfmon
+} // end of namespace isc
+
+#endif
--- /dev/null
+// Copyright (C) 2024 Internet Systems Consortium, Inc. ("ISC")
+//
+// This Source Code Form is subject to the terms of the Mozilla Public
+// License, v. 2.0. If a copy of the MPL was not distributed with this
+// file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+/// @file This file contains tests which exercise the AlarmStore class.
+#include <config.h>
+#include <alarm_store.h>
+#include <dhcp/dhcp6.h>
+#include <testutils/gtest_utils.h>
+#include <testutils/multi_threading_utils.h>
+
+#include <gtest/gtest.h>
+#include <sstream>
+
+using namespace std;
+using namespace isc;
+using namespace isc::dhcp;
+using namespace isc::perfmon;
+using namespace isc::test;
+using namespace boost::posix_time;
+
+namespace {
+
+// Verifies AlarmStore valid construction.
+TEST(AlarmStore, validConstructors) {
+ AlarmStorePtr store;
+
+ // Construct and verify v4 store.
+ EXPECT_NO_THROW_LOG(store.reset(new AlarmStore(AF_INET)));
+ ASSERT_TRUE(store);
+ EXPECT_EQ(store->getFamily(), AF_INET);
+
+ AlarmCollectionPtr alarms;
+ ASSERT_NO_THROW_LOG(alarms = store->getAll());
+ ASSERT_TRUE(alarms);
+ EXPECT_TRUE(alarms->empty());
+
+ // Construct and verify v6 store.
+ EXPECT_NO_THROW_LOG(store.reset(new AlarmStore(AF_INET6)));
+ ASSERT_TRUE(store);
+ EXPECT_EQ(store->getFamily(), AF_INET6);
+
+ ASSERT_NO_THROW_LOG(alarms = store->getAll());
+ ASSERT_TRUE(alarms);
+ EXPECT_TRUE(alarms->empty());
+}
+
+// Verifies AlarmStore invalid construction.
+TEST(AlarmStore, invalidConstructors) {
+ AlarmStorePtr store;
+
+ // Invalid family should throw.
+ EXPECT_THROW_MSG(AlarmStore(777),
+ BadValue,
+ "AlarmStore - invalid family 777, must be AF_INET or AF_INET6");
+}
+
+/// @brief Text fixture class for @c AlarmStore
+///
+/// In order to facilitate single and multi threaded testing,
+/// individual tests are implemented as methods that are called
+/// from within TEST_F bodies rather than in TEST_F bodies.
+class AlarmStoreTest : public ::testing::Test {
+public:
+
+ /// @brief Constructor
+ AlarmStoreTest() = default;
+
+ /// @brief Destructor
+ virtual ~AlarmStoreTest() = default;
+
+ /// @brief Creates a protocol-specific DurationKey for a given subnet
+ ///
+ /// The message-pair and socket-event pairs are fixed.
+ ///
+ /// @param family protocol family to test, AF_INET or AF_INET6
+ /// @param subnet SubnetID of the duration
+ DurationKeyPtr makeKey(uint16_t family, SubnetID subnet = 1) {
+ DurationKeyPtr key;
+ if (family == AF_INET) {
+ return (DurationKeyPtr(new DurationKey(AF_INET, DHCPDISCOVER, DHCPOFFER,
+ "socket_received", "buffer_read", subnet)));
+ }
+
+ return (DurationKeyPtr(new DurationKey(AF_INET6, DHCPV6_SOLICIT, DHCPV6_REPLY,
+ "socket_received", "buffer_read", subnet)));
+ }
+
+ /// @brief Verifies that alarms can be added to the store and fetched
+ /// by DurationKey.
+ ///
+ /// @param family protocol family to test, AF_INET or AF_INET6
+ void addAlarmTest(uint16_t family) {
+ Duration low_water(milliseconds(10));
+ Duration high_water(milliseconds(250));
+ AlarmStore store(family);
+
+ // Add four alarms with decreaing subnet ids.
+ std::vector<AlarmPtr> orig_alarms;
+ for (int subnet = 4; subnet > 0; --subnet) {
+ AlarmPtr alarm;
+ ASSERT_NO_THROW_LOG(alarm = store.addAlarm(makeKey(family, subnet),
+ low_water, high_water));
+ ASSERT_TRUE(alarm);
+ orig_alarms.push_back(alarm);
+ }
+
+ // Get all should retrieve all four in ascending order.
+ AlarmCollectionPtr alarms = store.getAll();
+ ASSERT_EQ(alarms->size(), orig_alarms.size());
+
+ int idx = orig_alarms.size() - 1;
+ for (auto const& d : *alarms) {
+ EXPECT_EQ(*d, *orig_alarms[idx]) << "failed on pass :" << idx;
+ --idx;
+ }
+
+ // Make sure we can fetch them all individually.
+ for (auto const& alarm : orig_alarms) {
+ AlarmPtr found;
+ ASSERT_NO_THROW_LOG(found = store.getAlarm(alarm));
+ ASSERT_TRUE(found);
+ EXPECT_EQ(*alarm, *found);
+ }
+
+ // Verify that clear() discards store contents.
+ store.clear();
+ alarms = store.getAll();
+ ASSERT_TRUE(alarms->empty());
+ }
+ /// @brief Verifies that duplicate alarms cannot be added to the store.
+ ///
+ /// @param family protocol family to test, AF_INET or AF_INET6
+ void addAlarmDuplicateTest(uint16_t family) {
+ AlarmStore store(family);
+
+ // Add a duration.
+ AlarmPtr alarm;
+ ASSERT_NO_THROW_LOG(alarm = store.addAlarm(makeKey(family), milliseconds(10),
+ milliseconds(250)));
+ ASSERT_TRUE(alarm);
+
+ // Attempting to add it again should evoke a duplicate key exception.
+ ASSERT_THROW(store.addAlarm(alarm), DuplicateAlarm);
+ }
+
+ /// @brief Verifies that duration key must be valid to add a duration to the store.
+ ///
+ /// Tests both v4 and v6.
+ void addAlarmInvalidTest() {
+ // Create a v4 store.
+ AlarmStorePtr store(new AlarmStore(AF_INET));
+
+ // Attempting to add with an empty key should throw.
+ ASSERT_THROW_MSG(store->addAlarm(DurationKeyPtr(),
+ milliseconds(10), milliseconds(250)),
+ BadValue,
+ "AlarmStore::addAlarm - key is empty");
+
+ // Attempting to a v6 key should fail.
+ ASSERT_THROW_MSG(store->addAlarm(makeKey(AF_INET6),
+ milliseconds(10), milliseconds(250)),
+ BadValue,
+ "AlarmStore::addAlarm"
+ " - family mismatch, key is v6, store is v4");
+
+ // Create a v6 store.
+ store.reset(new AlarmStore(AF_INET6));
+
+ // Attempting to add a v4 key should fail.
+ ASSERT_THROW_MSG(store->addAlarm(makeKey(AF_INET),
+ milliseconds(10), milliseconds(250)),
+ BadValue,
+ "AlarmStore::addAlarm"
+ " - family mismatch, key is v4, store is v6");
+ }
+
+ /// @brief Verify that alarms can be deleted from the store.
+ ///
+ /// @param family protocol family to test, AF_INET or AF_INET6
+ void deleteAlarmTest(uint16_t family) {
+ AlarmStore store(family);
+
+ std::vector<DurationKeyPtr> keys;
+ for (int subnet = 0; subnet < 3; ++subnet) {
+ AlarmPtr alarm;
+ DurationKeyPtr key = makeKey(family, subnet);
+ ASSERT_NO_THROW_LOG(alarm = store.addAlarm(key, milliseconds(10), milliseconds(250)));
+ ASSERT_TRUE(alarm);
+ keys.push_back(key);
+ }
+
+ // Verify we added three of them.
+ auto alarms = store.getAll();
+ ASSERT_EQ(alarms->size(), 3);
+
+ // Fetch the second duration.
+ AlarmPtr alarm;
+ ASSERT_NO_THROW_LOG(alarm = store.getAlarm(keys[1]));
+ ASSERT_TRUE(alarm);
+ EXPECT_EQ(*alarm, *(keys[1]));
+
+ // Delete it.
+ ASSERT_NO_THROW_LOG(store.deleteAlarm(alarm));
+
+ // Try to fetch it, shouldn't find it.
+ AlarmPtr alarm2;
+ ASSERT_NO_THROW_LOG(alarm2 = store.getAlarm(alarm));
+ ASSERT_FALSE(alarm2);
+
+ // Deleting it again should do no harm.
+ ASSERT_NO_THROW_LOG(store.deleteAlarm(alarm));
+
+ // Verify there are two left.
+ alarms = store.getAll();
+ ASSERT_EQ(alarms->size(), 2);
+ }
+
+ /// @brief Verify an invalid duration key on delete is detected.
+ ///
+ /// Tests both v4 and v6.
+ void deleteAlarmInvalidTest() {
+ // Create a v4 store.
+ AlarmStorePtr store(new AlarmStore(AF_INET));
+
+ // Attempting to delete an empty key should throw.
+ DurationKeyPtr key;
+ ASSERT_THROW_MSG(store->deleteAlarm(key),
+ BadValue,
+ "AlarmStore::deleteAlarm - key is empty");
+
+ // Attempting to delete a v6 key should fail.
+ ASSERT_THROW_MSG(store->deleteAlarm(makeKey(AF_INET6)),
+ BadValue,
+ "AlarmStore::deleteAlarm"
+ " - family mismatch, key is v6, store is v4");
+
+ // Create a v6 store.
+ store.reset(new AlarmStore(AF_INET6));
+
+ // Attempting to delete a v4 key should fail.
+ ASSERT_THROW_MSG(store->deleteAlarm(makeKey(AF_INET)),
+ BadValue,
+ "AlarmStore::deleteAlarm"
+ " - family mismatch, key is v4, store is v6");
+ }
+
+
+ /// @brief Verify that alarms in the store can be updated.
+ ///
+ /// @param family protocol family to test, AF_INET or AF_INET6
+ void updateAlarmTest(uint16_t family) {
+ AlarmStore store(family);
+
+ // Add the duration to the store.
+ AlarmPtr alarm;
+ ASSERT_NO_THROW(alarm.reset(new Alarm(*makeKey(family), milliseconds(10),
+ milliseconds(250))));
+ ASSERT_NO_THROW(store.addAlarm(alarm));
+
+ // Fetch it.
+ AlarmPtr found;
+ ASSERT_NO_THROW_LOG(found = store.getAlarm(alarm));
+ ASSERT_TRUE(found);
+
+ // Verify the fetched object is a copy.
+ ASSERT_NE(found, alarm);
+ ASSERT_EQ(*found, *alarm);
+
+ // Now change the thresholds and update it.
+ alarm->setLowWater(milliseconds(125));
+ alarm->setHighWater(milliseconds(500));
+ ASSERT_NO_THROW(store.updateAlarm(alarm));
+
+ // Fetch it again.
+ ASSERT_NO_THROW_LOG(found = store.getAlarm(alarm));
+
+ // Verify it has the expected thresholds.
+ EXPECT_EQ(found->getLowWater(), milliseconds(125));
+ EXPECT_EQ(found->getHighWater(), milliseconds(500));
+ }
+
+ /// @brief Verify an invalid duration key on update is detected.
+ ///
+ /// Tests both v4 and v6.
+ void updateAlarmInvalidTest() {
+ AlarmPtr alarm;
+
+ // Create a v4 store.
+ AlarmStorePtr store(new AlarmStore(AF_INET));
+
+ // Attempting to update an empty key should throw.
+ ASSERT_THROW_MSG(store->updateAlarm(alarm),
+ BadValue,
+ "AlarmStore::updateAlarm - key is empty");
+
+ // Create a v6 alarm.
+ ASSERT_NO_THROW_LOG(alarm.reset(new Alarm(*makeKey(AF_INET6), milliseconds(10),
+ milliseconds(250))));
+
+ // Attempting to update v6 alarm to a v4 store should fail.
+ ASSERT_THROW_MSG(store->updateAlarm(alarm),
+ BadValue,
+ "AlarmStore::updateAlarm"
+ " - family mismatch, key is v6, store is v4");
+
+ // Create a v6 store.
+ store.reset(new AlarmStore(AF_INET6));
+
+ // Updating a non-existent alarm should fail.
+ ASSERT_THROW_MSG(store->updateAlarm(alarm),
+ InvalidOperation,
+ "AlarmStore::updateAlarm alarm not found:"
+ " SOLICIT-REPLY.socket_received-buffer_read.1");
+
+ // Create a v4 alarm.
+ ASSERT_NO_THROW_LOG(alarm.reset(new Alarm(*makeKey(AF_INET), milliseconds(10),
+ milliseconds(250))));
+
+ // Attempting to update v4 duration to a v6 store fail.
+ ASSERT_THROW_MSG(store->updateAlarm(alarm),
+ BadValue,
+ "AlarmStore::updateAlarm"
+ " - family mismatch, key is v4, store is v6");
+ }
+};
+
+TEST_F(AlarmStoreTest, addAlarm) {
+ addAlarmTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, addAlarmMultiThreading) {
+ MultiThreadingTest mt;
+ addAlarmTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, addAlarm6) {
+ addAlarmTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, addAlarm6MultiThreading) {
+ MultiThreadingTest mt;
+ addAlarmTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, addAlarmDuplicate) {
+ addAlarmDuplicateTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, addAlarmDuplicateMultiThreading) {
+ MultiThreadingTest mt;
+ addAlarmDuplicateTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, addAlarm6Duplicate) {
+ addAlarmDuplicateTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, addAlarm6DuplicateMultiThreading) {
+ MultiThreadingTest mt;
+ addAlarmDuplicateTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, addAlarmInvalid) {
+ addAlarmInvalidTest();
+}
+
+TEST_F(AlarmStoreTest, addAlarmInvalidMultiThreading) {
+ MultiThreadingTest mt;
+ addAlarmInvalidTest();
+}
+
+TEST_F(AlarmStoreTest, deleteAlarm) {
+ deleteAlarmTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, deleteAlarmMultiThreading) {
+ MultiThreadingTest mt;
+ deleteAlarmTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, deleteAlarm6) {
+ deleteAlarmTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, deleteAlarm6MultiThreading) {
+ MultiThreadingTest mt;
+ deleteAlarmTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, deleteAlarmInvalid) {
+ deleteAlarmInvalidTest();
+}
+
+TEST_F(AlarmStoreTest, deleteAlarmInvalidMultiThreading) {
+ MultiThreadingTest mt;
+ deleteAlarmInvalidTest();
+}
+
+TEST_F(AlarmStoreTest, updateAlarm) {
+ updateAlarmTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, updateAlarmMultiThreading) {
+ MultiThreadingTest mt;
+ updateAlarmTest(AF_INET);
+}
+
+TEST_F(AlarmStoreTest, updateAlarm6) {
+ updateAlarmTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, updateAlarm6MultiThreading) {
+ MultiThreadingTest mt;
+ updateAlarmTest(AF_INET6);
+}
+
+TEST_F(AlarmStoreTest, updateAlarmInvalid) {
+ updateAlarmInvalidTest();
+}
+
+TEST_F(AlarmStoreTest, updateAlarmInvalidMultiThreading) {
+ MultiThreadingTest mt;
+ updateAlarmInvalidTest();
+}
+
+
+} // end of anonymous namespace