| 6 | #include <string> |
| 7 | |
| 8 | TEST(StdInputStream, SanitizesNullAndInvalidUtf8) |
| 9 | { |
| 10 | // bytes: 'A' 0xC3 0x28 'B' 0x00 'C' 0x80 |
| 11 | // - 0xC3 0x28 is an invalid 2-byte sequence; we replace the lead byte with '?' |
| 12 | // - 0x00 is replaced with '?' |
| 13 | // - 0x80 is a stray continuation byte; replaced with '?' |
| 14 | std::string bytes; |
| 15 | bytes.push_back('A'); |
| 16 | bytes.push_back(static_cast<char>(0xC3)); |
| 17 | bytes.push_back(static_cast<char>(0x28)); |
| 18 | bytes.push_back('B'); |
| 19 | bytes.push_back(static_cast<char>(0x00)); |
| 20 | bytes.push_back('C'); |
| 21 | bytes.push_back(static_cast<char>(0x80)); |
| 22 | |
| 23 | std::istringstream in(std::string(bytes.data(), bytes.size()), std::ios::binary); |
| 24 | Base::StdInputStream stream(in); |
| 25 | |
| 26 | XMLByte out[32] {}; |
| 27 | const XMLSize_t n = stream.readBytes(out, sizeof(out)); |
| 28 | ASSERT_EQ(n, bytes.size()); |
| 29 | |
| 30 | // Ensure no embedded NUL remains. |
| 31 | for (XMLSize_t i = 0; i < n; ++i) { |
| 32 | EXPECT_NE(out[i], static_cast<XMLByte>(0)) << "NUL byte remained at index " << i; |
| 33 | } |
| 34 | |
| 35 | EXPECT_EQ(out[0], static_cast<XMLByte>('A')); |
| 36 | EXPECT_EQ(out[1], static_cast<XMLByte>('?')); // invalid lead byte replaced |
| 37 | EXPECT_EQ(out[2], static_cast<XMLByte>('(')); // ASCII preserved |
| 38 | EXPECT_EQ(out[3], static_cast<XMLByte>('B')); |
| 39 | EXPECT_EQ(out[4], static_cast<XMLByte>('?')); // embedded NUL replaced |
| 40 | EXPECT_EQ(out[5], static_cast<XMLByte>('C')); |
| 41 | EXPECT_EQ(out[6], static_cast<XMLByte>('?')); // stray continuation replaced |
| 42 | } |