/* * Copyright (c) 2017, The OpenThread Authors. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of the copyright holder nor the * names of its contributors may be used to endorse or promote products * derived from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. */ /** * @file * This file includes definition for Thread Management Framework(TMF) Tlv. */ #ifndef OTBR_COMMON_TLV_HPP_ #define OTBR_COMMON_TLV_HPP_ #include "openthread-br/config.h" #include #include namespace otbr { /** * This class implements TMF Tlv functionality. */ class Tlv { enum { kLengthEscape = 0xff, ///< This length value indicates the actual length is of two-bytes length. }; public: /** * This method returns the Tlv type. * * @returns The Tlv type. */ uint8_t GetType(void) const { return mType; } /** * This method sets the Tlv type. */ void SetType(uint8_t aType) { mType = aType; } /** * This method returns the Tlv length. * * @returns The Tlv length. */ uint16_t GetLength(void) const { return (mLength != kLengthEscape ? mLength : static_cast((&mLength)[1] << 8 | (&mLength)[2])); } /** * This method sets the length. */ void SetLength(uint16_t aLength, bool aForceExtended = false) { if (aLength >= kLengthEscape || aForceExtended) { mLength = kLengthEscape; (&mLength)[1] = (aLength >> 8); (&mLength)[2] = (aLength & 0xff); } else { mLength = static_cast(aLength); } } /** * This method returns a pointer to the value. * * @returns The Tlv value. */ const void *GetValue(void) const { return reinterpret_cast(this) + sizeof(mType) + (mLength != kLengthEscape ? sizeof(mLength) : (sizeof(uint16_t) + sizeof(mLength))); } /** * This method returns the value as a uint16_t. * * @returns The uint16_t value. */ uint16_t GetValueUInt16(void) const { const uint8_t *p = static_cast(GetValue()); return static_cast(p[0] << 8 | p[1]); } /** * This method returns the value as a uint8_t. * * @returns The uint8_t value. */ uint8_t GetValueUInt8(void) const { return *static_cast(GetValue()); } /** * This method sets a uint64_t as the value. * * @param[in] aValue The uint64_t value. */ void SetValue(uint64_t aValue) { uint8_t *value; SetLength(sizeof(aValue), false); value = static_cast(GetValue()); for (int i = 0; i < int{sizeof(aValue)}; ++i) { value[i] = (aValue >> (8 * (sizeof(aValue) - i - 1))) & 0xff; } } /** * This method sets a uint32_t as the value. * * @param[in] aValue The uint32_t value. */ void SetValue(uint32_t aValue) { uint8_t *value; SetLength(sizeof(aValue), false); value = static_cast(GetValue()); for (int i = 0; i < int{sizeof(aValue)}; ++i) { value[i] = (aValue >> (8 * (sizeof(aValue) - i - 1))) & 0xff; } } /** * This method sets uint16_t as the value. * * @param[in] aValue The uint16_t value. */ void SetValue(uint16_t aValue) { uint8_t *value; SetLength(sizeof(aValue), false); value = static_cast(GetValue()); value[0] = (aValue >> 8); value[1] = (aValue & 0xff); } /** * This method sets uint8_t as the value. * * @param[in] aValue The uint8_t value. */ void SetValue(uint8_t aValue) { SetLength(sizeof(aValue), false); *static_cast(GetValue()) = aValue; } /** * This method sets int8_t as the value. * * @param[in] aValue The int8_t value. */ void SetValue(int8_t aValue) { SetLength(sizeof(aValue), false); *static_cast(GetValue()) = aValue; } /** * This method copies the value. */ void SetValue(const void *aValue, uint16_t aLength, bool aForceExtended = false) { SetLength(aLength, aForceExtended); memcpy(GetValue(), aValue, aLength); } /** * This method returns the pointer to the next Tlv. * * @returns A pointer to the next Tlv. */ const Tlv *GetNext(void) const { return reinterpret_cast(static_cast(GetValue()) + GetLength()); } /** * This method returns the pointer to the next Tlv. * * @returns A pointer to the next Tlv. */ Tlv *GetNext(void) { return reinterpret_cast(static_cast(GetValue()) + GetLength()); } private: void *GetValue(void) { return reinterpret_cast(this) + sizeof(mType) + (mLength != kLengthEscape ? sizeof(mLength) : (sizeof(uint16_t) + sizeof(mLength))); } uint8_t mType; uint8_t mLength; }; namespace Meshcop { enum { kState = 16, kCommissionerId = 10, kCommissionerSessionId = 11, kJoinerDtlsEncapsulation = 17, kSteeringData = 8, kJoinerUdpPort = 18, kJoinerIid = 19, kJoinerRouterLocator = 20, kJoinerRouterKek = 21, kUdpEncapsulation = 48, kIPv6Address = 49, }; enum { kStateAccepted = 1, kStatePending = 0, kStateRejected = -1, }; } // namespace Meshcop } // namespace otbr #endif // OTBR_COMMON_TLV_HPP_