| 256 | return false; |
| 257 | } |
| 258 | |
| 259 | digitCount++; |
| 260 | } |
| 261 | |
| 262 | return (digitCount > 0 && (digitCount % 2 == 0)); |
| 263 | } |
| 264 | |
| 265 | bool String::validateHex(std::string &hex) |
| 266 | { |
| 267 | if (hex.empty()) |
| 268 | return false; |
| 269 | |
| 270 | size_t len = hex.length(); |
| 271 | size_t startOffset = (len >= 2 && hex[0] == '0' && (hex[1] == 'x' || hex[1] == 'X')) ? 2 : 0; |
| 272 | |
| 273 | size_t actualByteCount = 0; |
| 274 | bool needsCleaning = (startOffset > 0); |
| 275 | |
| 276 | for (size_t i = startOffset; i < len; ++i) |
| 277 | { |
| 278 | unsigned char c = static_cast<unsigned char>(hex[i]); |
| 279 | |
| 280 | if (::isspace(c)) |
| 281 | { |
| 282 | needsCleaning = true; |
| 283 | continue; |
| 284 | } |
| 285 | |
| 286 | if (!::isxdigit(c)) |
| 287 | return false; |
| 288 | |
| 289 | actualByteCount++; |
| 290 | } |
| 291 | |
| 292 | if (actualByteCount == 0 || (actualByteCount % 2 != 0)) |
| 293 | return false; |
| 294 | |
| 295 | if (needsCleaning) |
| 296 | { |
| 297 | std::string cleaned; |
| 298 | cleaned.reserve(actualByteCount); |
| 299 | for (size_t i = startOffset; i < len; ++i) |
| 300 | { |
| 301 | unsigned char c = static_cast<unsigned char>(hex[i]); |
| 302 | if (!::isspace(c)) |
| 303 | { |
| 304 | cleaned.push_back(c); |
| 305 | } |
| 306 | } |
| 307 | hex = std::move(cleaned); |
nothing calls this directly
no outgoing calls
no test coverage detected