diff --git a/extensions/openpower-pels/repository.cpp b/extensions/openpower-pels/repository.cpp
index 4e40678..8458fcc 100644
--- a/extensions/openpower-pels/repository.cpp
+++ b/extensions/openpower-pels/repository.cpp
@@ -118,6 +118,8 @@
                 _pelAttributes.emplace(
                     LogID(pelID(pel.id()), obmcID(pel.obmcLogID())),
                     attributes);
+
+                updateRepoStats(attributes, true);
             }
             else
             {
@@ -167,6 +169,8 @@
     _pelAttributes.emplace(LogID(pelID(pel->id()), obmcID(pel->obmcLogID())),
                            attributes);
 
+    updateRepoStats(attributes, true);
+
     processAddCallbacks(*pel);
 }
 
@@ -206,6 +210,8 @@
     auto pel = findPEL(id);
     if (pel != _pelAttributes.end())
     {
+        updateRepoStats(pel->second, false);
+
         log<level::DEBUG>("Removing PEL from repository",
                           entry("PEL_ID=0x%X", pel->first.pelID.id),
                           entry("OBMC_LOG_ID=%d", pel->first.obmcID.id));
@@ -425,5 +431,73 @@
     }
 }
 
+bool Repository::isServiceableSev(const PELAttributes& pel)
+{
+    auto sevType = static_cast<SeverityType>(pel.severity & 0xF0);
+    auto sevPVEntry =
+        pel_values::findByValue(pel.severity, pel_values::severityValues);
+    std::string sevName = std::get<pel_values::registryNamePos>(*sevPVEntry);
+
+    bool check1 = (sevType == SeverityType::predictive) ||
+                  (sevType == SeverityType::unrecoverable) ||
+                  (sevType == SeverityType::critical);
+
+    bool check2 = ((sevType == SeverityType::recovered) ||
+                   (sevName == "symptom_recovered")) &&
+                  !pel.actionFlags.test(hiddenFlagBit);
+
+    bool check3 = (sevName == "symptom_predictive") ||
+                  (sevName == "symptom_unrecoverable") ||
+                  (sevName == "symptom_critical");
+
+    return check1 || check2 || check3;
+}
+
+void Repository::updateRepoStats(const PELAttributes& pel, bool pelAdded)
+{
+    auto isServiceable = Repository::isServiceableSev(pel);
+    auto bmcPEL = CreatorID::openBMC == static_cast<CreatorID>(pel.creator);
+
+    auto adjustSize = [pelAdded, &pel](auto& runningSize) {
+        if (pelAdded)
+        {
+            runningSize += pel.sizeOnDisk;
+        }
+        else
+        {
+            runningSize = std::max(static_cast<int64_t>(runningSize) -
+                                       static_cast<int64_t>(pel.sizeOnDisk),
+                                   static_cast<int64_t>(0));
+        }
+    };
+
+    adjustSize(_sizes.total);
+
+    if (bmcPEL)
+    {
+        adjustSize(_sizes.bmc);
+        if (isServiceable)
+        {
+            adjustSize(_sizes.bmcServiceable);
+        }
+        else
+        {
+            adjustSize(_sizes.bmcInfo);
+        }
+    }
+    else
+    {
+        adjustSize(_sizes.nonBMC);
+        if (isServiceable)
+        {
+            adjustSize(_sizes.nonBMCServiceable);
+        }
+        else
+        {
+            adjustSize(_sizes.nonBMCInfo);
+        }
+    }
+}
+
 } // namespace pels
 } // namespace openpower
diff --git a/extensions/openpower-pels/repository.hpp b/extensions/openpower-pels/repository.hpp
index ecfcf7e..e9b6a27 100644
--- a/extensions/openpower-pels/repository.hpp
+++ b/extensions/openpower-pels/repository.hpp
@@ -112,6 +112,27 @@
         }
     };
 
