diff --git a/apps/android/app/src/main/java/com/steipete/clawdis/node/bridge/BonjourEscapes.kt b/apps/android/app/src/main/java/com/steipete/clawdis/node/bridge/BonjourEscapes.kt index 5c875ba1a..c250751a3 100644 --- a/apps/android/app/src/main/java/com/steipete/clawdis/node/bridge/BonjourEscapes.kt +++ b/apps/android/app/src/main/java/com/steipete/clawdis/node/bridge/BonjourEscapes.kt @@ -4,7 +4,7 @@ object BonjourEscapes { fun decode(input: String): String { if (input.isEmpty()) return input - val out = StringBuilder(input.length) + val bytes = mutableListOf() var i = 0 while (i < input.length) { if (input[i] == '\\' && i + 3 < input.length) { @@ -14,17 +14,22 @@ object BonjourEscapes { if (d0.isDigit() && d1.isDigit() && d2.isDigit()) { val value = ((d0.code - '0'.code) * 100) + ((d1.code - '0'.code) * 10) + (d2.code - '0'.code) - if (value in 0..0x10FFFF) { - out.appendCodePoint(value) + if (value in 0..255) { + bytes.add(value.toByte()) i += 4 continue } } } - out.append(input[i]) - i += 1 + val codePoint = Character.codePointAt(input, i) + val charBytes = String(Character.toChars(codePoint)).toByteArray(Charsets.UTF_8) + for (b in charBytes) { + bytes.add(b) + } + i += Character.charCount(codePoint) } - return out.toString() + + return String(bytes.toByteArray(), Charsets.UTF_8) } } diff --git a/apps/android/app/src/test/java/com/steipete/clawdis/node/bridge/BonjourEscapesTest.kt b/apps/android/app/src/test/java/com/steipete/clawdis/node/bridge/BonjourEscapesTest.kt index 546430202..f898b6d19 100644 --- a/apps/android/app/src/test/java/com/steipete/clawdis/node/bridge/BonjourEscapesTest.kt +++ b/apps/android/app/src/test/java/com/steipete/clawdis/node/bridge/BonjourEscapesTest.kt @@ -14,6 +14,6 @@ class BonjourEscapesTest { fun decodeDecodesDecimalEscapes() { assertEquals("Clawdis Gateway", BonjourEscapes.decode("Clawdis\\032Gateway")) assertEquals("A B", BonjourEscapes.decode("A\\032B")) + assertEquals("Peter\u2019s Mac", BonjourEscapes.decode("Peter\\226\\128\\153s Mac")) } } -