diff options
Diffstat (limited to 'source/Core/UUID.cpp')
-rw-r--r-- | source/Core/UUID.cpp | 279 |
1 files changed, 279 insertions, 0 deletions
diff --git a/source/Core/UUID.cpp b/source/Core/UUID.cpp new file mode 100644 index 0000000000000..c1b3eb13d6563 --- /dev/null +++ b/source/Core/UUID.cpp @@ -0,0 +1,279 @@ +//===-- UUID.cpp ------------------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "lldb/Core/UUID.h" +// C Includes +#include <string.h> +#include <stdio.h> +#include <ctype.h> + +// C++ Includes +#include <string> + +// Other libraries and framework includes +// Project includes +#include "lldb/Core/Stream.h" + +namespace lldb_private { + +UUID::UUID() : m_num_uuid_bytes(16) +{ + ::memset (m_uuid, 0, sizeof(m_uuid)); +} + +UUID::UUID(const UUID& rhs) +{ + m_num_uuid_bytes = rhs.m_num_uuid_bytes; + ::memcpy (m_uuid, rhs.m_uuid, sizeof (m_uuid)); +} + +UUID::UUID (const void *uuid_bytes, uint32_t num_uuid_bytes) +{ + SetBytes (uuid_bytes, num_uuid_bytes); +} + +const UUID& +UUID::operator=(const UUID& rhs) +{ + if (this != &rhs) + { + m_num_uuid_bytes = rhs.m_num_uuid_bytes; + ::memcpy (m_uuid, rhs.m_uuid, sizeof (m_uuid)); + } + return *this; +} + +UUID::~UUID() +{ +} + +void +UUID::Clear() +{ + m_num_uuid_bytes = 16; + ::memset (m_uuid, 0, sizeof(m_uuid)); +} + +const void * +UUID::GetBytes() const +{ + return m_uuid; +} + +std::string +UUID::GetAsString (const char *separator) const +{ + std::string result; + char buf[256]; + if (!separator) + separator = "-"; + const uint8_t *u = (const uint8_t *)GetBytes(); + if (sizeof (buf) > (size_t)snprintf (buf, + sizeof (buf), + "%2.2X%2.2X%2.2X%2.2X%s%2.2X%2.2X%s%2.2X%2.2X%s%2.2X%2.2X%s%2.2X%2.2X%2.2X%2.2X%2.2X%2.2X", + u[0],u[1],u[2],u[3],separator, + u[4],u[5],separator, + u[6],u[7],separator, + u[8],u[9],separator, + u[10],u[11],u[12],u[13],u[14],u[15])) + { + result.append (buf); + if (m_num_uuid_bytes == 20) + { + if (sizeof (buf) > (size_t)snprintf (buf, sizeof (buf), "%s%2.2X%2.2X%2.2X%2.2X", separator,u[16],u[17],u[18],u[19])) + result.append (buf); + } + } + return result; +} + +void +UUID::Dump (Stream *s) const +{ + const uint8_t *u = (const uint8_t *)GetBytes(); + s->Printf ("%2.2X%2.2X%2.2X%2.2X-%2.2X%2.2X-%2.2X%2.2X-%2.2X%2.2X-%2.2X%2.2X%2.2X%2.2X%2.2X%2.2X", + u[0],u[1],u[2],u[3],u[4],u[5],u[6],u[7],u[8],u[9],u[10],u[11],u[12],u[13],u[14],u[15]); + if (m_num_uuid_bytes == 20) + { + s->Printf ("-%2.2X%2.2X%2.2X%2.2X", u[16],u[17],u[18],u[19]); + } +} + +bool +UUID::SetBytes (const void *uuid_bytes, uint32_t num_uuid_bytes) +{ + if (uuid_bytes) + { + switch (num_uuid_bytes) + { + case 20: + m_num_uuid_bytes = 20; + break; + case 16: + m_num_uuid_bytes = 16; + m_uuid[16] = m_uuid[17] = m_uuid[18] = m_uuid[19] = 0; + break; + default: + // Unsupported UUID byte size + m_num_uuid_bytes = 0; + break; + } + + if (m_num_uuid_bytes > 0) + { + ::memcpy (m_uuid, uuid_bytes, m_num_uuid_bytes); + return true; + } + } + ::memset (m_uuid, 0, sizeof(m_uuid)); + return false; +} + +size_t +UUID::GetByteSize() +{ + return m_num_uuid_bytes; +} + +bool +UUID::IsValid () const +{ + return m_uuid[0] || + m_uuid[1] || + m_uuid[2] || + m_uuid[3] || + m_uuid[4] || + m_uuid[5] || + m_uuid[6] || + m_uuid[7] || + m_uuid[8] || + m_uuid[9] || + m_uuid[10] || + m_uuid[11] || + m_uuid[12] || + m_uuid[13] || + m_uuid[14] || + m_uuid[15] || + m_uuid[16] || + m_uuid[17] || + m_uuid[18] || + m_uuid[19]; +} + +static inline int +xdigit_to_int (char ch) +{ + ch = tolower(ch); + if (ch >= 'a' && ch <= 'f') + return 10 + ch - 'a'; + return ch - '0'; +} + +size_t +UUID::DecodeUUIDBytesFromCString (const char *p, ValueType &uuid_bytes, const char **end, uint32_t num_uuid_bytes) +{ + size_t uuid_byte_idx = 0; + if (p) + { + while (*p) + { + if (isxdigit(p[0]) && isxdigit(p[1])) + { + int hi_nibble = xdigit_to_int(p[0]); + int lo_nibble = xdigit_to_int(p[1]); + // Translate the two hex nibble characters into a byte + uuid_bytes[uuid_byte_idx] = (hi_nibble << 4) + lo_nibble; + + // Skip both hex digits + p += 2; + + // Increment the byte that we are decoding within the UUID value + // and break out if we are done + if (++uuid_byte_idx == num_uuid_bytes) + break; + } + else if (*p == '-') + { + // Skip dashes + p++; + } + else + { + // UUID values can only consist of hex characters and '-' chars + break; + } + } + } + if (end) + *end = p; + // Clear trailing bytes to 0. + for (uint32_t i = uuid_byte_idx; i < sizeof(ValueType); i++) + uuid_bytes[i] = 0; + return uuid_byte_idx; +} +size_t +UUID::SetFromCString (const char *cstr, uint32_t num_uuid_bytes) +{ + if (cstr == NULL) + return 0; + + const char *p = cstr; + + // Skip leading whitespace characters + while (isspace(*p)) + ++p; + + const size_t uuid_byte_idx = UUID::DecodeUUIDBytesFromCString (p, m_uuid, &p, num_uuid_bytes); + + // If we successfully decoded a UUID, return the amount of characters that + // were consumed + if (uuid_byte_idx == num_uuid_bytes) + return p - cstr; + + // Else return zero to indicate we were not able to parse a UUID value + return 0; +} + +} + +bool +lldb_private::operator == (const lldb_private::UUID &lhs, const lldb_private::UUID &rhs) +{ + return ::memcmp (lhs.GetBytes(), rhs.GetBytes(), sizeof (lldb_private::UUID::ValueType)) == 0; +} + +bool +lldb_private::operator != (const lldb_private::UUID &lhs, const lldb_private::UUID &rhs) +{ + return ::memcmp (lhs.GetBytes(), rhs.GetBytes(), sizeof (lldb_private::UUID::ValueType)) != 0; +} + +bool +lldb_private::operator < (const lldb_private::UUID &lhs, const lldb_private::UUID &rhs) +{ + return ::memcmp (lhs.GetBytes(), rhs.GetBytes(), sizeof (lldb_private::UUID::ValueType)) < 0; +} + +bool +lldb_private::operator <= (const lldb_private::UUID &lhs, const lldb_private::UUID &rhs) +{ + return ::memcmp (lhs.GetBytes(), rhs.GetBytes(), sizeof (lldb_private::UUID::ValueType)) <= 0; +} + +bool +lldb_private::operator > (const lldb_private::UUID &lhs, const lldb_private::UUID &rhs) +{ + return ::memcmp (lhs.GetBytes(), rhs.GetBytes(), sizeof (lldb_private::UUID::ValueType)) > 0; +} + +bool +lldb_private::operator >= (const lldb_private::UUID &lhs, const lldb_private::UUID &rhs) +{ + return ::memcmp (lhs.GetBytes(), rhs.GetBytes(), sizeof (lldb_private::UUID::ValueType)) >= 0; +} |