+    /**
+     * @brief A structure for keeping a breakdown of the sizes of PELs
+     *        of different types in the repository.
+     */
+    struct SizeStats
+    {
+        uint64_t total;
+        uint64_t bmc;
+        uint64_t nonBMC;
+        uint64_t bmcServiceable;
+        uint64_t bmcInfo;
+        uint64_t nonBMCServiceable;
+        uint64_t nonBMCInfo;
+
+        SizeStats() :
+            total(0), bmc(0), nonBMC(0), bmcServiceable(0), bmcInfo(0),
+            nonBMCServiceable(0), nonBMCInfo(0)
+        {
+        }
+    };
+
     Repository() = delete;
     ~Repository() = default;
     Repository(const Repository&) = default;
@@ -313,6 +334,25 @@
      */
     void setPELHMCTransState(uint32_t pelID, TransmissionState state);
 
+    /**
+     * @brief Returns the size stats structure
+     *
+     * @return const SizeStats& - The stats structure
+     */
+    const SizeStats& getSizeStats() const
+    {
+        return _sizes;
+    }
+
+    /**
+     * @brief Says if the PEL is considered serviceable (not just
+     *        informational) as determined by its severity.
+     *
+     * @param[in] pel - The PELAttributes entry for the PEL
+     * @return bool - If serviceable or not
+     */
+    static bool isServiceableSev(const PELAttributes& pel);
+
   private:
     using PELUpdateFunc = std::function<void(PEL&)>;
 
@@ -372,6 +412,15 @@
     void write(const PEL& pel, const std::filesystem::path& path);
 
     /**
+     * @brief Updates the repository statistics after a PEL is
+     *        added or removed.
+     *
+     * @param[in] pel - The PELAttributes entry for the PEL
+     * @param[in] pelAdded - true if the PEL was added, false if removed
+     */
+    void updateRepoStats(const PELAttributes& pel, bool pelAdded);
+
+    /**
      * @brief The filesystem path to the PEL logs.
      */
     const std::filesystem::path _logPath;
@@ -402,6 +451,11 @@
      *        before pruning.
      */
     const size_t _maxNumPELs;
+
+    /**
+     * @brief Statistics on the sizes of the stored PELs.
+     */
+    SizeStats _sizes;
 };
 
 } // namespace pels
diff --git a/test/openpower-pels/repository_test.cpp b/test/openpower-pels/repository_test.cpp
index 446e10e..ae88551 100644
--- a/test/openpower-pels/repository_test.cpp
+++ b/test/openpower-pels/repository_test.cpp
@@ -434,3 +434,157 @@
 
     EXPECT_FALSE(fd);
 }
