Extended MaximInterface

Dependents:   mbed_DS28EC20_GPIO

Revision:
6:a8c83a2e6fa4
Parent:
0:f77ad7f72d04
--- a/Devices/DS28E15_22_25.cpp	Fri Jan 19 10:25:02 2018 -0600
+++ b/Devices/DS28E15_22_25.cpp	Wed Jan 23 13:11:04 2019 -0600
@@ -31,29 +31,28 @@
 *******************************************************************************/
 
 #include <algorithm>
-#include "DS28E15_22_25.hpp"
 #include <MaximInterface/Utilities/crc.hpp>
 #include <MaximInterface/Utilities/Error.hpp>
-
-using std::copy;
+#include "DS28E15_22_25.hpp"
 
 namespace MaximInterface {
 
 using namespace Sha256;
+using std::copy;
 
 static const int shaComputationDelayMs = 3;
 static const int eepromWriteDelayMs = 10;
 static inline int secretEepromWriteDelayMs(bool lowPower) {
   return lowPower ? 200 : 100;
 }
+
 static const int ds28e22_25_pagesPerBlock = 2;
 
 static error_code
-writeDataWithCrc(OneWireMaster & master, const uint_least8_t * data,
-                 size_t dataLen,
+writeDataWithCrc(OneWireMaster & master, span<const uint_least8_t> data,
                  OneWireMaster::Level level = OneWireMaster::NormalLevel,
                  uint_fast16_t crcStart = 0) {
-  error_code result = master.writeBlock(data, dataLen);
+  error_code result = master.writeBlock(data);
   if (result) {
     return result;
   }
@@ -66,13 +65,20 @@
   if (result) {
     return result;
   }
-  if (calculateCrc16(response, sizeof(response) / sizeof(response[0]),
-                     calculateCrc16(data, dataLen, crcStart)) != 0xB001) {
+  if (calculateCrc16(response, calculateCrc16(data, crcStart)) != 0xB001) {
     result = make_error_code(DS28E15_22_25::CrcError);
   }
   return result;
 }
 
+const int DS28E15_22_25::segmentsPerPage;
+
+DS28E15_22_25::AuthenticationData &
+DS28E15_22_25::AuthenticationData::setAnonymousRomId() {
+  std::fill(romId().begin(), romId().end(), 0xFF);
+  return *this;
+}
+
 error_code
 DS28E15_22_25::writeCommandWithCrc(Command command, uint_least8_t parameter,
                                    OneWireMaster::Level level) const {
@@ -80,26 +86,23 @@
   if (!result) {
     const uint_least8_t data[] = {static_cast<uint_least8_t>(command),
                                   parameter};
-    result =
-        writeDataWithCrc(*master, data, sizeof(data) / sizeof(data[0]), level);
+    result = writeDataWithCrc(*master, data);
   }
   return result;
 }
 
-static error_code readDataWithCrc(OneWireMaster & master, uint_least8_t * data,
-                                  size_t dataLen) {
-  error_code result = master.readBlock(data, dataLen);
+static error_code readDataWithCrc(OneWireMaster & master,
+                                  span<uint_least8_t> data) {
+  error_code result = master.readBlock(data);
   if (result) {
     return result;
   }
   uint_least8_t response[2];
-  const size_t responseLen = sizeof(response) / sizeof(response[0]);
-  result = master.readBlock(response, responseLen);
+  result = master.readBlock(response);
   if (result) {
     return result;
   }
-  if (calculateCrc16(response, responseLen, calculateCrc16(data, dataLen)) !=
-      0xB001) {
+  if (calculateCrc16(response, calculateCrc16(data)) != 0xB001) {
     result = make_error_code(DS28E15_22_25::CrcError);
   }
   return result;
@@ -117,7 +120,7 @@
   return result;
 }
 
-static error_code releaseSequence(OneWireMaster & master, const Sleep & sleep,
+static error_code releaseSequence(OneWireMaster & master, Sleep & sleep,
                                   int delayTimeMs) {
   error_code result = master.writeBytePower(0xAA);
   if (result) {
@@ -131,21 +134,11 @@
   return readCsByte(master);
 }
 
-DS28E15_22_25::BlockProtection::BlockProtection(bool readProtection,
-                                                bool writeProtection,
-                                                bool eepromEmulation,
-                                                bool authProtection,
-                                                int blockNum) {
-  setReadProtection(readProtection);
-  setWriteProtection(writeProtection);
-  setEepromEmulation(eepromEmulation);
-  setAuthProtection(authProtection);
-  setBlockNum(blockNum);
-}
-
-void DS28E15_22_25::BlockProtection::setBlockNum(int blockNum) {
+DS28E15_22_25::BlockProtection &
+DS28E15_22_25::BlockProtection::setBlockNum(int blockNum) {
   status &= ~blockNumMask;
   status |= (blockNum & blockNumMask);
+  return *this;
 }
 
 bool DS28E15_22_25::BlockProtection::noProtection() const {
@@ -153,41 +146,78 @@
          !authProtection();
 }
 
-void DS28E15_22_25::BlockProtection::setReadProtection(bool readProtection) {
+DS28E15_22_25::BlockProtection &
+DS28E15_22_25::BlockProtection::setReadProtection(bool readProtection) {
   if (readProtection) {
     status |= readProtectionMask;
   } else {
     status &= ~readProtectionMask;
   }
+  return *this;
 }
 
-void DS28E15_22_25::BlockProtection::setWriteProtection(bool writeProtection) {
+DS28E15_22_25::BlockProtection &
+DS28E15_22_25::BlockProtection::setWriteProtection(bool writeProtection) {
   if (writeProtection) {
     status |= writeProtectionMask;
   } else {
     status &= ~writeProtectionMask;
   }
+  return *this;
 }
 
-void DS28E15_22_25::BlockProtection::setEepromEmulation(bool eepromEmulation) {
+DS28E15_22_25::BlockProtection &
+DS28E15_22_25::BlockProtection::setEepromEmulation(bool eepromEmulation) {
   if (eepromEmulation) {
     status |= eepromEmulationMask;
   } else {
     status &= ~eepromEmulationMask;
   }
+  return *this;
 }
 
-void DS28E15_22_25::BlockProtection::setAuthProtection(bool authProtection) {
+DS28E15_22_25::BlockProtection &
+DS28E15_22_25::BlockProtection::setAuthProtection(bool authProtection) {
   if (authProtection) {
     status |= authProtectionMask;
   } else {
     status &= ~authProtectionMask;
   }
+  return *this;
+}
+
+DS28E15_22_25::ProtectionWriteMacData::ProtectionWriteMacData()
+    : result_(), oldProtection_(), newProtection_() {
+  setOldProtection(oldProtection_);
+  setNewProtection(newProtection_);
+}
+
+DS28E15_22_25::ProtectionWriteMacData &
+DS28E15_22_25::ProtectionWriteMacData::setOldProtection(
+    BlockProtection oldProtection) {
+  result_[oldProtectionIdx] = oldProtection.authProtection() ? 1 : 0;
+  result_[oldProtectionIdx + 1] = oldProtection.eepromEmulation() ? 1 : 0;
+  result_[oldProtectionIdx + 2] = oldProtection.writeProtection() ? 1 : 0;
+  result_[oldProtectionIdx + 3] = oldProtection.readProtection() ? 1 : 0;
+  oldProtection_ = oldProtection;
+  return *this;
+}
+
+DS28E15_22_25::ProtectionWriteMacData &
+DS28E15_22_25::ProtectionWriteMacData::setNewProtection(
+    BlockProtection newProtection) {
+  result_[blockNumIdx] = newProtection.blockNum();
+  result_[newProtectionIdx] = newProtection.authProtection() ? 1 : 0;
+  result_[newProtectionIdx + 1] = newProtection.eepromEmulation() ? 1 : 0;
+  result_[newProtectionIdx + 2] = newProtection.writeProtection() ? 1 : 0;
+  result_[newProtectionIdx + 3] = newProtection.readProtection() ? 1 : 0;
+  newProtection_ = newProtection;
+  return *this;
 }
 
 error_code
-DS28E15_22_25::writeAuthBlockProtection(const BlockProtection & newProtection,
-                                        const Hash & mac) {
+DS28E15_22_25::writeAuthBlockProtection(BlockProtection newProtection,
+                                        Hash::const_span mac) {
   error_code result =
       writeCommandWithCrc(AuthWriteBlockProtection, newProtection.statusByte(),
                           OneWireMaster::StrongLevel);
@@ -195,13 +225,13 @@
     return result;
   }
 
-  (*sleep)(shaComputationDelayMs);
+  sleep->invoke(shaComputationDelayMs);
   result = master->setLevel(OneWireMaster::NormalLevel);
   if (result) {
     return result;
   }
 
-  result = writeDataWithCrc(*master, mac.data(), mac.size());
+  result = writeDataWithCrc(*master, mac);
   if (result) {
     return result;
   }
@@ -215,8 +245,7 @@
   return result;
 }
 
-error_code
-DS28E15_22_25::writeBlockProtection(const BlockProtection & protection) {
+error_code DS28E15_22_25::writeBlockProtection(BlockProtection protection) {
   error_code result =
       writeCommandWithCrc(WriteBlockProtection, protection.statusByte());
   if (result) {
@@ -244,33 +273,8 @@
   return result;
 }
 
-AuthMacData DS28E15_22_25::createAuthMacData(const Page & pageData, int pageNum,
-                                             const Scratchpad & challenge,
-                                             const RomId & romId,
-                                             const ManId & manId) {
-  AuthMacData authMacData;
-  AuthMacData::iterator authMacDataIt = authMacData.begin();
-  authMacDataIt = copy(pageData.begin(), pageData.end(), authMacDataIt);
-  authMacDataIt = copy(challenge.begin(), challenge.end(), authMacDataIt);
-  authMacDataIt = copy(romId.begin(), romId.end(), authMacDataIt);
-  *authMacDataIt = manId[1];
-  *(++authMacDataIt) = manId[0];
-  *(++authMacDataIt) = pageNum;
-  *(++authMacDataIt) = 0x00;
-  return authMacData;
-}
-
-AuthMacData DS28E15_22_25::createAnonAuthMacData(const Page & pageData,
-                                                 int pageNum,
-                                                 const Scratchpad & challenge,
-                                                 const ManId & manId) {
-  RomId romId;
-  romId.fill(0xFF);
-  return createAuthMacData(pageData, pageNum, challenge, romId, manId);
-}
-
 error_code DS28E15_22_25::computeReadPageMac(int page_num, bool anon,
-                                             Hash & mac) const {
+                                             Hash::span mac) const {
   error_code result =
       writeCommandWithCrc(ComputePageMac, (anon ? 0xE0 : 0x00) | page_num,
                           OneWireMaster::StrongLevel);
@@ -278,7 +282,7 @@
     return result;
   }
 
-  (*sleep)(shaComputationDelayMs * 2);
+  sleep->invoke(shaComputationDelayMs * 2);
   result = master->setLevel(OneWireMaster::NormalLevel);
   if (result) {
     return result;
@@ -289,7 +293,7 @@
     return result;
   }
 
-  result = readDataWithCrc(*master, mac.data(), mac.size());
+  result = readDataWithCrc(*master, mac);
   return result;
 }
 
@@ -307,7 +311,7 @@
   return result;
 }
 
-error_code DS28E15_22_25::doWriteScratchpad(const Scratchpad & data,
+error_code DS28E15_22_25::doWriteScratchpad(Scratchpad::const_span data,
                                             Variant variant) {
   const uint_least8_t parameter =
       (variant == DS28E22 || variant == DS28E25) ? 0x20 : 0x00;
@@ -316,11 +320,11 @@
     return result;
   }
 
-  result = writeDataWithCrc(*master, data.data(), data.size());
+  result = writeDataWithCrc(*master, data);
   return result;
 }
 
-error_code DS28E15_22_25::doReadScratchpad(Scratchpad & data,
+error_code DS28E15_22_25::doReadScratchpad(Scratchpad::span data,
                                            Variant variant) const {
   const uint_least8_t parameter =
       (variant == DS28E22 || variant == DS28E25) ? 0x2F : 0x0F;
@@ -329,7 +333,7 @@
     return result;
   }
 
-  result = readDataWithCrc(*master, data.data(), data.size());
+  result = readDataWithCrc(*master, data);
   return result;
 }
 
@@ -344,7 +348,7 @@
   return result;
 }
 
-error_code DS28E15_22_25::readPage(int page, Page & rdbuf) const {
+error_code DS28E15_22_25::readPage(int page, Page::span rdbuf) const {
   error_code result = writeCommandWithCrc(ReadMemory, page);
   if (result) {
     return result;
@@ -354,31 +358,31 @@
   return result;
 }
 
-error_code DS28E15_22_25::continueReadPage(Page & rdbuf) const {
-  return readDataWithCrc(*master, rdbuf.data(), rdbuf.size());
+error_code DS28E15_22_25::continueReadPage(Page::span rdbuf) const {
+  return readDataWithCrc(*master, rdbuf);
 }
 
-error_code DS28E15_22_25::doWriteAuthSegment(const Segment & newData,
-                                             const Hash & mac, Variant variant,
-                                             bool continuing) {
+error_code DS28E15_22_25::doWriteAuthSegment(Segment::const_span newData,
+                                             Hash::const_span mac,
+                                             Variant variant, bool continuing) {
   // CRC gets calculated with CS byte when continuing on DS28E22 and DS28E25.
   const uint_fast16_t crcStart =
       ((variant == DS28E22 || variant == DS28E25) && continuing)
           ? calculateCrc16(0xAA)
           : 0;
-  error_code result = writeDataWithCrc(*master, newData.data(), newData.size(),
-                                       OneWireMaster::StrongLevel, crcStart);
+  error_code result =
+      writeDataWithCrc(*master, newData, OneWireMaster::StrongLevel, crcStart);
   if (result) {
     return result;
   }
 
-  (*sleep)(shaComputationDelayMs);
+  sleep->invoke(shaComputationDelayMs);
   result = master->setLevel(OneWireMaster::NormalLevel);
   if (result) {
     return result;
   }
 
-  result = writeDataWithCrc(*master, mac.data(), mac.size());
+  result = writeDataWithCrc(*master, mac);
   if (result) {
     return result;
   }
@@ -393,8 +397,8 @@
 }
 
 error_code DS28E15_22_25::doWriteAuthSegment(int pageNum, int segmentNum,
-                                             const Segment & newData,
-                                             const Hash & mac,
+                                             Segment::const_span newData,
+                                             Hash::const_span mac,
                                              Variant variant) {
   error_code result =
       writeCommandWithCrc(AuthWriteMemory, (segmentNum << 5) | pageNum);
@@ -406,67 +410,13 @@
   return result;
 }
 
-error_code DS28E15_22_25::doContinueWriteAuthSegment(const Segment & newData,
-                                                     const Hash & mac,
-                                                     Variant variant) {
+error_code DS28E15_22_25::doContinueWriteAuthSegment(
+    Segment::const_span newData, Hash::const_span mac, Variant variant) {
   return doWriteAuthSegment(newData, mac, variant, true);
 }
 
-WriteMacData DS28E15_22_25::createSegmentWriteMacData(
-    int pageNum, int segmentNum, const Segment & newData,
-    const Segment & oldData, const RomId & romId, const ManId & manId) {
-  WriteMacData MT;
-
-  // insert ROM number
-  copy(romId.begin(), romId.end(), MT.begin());
-
-  MT[11] = segmentNum;
-  MT[10] = pageNum;
-  MT[9] = manId[0];
-  MT[8] = manId[1];
-
-  // insert old data
-  copy(oldData.begin(), oldData.end(), MT.begin() + 12);
-
-  // insert new data
-  copy(newData.begin(), newData.end(), MT.begin() + 16);
-
-  return MT;
-}
-
-WriteMacData DS28E15_22_25::createProtectionWriteMacData(
-    const BlockProtection & newProtection,
-    const BlockProtection & oldProtection, const RomId & romId,
-    const ManId & manId) {
-  WriteMacData MT;
-
-  // insert ROM number
-  copy(romId.begin(), romId.end(), MT.begin());
-
-  // instert block and page
-  MT[11] = 0;
-  MT[10] = newProtection.blockNum();
-
-  MT[9] = manId[0];
-  MT[8] = manId[1];
-
-  // old data
-  MT[12] = oldProtection.authProtection() ? 0x01 : 0x00;
-  MT[13] = oldProtection.eepromEmulation() ? 0x01 : 0x00;
-  MT[14] = oldProtection.writeProtection() ? 0x01 : 0x00;
-  MT[15] = oldProtection.readProtection() ? 0x01 : 0x00;
-  // new data
-  MT[16] = newProtection.authProtection() ? 0x01 : 0x00;
-  MT[17] = newProtection.eepromEmulation() ? 0x01 : 0x00;
-  MT[18] = newProtection.writeProtection() ? 0x01 : 0x00;
-  MT[19] = newProtection.readProtection() ? 0x01 : 0x00;
-
-  // compute the mac
-  return MT;
-}
-
 error_code DS28E15_22_25::readSegment(int page, int segment,
-                                      Segment & data) const {
+                                      Segment::span data) const {
   error_code result = writeCommandWithCrc(ReadMemory, (segment << 5) | page);
   if (result) {
     return result;
@@ -476,12 +426,12 @@
   return result;
 }
 
-error_code DS28E15_22_25::continueReadSegment(Segment & data) const {
-  return master->readBlock(data.data(), data.size());
+error_code DS28E15_22_25::continueReadSegment(Segment::span data) const {
+  return master->readBlock(data);
 }
 
 error_code DS28E15_22_25::writeSegment(int page, int block,
-                                       const Segment & data) {
+                                       Segment::const_span data) {
   error_code result = writeCommandWithCrc(WriteMemory, (block << 5) | page);
   if (result) {
     return result;
@@ -491,8 +441,8 @@
   return result;
 }
 
-error_code DS28E15_22_25::continueWriteSegment(const Segment & data) {
-  error_code result = writeDataWithCrc(*master, data.data(), data.size());
+error_code DS28E15_22_25::continueWriteSegment(Segment::const_span data) {
+  error_code result = writeDataWithCrc(*master, data);
   if (result) {
     return result;
   }
@@ -501,55 +451,37 @@
   return result;
 }
 
-SlaveSecretData
-DS28E15_22_25::createSlaveSecretData(const Page & bindingPage,
-                                     int bindingPageNum,
-                                     const Scratchpad & partialSecret,
-                                     const RomId & romId, const ManId & manId) {
-  SlaveSecretData slaveSecretData;
-  SlaveSecretData::iterator slaveSecretDataIt = slaveSecretData.begin();
-  slaveSecretDataIt =
-      copy(bindingPage.begin(), bindingPage.end(), slaveSecretDataIt);
-  slaveSecretDataIt =
-      copy(partialSecret.begin(), partialSecret.end(), slaveSecretDataIt);
-  slaveSecretDataIt = copy(romId.begin(), romId.end(), slaveSecretDataIt);
-  *slaveSecretDataIt = manId[1];
-  *(++slaveSecretDataIt) = manId[0];
-  *(++slaveSecretDataIt) = bindingPageNum;
-  *(++slaveSecretDataIt) = 0x00;
-  return slaveSecretData;
-}
-
-error_code DS28E15_22_25::doReadAllBlockProtection(BlockProtection * protection,
-                                                   const size_t protectionLen,
-                                                   Variant variant) const {
+error_code
+DS28E15_22_25::doReadAllBlockProtection(span<BlockProtection> protection,
+                                        Variant variant) const {
   error_code result = writeCommandWithCrc(ReadStatus, 0);
   if (!result) {
     if (variant == DS28E22 || variant == DS28E25) {
       // Need to read extra data on DS28E22 to get CRC16.
       uint_least8_t buf[DS28E25::memoryPages];
-      result = readDataWithCrc(*master, buf, DS28E25::memoryPages);
+      result = readDataWithCrc(*master, buf);
       if (!result) {
         const int blocks = ((variant == DS28E22) ? DS28E22::memoryPages
                                                  : DS28E25::memoryPages) /
                            ds28e22_25_pagesPerBlock;
-        for (size_t i = 0;
-             i < std::min(protectionLen, static_cast<size_t>(blocks)); i++) {
+        for (span<BlockProtection>::index_type i = 0;
+             i < std::min<span<BlockProtection>::index_type>(protection.size(),
+                                                             blocks);
+             ++i) {
           protection[i].setStatusByte(
               (buf[i * ds28e22_25_pagesPerBlock] & 0xF0) | // Upper nibble
               ((buf[i * ds28e22_25_pagesPerBlock] & 0x0F) /
                ds28e22_25_pagesPerBlock)); // Lower nibble
         }
       }
-    } else // DS28E15
-    {
+    } else { // DS28E15
       uint_least8_t buf[DS28E15::protectionBlocks];
-      result = readDataWithCrc(*master, buf, DS28E15::protectionBlocks);
+      result = readDataWithCrc(*master, buf);
       if (!result) {
-        for (size_t i = 0;
-             i < std::min(protectionLen,
-                          static_cast<size_t>(DS28E15::protectionBlocks));
-             i++) {
+        for (span<BlockProtection>::index_type i = 0;
+             i < std::min<span<BlockProtection>::index_type>(
+                     protection.size(), DS28E15::protectionBlocks);
+             ++i) {
           protection[i].setStatusByte(buf[i]);
         }
       }
@@ -592,8 +524,8 @@
 error_code DS28E15_22_25::readPersonality(Personality & personality) const {
   error_code result = writeCommandWithCrc(ReadStatus, 0xE0);
   if (!result) {
-    array<uint_least8_t, 4> data;
-    result = readDataWithCrc(*master, data.data(), data.size());
+    uint_least8_t data[4];
+    result = readDataWithCrc(*master, data);
     if (!result) {
       personality.PB1 = data[0];
       personality.PB2 = data[1];
@@ -604,11 +536,14 @@
   return result;
 }
 
-error_code DS28EL15::writeScratchpad(const Scratchpad & data) {
+const int DS28EL15::memoryPages;
+const int DS28EL15::protectionBlocks;
+
+error_code DS28EL15::writeScratchpad(Scratchpad::const_span data) {
   return doWriteScratchpad(data, DS28E15);
 }
 
-error_code DS28EL15::readScratchpad(Scratchpad & data) const {
+error_code DS28EL15::readScratchpad(Scratchpad::span data) const {
   return doReadScratchpad(data, DS28E15);
 }
 
@@ -618,20 +553,19 @@
 }
 
 error_code DS28EL15::writeAuthSegment(int pageNum, int segmentNum,
-                                      const Segment & newData,
-                                      const Hash & mac) {
+                                      Segment::const_span newData,
+                                      Hash::const_span mac) {
   return doWriteAuthSegment(pageNum, segmentNum, newData, mac, DS28E15);
 }
 
-error_code DS28EL15::continueWriteAuthSegment(const Segment & newData,
-                                              const Hash & mac) {
+error_code DS28EL15::continueWriteAuthSegment(Segment::const_span newData,
+                                              Hash::const_span mac) {
   return doContinueWriteAuthSegment(newData, mac, DS28E15);
 }
 
 error_code DS28EL15::readAllBlockProtection(
-    array<BlockProtection, protectionBlocks> & protection) const {
-  return doReadAllBlockProtection(protection.data(), protection.size(),
-                                  DS28E15);
+    span<BlockProtection, protectionBlocks> protection) const {
+  return doReadAllBlockProtection(protection, DS28E15);
 }
 
 error_code DS28E15::loadSecret(bool lock) { return doLoadSecret(lock, false); }
@@ -640,11 +574,14 @@
   return doComputeSecret(pageNum, lock, false);
 }
 
-error_code DS28EL22::writeScratchpad(const Scratchpad & data) {
+const int DS28EL22::memoryPages;
+const int DS28EL22::protectionBlocks;
+
+error_code DS28EL22::writeScratchpad(Scratchpad::const_span data) {
   return doWriteScratchpad(data, DS28E22);
 }
 
-error_code DS28EL22::readScratchpad(Scratchpad & data) const {
+error_code DS28EL22::readScratchpad(Scratchpad::span data) const {
   return doReadScratchpad(data, DS28E22);
 }
 
@@ -654,20 +591,19 @@
 }
 
 error_code DS28EL22::writeAuthSegment(int pageNum, int segmentNum,
-                                      const Segment & newData,
-                                      const Hash & mac) {
+                                      Segment::const_span newData,
+                                      Hash::const_span mac) {
   return doWriteAuthSegment(pageNum, segmentNum, newData, mac, DS28E22);
 }
 
-error_code DS28EL22::continueWriteAuthSegment(const Segment & newData,
-                                              const Hash & mac) {
+error_code DS28EL22::continueWriteAuthSegment(Segment::const_span newData,
+                                              Hash::const_span mac) {
   return doContinueWriteAuthSegment(newData, mac, DS28E22);
 }
 
 error_code DS28EL22::readAllBlockProtection(
-    array<BlockProtection, protectionBlocks> & protection) const {
-  return doReadAllBlockProtection(protection.data(), protection.size(),
-                                  DS28E22);
+    span<BlockProtection, protectionBlocks> protection) const {
+  return doReadAllBlockProtection(protection, DS28E22);
 }
 
 error_code DS28E22::loadSecret(bool lock) { return doLoadSecret(lock, false); }
@@ -676,11 +612,14 @@
   return doComputeSecret(pageNum, lock, false);
 }
 
-error_code DS28EL25::writeScratchpad(const Scratchpad & data) {
+const int DS28EL25::memoryPages;
+const int DS28EL25::protectionBlocks;
+
+error_code DS28EL25::writeScratchpad(Scratchpad::const_span data) {
   return doWriteScratchpad(data, DS28E25);
 }
 
-error_code DS28EL25::readScratchpad(Scratchpad & data) const {
+error_code DS28EL25::readScratchpad(Scratchpad::span data) const {
   return doReadScratchpad(data, DS28E25);
 }
 
@@ -690,20 +629,19 @@
 }
 
 error_code DS28EL25::writeAuthSegment(int pageNum, int segmentNum,
-                                      const Segment & newData,
-                                      const Hash & mac) {
+                                      Segment::const_span newData,
+                                      Hash::const_span mac) {
   return doWriteAuthSegment(pageNum, segmentNum, newData, mac, DS28E25);
 }
 
-error_code DS28EL25::continueWriteAuthSegment(const Segment & newData,
-                                              const Hash & mac) {
+error_code DS28EL25::continueWriteAuthSegment(Segment::const_span newData,
+                                              Hash::const_span mac) {
   return doContinueWriteAuthSegment(newData, mac, DS28E25);
 }
 
 error_code DS28EL25::readAllBlockProtection(
-    array<BlockProtection, protectionBlocks> & protection) const {
-  return doReadAllBlockProtection(protection.data(), protection.size(),
-                                  DS28E25);
+    span<BlockProtection, protectionBlocks> protection) const {
+  return doReadAllBlockProtection(protection, DS28E25);
 }
 
 error_code DS28E25::loadSecret(bool lock) { return doLoadSecret(lock, false); }