Extended MaximInterface
Dependents: mbed_DS28EC20_GPIO
Diff: Devices/DS28E15_22_25.hpp
- Revision:
- 6:a8c83a2e6fa4
- Parent:
- 0:f77ad7f72d04
- Child:
- 7:471901a04573
--- a/Devices/DS28E15_22_25.hpp Fri Jan 19 10:25:02 2018 -0600 +++ b/Devices/DS28E15_22_25.hpp Wed Jan 23 13:11:04 2019 -0600 @@ -33,10 +33,11 @@ #ifndef MaximInterface_DS28E15_22_25 #define MaximInterface_DS28E15_22_25 +#include <stdint.h> #include <MaximInterface/Links/OneWireMaster.hpp> #include <MaximInterface/Links/SelectRom.hpp> #include <MaximInterface/Links/Sleep.hpp> -#include <MaximInterface/Utilities/array.hpp> +#include <MaximInterface/Utilities/array_span.hpp> #include <MaximInterface/Utilities/Export.h> #include <MaximInterface/Utilities/ManId.hpp> #include <MaximInterface/Utilities/Sha256.hpp> @@ -50,146 +51,43 @@ enum ErrorValue { CrcError = 1, OperationFailure }; /// Holds the contents of a device memory segment. - typedef array<uint_least8_t, 4> Segment; + typedef array_span<uint_least8_t, 4> Segment; /// Holds the contents of a device memory page. - typedef array<uint_least8_t, 32> Page; + typedef array_span<uint_least8_t, 32> Page; /// Number of segments per page. - static const int segmentsPerPage = Page::csize / Segment::csize; + static const int segmentsPerPage = Page::size / Segment::size; /// Holds the contents of the device scratchpad. - typedef array<uint_least8_t, 32> Scratchpad; + typedef array_span<uint_least8_t, 32> Scratchpad; - /// Container for the device personality. + /// Container for the device personality. struct Personality { uint_least8_t PB1; uint_least8_t PB2; - ManId manId; - + ManId::array manId; + bool secretLocked() const { return PB2 & 0x01; } }; /// Represents the status of a memory protection block. - class BlockProtection { - private: - static const unsigned int readProtectionMask = 0x80, - writeProtectionMask = 0x40, - eepromEmulationMask = 0x20, - authProtectionMask = 0x10, - blockNumMask = 0x0F; - uint_least8_t status; - - public: - explicit BlockProtection(uint_least8_t status = 0x00) : status(status) {} - MaximInterface_EXPORT BlockProtection(bool readProtection, - bool writeProtection, - bool eepromEmulation, - bool authProtection, - int blockNum); - - /// Get the byte representation used by the device. - uint_least8_t statusByte() const { return status; } - /// Set the byte representation used by the device. - void setStatusByte(uint_least8_t status) { this->status = status; } - - /// Get the Block Number which is indexed from zero. - int blockNum() const { return (status & blockNumMask); } - /// Set the Block Number which is indexed from zero. - MaximInterface_EXPORT void setBlockNum(int blockNum); - - /// Get the Read Protection status. - /// @returns True if Read Protection is enabled. - bool readProtection() const { - return ((status & readProtectionMask) == readProtectionMask); - } - /// Set the Read Protection status. - MaximInterface_EXPORT void setReadProtection(bool readProtection); - - /// Get the Write Protection status. - /// @returns True if Write Protection is enabled. - bool writeProtection() const { - return ((status & writeProtectionMask) == writeProtectionMask); - } - /// Set the Write Protection status. - MaximInterface_EXPORT void setWriteProtection(bool writeProtection); - - /// Get the EEPROM Emulation Mode status. - /// @returns True if EEPROM Emulation Mode is enabled. - bool eepromEmulation() const { - return ((status & eepromEmulationMask) == eepromEmulationMask); - } - /// Set the EEPROM Emulation Mode status. - MaximInterface_EXPORT void setEepromEmulation(bool eepromEmulation); - - /// Get the Authentication Protection status. - /// @returns True if Authentication Protection is enabled. - bool authProtection() const { - return ((status & authProtectionMask) == authProtectionMask); - } - /// Set the Authentication Protection status. - MaximInterface_EXPORT void setAuthProtection(bool authProtection); - - /// Check if no protection options are enabled. - /// @returns True if no protection options are enabled. - MaximInterface_EXPORT bool noProtection() const; - }; + class BlockProtection; /// Format data to hash for an Authenticated Write to a memory segment. - /// @param pageNum Page number for write operation. - /// @param segmentNum Segment number within page for write operation. - /// @param[in] newData New data to write to the segment. - /// @param[in] oldData Existing data contained in the segment. - /// @param[in] romId 1-Wire ROM ID of the device. - /// @param[in] manId Manufacturer ID of the device. - MaximInterface_EXPORT static Sha256::WriteMacData - createSegmentWriteMacData(int pageNum, int segmentNum, - const Segment & newData, const Segment & oldData, - const RomId & romId, const ManId & manId); + class SegmentWriteMacData; /// Format data to hash for an Authenticated Write to a memory protection block. - /// @param[in] newProtection New protection status to write. - /// @param[in] oldProtection Existing protection status in device. - /// @param[in] romId 1-Wire ROM ID of the device. - /// @param[in] manId Manufacturer ID of the device. - MaximInterface_EXPORT static Sha256::WriteMacData - createProtectionWriteMacData(const BlockProtection & newProtection, - const BlockProtection & oldProtection, - const RomId & romId, const ManId & manId); - - /// Format data to hash to compute the next secret from the existing secret. - /// @param[in] bindingPage Binding data from a device memory page. - /// @param bindingPageNum Number of the page where the binding data is from. - /// @param[in] partialSecret Partial secret data from the device scratchpad. - /// @param[in] romId 1-Wire ROM ID of the device. - /// @param[in] manId Manufacturer ID of the device. - MaximInterface_EXPORT static Sha256::SlaveSecretData - createSlaveSecretData(const Page & bindingPage, int bindingPageNum, - const Scratchpad & partialSecret, const RomId & romId, - const ManId & manId); + class ProtectionWriteMacData; - /// Format data to hash for device authentication. - /// @param[in] pageData Data from a device memory page. - /// @param pageNum Number of the page to use data from. - /// @param[in] challenge Random challenge to prevent replay attacks. - /// @param[in] romId 1-Wire ROM ID of the device. - /// @param[in] manId Manufacturer ID of the device. - MaximInterface_EXPORT static Sha256::AuthMacData - createAuthMacData(const Page & pageData, int pageNum, - const Scratchpad & challenge, const RomId & romId, - const ManId & manId); + /// Format data to hash for device authentication or computing the next secret + /// from the existing secret. + class AuthenticationData; - /// Format datat to hash for device authentication using anonymous mode. - /// @param[in] pageData Data from a device memory page. - /// @param pageNum Number of the page to use data from. - /// @param[in] challenge Random challenge to prevent replay attacks. - /// @param[in] manId Manufacturer ID of the device. - MaximInterface_EXPORT static Sha256::AuthMacData - createAnonAuthMacData(const Page & pageData, int pageNum, - const Scratchpad & challenge, const ManId & manId); - - void setSleep(const Sleep & sleep) { this->sleep = &sleep; } + void setSleep(Sleep & sleep) { this->sleep = &sleep; } + void setMaster(OneWireMaster & master) { this->master = &master; } + void setSelectRom(const SelectRom & selectRom) { this->selectRom = selectRom; } @@ -202,12 +100,13 @@ /// @param segmentNum Segment number within page for read operation. /// @param[out] data Buffer to read data from the segment into. MaximInterface_EXPORT error_code readSegment(int pageNum, int segmentNum, - Segment & data) const; + Segment::span data) const; /// Continue an in-progress readSegment operation. /// @note A CRC16 will encountered after reading the last segment of a page. /// @param[out] data Buffer to read data from the segment into. - MaximInterface_EXPORT error_code continueReadSegment(Segment & data) const; + MaximInterface_EXPORT error_code + continueReadSegment(Segment::span data) const; /// Write memory segment using the Write Memory command. /// @note 1-Wire ROM selection should have already occurred. @@ -215,44 +114,44 @@ /// @param segmentNum Segment number within page for write operation. /// @param[in] data Data to write to the memory segment. MaximInterface_EXPORT error_code writeSegment(int pageNum, int segmentNum, - const Segment & data); + Segment::const_span data); /// Continue an in-progress Write Memory command. /// @param[in] data Data to write to the memory segment. - MaximInterface_EXPORT error_code continueWriteSegment(const Segment & data); + MaximInterface_EXPORT error_code + continueWriteSegment(Segment::const_span data); /// Read memory page using the Read Memory command on the device. /// @param pageNum Page number for write operation. /// @param[out] rdbuf Buffer to read data from the page into. - MaximInterface_EXPORT error_code readPage(int pageNum, Page & rdbuf) const; + MaximInterface_EXPORT error_code readPage(int pageNum, + Page::span rdbuf) const; /// Continue an in-progress readPageOperation. /// @param[out] rdbuf Buffer to read data from the page into. - MaximInterface_EXPORT error_code continueReadPage(Page & rdbuf) const; + MaximInterface_EXPORT error_code continueReadPage(Page::span rdbuf) const; /// Perform a Compute Page MAC command on the device. /// Read back the MAC and verify the CRC16. /// @param pageNum Page number to use for the computation. /// @param anon True to compute in anonymous mode where ROM ID is not used. /// @param[out] mac The device computed MAC. - MaximInterface_EXPORT error_code computeReadPageMac(int pageNum, bool anon, - Sha256::Hash & mac) const; + MaximInterface_EXPORT error_code + computeReadPageMac(int pageNum, bool anon, Sha256::Hash::span mac) const; /// Update the status of a memory protection block using the /// Write Page Protection command. - /// @param[in] Desired protection status for the block. - /// It is not possible to disable existing protections. - /// @param continuing True to continue a previous Write Page Protection command. - /// False to begin a new command. + /// @param protection Desired protection status for the block. + /// It is not possible to disable existing protections. MaximInterface_EXPORT error_code - writeBlockProtection(const BlockProtection & protection); + writeBlockProtection(BlockProtection protection); /// Update the status of a memory protection block using the /// Authenticated Write Page Protection command. - /// @param[in] newProtection New protection status to write. + /// @param newProtection New protection status to write. /// @param[in] mac Write MAC computed for this operation. MaximInterface_EXPORT error_code writeAuthBlockProtection( - const BlockProtection & newProtection, const Sha256::Hash & mac); + BlockProtection newProtection, Sha256::Hash::const_span mac); /// Perform Load and Lock Secret command on the device. /// @note The secret should already be stored in the scratchpad on the device. @@ -274,27 +173,28 @@ protected: enum Variant { DS28E15, DS28E22, DS28E25 }; - DS28E15_22_25(const Sleep & sleep, OneWireMaster & master, + DS28E15_22_25(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : selectRom(selectRom), master(&master), sleep(&sleep) {} + + ~DS28E15_22_25() {} - error_code doWriteScratchpad(const Scratchpad & data, Variant variant); + error_code doWriteScratchpad(Scratchpad::const_span data, Variant variant); - error_code doReadScratchpad(Scratchpad & data, Variant variant) const; + error_code doReadScratchpad(Scratchpad::span data, Variant variant) const; error_code doReadBlockProtection(int blockNum, BlockProtection & protection, Variant variant) const; error_code doWriteAuthSegment(int pageNum, int segmentNum, - const Segment & newData, - const Sha256::Hash & mac, Variant variant); + Segment::const_span newData, + Sha256::Hash::const_span mac, Variant variant); - error_code doContinueWriteAuthSegment(const Segment & newData, - const Sha256::Hash & mac, + error_code doContinueWriteAuthSegment(Segment::const_span newData, + Sha256::Hash::const_span mac, Variant variant); - error_code doReadAllBlockProtection(BlockProtection * protection, - size_t protectionLen, + error_code doReadAllBlockProtection(span<BlockProtection> protection, Variant variant) const; error_code doLoadSecret(bool lock, bool lowPower); @@ -315,8 +215,8 @@ AuthWriteBlockProtection = 0xCC, }; - error_code doWriteAuthSegment(const Segment & newData, - const Sha256::Hash & mac, Variant variant, + error_code doWriteAuthSegment(Segment::const_span newData, + Sha256::Hash::const_span mac, Variant variant, bool continuing); error_code writeCommandWithCrc( @@ -325,23 +225,13 @@ SelectRom selectRom; OneWireMaster * master; - const Sleep * sleep; + Sleep * sleep; }; inline error_code make_error_code(DS28E15_22_25::ErrorValue e) { return error_code(e, DS28E15_22_25::errorCategory()); } -inline bool operator==(DS28E15_22_25::BlockProtection lhs, - DS28E15_22_25::BlockProtection rhs) { - return lhs.statusByte() == rhs.statusByte(); -} - -inline bool operator!=(DS28E15_22_25::BlockProtection lhs, - DS28E15_22_25::BlockProtection rhs) { - return !operator==(lhs, rhs); -} - /// Interface to the DS28EL15 (low power) authenticator. class DS28EL15 : public DS28E15_22_25 { public: @@ -349,17 +239,16 @@ static const int memoryPages = 2; static const int protectionBlocks = 4; - DS28EL15(const Sleep & sleep, OneWireMaster & master, - const SelectRom & selectRom) + DS28EL15(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28E15_22_25(sleep, master, selectRom) {} /// Perform Write Scratchpad operation on the device. /// @param[in] data Data to write to the scratchpad. - MaximInterface_EXPORT error_code writeScratchpad(const Scratchpad & data); + MaximInterface_EXPORT error_code writeScratchpad(Scratchpad::const_span data); /// Perform a Read Scratchpad operation on the device. /// @param[out] data Buffer to read data from the scratchpad into. - MaximInterface_EXPORT error_code readScratchpad(Scratchpad & data) const; + MaximInterface_EXPORT error_code readScratchpad(Scratchpad::span data) const; /// Read the status of a memory protection block using the Read Status command. /// @param blockNum Block number to to read status of. @@ -372,27 +261,26 @@ /// @param segmentNum Segment number within page for write operation. /// @param[in] newData New data to write to the segment. /// @param[in] mac Write MAC computed for this operation. - MaximInterface_EXPORT error_code writeAuthSegment(int pageNum, int segmentNum, - const Segment & newData, - const Sha256::Hash & mac); + MaximInterface_EXPORT error_code + writeAuthSegment(int pageNum, int segmentNum, Segment::const_span newData, + Sha256::Hash::const_span mac); /// Continue an in-progress Authenticated Write Memory command. /// @param[in] newData New data to write to the segment. /// @param[in] mac Write MAC computed for this operation. - MaximInterface_EXPORT error_code - continueWriteAuthSegment(const Segment & newData, const Sha256::Hash & mac); + MaximInterface_EXPORT error_code continueWriteAuthSegment( + Segment::const_span newData, Sha256::Hash::const_span mac); /// Read the status of all memory protection blocks using the Read Status command. /// @param[out] protection Receives protection statuses read from device. MaximInterface_EXPORT error_code readAllBlockProtection( - array<BlockProtection, protectionBlocks> & protection) const; + span<BlockProtection, protectionBlocks> protection) const; }; /// Interface to the DS28E15 authenticator. class DS28E15 : public DS28EL15 { public: - DS28E15(const Sleep & sleep, OneWireMaster & master, - const SelectRom & selectRom) + DS28E15(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28EL15(sleep, master, selectRom) {} /// Perform Load and Lock Secret command on the device. @@ -413,17 +301,16 @@ static const int memoryPages = 8; static const int protectionBlocks = 4; - DS28EL22(const Sleep & sleep, OneWireMaster & master, - const SelectRom & selectRom) + DS28EL22(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28E15_22_25(sleep, master, selectRom) {} /// Perform Write Scratchpad operation on the device. /// @param[in] data Data to write to the scratchpad. - MaximInterface_EXPORT error_code writeScratchpad(const Scratchpad & data); + MaximInterface_EXPORT error_code writeScratchpad(Scratchpad::const_span data); /// Perform a Read Scratchpad operation on the device. /// @param[out] data Buffer to read data from the scratchpad into. - MaximInterface_EXPORT error_code readScratchpad(Scratchpad & data) const; + MaximInterface_EXPORT error_code readScratchpad(Scratchpad::span data) const; /// Read the status of a memory protection block using the Read Status command. /// @param blockNum Block number to to read status of. @@ -436,27 +323,26 @@ /// @param segmentNum Segment number within page for write operation. /// @param[in] newData New data to write to the segment. /// @param[in] mac Write MAC computed for this operation. - MaximInterface_EXPORT error_code writeAuthSegment(int pageNum, int segmentNum, - const Segment & newData, - const Sha256::Hash & mac); + MaximInterface_EXPORT error_code + writeAuthSegment(int pageNum, int segmentNum, Segment::const_span newData, + Sha256::Hash::const_span mac); /// Continue an in-progress Authenticated Write Memory command. /// @param[in] newData New data to write to the segment. /// @param[in] mac Write MAC computed for this operation. - MaximInterface_EXPORT error_code - continueWriteAuthSegment(const Segment & newData, const Sha256::Hash & mac); + MaximInterface_EXPORT error_code continueWriteAuthSegment( + Segment::const_span newData, Sha256::Hash::const_span mac); /// Read the status of all memory protection blocks using the Read Status command. /// @param[out] protection Receives protection statuses read from device. MaximInterface_EXPORT error_code readAllBlockProtection( - array<BlockProtection, protectionBlocks> & protection) const; + span<BlockProtection, protectionBlocks> protection) const; }; /// Interface to the DS28E22 authenticator. class DS28E22 : public DS28EL22 { public: - DS28E22(const Sleep & sleep, OneWireMaster & master, - const SelectRom & selectRom) + DS28E22(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28EL22(sleep, master, selectRom) {} /// Perform Load and Lock Secret command on the device. @@ -477,17 +363,16 @@ static const int memoryPages = 16; static const int protectionBlocks = 8; - DS28EL25(const Sleep & sleep, OneWireMaster & master, - const SelectRom & selectRom) + DS28EL25(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28E15_22_25(sleep, master, selectRom) {} /// Perform Write Scratchpad operation on the device. /// @param[in] data Data to write to the scratchpad. - MaximInterface_EXPORT error_code writeScratchpad(const Scratchpad & data); + MaximInterface_EXPORT error_code writeScratchpad(Scratchpad::const_span data); /// Perform a Read Scratchpad operation on the device. /// @param[out] data Buffer to read data from the scratchpad into. - MaximInterface_EXPORT error_code readScratchpad(Scratchpad & data) const; + MaximInterface_EXPORT error_code readScratchpad(Scratchpad::span data) const; /// Read the status of a memory protection block using the Read Status command. /// @param blockNum Block number to to read status of. @@ -500,27 +385,26 @@ /// @param segmentNum Segment number within page for write operation. /// @param[in] newData New data to write to the segment. /// @param[in] mac Write MAC computed for this operation. - MaximInterface_EXPORT error_code writeAuthSegment(int pageNum, int segmentNum, - const Segment & newData, - const Sha256::Hash & mac); + MaximInterface_EXPORT error_code + writeAuthSegment(int pageNum, int segmentNum, Segment::const_span newData, + Sha256::Hash::const_span mac); /// Continue an in-progress Authenticated Write Memory command. /// @param[in] newData New data to write to the segment. /// @param[in] mac Write MAC computed for this operation. - MaximInterface_EXPORT error_code - continueWriteAuthSegment(const Segment & newData, const Sha256::Hash & mac); + MaximInterface_EXPORT error_code continueWriteAuthSegment( + Segment::const_span newData, Sha256::Hash::const_span mac); /// Read the status of all memory protection blocks using the Read Status command. /// @param[out] protection Receives protection statuses read from device. MaximInterface_EXPORT error_code readAllBlockProtection( - array<BlockProtection, protectionBlocks> & protection) const; + span<BlockProtection, protectionBlocks> protection) const; }; /// Interface to the DS28E25 authenticator. class DS28E25 : public DS28EL25 { public: - DS28E25(const Sleep & sleep, OneWireMaster & master, - const SelectRom & selectRom) + DS28E25(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28EL25(sleep, master, selectRom) {} /// Perform Load and Lock Secret command on the device. @@ -534,6 +418,357 @@ MaximInterface_EXPORT error_code computeSecret(int pageNum, bool lock); }; +class DS28E15_22_25::BlockProtection { +public: + explicit BlockProtection(uint_least8_t status = 0x00) : status(status) {} + + /// Get the byte representation used by the device. + uint_least8_t statusByte() const { return status; } + + /// Set the byte representation used by the device. + BlockProtection & setStatusByte(uint_least8_t status) { + this->status = status; + return *this; + } + + /// Get the Block Number which is indexed from zero. + int blockNum() const { return (status & blockNumMask); } + + /// Set the Block Number which is indexed from zero. + MaximInterface_EXPORT BlockProtection & setBlockNum(int blockNum); + + /// Get the Read Protection status. + /// @returns True if Read Protection is enabled. + bool readProtection() const { + return ((status & readProtectionMask) == readProtectionMask); + } + + /// Set the Read Protection status. + MaximInterface_EXPORT BlockProtection & + setReadProtection(bool readProtection); + + /// Get the Write Protection status. + /// @returns True if Write Protection is enabled. + bool writeProtection() const { + return ((status & writeProtectionMask) == writeProtectionMask); + } + + /// Set the Write Protection status. + MaximInterface_EXPORT BlockProtection & + setWriteProtection(bool writeProtection); + + /// Get the EEPROM Emulation Mode status. + /// @returns True if EEPROM Emulation Mode is enabled. + bool eepromEmulation() const { + return ((status & eepromEmulationMask) == eepromEmulationMask); + } + + /// Set the EEPROM Emulation Mode status. + MaximInterface_EXPORT BlockProtection & + setEepromEmulation(bool eepromEmulation); + + /// Get the Authentication Protection status. + /// @returns True if Authentication Protection is enabled. + bool authProtection() const { + return ((status & authProtectionMask) == authProtectionMask); + } + + /// Set the Authentication Protection status. + MaximInterface_EXPORT BlockProtection & + setAuthProtection(bool authProtection); + + /// Check if no protection options are enabled. + /// @returns True if no protection options are enabled. + MaximInterface_EXPORT bool noProtection() const; + +private: + static const unsigned int readProtectionMask = 0x80, + writeProtectionMask = 0x40, + eepromEmulationMask = 0x20, + authProtectionMask = 0x10, + blockNumMask = 0x0F; + uint_least8_t status; +}; + +inline bool operator==(DS28E15_22_25::BlockProtection lhs, + DS28E15_22_25::BlockProtection rhs) { + return lhs.statusByte() == rhs.statusByte(); +} + +inline bool operator!=(DS28E15_22_25::BlockProtection lhs, + DS28E15_22_25::BlockProtection rhs) { + return !operator==(lhs, rhs); +} + +class DS28E15_22_25::SegmentWriteMacData { +public: + SegmentWriteMacData() : result_() {} + + /// Formatted data result. + Sha256::WriteMacData::const_span result() const { return result_; } + + /// @{ + /// 1-Wire ROM ID of the device. + RomId::span romId() { + return make_span(result_).subspan<romIdIdx, RomId::size>(); + } + + RomId::const_span romId() const { + return const_cast<SegmentWriteMacData &>(*this).romId(); + } + + SegmentWriteMacData & setRomId(RomId::const_span romId) { + copy(romId, this->romId()); + return *this; + } + /// @} + + /// @{ + /// Manufacturer ID of the device. + ManId::span manId() { + return make_span(result_).subspan<manIdIdx, ManId::size>(); + } + + ManId::const_span manId() const { + return const_cast<SegmentWriteMacData &>(*this).manId(); + } + + SegmentWriteMacData & setManId(ManId::const_span manId) { + copy(manId, this->manId()); + return *this; + } + /// @} + + /// @{ + /// Page number for write operation. + int pageNum() const { return result_[pageNumIdx]; } + + SegmentWriteMacData & setPageNum(int pageNum) { + result_[pageNumIdx] = pageNum; + return *this; + } + /// @} + + /// @{ + /// Segment number within page for write operation. + int segmentNum() const { return result_[segmentNumIdx]; } + + SegmentWriteMacData & setSegmentNum(int segmentNum) { + result_[segmentNumIdx] = segmentNum; + return *this; + } + /// @} + + /// @{ + /// Existing data contained in the segment. + Segment::span oldData() { + return make_span(result_).subspan<oldDataIdx, Segment::size>(); + } + + Segment::const_span oldData() const { + return const_cast<SegmentWriteMacData &>(*this).oldData(); + } + + SegmentWriteMacData & setOldData(Segment::const_span oldData) { + copy(oldData, this->oldData()); + return *this; + } + /// @} + + /// @{ + /// New data to write to the segment. + Segment::span newData() { + return make_span(result_).subspan<newDataIdx, Segment::size>(); + } + + Segment::const_span newData() const { + return const_cast<SegmentWriteMacData &>(*this).newData(); + } + + SegmentWriteMacData & setNewData(Segment::const_span newData) { + copy(newData, this->newData()); + return *this; + } + /// @} + +private: + typedef Sha256::WriteMacData::span::index_type index; + + static const index romIdIdx = 0; + static const index manIdIdx = romIdIdx + RomId::size; + static const index pageNumIdx = manIdIdx + ManId::size; + static const index segmentNumIdx = pageNumIdx + 1; + static const index oldDataIdx = segmentNumIdx + 1; + static const index newDataIdx = oldDataIdx + Segment::size; + + Sha256::WriteMacData::array result_; +}; + +class DS28E15_22_25::ProtectionWriteMacData { +public: + MaximInterface_EXPORT ProtectionWriteMacData(); + + /// Formatted data result. + Sha256::WriteMacData::const_span result() const { return result_; } + + /// @{ + /// 1-Wire ROM ID of the device. + RomId::span romId() { + return make_span(result_).subspan<romIdIdx, RomId::size>(); + } + + RomId::const_span romId() const { + return const_cast<ProtectionWriteMacData &>(*this).romId(); + } + + ProtectionWriteMacData & setRomId(RomId::const_span romId) { + copy(romId, this->romId()); + return *this; + } + /// @} + + /// @{ + /// Manufacturer ID of the device. + ManId::span manId() { + return make_span(result_).subspan<manIdIdx, ManId::size>(); + } + + ManId::const_span manId() const { + return const_cast<ProtectionWriteMacData &>(*this).manId(); + } + + ProtectionWriteMacData & setManId(ManId::const_span manId) { + copy(manId, this->manId()); + return *this; + } + /// @} + + /// @{ + /// Existing protection status in device. + BlockProtection oldProtection() const { return oldProtection_; } + + MaximInterface_EXPORT ProtectionWriteMacData & + setOldProtection(BlockProtection oldProtection); + /// @} + + /// @{ + /// New protection status to write. + BlockProtection newProtection() const { return newProtection_; } + + MaximInterface_EXPORT ProtectionWriteMacData & + setNewProtection(BlockProtection newProtection); + /// @} + +private: + typedef Sha256::WriteMacData::span::index_type index; + + static const index romIdIdx = 0; + static const index manIdIdx = romIdIdx + RomId::size; + static const index blockNumIdx = manIdIdx + ManId::size; + static const index oldProtectionIdx = blockNumIdx + 2; + static const index newProtectionIdx = oldProtectionIdx + 4; + + Sha256::WriteMacData::array result_; + BlockProtection oldProtection_; + BlockProtection newProtection_; +}; + +class DS28E15_22_25::AuthenticationData { +public: + AuthenticationData() : result_() {} + + /// Formatted data result. + Sha256::AuthenticationData::const_span result() const { return result_; } + + /// @{ + /// Data from a device memory page. + Page::span page() { + return make_span(result_).subspan<pageIdx, Page::size>(); + } + + Page::const_span page() const { + return const_cast<AuthenticationData &>(*this).page(); + } + + AuthenticationData & setPage(Page::const_span page) { + copy(page, this->page()); + return *this; + } + /// @} + + /// @{ + /// Data from device scratchpad used as a random challenge in device + /// authentication and a partial secret in secret computation. + Scratchpad::span scratchpad() { + return make_span(result_).subspan<scratchpadIdx, Scratchpad::size>(); + } + + Scratchpad::const_span scratchpad() const { + return const_cast<AuthenticationData &>(*this).scratchpad(); + } + + AuthenticationData & setScratchpad(Scratchpad::const_span scratchpad) { + copy(scratchpad, this->scratchpad()); + return *this; + } + /// @} + + /// @{ + /// 1-Wire ROM ID of the device. + RomId::span romId() { + return make_span(result_).subspan<romIdIdx, RomId::size>(); + } + + RomId::const_span romId() const { + return const_cast<AuthenticationData &>(*this).romId(); + } + + AuthenticationData & setRomId(RomId::const_span romId) { + copy(romId, this->romId()); + return *this; + } + + MaximInterface_EXPORT AuthenticationData & setAnonymousRomId(); + /// @} + + /// @{ + /// Manufacturer ID of the device. + ManId::span manId() { + return make_span(result_).subspan<manIdIdx, ManId::size>(); + } + + ManId::const_span manId() const { + return const_cast<AuthenticationData &>(*this).manId(); + } + + AuthenticationData & setManId(ManId::const_span manId) { + copy(manId, this->manId()); + return *this; + } + /// @} + + /// @{ + /// Number of the page to use data from. + int pageNum() const { return result_[pageNumIdx]; } + + AuthenticationData & setPageNum(int pageNum) { + result_[pageNumIdx] = pageNum; + return *this; + } + /// @} + +private: + typedef Sha256::AuthenticationData::span::index_type index; + + static const index pageIdx = 0; + static const index scratchpadIdx = pageIdx + Page::size; + static const index romIdIdx = scratchpadIdx + Scratchpad::size; + static const index manIdIdx = romIdIdx + RomId::size; + static const index pageNumIdx = manIdIdx + ManId::size; + + Sha256::AuthenticationData::array result_; +}; + } // namespace MaximInterface #endif