Extended MaximInterface
Dependents: mbed_DS28EC20_GPIO
Revision 7:471901a04573, committed 2019-03-04
- Comitter:
- IanBenzMaxim
- Date:
- Mon Mar 04 08:10:00 2019 -0600
- Parent:
- 6:a8c83a2e6fa4
- Child:
- 8:211d1b8f730c
- Commit message:
- Updated to version 1.7.
Changed in this revision
--- a/Devices/DS18B20.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS18B20.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -40,7 +40,7 @@ namespace MaximInterface { -/// DS18B20 Programmable Resolution 1-Wire Digital Thermometer +/// @brief DS18B20 Programmable Resolution 1-Wire Digital Thermometer /// @details The DS18B20 digital thermometer provides 9-bit to 12-bit /// Celsius temperature measurements and has an alarm function with /// nonvolatile user-programmable upper and lower trigger points. The @@ -125,6 +125,7 @@ }; /// Reads the current temperature as an integer value with decimal. +/// @param ds18b20 Device to read. /// @param[out] temperature Temperature in degrees Celsius multiplied by 16. MaximInterface_EXPORT error_code readTemperature(DS18B20 & ds18b20, int & temperature);
--- a/Devices/DS1920.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS1920.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -40,7 +40,7 @@ namespace MaximInterface { -/// DS1920 1-Wire Temperature iButton +/// @brief DS1920 1-Wire Temperature iButton /// @details The iButton® temperature logger (DS1920) provides /// direct-to-digital 9-bit temperature readings over a range of /// -55°C to +100°C in 0.5° increments. The iButton communicates with @@ -68,7 +68,7 @@ this->selectRom = selectRom; } - /// Write Scratchpad Command + /// @brief Write Scratchpad Command /// @details If the result of a temperature measurement is higher /// than TH or lower than TL, an alarm flag inside the device is /// set. This flag is updated with every temperature measurement. @@ -79,21 +79,21 @@ MaximInterface_EXPORT error_code writeScratchpad(uint_least8_t th, uint_least8_t tl); - /// Read Scratchpad Command + /// @brief Read Scratchpad Command /// @param[out] scratchpad Contents of scratchpad. MaximInterface_EXPORT error_code readScratchpad(Scratchpad::span scratchpad); - /// Copy Scratchpad Command + /// @brief Copy Scratchpad Command /// @details This command copies from the scratchpad into the /// EEPROM of the DS1920, storing the temperature trigger bytes /// in nonvolatile memory. MaximInterface_EXPORT error_code copyScratchpad(); - /// Convert Temperature Command + /// @brief Convert Temperature Command /// @details This command begins a temperature conversion. MaximInterface_EXPORT error_code convertTemperature(); - /// Recall Command + /// @brief Recall Command /// @details This command recalls the temperature trigger values /// stored in EEPROM to the scratchpad. MaximInterface_EXPORT error_code recallEeprom(); @@ -106,7 +106,8 @@ const Sleep * sleep; }; -/// Reads the current temperature as an integer value. +/// @brief Reads the current temperature as an integer value. +/// @param ds1920 Device to read. /// @param[out] temperature Temperature in degrees Celsius multiplied by 2. MaximInterface_EXPORT error_code readTemperature(DS1920 & ds1920, int & temperature);
--- a/Devices/DS2413.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2413.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -40,7 +40,7 @@ namespace MaximInterface { -/// DS2413 1-Wire Dual Channel Addressable Switch +/// @brief DS2413 1-Wire Dual Channel Addressable Switch /// @details The DS2413 is a dual-channel programmable I/O 1-Wire® /// chip. The PIO outputs are configured as open-drain and provide up /// to 20mA continuous sink capability and off-state operating voltage @@ -88,14 +88,13 @@ OneWireMaster * master; }; -/// @{ -/// Write the output logic state for only a single PIO pin. +/// Write the output logic state for only PIOA. MaximInterface_EXPORT error_code writePioAOutputState(DS2413 & ds2413, bool pioAState); - + +/// Write the output logic state for only PIOB. MaximInterface_EXPORT error_code writePioBOutputState(DS2413 & ds2413, bool pioBState); -/// @} inline error_code make_error_code(DS2413::ErrorValue e) { return error_code(e, DS2413::errorCategory());
--- a/Devices/DS2431.cpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2431.cpp Mon Mar 04 08:10:00 2019 -0600 @@ -55,59 +55,59 @@ error_code DS2431::readMemory(Address beginAddress, span<uint_least8_t> data) const { - error_code owmResult = selectRom(*master); - if (owmResult) { - return owmResult; + error_code result = selectRom(*master); + if (result) { + return result; } const uint_least8_t sendBlock[] = {0xF0, beginAddress, 0x00}; - owmResult = master->writeBlock(sendBlock); - if (owmResult) { - return owmResult; + result = master->writeBlock(sendBlock); + if (result) { + return result; } - owmResult = master->readBlock(data); - return owmResult; + result = master->readBlock(data); + return result; } error_code DS2431::writeScratchpad(Address targetAddress, Scratchpad::const_span data) { - error_code owmResult = selectRom(*master); - if (owmResult) { - return owmResult; + error_code result = selectRom(*master); + if (result) { + return result; } uint_least8_t block[3 + Scratchpad::size] = {0x0F, targetAddress, 0x00}; std::copy(data.begin(), data.end(), block + 3); - owmResult = master->writeBlock(block); - if (owmResult) { - return owmResult; + result = master->writeBlock(block); + if (result) { + return result; } const uint_fast16_t calculatedCrc = calculateCrc16(block) ^ 0xFFFFU; - owmResult = master->readBlock(make_span(block, 2)); - if (owmResult) { - return owmResult; + result = master->readBlock(make_span(block, 2)); + if (result) { + return result; } if (calculatedCrc != ((static_cast<uint_fast16_t>(block[1]) << 8) | block[0])) { - owmResult = make_error_code(CrcError); + result = make_error_code(CrcError); } - return owmResult; + return result; } error_code DS2431::readScratchpad(Scratchpad::span data, uint_least8_t & esByte) { typedef array<uint_least8_t, 6 + Scratchpad::size> Block; - error_code owmResult = selectRom(*master); - if (owmResult) { - return owmResult; + error_code result = selectRom(*master); + if (result) { + return result; } Block block = {0xAA}; - owmResult = master->writeByte(block.front()); - if (owmResult) { - return owmResult; + result = master->writeByte(block.front()); + if (result) { + return result; } - owmResult = master->readBlock(make_span(block.data() + 1, block.size() - 1)); - if (owmResult) { - return owmResult; + result = master->readBlock(make_span(block).subspan(1)); + if (result) { + return result; } Block::const_iterator blockIt = block.end(); uint_fast16_t receivedCrc = static_cast<uint_fast16_t>(*(--blockIt)) << 8; @@ -120,38 +120,38 @@ std::copy(blockIt, blockItEnd, data.begin()); esByte = *(--blockIt); } else { - owmResult = make_error_code(CrcError); + result = make_error_code(CrcError); } - return owmResult; + return result; } error_code DS2431::copyScratchpad(Address targetAddress, uint_least8_t esByte) { - error_code owmResult = selectRom(*master); - if (owmResult) { - return owmResult; + error_code result = selectRom(*master); + if (result) { + return result; } uint_least8_t block[] = {0x55, targetAddress, 0x00}; - owmResult = master->writeBlock(block); - if (owmResult) { - return owmResult; + result = master->writeBlock(block); + if (result) { + return result; } - owmResult = master->writeByteSetLevel(esByte, OneWireMaster::StrongLevel); - if (owmResult) { - return owmResult; + result = master->writeByteSetLevel(esByte, OneWireMaster::StrongLevel); + if (result) { + return result; } sleep->invoke(10); - owmResult = master->setLevel(OneWireMaster::NormalLevel); - if (owmResult) { - return owmResult; + result = master->setLevel(OneWireMaster::NormalLevel); + if (result) { + return result; } - owmResult = master->readByte(block[0]); - if (owmResult) { - return owmResult; + result = master->readByte(block[0]); + if (result) { + return result; } if (block[0] != 0xAA) { - owmResult = make_error_code(OperationFailure); + result = make_error_code(OperationFailure); } - return owmResult; + return result; } const error_category & DS2431::errorCategory() { @@ -165,11 +165,9 @@ return "CRC Error"; case OperationFailure: - return "Operation Failure"; - - default: - return defaultErrorMessage(condition); + return "Operation Failure"; } + return defaultErrorMessage(condition); } } instance; return instance;
--- a/Devices/DS2431.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2431.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -40,7 +40,7 @@ namespace MaximInterface { -/// DS2431 1024-bit 1-Wire EEPROM +/// @brief DS2431 1024-bit 1-Wire EEPROM /// @details The DS2431 is a 1024-bit, 1-Wire® EEPROM chip organized /// as four memory pages of 256 bits each. Data is written to an 8-byte /// scratchpad, verified, and then copied to the EEPROM memory. As a @@ -70,26 +70,27 @@ this->selectRom = selectRom; } - /// Reads block of data from EEPROM memory. + /// @brief Reads block of data from EEPROM memory. /// @param[in] beginAddress EEPROM memory address to start reading from. /// @param[out] data EEPROM data read from the device. MaximInterface_EXPORT error_code readMemory(Address beginAddress, span<uint_least8_t> data) const; - /// Writes 8 bytes to the scratchpad. - /// @param[in] targetAddress EEPROM memory address that this data. - /// will be copied to. Must be on row boundary. + /// @brief Writes 8 bytes to the scratchpad. + /// @param[in] targetAddress + /// EEPROM memory address that this data will be copied to. + /// Must be on row boundary. /// @param[in] data Data to write to scratchpad. MaximInterface_EXPORT error_code writeScratchpad(Address targetAddress, Scratchpad::const_span data); - /// Reads contents of scratchpad. + /// @brief Reads contents of scratchpad. /// @param[out] data Data read from scratchpad. /// @param[out] esByte E/S byte read before scratchpad data. MaximInterface_EXPORT error_code readScratchpad(Scratchpad::span data, uint_least8_t & esByte); - /// Copies contents of scratchpad to EEPROM. + /// @brief Copies contents of scratchpad to EEPROM. /// @param[in] targetAddress EEPROM memory address that scratchpad /// will be copied to. Must be on row boundary. /// @param[in] esByte E/S byte from preceding Read Scratchpad command. @@ -104,8 +105,10 @@ const Sleep * sleep; }; +/// @brief /// Writes data to EEPROM using Write Scratchpad, Read Scratchpad, /// and Copy Scratchpad commands. +/// @param device Device to write. /// @param[in] targetAddress EEPROM memory address to start writing at. /// @param[in] data Data to write to EEPROM. MaximInterface_EXPORT error_code writeMemory(DS2431 & device,
--- a/Devices/DS2465.cpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2465.cpp Mon Mar 04 08:10:00 2019 -0600 @@ -206,9 +206,7 @@ return error_code(); } // Set the level - Config newConfig = curConfig; - newConfig.setSPU(level == StrongLevel); - return writeConfig(newConfig); + return writeConfig(Config(curConfig).setSPU(level == StrongLevel)); } error_code DS2465::setLevel(Level newLevel) { @@ -229,9 +227,7 @@ return error_code(); } // Set the speed - Config newConfig = curConfig; - newConfig.set1WS(newSpeed == OverdriveSpeed); - return writeConfig(newConfig); + return writeConfig(Config(curConfig).set1WS(newSpeed == OverdriveSpeed)); } error_code DS2465::triplet(TripletData & data) {
--- a/Devices/DS2465.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2465.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -47,7 +47,7 @@ public: enum ErrorValue { HardwareError = 1, ArgumentOutOfRangeError }; - /// 1-Wire port adjustment parameters. + /// @brief 1-Wire port adjustment parameters. /// @note See datasheet page 13. enum PortParameter { tRSTL_STD, @@ -80,10 +80,14 @@ explicit Config(uint_least8_t readByte = optionAPU) : readByte_(readByte & 0xF) {} + /// @name 1WS + /// @brief 1-Wire Speed /// @{ - /// 1-Wire Speed + + /// Get 1WS bit. bool get1WS() const { return (readByte_ & option1WS) == option1WS; } + /// Set 1WS bit. Config & set1WS(bool new1WS) { if (new1WS) { readByte_ |= option1WS; @@ -92,12 +96,17 @@ } return *this; } + /// @} + /// @name SPU + /// @brief Strong Pullup /// @{ - /// Strong Pullup + + /// Get SPU bit. bool getSPU() const { return (readByte_ & optionSPU) == optionSPU; } + /// Set SPU bit. Config & setSPU(bool newSPU) { if (newSPU) { readByte_ |= optionSPU; @@ -106,12 +115,17 @@ } return *this; } + /// @} + /// @name PDN + /// @brief 1-Wire Power Down /// @{ - /// 1-Wire Power Down + + /// Get PDN bit. bool getPDN() const { return (readByte_ & optionPDN) == optionPDN; } + /// Set PDN bit. Config & setPDN(bool newPDN) { if (newPDN) { readByte_ |= optionPDN; @@ -120,12 +134,17 @@ } return *this; } + /// @} + /// @name APU + /// @brief Active Pullup /// @{ - /// Active Pullup + + /// Get APU bit. bool getAPU() const { return (readByte_ & optionAPU) == optionAPU; } + /// Set APU bit. Config & setAPU(bool newAPU) { if (newAPU) { readByte_ |= optionAPU; @@ -134,6 +153,7 @@ } return *this; } + /// @} /// Byte representation that is read from the DS2465. @@ -166,14 +186,14 @@ /// Initialize hardware for use. MaximInterface_EXPORT error_code initialize(Config config = Config()); - /// Write a new configuration to the DS2465. + /// @brief Write a new configuration to the DS2465. /// @param[in] config New configuration to write. MaximInterface_EXPORT error_code writeConfig(Config config); - /// Write a new port configuration parameter to the DS2465. + /// @brief Write a new port configuration parameter to the DS2465. /// @param[in] param Parameter to adjust. - /// @param[in] val New parameter value to set. Consult datasheet for value - /// mappings. + /// @param[in] val + /// New parameter value to set. Consult datasheet for value mappings. MaximInterface_EXPORT error_code writePortParameter(PortParameter param, int val); @@ -198,26 +218,31 @@ MaximInterface_EXPORT virtual error_code setSpeed(Speed newSpeed); - /// @note The DS2465 only supports enabling strong pullup following a 1-Wire - /// read or write operation. + /// @copydoc OneWireMaster::setLevel + /// @note + /// The DS2465 only supports enabling strong pullup following a 1-Wire read or + /// write operation. MaximInterface_EXPORT virtual error_code setLevel(Level newLevel); MaximInterface_EXPORT virtual error_code triplet(TripletData & data); // DS2465 Coprocessor Commands - /// Read data from an EEPROM memory page. + /// @brief Read data from an EEPROM memory page. /// @param pageNum Page number to read from. + /// @param[out] data Data that was read. MaximInterface_EXPORT error_code readPage(int pageNum, Page::span data) const; - /// Write data to an EEPROM memory page. + /// @brief Write data to an EEPROM memory page. /// @param pageNum Page number to copy to. + /// @param data Data to write. MaximInterface_EXPORT error_code writePage(int pageNum, Page::const_span data); - /// Write data to an EEPROM memory segment. + /// @brief Write data to an EEPROM memory segment. /// @param pageNum Page number to copy to. /// @param segmentNum Segment number to copy to. + /// @param data Data to write. MaximInterface_EXPORT error_code writeSegment(int pageNum, int segmentNum, Segment::const_span data); @@ -225,12 +250,12 @@ MaximInterface_EXPORT error_code writeMasterSecret(Sha256::Hash::const_span masterSecret); - /// Compute Next Master Secret. + /// @brief Compute Next Master Secret. /// @param data Combined data fields for computation. MaximInterface_EXPORT error_code computeNextMasterSecret(Sha256::AuthenticationData::const_span data); - /// Compute Next Master Secret with page swapping. + /// @brief Compute Next Master Secret with page swapping. /// @param data Combined data fields for computation. /// @param pageNum Page number to swap in. /// @param region Region of the page to swap in. @@ -238,18 +263,18 @@ computeNextMasterSecretWithSwap(Sha256::AuthenticationData::const_span data, int pageNum, PageRegion region); - /// Compute Write MAC. + /// @brief Compute Write MAC. /// @param data Combined data fields for computation. /// @param[out] mac Computed Write MAC. MaximInterface_EXPORT error_code computeWriteMac( Sha256::WriteMacData::const_span data, Sha256::Hash::span mac) const; - /// Compute Write MAC. + /// @brief Compute Write MAC. /// @param data Combined data fields for computation. MaximInterface_EXPORT error_code computeAndTransmitWriteMac(Sha256::WriteMacData::const_span data) const; - /// Compute Write MAC with page swapping. + /// @brief Compute Write MAC with page swapping. /// @param data Combined data fields for computation. /// @param pageNum Page number to swap in. /// @param segmentNum Segment number to swap in. @@ -258,19 +283,19 @@ computeWriteMacWithSwap(Sha256::WriteMacData::const_span data, int pageNum, int segmentNum, Sha256::Hash::span mac) const; - /// Compute Write MAC with page swapping. + /// @brief Compute Write MAC with page swapping. /// @param data Combined data fields for computation. /// @param pageNum Page number to swap in. /// @param segmentNum Segment number to swap in. MaximInterface_EXPORT error_code computeAndTransmitWriteMacWithSwap( Sha256::WriteMacData::const_span data, int pageNum, int segmentNum) const; - /// Compute Slave Secret (S-Secret). + /// @brief Compute Slave Secret (S-Secret). /// @param data Combined data fields for computation. MaximInterface_EXPORT error_code computeSlaveSecret(Sha256::AuthenticationData::const_span data); - /// Compute Slave Secret (S-Secret) with page swapping. + /// @brief Compute Slave Secret (S-Secret) with page swapping. /// @param data Combined data fields for computation. /// @param pageNum Page number to swap in. /// @param region Region of the page to swap in. @@ -278,19 +303,19 @@ computeSlaveSecretWithSwap(Sha256::AuthenticationData::const_span data, int pageNum, PageRegion region); - /// Compute Authentication MAC. + /// @brief Compute Authentication MAC. /// @param data Combined data fields for computation. /// @param[out] mac Computed Auth MAC. MaximInterface_EXPORT error_code computeAuthMac(Sha256::AuthenticationData::const_span data, Sha256::Hash::span mac) const; - /// Compute Authentication MAC. + /// @brief Compute Authentication MAC. /// @param data Combined data fields for computation. MaximInterface_EXPORT error_code computeAndTransmitAuthMac(Sha256::AuthenticationData::const_span data) const; - /// Compute Authentication MAC with page swapping. + /// @brief Compute Authentication MAC with page swapping. /// @param data Combined data fields for computation. /// @param pageNum Page number to swap in. /// @param region Region of the page to swap in. @@ -299,7 +324,7 @@ Sha256::AuthenticationData::const_span data, int pageNum, PageRegion region, Sha256::Hash::span mac) const; - /// Compute Authentication MAC with page swapping. + /// @brief Compute Authentication MAC with page swapping. /// @param data Combined data fields for computation. /// @param pageNum Page number to swap in. /// @param region Region of the page to swap in. @@ -315,29 +340,31 @@ uint_least8_t address_; Config curConfig; - /// Performs a soft reset on the DS2465. + /// @brief Performs a soft reset on the DS2465. /// @note This is not a 1-Wire Reset. error_code resetDevice(); - /// Polls the DS2465 status waiting for the 1-Wire Busy bit (1WB) to be cleared. + /// @brief + /// Polls the DS2465 status waiting for the 1-Wire Busy bit (1WB) to be + /// cleared. /// @param[out] pStatus Optionally retrive the status byte when 1WB cleared. /// @returns Success or TimeoutError if poll limit reached. error_code pollBusy(uint_least8_t * pStatus = NULL) const; - /// Ensure that the desired 1-Wire level is set in the configuration. + /// @brief Ensure that the desired 1-Wire level is set in the configuration. /// @param level Desired 1-Wire level. error_code configureLevel(Level level); - /// Const since only for internal use. + /// @note Const since only for internal use. error_code writeMemory(uint_least8_t addr, span<const uint_least8_t> buf) const; - /// Read memory from the DS2465. + /// @brief Read memory from the DS2465. /// @param addr Address to begin reading from. /// @param[out] buf Buffer to hold read data. error_code readMemory(uint_least8_t addr, span<uint_least8_t> buf) const; - /// Read memory from the DS2465 at the current pointer. + /// @brief Read memory from the DS2465 at the current pointer. /// @param[out] buf Buffer to hold read data. error_code readMemory(span<uint_least8_t> buf) const;
--- a/Devices/DS2482_DS2484.cpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2482_DS2484.cpp Mon Mar 04 08:10:00 2019 -0600 @@ -222,9 +222,7 @@ return error_code(); } // Set the speed - Config newConfig = curConfig; - newConfig.set1WS(newSpeed == OverdriveSpeed); - return writeConfig(newConfig); + return writeConfig(Config(curConfig).set1WS(newSpeed == OverdriveSpeed)); } error_code DS2482_DS2484::setLevel(Level newLevel) { @@ -297,9 +295,7 @@ return error_code(); } // Set the level - Config newConfig = curConfig; - newConfig.setSPU(level == StrongLevel); - return writeConfig(newConfig); + return writeConfig(Config(curConfig).setSPU(level == StrongLevel)); } error_code DS2482_DS2484::sendCommand(uint_least8_t cmd) const { @@ -412,7 +408,7 @@ } uint_least8_t portConfig = val + 1; - for (int numReads = -1; numReads < param; numReads++) { + for (int reads = -1; reads < param; ++reads) { result = readRegister(portConfig); if (result) { return result;
--- a/Devices/DS2482_DS2484.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS2482_DS2484.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -51,10 +51,14 @@ explicit Config(uint_least8_t readByte = optionAPU) : readByte_(readByte & 0xF) {} + /// @name 1WS + /// @brief 1-Wire Speed /// @{ - /// 1-Wire Speed + + /// Get 1WS bit. bool get1WS() const { return (readByte_ & option1WS) == option1WS; } + /// Set 1WS bit. Config & set1WS(bool new1WS) { if (new1WS) { readByte_ |= option1WS; @@ -63,12 +67,17 @@ } return *this; } + /// @} + /// @name SPU + /// @brief Strong Pullup /// @{ - /// Strong Pullup + + /// Get SPU bit. bool getSPU() const { return (readByte_ & optionSPU) == optionSPU; } + /// Set SPU bit. Config & setSPU(bool newSPU) { if (newSPU) { readByte_ |= optionSPU; @@ -77,12 +86,17 @@ } return *this; } + /// @} + /// @name PDN + /// @brief 1-Wire Power Down /// @{ - /// 1-Wire Power Down + + /// Get PDN bit. bool getPDN() const { return (readByte_ & optionPDN) == optionPDN; } + /// Set PDN bit. Config & setPDN(bool newPDN) { if (newPDN) { readByte_ |= optionPDN; @@ -91,12 +105,17 @@ } return *this; } + /// @} + /// @name APU + /// @brief Active Pullup /// @{ - /// Active Pullup + + /// Get APU bit. bool getAPU() const { return (readByte_ & optionAPU) == optionAPU; } + /// Set APU bit. Config & setAPU(bool newAPU) { if (newAPU) { readByte_ |= optionAPU; @@ -105,6 +124,7 @@ } return *this; } + /// @} /// Byte representation that is read from the device. @@ -128,11 +148,10 @@ /// Initialize hardware for use. MaximInterface_EXPORT error_code initialize(Config config = Config()); - /// Write a new configuration to the device. + /// @brief Write a new configuration to the device. /// @param[in] config New configuration to write. MaximInterface_EXPORT error_code writeConfig(Config config); - /// @note Perform a 1-Wire triplet using the device command. MaximInterface_EXPORT virtual error_code triplet(TripletData & data); MaximInterface_EXPORT virtual error_code reset(); @@ -162,26 +181,27 @@ /// @note Allow marking const since not public. error_code sendCommand(uint_least8_t cmd, uint_least8_t param) const; - /// Reads a register from the device. + /// @brief Reads a register from the device. /// @param reg Register to read from. /// @param[out] buf Buffer to hold read data. error_code readRegister(uint_least8_t reg, uint_least8_t & buf) const; - /// Reads the current register from the device. + /// @brief Reads the current register from the device. /// @param[out] buf Buffer to hold read data. error_code readRegister(uint_least8_t & buf) const; private: - /// Performs a soft reset on the device. + /// @brief Performs a soft reset on the device. /// @note This is not a 1-Wire Reset. error_code resetDevice(); + /// @brief /// Polls the device status waiting for the 1-Wire Busy bit (1WB) to be cleared. /// @param[out] pStatus Optionally retrieve the status byte when 1WB cleared. /// @returns Success or TimeoutError if poll limit reached. error_code pollBusy(uint_least8_t * pStatus = NULL); - /// Ensure that the desired 1-Wire level is set in the configuration. + /// @brief Ensure that the desired 1-Wire level is set in the configuration. /// @param level Desired 1-Wire level. error_code configureLevel(Level level); @@ -206,7 +226,7 @@ DS2482_800(I2CMaster & i2c_bus, uint_least8_t adrs) : DS2482_DS2484(i2c_bus, adrs) {} - /// Select the active 1-Wire channel. + /// @brief Select the active 1-Wire channel. /// @param channel Channel number to select from 0 to 7. MaximInterface_EXPORT error_code selectChannel(int channel); }; @@ -214,7 +234,7 @@ /// DS2484 I2C to 1-Wire Master class DS2484 : public DS2482_DS2484 { public: - /// 1-Wire port adjustment parameters. + /// @brief 1-Wire port adjustment parameters. /// @note See datasheet page 13. enum PortParameter { tRSTL = 0, @@ -230,7 +250,7 @@ explicit DS2484(I2CMaster & i2c_bus, uint_least8_t adrs = 0x30) : DS2482_DS2484(i2c_bus, adrs) {} - /// Adjust 1-Wire port parameters. + /// @brief Adjust 1-Wire port parameters. /// @param param Parameter to adjust. /// @param val New parameter value to set. Consult datasheet for value mappings. MaximInterface_EXPORT error_code adjustPort(PortParameter param, int val);
--- a/Devices/DS28C36_DS2476.cpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS28C36_DS2476.cpp Mon Mar 04 08:10:00 2019 -0600 @@ -670,9 +670,10 @@ error_code readRomIdAndManId(DS28C36 & ds28c36, RomId::span romId, ManId::span manId) { - DS28C36::RomOptions romOptions; - error_code result = ds28c36.readMemory(DS28C36::romOptionsPage, romOptions); + DS28C36::Page::array page; + error_code result = ds28c36.readMemory(DS28C36::romOptionsPage, page); if (!result) { + const DS28C36::RomOptions romOptions(page); copy(romOptions.romId(), romId); copy(romOptions.manId(), manId); } @@ -680,12 +681,26 @@ } error_code enableCoprocessor(DS2476 & ds2476) { - DS2476::GpioControl gpioControl; - error_code result = ds2476.readMemory(DS2476::gpioControlPage, gpioControl); + DS2476::Page::array page; + error_code result = ds2476.readMemory(DS2476::gpioControlPage, page); if (!result) { + DS2476::GpioControl gpioControl(page); if (!gpioControl.pioaConducting()) { gpioControl.setPioaConducting(true); - result = ds2476.writeMemory(DS2476::gpioControlPage, gpioControl); + result = ds2476.writeMemory(DS2476::gpioControlPage, page); + } + } + return result; +} + +error_code enableRomId(DS2476 & ds2476) { + DS2476::Page::array page; + error_code result = ds2476.readMemory(DS2476::romOptionsPage, page); + if (!result) { + DS2476::RomOptions romOptions(page); + if (!romOptions.romBlockDisable()) { + romOptions.setRomBlockDisable(true); + result = ds2476.writeMemory(DS2476::romOptionsPage, page); } } return result;
--- a/Devices/DS28C36_DS2476.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS28C36_DS2476.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -61,7 +61,9 @@ InvalidResponseError = 0x101 ///< Response does not match expected format. }; - // Device memory pages. + /// @name Device memory pages + /// @{ + static const int publicKeyAxPage = 16; static const int publicKeyAyPage = 17; static const int publicKeyBxPage = 18; @@ -78,6 +80,8 @@ static const int gpioControlPage = 29; static const int publicKeySxPage = 30; static const int publicKeySyPage = 31; + + /// @} /// Number of memory pages on the device. static const int memoryPages = 32; @@ -101,24 +105,22 @@ /// Holds a device memory page. typedef array_span<uint_least8_t, 32> Page; - /// Format page authentication input data. + // Format page authentication input data. class PageAuthenticationData; - /// Format authenticated write input data. + // Format authenticated write input data. class WriteAuthenticationData; - /// Format compute secret input data. + // Format compute secret input data. class ComputeSecretData; - /// Format encryption or decryption HMAC input data. + // Format encryption or decryption HMAC input data. class EncryptionHmacData; - /// Access fields in the ROM Options page. Can be used with writeMemory and - /// readMemory functions. + // Access fields in the ROM Options page. class RomOptions; - /// Access fields in the GPIO Control page. Can be used with writeMemory and - /// readMemory functions. + // Access fields in the GPIO Control page. class GpioControl; /// Page protection types. @@ -148,33 +150,33 @@ void setAddress(uint_least8_t address) { address_ = address & 0xFE; } - /// Write memory with no protection. + /// @brief Write memory with no protection. /// @param pageNum Number of page to write. /// @param page Data to write. MaximInterface_EXPORT error_code writeMemory(int pageNum, Page::const_span page); - /// Read memory with no protection. + /// @brief Read memory with no protection. /// @param pageNum Number of page to read. /// @param[out] page Data that was read. MaximInterface_EXPORT error_code readMemory(int pageNum, Page::span page); - /// Write the temporary buffer. + /// @brief Write the temporary buffer. /// @param data Data to write. MaximInterface_EXPORT error_code writeBuffer(span<const uint_least8_t> data); - /// Read the temporary buffer. + /// @brief Read the temporary buffer. /// @param[out] data Data that was read. MaximInterface_EXPORT error_code readBuffer(std::vector<uint_least8_t> & data); - /// Read the protection settings of a page. + /// @brief Read the protection settings of a page. /// @param pageNum Number of page to read. /// @param[out] protection Protection that was read. MaximInterface_EXPORT error_code readPageProtection(int pageNum, PageProtection & protection); - /// Set the protection settings of a page. + /// @brief Set the protection settings of a page. /// @param pageNum Number of page to write. /// @param protection Protection to write. MaximInterface_EXPORT error_code @@ -183,11 +185,11 @@ /// Decrement the decrement-only counter. MaximInterface_EXPORT error_code decrementCounter(); - /// Read a block of random data from the RNG. + /// @brief Read a block of random data from the RNG. /// @param[out] data Random data from RNG with length from 1 to 64. MaximInterface_EXPORT error_code readRng(span<uint_least8_t> data); - /// Read memory with encryption. + /// @brief Read memory with encryption. /// @param pageNum Number of page to read from. /// @param secretNum Secret to use for encryption. /// @param[out] challenge Encryption challenge that was read. @@ -196,29 +198,30 @@ encryptedReadMemory(int pageNum, SecretNum secretNum, EncryptionChallenge::span challenge, Page::span data); - /// Compute and read page authentication with ECDSA. + /// @brief Compute and read page authentication with ECDSA. /// @param pageNum Number of page to authenticate. - /// @param keyNum Private key to use for authentication. + /// @param keyNum + /// Private key to use for authentication. /// Key S cannot be used with this command. /// @param[out] signature Computed page signature. MaximInterface_EXPORT error_code computeAndReadPageAuthentication( int pageNum, KeyNum keyNum, Ecc256::Signature::span signature); - /// Compute and read page authentication with HMAC. + /// @brief Compute and read page authentication with HMAC. /// @param pageNum Number of page to authenticate. /// @param secretNum Secret to use for authentication. /// @param[out] hmac Computed page HMAC. MaximInterface_EXPORT error_code computeAndReadPageAuthentication( int pageNum, SecretNum secretNum, Sha256::Hash::span hmac); - /// Write with SHA2 authentication. + /// @brief Write with SHA2 authentication. /// @param pageNum Number of page to write. /// @param secretNum Secret to use for authentication. /// @param page Data to write. MaximInterface_EXPORT error_code authenticatedSha2WriteMemory( int pageNum, SecretNum secretNum, Page::const_span page); - /// Compute SHA2 secret and optionally lock. + /// @brief Compute SHA2 secret and optionally lock. /// @param pageNum Number of page to use in computation. /// @param msecretNum Master secret to use in computation. /// @param dsecretNum Destination secret to receive the computation result. @@ -228,13 +231,13 @@ computeAndLockSha2Secret(int pageNum, SecretNum msecretNum, SecretNum dsecretNum, bool writeProtectEnable); - /// Generate a new ECDSA key pair. + /// @brief Generate a new ECDSA key pair. /// @param keyNum Key to generate. Key S cannot be used with this command. /// @param writeProtectEnable True to lock the key against further writes. MaximInterface_EXPORT error_code generateEcc256KeyPair(KeyNum keyNum, bool writeProtectEnable); - /// Compute a hash over multiple blocks. + /// @brief Compute a hash over multiple blocks. /// @param firstBlock True if this is the first block being hashed. /// @param lastBlock True if this is the last block being hashed. /// @param data @@ -242,7 +245,7 @@ MaximInterface_EXPORT error_code computeMultiblockHash( bool firstBlock, bool lastBlock, span<const uint_least8_t> data); - /// Verify ECDSA signature. + /// @brief Verify ECDSA signature. /// @param keyNum Public key to use for verification. /// @param hashType Source of the data hash input. /// @param signature Signature to verify. @@ -252,18 +255,20 @@ KeyNum keyNum, HashType hashType, Ecc256::Signature::const_span signature, PioState pioa = Unchanged, PioState piob = Unchanged); - /// Authenticate a public key for authenticated writes or encrypted reads with ECDH. + /// @brief + /// Authenticate a public key for authenticated writes or encrypted reads + /// with ECDH. /// @param authWrites True to select authentication for writes. /// @param ecdh True to select ECDH key exchange. - /// @param keyNum Private key to use for ECDH key exchange. - /// Key A or B can be selected. + /// @param keyNum + /// Private key to use for ECDH key exchange. Key A or B can be selected. /// @param csOffset Certificate customization field ending offset in buffer. /// @param signature Signature to use for authentication of public key S. MaximInterface_EXPORT error_code authenticateEcdsaPublicKey( bool authWrites, bool ecdh, KeyNum keyNum, int csOffset, Ecc256::Signature::const_span signature); - /// Write with ECDSA authentication. + /// @brief Write with ECDSA authentication. /// @param pageNum Number of page to write. /// @param page Data to write. MaximInterface_EXPORT error_code @@ -316,19 +321,20 @@ DS2476(Sleep & sleep, I2CMaster & master, uint_least8_t address = 0x76) : DS28C36(sleep, master, address) {} - /// Generate ECDSA signature. - /// @param keyNum Private key to use to create signature. + /// @brief Generate ECDSA signature. + /// @param keyNum + /// Private key to use to create signature. /// Key S cannot be used with this command. /// @param[out] signature Computed signature. MaximInterface_EXPORT error_code generateEcdsaSignature(KeyNum keyNum, Ecc256::Signature::span signature); - /// Compute unique SHA2 secret. + /// @brief Compute unique SHA2 secret. /// @param msecretNum Master secret to use in computation. MaximInterface_EXPORT error_code computeSha2UniqueSecret(SecretNum msecretNum); - /// Compute SHA2 HMAC. + /// @brief Compute SHA2 HMAC. /// @param[out] hmac Computed HMAC. MaximInterface_EXPORT error_code computeSha2Hmac(Sha256::Hash::span hmac); }; @@ -337,12 +343,15 @@ return error_code(e, DS28C36::errorCategory()); } +/// @brief /// Hash arbitrary length data with successive Compute Multiblock Hash commands. +/// @param ds28c36 Device for computation. /// @param data Data to hash. MaximInterface_EXPORT error_code computeMultiblockHash(DS28C36 & ds28c36, span<const uint_least8_t> data); -/// Verify ECDSA signature. +/// @brief Verify ECDSA signature. +/// @param ds28c36 Device for computation. /// @param publicKey Public key to use for verification. /// @param data Data to verify. /// @param signature Signature to verify. @@ -354,7 +363,8 @@ DS28C36::PioState pioa = DS28C36::Unchanged, DS28C36::PioState piob = DS28C36::Unchanged); -/// Verify ECDSA signature. +/// @brief Verify ECDSA signature. +/// @param ds28c36 Device for computation. /// @param publicKey /// Public key to use for verification which is loaded into Public Key S. /// @param data Data to verify. @@ -367,18 +377,27 @@ DS28C36::PioState pioa = DS28C36::Unchanged, DS28C36::PioState piob = DS28C36::Unchanged); +/// @brief /// Read the device ROM ID and MAN ID using the Read Memory command on the /// ROM Options page. +/// @param ds28c36 Device to read. /// @param[out] romId Read ROM ID valid when operation is successful. /// @param[out] manId Read MAN ID valid when operation is successful. MaximInterface_EXPORT error_code readRomIdAndManId(DS28C36 & ds28c36, RomId::span romId, ManId::span manId); +/// @brief /// Enable coprocessor functionality on the DS2476 by writing to the -/// ROM Options page. +/// GPIO Control page. MaximInterface_EXPORT error_code enableCoprocessor(DS2476 & ds2476); +/// @brief +/// Disable blocking of the ROM ID on the DS2476 by writing to the +/// ROM Options page. +MaximInterface_EXPORT error_code enableRomId(DS2476 & ds2476); + +/// Format page authentication input data. class DS28C36::PageAuthenticationData { public: typedef array_span<uint_least8_t, @@ -390,80 +409,110 @@ /// Formatted data result. Result::const_span result() const { return result_; } + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<PageAuthenticationData &>(*this).romId(); } + /// Set ROM ID. PageAuthenticationData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// Set ROM ID for use in anonymous mode. MaximInterface_EXPORT PageAuthenticationData & setAnonymousRomId(); + /// @} + /// @name Page + /// @brief Data from a device memory page. /// @{ - /// Data from a device memory page. + + /// Get mutable page. Page::span page() { return make_span(result_).subspan<pageIdx, Page::size>(); } + /// Get immutable page. Page::const_span page() const { return const_cast<PageAuthenticationData &>(*this).page(); } + /// Set page. PageAuthenticationData & setPage(Page::const_span page) { copy(page, this->page()); return *this; } + /// @} + /// @name Challenge + /// @brief Random challenge used to prevent replay attacks. /// @{ - /// Random challenge used to prevent replay attacks. + + /// Get mutable Challenge. Page::span challenge() { return make_span(result_).subspan<challengeIdx, Page::size>(); } + /// Get immutable Challenge. Page::const_span challenge() const { return const_cast<PageAuthenticationData &>(*this).challenge(); } + /// Set Challenge. PageAuthenticationData & setChallenge(Page::const_span challenge) { copy(challenge, this->challenge()); return *this; } + /// @} + /// @name Page number + /// @brief Number of the page to use data from. /// @{ - /// Number of the page to use data from. + + /// Get page number. int pageNum() const { return result_[pageNumIdx]; } + /// Set page number. PageAuthenticationData & setPageNum(int pageNum) { result_[pageNumIdx] = pageNum; return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<PageAuthenticationData &>(*this).manId(); } + /// Set MAN ID. PageAuthenticationData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} private: @@ -478,6 +527,7 @@ Result::array result_; }; +/// Format authenticated write input data. class DS28C36::WriteAuthenticationData { public: typedef PageAuthenticationData::Result Result; @@ -487,73 +537,104 @@ /// Formatted data result. Result::const_span result() const { return data.result(); } + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return data.romId(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return data.romId(); } + /// Set ROM ID. WriteAuthenticationData & setRomId(RomId::const_span romId) { data.setRomId(romId); return *this; } + /// Set ROM ID for use in anonymous mode. WriteAuthenticationData & setAnonymousRomId() { data.setAnonymousRomId(); return *this; } + /// @} + /// @name Old page + /// @brief Existing data contained in the page. /// @{ - /// Existing data contained in the page. + + /// Get mutable old page. Page::span oldPage() { return data.page(); } + /// Get immutable old page. Page::const_span oldPage() const { return data.page(); } + /// Set old page. WriteAuthenticationData & setOldPage(Page::const_span oldPage) { data.setPage(oldPage); return *this; } + /// @} + /// @name New page + /// @brief New data to write to the page. /// @{ - /// New data to write to the page. + + /// Get mutable new page. Page::span newPage() { return data.challenge(); } + /// Get immutable new page. Page::const_span newPage() const { return data.challenge(); } + /// Set new page. WriteAuthenticationData & setNewPage(Page::const_span newPage) { data.setChallenge(newPage); return *this; } + /// @} + /// @name Page number + /// @brief Page number for write operation. /// @{ - /// Page number for write operation. + + /// Get page number. int pageNum() const { return data.pageNum(); } + /// Set page number. WriteAuthenticationData & setPageNum(int pageNum) { data.setPageNum(pageNum); return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return data.manId(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return data.manId(); } + /// Set MAN ID. WriteAuthenticationData & setManId(ManId::const_span manId) { data.setManId(manId); return *this; } + /// @} private: PageAuthenticationData data; }; +/// Format compute secret input data. class DS28C36::ComputeSecretData { public: typedef PageAuthenticationData::Result Result; @@ -563,68 +644,98 @@ /// Formatted data result. Result::const_span result() const { return data.result(); } + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return data.romId(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return data.romId(); } + /// Set ROM ID. ComputeSecretData & setRomId(RomId::const_span romId) { data.setRomId(romId); return *this; } + /// @} + /// @name Binding Data + /// @brief Binding Data contained in the selected page. /// @{ - /// Binding Data contained in the selected page. + + /// Get mutable Binding Data. Page::span bindingData() { return data.page(); } + /// Get immutable Binding Data. Page::const_span bindingData() const { return data.page(); } + /// Set Binding Data. ComputeSecretData & setBindingData(Page::const_span bindingData) { data.setPage(bindingData); return *this; } + /// @} + /// @name Partial Secret + /// @brief Partial Secret used for customization. /// @{ - /// Partial Secret used for customization. + + /// Get mutable Partial Secret. Page::span partialSecret() { return data.challenge(); } + /// Get immutable Partial Secret. Page::const_span partialSecret() const { return data.challenge(); } + /// Set Partial Secret. ComputeSecretData & setPartialSecret(Page::const_span partialSecret) { data.setChallenge(partialSecret); return *this; } + /// @} + /// @name Page number + /// @brief Page number for Binding Data. /// @{ - /// Page number for Binding Data. + + /// Get page number. int pageNum() const { return data.pageNum(); } + /// Set page number. ComputeSecretData & setPageNum(int pageNum) { data.setPageNum(pageNum); return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return data.manId(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return data.manId(); } + /// Set MAN ID. ComputeSecretData & setManId(ManId::const_span manId) { data.setManId(manId); return *this; } + /// @} private: PageAuthenticationData data; }; +/// Format encryption or decryption HMAC input data. class DS28C36::EncryptionHmacData { public: typedef array_span<uint_least8_t, @@ -636,66 +747,90 @@ /// Formatted data result. Result::const_span result() const { return result_; } + /// @name Encryption Challenge + /// @brief Random challenge used to prevent replay attacks. /// @{ - /// Random challenge used to prevent replay attacks. + + /// Get mutable Encryption Challenge. EncryptionChallenge::span encryptionChallenge() { return make_span(result_) .subspan<encryptionChallengeIdx, EncryptionChallenge::size>(); } + /// Get immutable Encryption Challenge. EncryptionChallenge::const_span encryptionChallenge() const { return const_cast<EncryptionHmacData &>(*this).encryptionChallenge(); } + /// Set Encryption Challenge. EncryptionHmacData & setEncryptionChallenge(EncryptionChallenge::const_span encryptionChallenge) { copy(encryptionChallenge, this->encryptionChallenge()); return *this; } + /// @} + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<EncryptionHmacData &>(*this).romId(); } + /// Set ROM ID. EncryptionHmacData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// Set ROM ID for use in anonymous mode. MaximInterface_EXPORT EncryptionHmacData & setAnonymousRomId(); + /// @} + /// @name Page number + /// @brief Number of the page to use data from. /// @{ - /// Number of the page to use data from. + + /// Get page number. int pageNum() const { return result_[pageNumIdx]; } + /// Set page number. EncryptionHmacData & setPageNum(int pageNum) { result_[pageNumIdx] = pageNum; return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<EncryptionHmacData &>(*this).manId(); } + /// Set MAN ID. EncryptionHmacData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} private: @@ -710,51 +845,64 @@ Result::array result_; }; +/// Access fields in the ROM Options page. class DS28C36::RomOptions { public: - operator Page::const_span() const { return page; } - operator Page::span() { return page; } + explicit RomOptions(Page::span page) : page(page) {} - bool anonymous() const { return page[anonymousIdx] == anonymousValue; } + bool romBlockDisable() const { + return page[romBlockDisableIdx] == enabledValue; + } + + RomOptions & setRomBlockDisable(bool romBlockDisable) { + page[romBlockDisableIdx] = (romBlockDisable ? enabledValue : 0); + return *this; + } + + bool anonymous() const { return page[anonymousIdx] == enabledValue; } - void setAnonymous(bool anonymous) { - page[anonymousIdx] = (anonymous ? anonymousValue : 0); + RomOptions & setAnonymous(bool anonymous) { + page[anonymousIdx] = (anonymous ? enabledValue : 0); + return *this; } ManId::const_span manId() const { - return make_span(page).subspan<22, ManId::size>(); + return page.subspan<22, ManId::size>(); } RomId::const_span romId() const { - return make_span(page).subspan<24, RomId::size>(); + return page.subspan<24, RomId::size>(); } private: - static const Page::array::size_type anonymousIdx = 1; - static const Page::array::value_type anonymousValue = 0xAA; + static const Page::span::index_type romBlockDisableIdx = 0; + static const Page::span::index_type anonymousIdx = 1; + static const Page::span::value_type enabledValue = 0xAA; - Page::array page; + Page::span page; }; +/// Access fields in the GPIO Control page. class DS28C36::GpioControl { public: - operator Page::const_span() const { return page; } - operator Page::span() { return page; } + explicit GpioControl(Page::span page) : page(page) {} bool pioaConducting() const { return page[pioaConductingIdx] == pioConductingValue; } - void setPioaConducting(bool pioaConducting) { + GpioControl & setPioaConducting(bool pioaConducting) { page[pioaConductingIdx] = (pioaConducting ? pioConductingValue : 0x55); + return *this; } bool piobConducting() const { return page[piobConductingIdx] == pioConductingValue; } - void setPiobConducting(bool piobConducting) { + GpioControl & setPiobConducting(bool piobConducting) { page[piobConductingIdx] = (piobConducting ? pioConductingValue : 0x55); + return *this; } bool pioaLevel() const { return page[2] == pioLevelValue; } @@ -762,12 +910,12 @@ bool piobLevel() const { return page[3] == pioLevelValue; } private: - static const Page::array::size_type pioaConductingIdx = 0; - static const Page::array::size_type piobConductingIdx = 1; - static const Page::array::value_type pioConductingValue = 0xAA; - static const Page::array::value_type pioLevelValue = 0x55; + static const Page::span::index_type pioaConductingIdx = 0; + static const Page::span::index_type piobConductingIdx = 1; + static const Page::span::value_type pioConductingValue = 0xAA; + static const Page::span::value_type pioLevelValue = 0x55; - Page::array page; + Page::span page; }; } // namespace MaximInterface
--- a/Devices/DS28E15_22_25.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS28E15_22_25.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -44,6 +44,7 @@ namespace MaximInterface { +/// @brief /// Interface to the DS28E15/22/25 series of authenticators /// including low power variants. class DS28E15_22_25 { @@ -71,17 +72,17 @@ bool secretLocked() const { return PB2 & 0x01; } }; - /// Represents the status of a memory protection block. + // Represents the status of a memory protection block. class BlockProtection; - /// Format data to hash for an Authenticated Write to a memory segment. + // Format data to hash for an Authenticated Write to a memory segment. class SegmentWriteMacData; - /// Format data to hash for an Authenticated Write to a memory protection block. + // Format data to hash for an Authenticated Write to a memory protection block. class ProtectionWriteMacData; - /// Format data to hash for device authentication or computing the next secret - /// from the existing secret. + // Format data to hash for device authentication or computing the next secret + // from the existing secret. class AuthenticationData; void setSleep(Sleep & sleep) { this->sleep = &sleep; } @@ -95,20 +96,20 @@ // Const member functions should not affect the state of the memory, // block protection, or secret on the device. - /// Read memory segment using the Read Memory command on the device. + /// @brief Read memory segment using the Read Memory command on the device. /// @param pageNum Page number for read operation. /// @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::span data) const; - /// Continue an in-progress readSegment operation. + /// @brief 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::span data) const; - /// Write memory segment using the Write Memory command. + /// @brief Write memory segment using the Write Memory command. /// @note 1-Wire ROM selection should have already occurred. /// @param pageNum Page number for write operation. /// @param segmentNum Segment number within page for write operation. @@ -116,21 +117,22 @@ MaximInterface_EXPORT error_code writeSegment(int pageNum, int segmentNum, Segment::const_span data); - /// Continue an in-progress Write Memory command. + /// @brief Continue an in-progress Write Memory command. /// @param[in] data Data to write to the memory segment. MaximInterface_EXPORT error_code continueWriteSegment(Segment::const_span data); - /// Read memory page using the Read Memory command on the device. + /// @brief 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::span rdbuf) const; - /// Continue an in-progress readPageOperation. + /// @brief Continue an in-progress readPageOperation. /// @param[out] rdbuf Buffer to read data from the page into. MaximInterface_EXPORT error_code continueReadPage(Page::span rdbuf) const; + /// @brief /// 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. @@ -139,13 +141,16 @@ MaximInterface_EXPORT error_code computeReadPageMac(int pageNum, bool anon, Sha256::Hash::span mac) const; + /// @brief /// Update the status of a memory protection block using the /// Write Page Protection command. - /// @param protection Desired protection status for the block. - /// It is not possible to disable existing protections. + /// @param protection + /// Desired protection status for the block. + /// It is not possible to disable existing protections. MaximInterface_EXPORT error_code writeBlockProtection(BlockProtection protection); + /// @brief /// Update the status of a memory protection block using the /// Authenticated Write Page Protection command. /// @param newProtection New protection status to write. @@ -153,17 +158,19 @@ MaximInterface_EXPORT error_code writeAuthBlockProtection( BlockProtection newProtection, Sha256::Hash::const_span mac); - /// Perform Load and Lock Secret command on the device. + /// @brief Perform Load and Lock Secret command on the device. /// @note The secret should already be stored in the scratchpad on the device. - /// @param lock Prevent further changes to the secret on the device after loading. + /// @param lock + /// Prevent further changes to the secret on the device after loading. MaximInterface_EXPORT error_code loadSecret(bool lock); - /// Perform a Compute and Lock Secret command on the device. + /// @brief Perform a Compute and Lock Secret command on the device. /// @param pageNum Page number to use as the binding data. - /// @param lock Prevent further changes to the secret on the device after computing. + /// @param lock + /// Prevent further changes to the secret on the device after computing. MaximInterface_EXPORT error_code computeSecret(int pageNum, bool lock); - /// Read the personality bytes using the Read Status command. + /// @brief Read the personality bytes using the Read Status command. /// @param[out] personality Receives personality read from device. MaximInterface_EXPORT error_code readPersonality(Personality & personality) const; @@ -242,21 +249,22 @@ DS28EL15(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28E15_22_25(sleep, master, selectRom) {} - /// Perform Write Scratchpad operation on the device. + /// @brief Perform Write Scratchpad operation on the device. /// @param[in] data Data to write to the scratchpad. MaximInterface_EXPORT error_code writeScratchpad(Scratchpad::const_span data); - /// Perform a Read Scratchpad operation on the device. + /// @brief 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::span data) const; + /// @brief /// Read the status of a memory protection block using the Read Status command. /// @param blockNum Block number to to read status of. /// @param[out] protection Receives protection status read from device. MaximInterface_EXPORT error_code readBlockProtection(int blockNum, BlockProtection & protection) const; - /// Write memory segment using the Authenticated Write Memory command. + /// @brief Write memory segment using the Authenticated Write Memory command. /// @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. @@ -265,12 +273,13 @@ writeAuthSegment(int pageNum, int segmentNum, Segment::const_span newData, Sha256::Hash::const_span mac); - /// Continue an in-progress Authenticated Write Memory command. + /// @brief 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( Segment::const_span newData, Sha256::Hash::const_span mac); + /// @brief /// 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( @@ -283,14 +292,16 @@ DS28E15(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28EL15(sleep, master, selectRom) {} - /// Perform Load and Lock Secret command on the device. + /// @brief Perform Load and Lock Secret command on the device. /// @note The secret should already be stored in the scratchpad on the device. - /// @param lock Prevent further changes to the secret on the device after loading. + /// @param lock + /// Prevent further changes to the secret on the device after loading. MaximInterface_EXPORT error_code loadSecret(bool lock); - /// Perform a Compute and Lock Secret command on the device. + /// @brief Perform a Compute and Lock Secret command on the device. /// @param pageNum Page number to use as the binding data. - /// @param lock Prevent further changes to the secret on the device after computing. + /// @param lock + /// Prevent further changes to the secret on the device after computing. MaximInterface_EXPORT error_code computeSecret(int pageNum, bool lock); }; @@ -304,14 +315,81 @@ DS28EL22(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28E15_22_25(sleep, master, selectRom) {} - /// Perform Write Scratchpad operation on the device. + /// @brief Perform Write Scratchpad operation on the device. /// @param[in] data Data to write to the scratchpad. MaximInterface_EXPORT error_code writeScratchpad(Scratchpad::const_span data); - /// Perform a Read Scratchpad operation on the device. + /// @brief 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::span data) const; + /// @brief + /// Read the status of a memory protection block using the Read Status command. + /// @param blockNum Block number to to read status of. + /// @param[out] protection Receives protection status read from device. + MaximInterface_EXPORT error_code + readBlockProtection(int blockNum, BlockProtection & protection) const; + + /// @brief Write memory segment using the Authenticated Write Memory command. + /// @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] mac Write MAC computed for this operation. + MaximInterface_EXPORT error_code + writeAuthSegment(int pageNum, int segmentNum, Segment::const_span newData, + Sha256::Hash::const_span mac); + + /// @brief 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( + Segment::const_span newData, Sha256::Hash::const_span mac); + + /// @brief + /// 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( + span<BlockProtection, protectionBlocks> protection) const; +}; + +/// Interface to the DS28E22 authenticator. +class DS28E22 : public DS28EL22 { +public: + DS28E22(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) + : DS28EL22(sleep, master, selectRom) {} + + /// @brief Perform Load and Lock Secret command on the device. + /// @note The secret should already be stored in the scratchpad on the device. + /// @param lock + /// Prevent further changes to the secret on the device after loading. + MaximInterface_EXPORT error_code loadSecret(bool lock); + + /// @brief Perform a Compute and Lock Secret command on the device. + /// @param pageNum Page number to use as the binding data. + /// @param lock + /// Prevent further changes to the secret on the device after computing. + MaximInterface_EXPORT error_code computeSecret(int pageNum, bool lock); +}; + +/// Interface to the DS28EL25 (low power) authenticator. +class DS28EL25 : public DS28E15_22_25 { +public: + // DS28E15_22_25 traits + static const int memoryPages = 16; + static const int protectionBlocks = 8; + + DS28EL25(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) + : DS28E15_22_25(sleep, master, selectRom) {} + + /// @brief Perform Write Scratchpad operation on the device. + /// @param[in] data Data to write to the scratchpad. + MaximInterface_EXPORT error_code writeScratchpad(Scratchpad::const_span data); + + /// @brief 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::span data) const; + + /// @brief /// Read the status of a memory protection block using the Read Status command. /// @param blockNum Block number to to read status of. /// @param[out] protection Receives protection status read from device. @@ -327,74 +405,13 @@ writeAuthSegment(int pageNum, int segmentNum, Segment::const_span newData, Sha256::Hash::const_span mac); - /// Continue an in-progress Authenticated Write Memory command. + /// @brief 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( 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( - span<BlockProtection, protectionBlocks> protection) const; -}; - -/// Interface to the DS28E22 authenticator. -class DS28E22 : public DS28EL22 { -public: - DS28E22(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) - : DS28EL22(sleep, master, selectRom) {} - - /// Perform Load and Lock Secret command on the device. - /// @note The secret should already be stored in the scratchpad on the device. - /// @param lock Prevent further changes to the secret on the device after loading. - MaximInterface_EXPORT error_code loadSecret(bool lock); - - /// Perform a Compute and Lock Secret command on the device. - /// @param pageNum Page number to use as the binding data. - /// @param lock Prevent further changes to the secret on the device after computing. - MaximInterface_EXPORT error_code computeSecret(int pageNum, bool lock); -}; - -/// Interface to the DS28EL25 (low power) authenticator. -class DS28EL25 : public DS28E15_22_25 { -public: - // DS28E15_22_25 traits - static const int memoryPages = 16; - static const int protectionBlocks = 8; - - 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(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::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. - /// @param[out] protection Receives protection status read from device. - MaximInterface_EXPORT error_code - readBlockProtection(int blockNum, BlockProtection & protection) const; - - /// Write memory segment using the Authenticated Write Memory command. - /// @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] mac Write MAC computed for this operation. - 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( - Segment::const_span newData, Sha256::Hash::const_span mac); - + /// @brief /// 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( @@ -407,17 +424,19 @@ DS28E25(Sleep & sleep, OneWireMaster & master, const SelectRom & selectRom) : DS28EL25(sleep, master, selectRom) {} - /// Perform Load and Lock Secret command on the device. + /// @brief Perform Load and Lock Secret command on the device. /// @note The secret should already be stored in the scratchpad on the device. /// @param lock Prevent further changes to the secret on the device after loading. MaximInterface_EXPORT error_code loadSecret(bool lock); - /// Perform a Compute and Lock Secret command on the device. + /// @brief Perform a Compute and Lock Secret command on the device. /// @param pageNum Page number to use as the binding data. - /// @param lock Prevent further changes to the secret on the device after computing. + /// @param lock + /// Prevent further changes to the secret on the device after computing. MaximInterface_EXPORT error_code computeSecret(int pageNum, bool lock); }; +/// Represents the status of a memory protection block. class DS28E15_22_25::BlockProtection { public: explicit BlockProtection(uint_least8_t status = 0x00) : status(status) {} @@ -437,7 +456,7 @@ /// Set the Block Number which is indexed from zero. MaximInterface_EXPORT BlockProtection & setBlockNum(int blockNum); - /// Get the Read Protection status. + /// @brief Get the Read Protection status. /// @returns True if Read Protection is enabled. bool readProtection() const { return ((status & readProtectionMask) == readProtectionMask); @@ -447,7 +466,7 @@ MaximInterface_EXPORT BlockProtection & setReadProtection(bool readProtection); - /// Get the Write Protection status. + /// @brief Get the Write Protection status. /// @returns True if Write Protection is enabled. bool writeProtection() const { return ((status & writeProtectionMask) == writeProtectionMask); @@ -457,7 +476,7 @@ MaximInterface_EXPORT BlockProtection & setWriteProtection(bool writeProtection); - /// Get the EEPROM Emulation Mode status. + /// @brief Get the EEPROM Emulation Mode status. /// @returns True if EEPROM Emulation Mode is enabled. bool eepromEmulation() const { return ((status & eepromEmulationMask) == eepromEmulationMask); @@ -467,7 +486,7 @@ MaximInterface_EXPORT BlockProtection & setEepromEmulation(bool eepromEmulation); - /// Get the Authentication Protection status. + /// @brief Get the Authentication Protection status. /// @returns True if Authentication Protection is enabled. bool authProtection() const { return ((status & authProtectionMask) == authProtectionMask); @@ -477,7 +496,7 @@ MaximInterface_EXPORT BlockProtection & setAuthProtection(bool authProtection); - /// Check if no protection options are enabled. + /// @brief Check if no protection options are enabled. /// @returns True if no protection options are enabled. MaximInterface_EXPORT bool noProtection() const; @@ -500,6 +519,7 @@ return !operator==(lhs, rhs); } +/// Format data to hash for an Authenticated Write to a memory segment. class DS28E15_22_25::SegmentWriteMacData { public: SegmentWriteMacData() : result_() {} @@ -507,88 +527,122 @@ /// Formatted data result. Sha256::WriteMacData::const_span result() const { return result_; } + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<SegmentWriteMacData &>(*this).romId(); } + /// Set ROM ID. SegmentWriteMacData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<SegmentWriteMacData &>(*this).manId(); } + /// Set MAN ID. SegmentWriteMacData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} + /// @name Page number + /// @brief Page number for write operation. /// @{ - /// Page number for write operation. + + /// Get page number. int pageNum() const { return result_[pageNumIdx]; } + /// Set page number. SegmentWriteMacData & setPageNum(int pageNum) { result_[pageNumIdx] = pageNum; return *this; } + /// @} + /// @name Segment number + /// @brief Segment number within page for write operation. /// @{ - /// Segment number within page for write operation. + + /// Get segment number. int segmentNum() const { return result_[segmentNumIdx]; } + /// Set segment number. SegmentWriteMacData & setSegmentNum(int segmentNum) { result_[segmentNumIdx] = segmentNum; return *this; } + /// @} + /// @name Old data + /// @brief Existing data contained in the segment. /// @{ - /// Existing data contained in the segment. + + /// Get mutable old data. Segment::span oldData() { return make_span(result_).subspan<oldDataIdx, Segment::size>(); } + /// Get immutable old data. Segment::const_span oldData() const { return const_cast<SegmentWriteMacData &>(*this).oldData(); } + /// Set old data. SegmentWriteMacData & setOldData(Segment::const_span oldData) { copy(oldData, this->oldData()); return *this; } + /// @} + /// @name New data + /// @brief New data to write to the segment. /// @{ - /// New data to write to the segment. + + /// Get mutable new data. Segment::span newData() { return make_span(result_).subspan<newDataIdx, Segment::size>(); } + /// Get immutable new data. Segment::const_span newData() const { return const_cast<SegmentWriteMacData &>(*this).newData(); } + /// Set new data. SegmentWriteMacData & setNewData(Segment::const_span newData) { copy(newData, this->newData()); return *this; } + /// @} private: @@ -604,6 +658,7 @@ Sha256::WriteMacData::array result_; }; +/// Format data to hash for an Authenticated Write to a memory protection block. class DS28E15_22_25::ProtectionWriteMacData { public: MaximInterface_EXPORT ProtectionWriteMacData(); @@ -611,52 +666,74 @@ /// Formatted data result. Sha256::WriteMacData::const_span result() const { return result_; } + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<ProtectionWriteMacData &>(*this).romId(); } + /// Set ROM ID. ProtectionWriteMacData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<ProtectionWriteMacData &>(*this).manId(); } + /// Set MAN ID. ProtectionWriteMacData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} + /// @name Old protection + /// @brief Existing protection status in device. /// @{ - /// Existing protection status in device. + + /// Get old protection. BlockProtection oldProtection() const { return oldProtection_; } + /// Set old protection. MaximInterface_EXPORT ProtectionWriteMacData & setOldProtection(BlockProtection oldProtection); + /// @} + /// @name New protection + /// @brief New protection status to write. /// @{ - /// New protection status to write. + + /// Get new protection. BlockProtection newProtection() const { return newProtection_; } + /// Set new protection. MaximInterface_EXPORT ProtectionWriteMacData & setNewProtection(BlockProtection newProtection); + /// @} private: @@ -673,6 +750,9 @@ BlockProtection newProtection_; }; +/// @brief +/// Format data to hash for device authentication or computing the next secret +/// from the existing secret. class DS28E15_22_25::AuthenticationData { public: AuthenticationData() : result_() {} @@ -680,81 +760,112 @@ /// Formatted data result. Sha256::AuthenticationData::const_span result() const { return result_; } + /// @name Page + /// @brief Data from a device memory page. /// @{ - /// Data from a device memory page. + + /// Get mutable page. Page::span page() { return make_span(result_).subspan<pageIdx, Page::size>(); } + /// Get immutable page. Page::const_span page() const { return const_cast<AuthenticationData &>(*this).page(); } + /// Set page. AuthenticationData & setPage(Page::const_span page) { copy(page, this->page()); return *this; } + /// @} - /// @{ + /// @name Scratchpad + /// @brief /// Data from device scratchpad used as a random challenge in device /// authentication and a partial secret in secret computation. + /// @{ + + /// Get mutable scratchpad. Scratchpad::span scratchpad() { return make_span(result_).subspan<scratchpadIdx, Scratchpad::size>(); } + /// Get immutable scratchpad. Scratchpad::const_span scratchpad() const { return const_cast<AuthenticationData &>(*this).scratchpad(); } + /// Set scratchpad. AuthenticationData & setScratchpad(Scratchpad::const_span scratchpad) { copy(scratchpad, this->scratchpad()); return *this; } + /// @} + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<AuthenticationData &>(*this).romId(); } + /// Set ROM ID. AuthenticationData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// Set ROM ID for use in anonymous mode. MaximInterface_EXPORT AuthenticationData & setAnonymousRomId(); + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<AuthenticationData &>(*this).manId(); } + /// Set MAN ID. AuthenticationData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} + /// @name Page number + /// @brief Number of the page to use data from. /// @{ - /// Number of the page to use data from. + + /// Get page number. int pageNum() const { return result_[pageNumIdx]; } + /// Set page number. AuthenticationData & setPageNum(int pageNum) { result_[pageNumIdx] = pageNum; return *this; } + /// @} private:
--- a/Devices/DS28E17.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS28E17.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -40,7 +40,7 @@ namespace MaximInterface { -/// DS28E17 1-Wire®-to-I2C Master Bridge +/// @brief DS28E17 1-Wire®-to-I2C Master Bridge /// @details The DS28E17 is a 1-Wire slave to I2C master bridge /// device that interfaces directly to I2C slaves at standard /// (100kHz max) or fast (400kHz max). Data transfers serially by @@ -75,7 +75,7 @@ this->selectRom = selectRom; } - /// Write Data With Stop command. + /// @brief Write Data With Stop command. /// @details Output on I2C: S, Address + Write, Write Data [1-255], P /// @param[in] I2C_addr /// I2C slave address. The least significant bit of the I2C @@ -89,7 +89,7 @@ writeDataWithStop(uint_least8_t I2C_addr, span<const uint_least8_t> data, uint_least8_t * wr_status = NULL); - /// Write Data No Stop command. + /// @brief Write Data No Stop command. /// @details Output on I2C: S, Address + Write, Write Data [1-255] /// @param[in] I2C_addr /// I2C slave address. The least significant bit of the I2C address @@ -103,7 +103,7 @@ writeDataNoStop(uint_least8_t I2C_addr, span<const uint_least8_t> data, uint_least8_t * wr_status = NULL); - /// Write Data Only command. + /// @brief Write Data Only command. /// @details Output on I2C: Write Data [1-255] /// @param[in] data I2C data to write with length 1-255. /// @param[out] wr_status @@ -114,7 +114,7 @@ writeDataOnly(span<const uint_least8_t> data, uint_least8_t * wr_status = NULL); - /// Write Data Only With Stop command. + /// @brief Write Data Only With Stop command. /// @details Output on I2C: Write Data [1-255], P /// @param[in] data I2C data to write with length 1-255. /// @param[out] wr_status @@ -125,7 +125,7 @@ writeDataOnlyWithStop(span<const uint_least8_t> data, uint_least8_t * wr_status = NULL); - /// Write, Read Data With Stop command. + /// @brief Write, Read Data With Stop command. /// @details Output on I2C: /// S, Slave Address + Write, Write Data [1-255], /// Sr, Address + Read, Read Data [1-255], P (NACK last read byte) @@ -142,7 +142,7 @@ uint_least8_t I2C_addr, span<const uint_least8_t> write_data, span<uint_least8_t> read_data, uint_least8_t * wr_status = NULL); - /// Read Data With Stop command. + /// @brief Read Data With Stop command. /// @details Output on I2C: /// S, Slave Address + Read, Read Data [1-255], P (NACK last read byte) /// @param[in] I2C_addr @@ -155,17 +155,17 @@ /// Write to Configuration Register of DS28E17. MaximInterface_EXPORT error_code writeConfigReg(I2CSpeed speed); - /// Read the Configuration Register of DS28E17. + /// @brief Read the Configuration Register of DS28E17. /// @param[out] speed Speed read from configuration register. MaximInterface_EXPORT error_code readConfigReg(I2CSpeed & speed); - /// The Enable Sleep Mode command puts the device into a low current mode. + /// @brief Put the device into a low current mode. /// @details All 1-Wire communication is ignored until woken up. Immediately /// after the command, the device monitors the WAKEUP input pin and exits /// sleep mode on a rising edge. MaximInterface_EXPORT error_code enableSleepMode(); - /// Read the Device Revision of DS28E17. + /// @brief Read the Device Revision of DS28E17. /// @details The upper nibble is the major revision, /// and the lower nibble is the minor revision. /// @param[out] rev Device Revision.
--- a/Devices/DS28E38.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Devices/DS28E38.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -57,18 +57,22 @@ 0x100 ///< Command response does not match expected format. }; - // Device memory pages. + /// @name Device memory pages + /// @{ + static const int decrementCounterPage = 3; static const int publicKeyXPage = 4; static const int publicKeyYPage = 5; static const int privateKeyPage = 6; + + /// @} static const int memoryPages = 7; /// Holds a device memory page. typedef array_span<uint_least8_t, 32> Page; - /// Format page authentication input data. + // Format page authentication input data. class PageAuthenticationData; /// Page protection types. @@ -103,17 +107,18 @@ doRunCommand = runCommand; } - /// Write memory with no protection. + /// @brief Write memory with no protection. /// @param pageNum Number of page to write. /// @param page Data to write. MaximInterface_EXPORT error_code writeMemory(int pageNum, Page::const_span page); - /// Read memory with no protection. + /// @brief Read memory with no protection. /// @param pageNum Number of page to read. /// @param[out] page Data that was read. MaximInterface_EXPORT error_code readMemory(int pageNum, Page::span page); + /// @brief /// Reads the current status of the device and optionally performs an /// entropy health test. /// @param entropyHealthTest True to perform an entropy health test. @@ -121,13 +126,13 @@ MaximInterface_EXPORT error_code readStatus(bool entropyHealthTest, Status & status); - /// Set the protection settings of a page. + /// @brief Set the protection settings of a page. /// @param pageNum Number of page to write. /// @param protection Protection to write. MaximInterface_EXPORT error_code setPageProtection(int pageNum, const PageProtection & protection); - /// Compute and read page authentication with ECDSA. + /// @brief Compute and read page authentication with ECDSA. /// @param pageNum Number of page to authenticate. /// @param anonymous True to disable use of ROM ID in computation. /// @param challenge Random challenge used to prevent replay attacks. @@ -142,13 +147,13 @@ /// Permanently disable the device. MaximInterface_EXPORT error_code disableDevice(); - /// Generate a new ECDSA public key from an existing private key. + /// @brief Generate a new ECDSA public key from an existing private key. /// @param privateKeyPuf True if PUF is used as the private key. /// @param writeProtectEnable True to lock the key against further writes. MaximInterface_EXPORT error_code generateEcc256KeyPair(bool privateKeyPuf, bool writeProtectEnable); - /// Read a block of random data from the RNG. + /// @brief Read a block of random data from the RNG. /// @param[out] data Random data from RNG with length from 1 to 64. MaximInterface_EXPORT error_code readRng(span<uint_least8_t> data); @@ -170,12 +175,13 @@ return error_code(e, DS28E38::errorCategory()); } -/// Read the device MAN ID using the Read Status command. +/// @brief Read the device MAN ID using the Read Status command. /// @param ds28e38 Device to read. /// @param[out] manId Read MAN ID valid when operation is successful. MaximInterface_EXPORT error_code readManId(DS28E38 & ds28e38, ManId::span manId); +/// Format page authentication input data. class DS28E38::PageAuthenticationData { public: typedef array_span<uint_least8_t, @@ -187,80 +193,110 @@ /// Formatted data result. Result::const_span result() const { return result_; } + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<PageAuthenticationData &>(*this).romId(); } + /// Set ROM ID. PageAuthenticationData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// Set ROM ID for use in anonymous mode. MaximInterface_EXPORT PageAuthenticationData & setAnonymousRomId(); + /// @} + /// @name Page + /// @brief Data from a device memory page. /// @{ - /// Data from a device memory page. + + /// Get mutable page. Page::span page() { return make_span(result_).subspan<pageIdx, Page::size>(); } + /// Get immutable page. Page::const_span page() const { return const_cast<PageAuthenticationData &>(*this).page(); } + /// Set page. PageAuthenticationData & setPage(Page::const_span page) { copy(page, this->page()); return *this; } + /// @} + /// @name Challenge + /// @brief Random challenge used to prevent replay attacks. /// @{ - /// Random challenge used to prevent replay attacks. + + /// Get mutable Challenge. Page::span challenge() { return make_span(result_).subspan<challengeIdx, Page::size>(); } + /// Get immutable Challenge. Page::const_span challenge() const { return const_cast<PageAuthenticationData &>(*this).challenge(); } + /// Set Challenge. PageAuthenticationData & setChallenge(Page::const_span challenge) { copy(challenge, this->challenge()); return *this; } + /// @} + /// @name Page number + /// @brief Number of the page to use data from. /// @{ - /// Number of the page to use data from. + + /// Get page number. int pageNum() const { return result_[pageNumIdx]; } + /// Set page number. PageAuthenticationData & setPageNum(int pageNum) { result_[pageNumIdx] = pageNum; return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<PageAuthenticationData &>(*this).manId(); } + /// Set MAN ID. PageAuthenticationData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} private:
--- a/Links/I2CMaster.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Links/I2CMaster.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -51,7 +51,7 @@ virtual ~I2CMaster() {} - /// Send start condition and address on the bus. + /// @brief Send start condition and address on the bus. /// @param address Address with R/W bit. virtual error_code start(uint_least8_t address) = 0; @@ -65,9 +65,11 @@ MaximInterface_EXPORT virtual error_code writeBlock(span<const uint_least8_t> data); + /// @brief /// Perform a complete write transaction on the bus with optional stop /// condition. /// @param address Address in 8-bit format. + /// @param data Data to write to the bus. /// @param sendStop /// True to send a stop condition or false to set up a repeated start. error_code writePacket(uint_least8_t address, span<const uint_least8_t> data, @@ -75,20 +77,22 @@ return writePacketImpl(address, data, sendStop); } - /// Read data byte from the bus. + /// @brief Read data byte from the bus. /// @param status Determines whether an ACK or NACK is sent after reading. /// @param[out] data Data read from the bus if successful. virtual error_code readByte(AckStatus status, uint_least8_t & data) = 0; - /// Read data block from the bus. + /// @brief Read data block from the bus. /// @param status Determines whether an ACK or NACK is sent after reading. /// @param[out] data Data read from the bus if successful. MaximInterface_EXPORT virtual error_code readBlock(AckStatus status, span<uint_least8_t> data); + /// @brief /// Perform a complete read transaction on the bus with optional stop /// condition. /// @param address Address in 8-bit format. + /// @param[out] data Data read from the bus if successful. /// @param sendStop /// True to send a stop condition or false to set up a repeated start. error_code readPacket(uint_least8_t address, span<uint_least8_t> data,
--- a/Links/OneWireMaster.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Links/OneWireMaster.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -65,10 +65,13 @@ virtual ~OneWireMaster() {} + /// @brief /// Reset all of the devices on the 1-Wire bus and check for a presence pulse. - /// @returns NoSlaveError if reset was performed but no presence pulse was detected. + /// @returns + /// NoSlaveError if reset was performed but no presence pulse was detected. virtual error_code reset() = 0; + /// @brief /// Send and receive one bit of communication and set a new level on the /// 1-Wire bus. /// @param[in,out] sendRecvBit @@ -76,24 +79,26 @@ /// @param afterLevel Level to set the 1-Wire bus to after communication. virtual error_code touchBitSetLevel(bool & sendRecvBit, Level afterLevel) = 0; + /// @brief /// Send one byte of communication and set a new level on the 1-Wire bus. /// @param sendByte Byte to send on the 1-Wire bus. /// @param afterLevel Level to set the 1-Wire bus to after communication. MaximInterface_EXPORT virtual error_code writeByteSetLevel(uint_least8_t sendByte, Level afterLevel); + /// @brief /// Receive one byte of communication and set a new level on the 1-Wire bus. /// @param recvByte Buffer to receive the data from the 1-Wire bus. /// @param afterLevel Level to set the 1-Wire bus to after communication. MaximInterface_EXPORT virtual error_code readByteSetLevel(uint_least8_t & recvByte, Level afterLevel); - /// Send a block of communication on the 1-Wire bus. + /// @brief Send a block of communication on the 1-Wire bus. /// @param[in] sendBuf Buffer to send on the 1-Wire bus. MaximInterface_EXPORT virtual error_code writeBlock(span<const uint_least8_t> sendBuf); - /// Receive a block of communication on the 1-Wire bus. + /// @brief Receive a block of communication on the 1-Wire bus. /// @param[out] recvBuf Buffer to receive the data from the 1-Wire bus. MaximInterface_EXPORT virtual error_code readBlock(span<uint_least8_t> recvBuf); @@ -104,16 +109,17 @@ /// Set the 1-Wire bus level. virtual error_code setLevel(Level newLevel) = 0; - /// 1-Wire Triplet operation. + /// @brief 1-Wire Triplet operation. /// @details Perform one bit of a 1-Wire search. This command /// does two read bits and one write bit. The write bit is either /// the default direction (all devices have same bit) or in case /// of a discrepancy, the data.writeBit parameter is used. - ///@param[in,out] data + /// @param[in,out] data /// Input with desired writeBit in case both read bits are zero. /// Output with all data fields set. MaximInterface_EXPORT virtual error_code triplet(TripletData & data); + /// @brief /// Send one bit of communication and set a new level on the 1-Wire bus. /// @param sendBit Bit to send on the 1-Wire bus. /// @param afterLevel Level to set the 1-Wire bus to after communication. @@ -121,6 +127,7 @@ return touchBitSetLevel(sendBit, afterLevel); } + /// @brief /// Receive one bit of communication and set a new level on the 1-Wire bus. /// @param[out] recvBit Received data from the 1-Wire bus. /// @param afterLevel Level to set the 1-Wire bus to after communication.
--- a/Links/RomCommands.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Links/RomCommands.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -31,7 +31,7 @@ *******************************************************************************/ /// @file -/// ROM Commands for enumerating and selecting 1-Wire devices. +/// @brief ROM Commands for enumerating and selecting 1-Wire devices. #ifndef MaximInterface_RomCommands #define MaximInterface_RomCommands @@ -66,6 +66,7 @@ } }; +/// @brief /// Set the search state to skip the current device family on the next /// Search ROM command. MaximInterface_EXPORT void skipCurrentFamily(SearchRomState & searchState); @@ -74,43 +75,53 @@ MaximInterface_EXPORT error_code verifyRom(OneWireMaster & master, RomId::const_span romId); -/// Use Read ROM command to read ROM ID from device on bus. -/// @note Only use this command with a single drop bus, data -/// collisions will occur if more than 1 device on bus. +/// @brief Use Read ROM command to read ROM ID from device on bus. +/// @note +/// Only use this command with a single-drop bus. +/// Data collisions will occur if there is more than one device on the bus. +/// @param master 1-Wire master for operation. /// @param[out] romId ROM ID read from device. MaximInterface_EXPORT error_code readRom(OneWireMaster & master, RomId::span romId); -/// Issue Skip ROM command on bus. -/// @note Only use this command with a single drop bus, data -/// collisions will occur if more than 1 device on bus. +/// @brief Issue Skip ROM command on bus. +/// @note +/// Only use this command with a single-drop bus. +/// Data collisions will occur if there is more than one device on the bus. MaximInterface_EXPORT error_code skipRom(OneWireMaster & master); -/// Use the Match ROM command to select the device by its known ID. -/// @note This command causes all devices supporting Overdrive -/// mode to switch to Overdrive timing. +/// @brief Use the Match ROM command to select the device by its known ID. +/// @note +/// This command causes all devices supporting Overdrive mode to switch to +/// Overdrive timing. +/// @param master 1-Wire master for operation. /// @param[in] romId ROM ID of device to select. MaximInterface_EXPORT error_code matchRom(OneWireMaster & master, RomId::const_span romId); -/// Issue Overdrive Skip ROM command on bus. -/// @note This command causes all devices supporting Overdrive -/// mode to switch to Overdrive timing. -/// @note Only use this command with a single drop bus, data -/// collisions will occur if more than 1 device on bus. +/// @brief Issue Overdrive Skip ROM command on bus. +/// @note +/// This command causes all devices supporting Overdrive mode to switch to +/// Overdrive timing. +/// @note +/// Only use this command with a single-drop bus. +/// Data collisions will occur if there is more than one device on the bus. MaximInterface_EXPORT error_code overdriveSkipRom(OneWireMaster & master); +/// @brief /// Use the Overdrive Match ROM command to select the device by its known ID. +/// @param master 1-Wire master for operation. /// @param[in] romId ROM ID of device to select. MaximInterface_EXPORT error_code overdriveMatchRom(OneWireMaster & master, RomId::const_span romId); -/// Perform a Resume ROM command on bus. -/// @details Resumes communication with the last device selected -/// though a Match ROM or Search ROM operation. +/// @brief Perform a Resume ROM command on bus. +/// @details +/// Resumes communication with the last device selected through a Match ROM or +/// Search ROM operation. MaximInterface_EXPORT error_code resumeRom(OneWireMaster & master); -/// Find device on the 1-Wire bus. +/// @brief Find device on the 1-Wire bus. /// @details /// This command uses the Search ROM command to enumerate all 1-Wire devices in /// sequence. Begin with a new search state and continue using the same search
--- a/Links/SelectRom.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Links/SelectRom.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -64,6 +64,7 @@ RomId::array romId_; }; +/// @brief /// Selector for a multidrop 1-Wire bus where slaves support the Resume ROM /// command. class SelectMatchRomWithResume {
--- a/Links/SerialPort.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Links/SerialPort.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -46,7 +46,7 @@ /// Disconnect from the current port. virtual error_code disconnect() = 0; - /// Check if currently connected to a port. + /// @brief Check if currently connected to a port. /// @returns True if connected. virtual bool connected() const = 0;
--- a/Links/Uart.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Links/Uart.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -66,11 +66,13 @@ MaximInterface_EXPORT virtual error_code writeBlock(span<const uint_least8_t> data); + /// @brief /// Reads a byte of data from the port. Block until data is received or a /// timeout is reached. /// @param[out] data Data read from the port if successful. virtual error_code readByte(uint_least8_t & data) = 0; + /// @brief /// Read a block of data from the port. Block until data is received or a /// timeout is reached. /// @param[out] data Data read from the port if successful.
--- a/Platforms/mbed/TARGET_Maxim/TARGET_MAX32600/owlink.h Wed Jan 23 13:11:04 2019 -0600 +++ b/Platforms/mbed/TARGET_Maxim/TARGET_MAX32600/owlink.h Mon Mar 04 08:10:00 2019 -0600 @@ -39,8 +39,7 @@ extern "C" { #endif -/// Timing parameters for the 1-Wire bus. -/// @note All times are in terms of microseconds. +/// Timing parameters for the 1-Wire bus in microseconds. struct OneWireTiming { uint16_t tRSTL; ///< Reset Low Time uint16_t tMSP; ///< Presence-Detect Sample Time @@ -53,10 +52,11 @@ /// Delay for the specified number of microseconds. void ow_usdelay(unsigned int time_us); -/// Send and receive one bit of communication and set a new level on the 1-Wire bus. +/// @brief Send and receive one bit, and set a new level on the 1-Wire bus. /// @note GPIO pin must be configured for open drain operation. -/// @param[in,out] sendRecvBit Buffer containing the bit to send on 1-Wire bus in lsb. -/// Read data from 1-Wire bus will be returned in lsb. +/// @param[in,out] sendRecvBit +/// Buffer containing the bit to send on 1-Wire bus in lsb. +/// Read data from 1-Wire bus will be returned in lsb. /// @param[in] inReg Input register for GPIO pin. /// @param[in,out] outReg Output register for GPIO pin. /// @param pinMask Pin mask for input and output registers.
--- a/Utilities/ChangeSizeType.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/ChangeSizeType.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -41,9 +41,14 @@ namespace MaximInterface { -/// Adapts functions taking a data pointer and data size where the size type is -/// nonstandard. The function will be called multiple times if necessary to -/// process all data. +/// @brief +/// Adapts functions taking an array pointer and size where the size type is +/// nonstandard. +/// @tparam NewSize Nonstandard size type. +/// @tparam Func Must be callable as func(Data *, NewSize). +/// @tparam Data Array element type. +/// @param func Callback for processing chunks of data. +/// @param data Data to process with callback. template <typename NewSize, typename Func, typename Data> error_code changeSizeType(Func func, span<Data> data) { using namespace std;
--- a/Utilities/Ecc256.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/Ecc256.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -169,49 +169,68 @@ /// Formatted data result. Result::const_span result() const { return result_; } + /// @name Public Key + /// @brief Public key of the device. /// @{ - /// Public key of the device. + + /// Get mutable Public Key. MaximInterface_EXPORT PublicKey::span publicKey(); + + /// Get immutable Public Key. PublicKey::const_span publicKey() const { return const_cast<CertificateData &>(*this).publicKey(); } + /// Set Public Key. CertificateData & setPublicKey(PublicKey::const_span publicKey) { copy(publicKey, this->publicKey()); return *this; } + /// @} + /// @name ROM ID + /// @brief 1-Wire ROM ID of the device. /// @{ - /// 1-Wire ROM ID of the device. + + /// Get mutable ROM ID. RomId::span romId() { return make_span(result_).subspan<romIdIdx, RomId::size>(); } + /// Get immutable ROM ID. RomId::const_span romId() const { return const_cast<CertificateData &>(*this).romId(); } + /// Set ROM ID. CertificateData & setRomId(RomId::const_span romId) { copy(romId, this->romId()); return *this; } + /// @} + /// @name MAN ID + /// @brief Manufacturer ID of the device. /// @{ - /// Manufacturer ID of the device. + + /// Get mutable MAN ID. ManId::span manId() { return make_span(result_).subspan<manIdIdx, ManId::size>(); } + /// Get immutable MAN ID. ManId::const_span manId() const { return const_cast<CertificateData &>(*this).manId(); } + /// Set MAN ID. CertificateData & setManId(ManId::const_span manId) { copy(manId, this->manId()); return *this; } + /// @} private:
--- a/Utilities/Error.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/Error.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -37,8 +37,8 @@ namespace MaximInterface { -/// Get the default error message associated with a condition. Typically used -/// by an error_category when the condition is unknown. +/// @brief Get the default error message associated with a condition. +/// @details Typically used by an error_category when the condition is unknown. MaximInterface_EXPORT const char * defaultErrorMessage(int condition); }
--- a/Utilities/FlagSet.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/FlagSet.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -38,6 +38,7 @@ namespace MaximInterface { +/// @brief /// Provides functionality similar to std::bitset except using a bit flag, /// typically of an enum type, as the indexer. template <typename Flag, size_t flagBits> class FlagSet { @@ -87,6 +88,7 @@ /// @name Element access /// @{ + bool operator[](Flag flag) const { return test(flag); } reference operator[](Flag flag) { return reference(*this, flag); } @@ -98,15 +100,19 @@ bool none() const { return bits.none(); } size_t count() const { return bits.count(); } + /// @} /// @name Capacity /// @{ + size_t size() const { return bits.size(); } + /// @} /// @name Modifiers /// @{ + FlagSet & operator&=(const FlagSet & other) { bits &= other.bits; return *this; @@ -154,16 +160,19 @@ bits ^= flag; return *this; } + /// @} /// @name Conversions /// @{ + template <typename CharT, typename Traits, typename Allocator> std::basic_string<CharT, Traits, Allocator> to_string() const { return bits.template to_string<CharT, Traits, Allocator>(); } unsigned long to_ulong() const { return bits.to_ulong(); } + /// @} private:
--- a/Utilities/Function.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/Function.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -240,7 +240,7 @@ } // namespace detail -// Function wrapper similar to std::function for 0-2 argument functions. +// Function wrapper similar to std::function for 0-3 argument functions. template <typename> class Function; // Function implementation for zero argument functions.
--- a/Utilities/RomId.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/RomId.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -41,29 +41,37 @@ /// Standard container for a 1-Wire ROM ID. typedef array_span<uint_least8_t, 8> RomId; +/// @name Family Code /// @{ -/// Access the Family Code byte. + +/// Get the Family Code byte. inline RomId::element familyCode(RomId::const_span romId) { return romId[0]; } +/// Set the Family Code byte. inline void setFamilyCode(RomId::span romId, RomId::element familyCode) { romId[0] = familyCode; } + /// @} +/// @name CRC8 /// @{ -/// Access the CRC8 byte. + +/// Get the CRC8 byte. inline RomId::element crc8(RomId::const_span romId) { return *romId.last<1>().data(); } +/// Set the CRC8 byte. inline void setCrc8(RomId::span romId, RomId::element crc8) { *romId.last<1>().data() = crc8; } + /// @} -/// Check if the ROM ID is valid (Family Code and CRC8 are both valid). +/// @brief Check if the ROM ID is valid (Family Code and CRC8 are both valid). /// @returns True if the ROM ID is valid. inline bool valid(RomId::const_span romId) { return calculateCrc8(romId.first(romId.size() - 1)) == crc8(romId);
--- a/Utilities/SafeBool.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/SafeBool.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -49,6 +49,8 @@ } // namespace detail +/// @brief Type definition for SafeBool. +/// @details /// SafeBool is a boolean type that eliminates many error-prone implicit /// conversions allowed by the fundamental bool type. /// @note
--- a/Utilities/Segment.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/Segment.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -39,8 +39,9 @@ namespace MaximInterface { +/// @brief /// Advances a given iterator by a given number of elements with bounds checking. -/// InputIt must meet the requirements of InputIterator. +/// @tparam InputIt Must meet the requirements of InputIterator. /// @param[in,out] it Iterator to advance. /// @param bound /// Past-the-end boundary iterator. If distance is positive, bound must be @@ -97,14 +98,17 @@ return distance; } -/// Locates an iterator sub-range using segment number addressing. Useful for -/// devices that divide the memory space into uniform chunks such as pages and -/// segments. ForwardIt must meet the requirements of ForwardIterator. +/// @brief Locates an iterator sub-range using segment number addressing. +/// @details +/// Useful for devices that divide the memory space into uniform chunks such as +/// pages and segments. +/// @tparam ForwardIt Must meet the requirements of ForwardIterator. /// @param begin Beginning of the input data range. /// @param end End of the input data range. /// @param segmentSize Number of elements contained in a segment. /// @param segmentNum Zero-indexed number of the desired segment. -/// @returns Pair of iterators representing the sub-range of the segment within +/// @returns +/// Pair of iterators representing the sub-range of the segment within /// the input range. If the segment does not exist within the input range, both /// iterators in the pair are set to the end iterator of the input range. template <typename ForwardIt, typename Index>
--- a/Utilities/Sha256.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/Sha256.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -42,12 +42,12 @@ /// Container for a SHA-256 hash. typedef array_span<uint_least8_t, 32> Hash; -/// Data for Compute Write MAC operation. +/// @brief Data for Compute Write MAC operation. /// @details /// Used by SHA-256 MAC authenticators including DS28E15/22/25 and DS2465. typedef array_span<uint_least8_t, 20> WriteMacData; -/// Data for the Compute Auth. MAC and Compute Slave Secret operations. +/// @brief Data for the Compute Auth. MAC and Compute Slave Secret operations. /// @copydetails WriteMacData typedef array_span<uint_least8_t, 76> AuthenticationData;
--- a/Utilities/array.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/array.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -57,6 +57,7 @@ /// @name Element access /// @{ + reference operator[](size_type pos) { return const_cast<reference>( static_cast<const array &>(*this).operator[](pos)); @@ -81,10 +82,12 @@ } const_pointer data() const { return _buffer; } + /// @} /// @name Iterators - /// @{ + /// @{ + iterator begin() { return const_cast<iterator>(static_cast<const array &>(*this).cbegin()); } @@ -116,10 +119,12 @@ } const_reverse_iterator crend() const { return rend(); } + /// @} /// @name Capacity /// @{ + static bool empty() { return size() == 0; } static size_type size() { return N; } @@ -128,17 +133,20 @@ /// Alternative to size() when a constant expression is required. static const size_type csize = N; + /// @} /// @name Operations /// @{ + void fill(const_reference value) { std::fill(begin(), end(), value); } void swap(array & other) { std::swap_ranges(begin(), end(), other.begin()); } + /// @} /// @private - /// Implementation detail set public to allow aggregate initialization. + /// @note Implementation detail set public to allow aggregate initialization. T _buffer[N]; };
--- a/Utilities/array_span.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/array_span.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -39,9 +39,10 @@ namespace MaximInterface { +/// @brief /// Defines a standard set of types for data fields that are represented as a /// fixed-size array of elements. -/// @note A const qualifier on T is not allowed. +/// @tparam T A const qualifier is not allowed. template <typename T, size_t N> struct array_span { typedef typename remove_volatile<T>::type element; static const size_t size = N;
--- a/Utilities/crc.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/crc.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -40,28 +40,28 @@ namespace MaximInterface { -/// Perform a CRC8 calculation. +/// @brief Perform a CRC8 calculation. /// @param data Data to pass though the CRC generator. /// @param crc Beginning state of the CRC generator. /// @returns The calculated CRC8. MaximInterface_EXPORT uint_fast8_t calculateCrc8(uint_fast8_t data, uint_fast8_t crc = 0); -/// Perform a CRC8 calculation with variable length data. +/// @brief Perform a CRC8 calculation with variable length data. /// @param[in] data Data array to pass through the CRC generator. /// @param crc Beginning state of the CRC generator. /// @returns The calculated CRC8. MaximInterface_EXPORT uint_fast8_t calculateCrc8(span<const uint_least8_t> data, uint_fast8_t crc = 0); -/// Perform a CRC16 calculation. +/// @brief Perform a CRC16 calculation. /// @param data Data to pass though the CRC generator. /// @param crc Beginning state of the CRC generator. /// @returns The calculated CRC16. MaximInterface_EXPORT uint_fast16_t calculateCrc16(uint_fast8_t data, uint_fast16_t crc = 0); -/// Perform a CRC16 calculation with variable length data. +/// @brief Perform a CRC16 calculation with variable length data. /// @param[in] data Data array to pass through the CRC generator. /// @param crc Beginning state of the CRC generator. /// @returns The calculated CRC16.
--- a/Utilities/optional.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/optional.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -47,7 +47,7 @@ static const nullopt_t nullopt(0); -/// Optional value container similar to std::optional. +/// @brief Optional value container similar to std::optional. /// @details /// To prevent the need for aligned storage, this implementation imposes that /// types must be DefaultConstructible, CopyConstructible, and CopyAssignable.
--- a/Utilities/span.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/span.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -77,6 +77,7 @@ public: /// @name Iterators /// @{ + iterator begin() const { return const_cast<iterator>(static_cast<const span_base &>(*this).cbegin()); } @@ -100,19 +101,23 @@ const_reverse_iterator crend() const { return const_reverse_iterator(cbegin()); } + /// @} /// @name Element access /// @{ + reference operator[](index_type idx) const { return data()[idx]; } reference operator()(index_type idx) const { return operator[](idx); } pointer data() const { return data_; } + /// @} /// @name Subviews /// @{ + template <index_type Count> span<element_type, Count> first() const { return subspan<0, Count>(); } @@ -133,6 +138,7 @@ return span<element_type>( data() + Offset, Count == dynamic_extent ? size() - Offset : Count); } + /// @} private: @@ -185,18 +191,22 @@ /// @name Observers /// @{ + static index_type size() { return extent; } static index_type size_bytes() { return size() * sizeof(element_type); } static bool empty() { return size() == 0; } + /// @} /// @name Subviews /// @{ + template <index_type Count> span<element_type, Count> last() const { return this->template subspan<extent - Count, Count>(); } + /// @} }; @@ -246,18 +256,22 @@ /// @name Observers /// @{ + index_type size() const { return size_; } index_type size_bytes() const { return size() * sizeof(element_type); } bool empty() const { return size() == 0; } + /// @} /// @name Subviews /// @{ + template <index_type Count> span<element_type, Count> last() const { return span<element_type, Count>(this->data() + (size() - Count), Count); } + /// @} private:
--- a/Utilities/system_error.hpp Wed Jan 23 13:11:04 2019 -0600 +++ b/Utilities/system_error.hpp Mon Mar 04 08:10:00 2019 -0600 @@ -31,8 +31,9 @@ *******************************************************************************/ /// @file -/// Error handling constructs similar std::error_code, std::error_condition, and -/// std::error_category. +/// @brief +/// Error handling constructs similar to std::error_code, std::error_condition, +/// and std::error_category. #ifndef MaximInterface_system_error #define MaximInterface_system_error