in src/agent/UnicodeEncoding.h [100:151]
static inline uint32_t decodeUtf8(const char *in) {
const uint32_t kInvalid = static_cast<uint32_t>(-1);
switch (utf8CharLength(in[0])) {
case 1: {
return in[0];
}
case 2: {
if ((in[1] & 0xC0) != 0x80) {
return kInvalid;
}
uint32_t tmp = 0;
tmp = (in[0] & 0x1F) << 6;
tmp |= (in[1] & 0x3F);
return tmp <= 0x7F ? kInvalid : tmp;
}
case 3: {
if ((in[1] & 0xC0) != 0x80 ||
(in[2] & 0xC0) != 0x80) {
return kInvalid;
}
uint32_t tmp = 0;
tmp = (in[0] & 0x0F) << 12;
tmp |= (in[1] & 0x3F) << 6;
tmp |= (in[2] & 0x3F);
if (tmp <= 0x07FF || (tmp >= 0xD800 && tmp <= 0xDFFF)) {
return kInvalid;
} else {
return tmp;
}
}
case 4: {
if ((in[1] & 0xC0) != 0x80 ||
(in[2] & 0xC0) != 0x80 ||
(in[3] & 0xC0) != 0x80) {
return kInvalid;
}
uint32_t tmp = 0;
tmp = (in[0] & 0x07) << 18;
tmp |= (in[1] & 0x3F) << 12;
tmp |= (in[2] & 0x3F) << 6;
tmp |= (in[3] & 0x3F);
if (tmp <= 0xFFFF || tmp > 0x10FFFF) {
return kInvalid;
} else {
return tmp;
}
}
default: {
return kInvalid;
}
}
}