#include #include #include #include namespace trygvis { namespace bluetooth { using namespace std; std::ostream &operator<<(std::ostream &s, Uuid const &uuid) { s << uuid.str(); return s; } std::string Uuid::str() const { char str[37]; std::snprintf(str, sizeof(str), "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x", value[0], value[1], value[2], value[3], value[4], value[5], value[6], value[7], value[8], value[9], value[10], value[11], value[12], value[13], value[14], value[15]); return {str}; } o Uuid::fromString(const std::string &str) { try { if (str.size() == 4) { unsigned long x = std::stoul(str, nullptr, 16); if (x > std::numeric_limits::max()) { return {}; } return {ShortUuid{static_cast(x)}.toLong()}; } else if (str.size() == 36) { uint8_t bytes[16]; unsigned i = 0; for (unsigned byte = 0; byte < 16; byte++) { switch (byte) { case 4: case 6: case 8: case 10: i++; break; default: break; } auto tmp = str.substr(i, 2); // cout << "str=" << tmp << endl; unsigned long x = std::stoul(tmp, nullptr, 16); if (x > std::numeric_limits::max()) { return {}; } bytes[byte] = static_cast(x); i += 2; } return {Uuid{bytes}}; } else { return {}; } } catch (std::invalid_argument &) { return {}; } catch (std::out_of_range &) { return {}; } } Uuid makeUuid(const Uuid &base, uint8_t a, uint8_t b) { uint8_t value[16]; memcpy(value, base.value, 16); value[2] = a; value[3] = b; return Uuid{value}; } std::string ShortUuid::str() const noexcept { char str[sizeof("abcd")]; std::snprintf(str, sizeof(str), "%02x%02x", int(value >> 8), int(value & 0xff)); return {str}; } } // namespace bluetooth } // namespace trygvis