+
+// Test the repo size statistics
+TEST_F(RepositoryTest, TestRepoSizes)
+{
+    uint32_t id = 1;
+
+    Repository repo{repoPath, 10000, 500};
+
+    // All of the size stats are the sizes on disk a PEL takes up,
+    // which is different than the file size.  Disk usage seems
+    // to have a granularity of 4096 bytes.  This probably shouldn't
+    // be hardcoded, but I don't know how to look it up dynamically.
+
+    // All sizes are zero
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 0);
+        EXPECT_EQ(stats.bmc, 0);
+        EXPECT_EQ(stats.nonBMC, 0);
+        EXPECT_EQ(stats.bmcServiceable, 0);
+        EXPECT_EQ(stats.bmcInfo, 0);
+        EXPECT_EQ(stats.nonBMCServiceable, 0);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+
+    // Add a 2000B BMC predictive error
+    auto data = pelFactory(id++, 'O', 0x20, 0x8800, 2000);
+    auto pel = std::make_unique<PEL>(data);
+    auto pelID1 = pel->id();
+    repo.add(pel);
+
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 4096);
+        EXPECT_EQ(stats.bmc, 4096);
+        EXPECT_EQ(stats.nonBMC, 0);
+        EXPECT_EQ(stats.bmcServiceable, 4096);
+        EXPECT_EQ(stats.bmcInfo, 0);
+        EXPECT_EQ(stats.nonBMCServiceable, 0);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+
+    // Add a 5000B BMC informational error
+    data = pelFactory(id++, 'O', 0x00, 0x8800, 5000);
+    pel = std::make_unique<PEL>(data);
+    auto pelID2 = pel->id();
+    repo.add(pel);
+
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 4096 + 8192);
+        EXPECT_EQ(stats.bmc, 4096 + 8192);
+        EXPECT_EQ(stats.nonBMC, 0);
+        EXPECT_EQ(stats.bmcServiceable, 4096);
+        EXPECT_EQ(stats.bmcInfo, 8192);
+        EXPECT_EQ(stats.nonBMCServiceable, 0);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+
+    // Add a 4000B Hostboot unrecoverable error
+    data = pelFactory(id++, 'B', 0x40, 0x8800, 4000);
+    pel = std::make_unique<PEL>(data);
+    auto pelID3 = pel->id();
+    repo.add(pel);
+
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 4096 + 8192 + 4096);
+        EXPECT_EQ(stats.bmc, 4096 + 8192);
+        EXPECT_EQ(stats.nonBMC, 4096);
+        EXPECT_EQ(stats.bmcServiceable, 4096);
+        EXPECT_EQ(stats.bmcInfo, 8192);
+        EXPECT_EQ(stats.nonBMCServiceable, 4096);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+
+    // Add a 5000B Hostboot informational error
+    data = pelFactory(id++, 'B', 0x00, 0x8800, 5000);
+    pel = std::make_unique<PEL>(data);
+    auto pelID4 = pel->id();
+    repo.add(pel);
+
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 4096 + 8192 + 4096 + 8192);
+        EXPECT_EQ(stats.bmc, 4096 + 8192);
+        EXPECT_EQ(stats.nonBMC, 4096 + 8192);
+        EXPECT_EQ(stats.bmcServiceable, 4096);
+        EXPECT_EQ(stats.bmcInfo, 8192);
+        EXPECT_EQ(stats.nonBMCServiceable, 4096);
+        EXPECT_EQ(stats.nonBMCInfo, 8192);
+    }
+
+    // Remove the BMC serviceable error
+    using ID = Repository::LogID;
+    ID id1{ID::Pel(pelID1)};
+
+    repo.remove(id1);
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 8192 + 4096 + 8192);
+        EXPECT_EQ(stats.bmc, 8192);
+        EXPECT_EQ(stats.nonBMC, 4096 + 8192);
+        EXPECT_EQ(stats.bmcServiceable, 0);
+        EXPECT_EQ(stats.bmcInfo, 8192);
+        EXPECT_EQ(stats.nonBMCServiceable, 4096);
+        EXPECT_EQ(stats.nonBMCInfo, 8192);
+    }
+
+    // Remove the Hostboot informational error
+    ID id4{ID::Pel(pelID4)};
+
+    repo.remove(id4);
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 8192 + 4096);
+        EXPECT_EQ(stats.bmc, 8192);
+        EXPECT_EQ(stats.nonBMC, 4096);
+        EXPECT_EQ(stats.bmcServiceable, 0);
+        EXPECT_EQ(stats.bmcInfo, 8192);
+        EXPECT_EQ(stats.nonBMCServiceable, 4096);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+
+    // Remove the BMC informational error
+    ID id2{ID::Pel(pelID2)};
+
+    repo.remove(id2);
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 4096);
+        EXPECT_EQ(stats.bmc, 0);
+        EXPECT_EQ(stats.nonBMC, 4096);
+        EXPECT_EQ(stats.bmcServiceable, 0);
+        EXPECT_EQ(stats.bmcInfo, 0);
+        EXPECT_EQ(stats.nonBMCServiceable, 4096);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+
+    // Remove the hostboot unrecoverable error
+    ID id3{ID::Pel(pelID3)};
+
+    repo.remove(id3);
+    {
+        const auto& stats = repo.getSizeStats();
+        EXPECT_EQ(stats.total, 0);
+        EXPECT_EQ(stats.bmc, 0);
+        EXPECT_EQ(stats.nonBMC, 0);
+        EXPECT_EQ(stats.bmcServiceable, 0);
+        EXPECT_EQ(stats.bmcInfo, 0);
+        EXPECT_EQ(stats.nonBMCServiceable, 0);
+        EXPECT_EQ(stats.nonBMCInfo, 0);
+    }
+}
