1 // Copyright 2020 The Pigweed Authors 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not 4 // use this file except in compliance with the License. You may obtain a copy of 5 // the License at 6 // 7 // https://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 12 // License for the specific language governing permissions and limitations under 13 // the License. 14 #pragma once 15 16 #include <cstdint> 17 18 namespace pw::i2c { 19 20 /// A helper class that represents I2C addresses. 21 /// 22 /// @code{.cpp} 23 /// #include "pw_i2c/address.h" 24 /// 25 /// constexpr pw::i2c::Address kAddress1 = pw::i2c::Address::SevenBit<0x42>(); 26 /// uint8_t raw_address_1 = kAddress1.GetSevenBit(); 27 /// 28 /// const pw::i2c::Address kAddress2(0x200); // 10-bit 29 /// uint16_t raw_address_2 = kAddress2.GetTenBit(); 30 /// // Note: kAddress2.GetSevenBit() would fail an assertion here. 31 /// @endcode 32 class Address { 33 public: 34 static constexpr uint8_t kMaxSevenBitAddress = (1 << 7) - 1; 35 static constexpr uint16_t kMaxTenBitAddress = (1 << 10) - 1; 36 37 /// Creates a `pw::i2c::Address` instance for an address that's 10 bits 38 /// or less. 39 /// 40 /// This constant expression does a compile-time assertion to ensure that the 41 /// provided address is 10 bits or less. 42 /// 43 /// @code{.cpp} 44 /// constexpr pw::i2c::Address kAddress = pw::i2c::Address::TenBit(0x200); 45 /// @endcode 46 /// 47 /// @returns A `pw::i2c::Address` instance. 48 template <uint16_t kAddress> TenBit()49 static constexpr Address TenBit() { 50 static_assert(kAddress <= kMaxTenBitAddress); 51 return Address(kAddress, kAlreadyCheckedAddress); 52 } 53 54 /// Creates a `pw::i2c::Address` instance for an address that's 7 bits 55 /// or less. 56 /// 57 /// This constant expression does a compile-time assertion to ensure that the 58 /// provided address is 7 bits or less. 59 /// 60 /// @code{.cpp} 61 /// constexpr pw::i2c::Address kAddress = pw::i2c::Address::SevenBit(0x42); 62 /// @endcode 63 /// 64 /// @returns A `pw::i2c::Address` instance. 65 template <uint8_t kAddress> SevenBit()66 static constexpr Address SevenBit() { 67 static_assert(kAddress <= kMaxSevenBitAddress); 68 return Address(kAddress, kAlreadyCheckedAddress); 69 } 70 71 /// Creates a `pw::i2c::Address` instance. 72 /// 73 /// @param[in] address A 10-bit address as an unsigned integer. This method 74 /// does a runtime assertion to ensure that `address` is 10 bits or less. 75 /// 76 /// @code{.cpp} 77 /// constexpr pw::i2c::Address kAddress(0x200); 78 /// @endcode 79 /// 80 /// @returns A `pw::i2c::Address` instance. 81 explicit Address(uint16_t address); 82 83 /// Gets the 7-bit address that was provided when this instance was created. 84 /// 85 /// This method does a runtime assertion to ensure that the address is 7 bits 86 /// or less. 87 /// 88 /// @returns A 7-bit address as an unsigned integer. 89 uint8_t GetSevenBit() const; 90 91 /// Gets the 10-bit address that was provided when this instance was created. 92 /// 93 /// @returns A 10-bit address as an unsigned integer. GetTenBit()94 uint16_t GetTenBit() const { return address_; } 95 96 private: 97 enum AlreadyCheckedAddress { kAlreadyCheckedAddress }; Address(uint16_t address,AlreadyCheckedAddress)98 constexpr Address(uint16_t address, AlreadyCheckedAddress) 99 : address_(address) {} 100 101 uint16_t address_; 102 }; 103 104 } // namespace pw::i2c 105