Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: mbed_DS28EC20_GPIO
DS28E17.cpp
00001 /******************************************************************************* 00002 * Copyright (C) 2017 Maxim Integrated Products, Inc., All Rights Reserved. 00003 * 00004 * Permission is hereby granted, free of charge, to any person obtaining a 00005 * copy of this software and associated documentation files (the "Software"), 00006 * to deal in the Software without restriction, including without limitation 00007 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 00008 * and/or sell copies of the Software, and to permit persons to whom the 00009 * Software is furnished to do so, subject to the following conditions: 00010 * 00011 * The above copyright notice and this permission notice shall be included 00012 * in all copies or substantial portions of the Software. 00013 * 00014 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 00015 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 00016 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 00017 * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES 00018 * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 00019 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 00020 * OTHER DEALINGS IN THE SOFTWARE. 00021 * 00022 * Except as contained in this notice, the name of Maxim Integrated 00023 * Products, Inc. shall not be used except as stated in the Maxim Integrated 00024 * Products, Inc. Branding Policy. 00025 * 00026 * The mere transfer of this software does not imply any licenses 00027 * of trade secrets, proprietary technology, copyrights, patents, 00028 * trademarks, maskwork rights, or any other form of intellectual 00029 * property whatsoever. Maxim Integrated Products, Inc. retains all 00030 * ownership rights. 00031 *******************************************************************************/ 00032 00033 #include <stddef.h> 00034 #include <MaximInterface/Links/OneWireMaster.hpp> 00035 #include <MaximInterface/Utilities/crc.hpp> 00036 #include <MaximInterface/Utilities/Error.hpp> 00037 #include "DS28E17.hpp" 00038 00039 namespace MaximInterface { 00040 00041 error_code DS28E17::writeDataWithStop(uint_least8_t I2C_addr, 00042 span<const uint_least8_t> data, 00043 uint_least8_t * wr_status) { 00044 return sendPacket(WriteDataWithStopCmd, &I2C_addr, data, 00045 span<uint_least8_t>(), wr_status); 00046 } 00047 00048 error_code DS28E17::writeDataNoStop(uint_least8_t I2C_addr, 00049 span<const uint_least8_t> data, 00050 uint_least8_t * wr_status) { 00051 return sendPacket(WriteDataNoStopCmd, &I2C_addr, data, span<uint_least8_t>(), 00052 wr_status); 00053 } 00054 00055 error_code DS28E17::writeDataOnly(span<const uint_least8_t> data, 00056 uint_least8_t * wr_status) { 00057 return sendPacket(WriteDataOnlyCmd, NULL, data, span<uint_least8_t>(), 00058 wr_status); 00059 } 00060 00061 error_code DS28E17::writeDataOnlyWithStop(span<const uint_least8_t> data, 00062 uint_least8_t * wr_status) { 00063 return sendPacket(WriteDataOnlyWithStopCmd, NULL, data, span<uint_least8_t>(), 00064 wr_status); 00065 } 00066 00067 error_code DS28E17::writeReadDataWithStop(uint_least8_t I2C_addr, 00068 span<const uint_least8_t> write_data, 00069 span<uint_least8_t> read_data, 00070 uint_least8_t * wr_status) { 00071 return sendPacket(WriteReadDataWithStopCmd, &I2C_addr, write_data, read_data, 00072 wr_status); 00073 } 00074 00075 error_code DS28E17::readDataWithStop(uint_least8_t I2C_addr, 00076 span<uint_least8_t> data) { 00077 return sendPacket(ReadDataWithStopCmd, &I2C_addr, span<const uint_least8_t>(), 00078 data, NULL); 00079 } 00080 00081 error_code DS28E17::writeConfigReg(I2CSpeed speed) { 00082 error_code result = selectRom(*master); 00083 if (!result) { 00084 // Send CMD and Data 00085 const uint_least8_t send_block[] = {WriteConfigurationCmd, 00086 static_cast<uint_least8_t>(speed)}; 00087 result = master->writeBlock(send_block); 00088 } 00089 return result; 00090 } 00091 00092 error_code DS28E17::readConfigReg(I2CSpeed & speed) { 00093 error_code result = selectRom(*master); 00094 if (!result) { 00095 // Send CMD and receive Data 00096 result = master->writeByte(ReadConfigurationCmd); 00097 if (!result) { 00098 uint_least8_t config; 00099 result = master->readByte(config); 00100 if (!result) { 00101 switch (config) { 00102 case Speed100kHz: 00103 case Speed400kHz: 00104 case Speed900kHz: 00105 speed = static_cast<I2CSpeed>(config); 00106 break; 00107 00108 default: 00109 result = make_error_code(OutOfRangeError); 00110 break; 00111 } 00112 } 00113 } 00114 } 00115 return result; 00116 } 00117 00118 error_code DS28E17::enableSleepMode() { 00119 error_code result = selectRom(*master); 00120 if (!result) { 00121 // Send CMD 00122 result = master->writeByte(EnableSleepModeCmd); 00123 } 00124 return result; 00125 } 00126 00127 error_code DS28E17::readDeviceRevision(uint_least8_t & rev) { 00128 error_code result = selectRom(*master); 00129 if (!result) { 00130 // Send CMD and receive Data 00131 result = master->writeByte(ReadDeviceRevisionCmd); 00132 if (!result) { 00133 result = master->readByte(rev); 00134 } 00135 } 00136 return result; 00137 } 00138 00139 error_code DS28E17::sendPacket(Command command, const uint_least8_t * I2C_addr, 00140 span<const uint_least8_t> write_data, 00141 span<uint_least8_t> read_data, 00142 uint_least8_t * wr_status) { 00143 const int pollLimit = 10000; 00144 const span<const uint_least8_t>::index_type maxDataLen = 255; 00145 00146 if ((!write_data.empty() && write_data.size() > maxDataLen) || 00147 (!read_data.empty() && read_data.size() > maxDataLen)) { 00148 return make_error_code(OutOfRangeError); 00149 } 00150 00151 error_code result = selectRom(*master); 00152 if (result) { 00153 return result; 00154 } 00155 uint_fast16_t crc16 = calculateCrc16(command); 00156 result = master->writeByte(command); 00157 if (result) { 00158 return result; 00159 } 00160 if (I2C_addr) { 00161 crc16 = calculateCrc16(*I2C_addr, crc16); 00162 result = master->writeByte(*I2C_addr); 00163 if (result) { 00164 return result; 00165 } 00166 } 00167 if (!write_data.empty()) { 00168 crc16 = calculateCrc16(static_cast<uint_fast8_t>(write_data.size()), crc16); 00169 result = master->writeByte(static_cast<uint_least8_t>(write_data.size())); 00170 if (result) { 00171 return result; 00172 } 00173 crc16 = calculateCrc16(write_data, crc16); 00174 result = master->writeBlock(write_data); 00175 if (result) { 00176 return result; 00177 } 00178 } 00179 if (!read_data.empty()) { 00180 crc16 = calculateCrc16(static_cast<uint_fast8_t>(read_data.size()), crc16); 00181 result = master->writeByte(static_cast<uint_least8_t>(read_data.size())); 00182 if (result) { 00183 return result; 00184 } 00185 } 00186 crc16 ^= 0xFFFFU; 00187 const uint_least8_t crc16Bytes[] = {static_cast<uint_least8_t>(crc16), 00188 static_cast<uint_least8_t>(crc16 >> 8)}; 00189 result = master->writeBlock(crc16Bytes); 00190 if (result) { 00191 return result; 00192 } 00193 // Poll for Zero 1-Wire bit and return if an error occurs 00194 int poll_count = 0; 00195 bool recvbit; 00196 do { 00197 if (poll_count++ < pollLimit) { 00198 return make_error_code(TimeoutError); 00199 } 00200 result = master->readBit(recvbit); 00201 if (result) { 00202 return result; 00203 } 00204 } while (recvbit); 00205 uint_least8_t status; 00206 result = master->readByte(status); 00207 if (result) { 00208 return result; 00209 } 00210 if ((status & 0x1) == 0x1) { 00211 return make_error_code(InvalidCrc16Error); 00212 } 00213 if ((status & 0x2) == 0x2) { 00214 return make_error_code(AddressNackError); 00215 } 00216 if ((status & 0x8) == 0x8) { 00217 return make_error_code(InvalidStartError); 00218 } 00219 if (!write_data.empty()) { 00220 result = master->readByte(status); 00221 if (result) { 00222 return result; 00223 } 00224 if (wr_status) { 00225 *wr_status = status; 00226 } 00227 if (status != 0) { 00228 return make_error_code(WriteNackError); 00229 } 00230 } 00231 if (!read_data.empty()) { 00232 result = master->readBlock(read_data); 00233 } 00234 return result; 00235 } 00236 00237 const error_category & DS28E17::errorCategory() { 00238 static class : public error_category { 00239 public: 00240 virtual const char * name() const { return "DS28E17"; } 00241 00242 virtual std::string message(int condition) const { 00243 switch (condition) { 00244 case TimeoutError: 00245 return "Timeout Error"; 00246 00247 case OutOfRangeError: 00248 return "Out of Range Error"; 00249 00250 case InvalidCrc16Error: 00251 return "Invalid CRC16 Error"; 00252 00253 case AddressNackError: 00254 return "Address Nack Error"; 00255 00256 case InvalidStartError: 00257 return "Invalid Start Error"; 00258 00259 case WriteNackError: 00260 return "Write Nack Error"; 00261 00262 default: 00263 return defaultErrorMessage(condition); 00264 } 00265 } 00266 } instance; 00267 return instance; 00268 } 00269 00270 } // namespace MaximInterface
Generated on Tue Jul 12 2022 23:29:45 by
1.7.2