From 7978f0ac8dcebee1f4696bbb0d04638e6a9499cf Mon Sep 17 00:00:00 2001 From: Abduqodiri Qurbonzoda Date: Sun, 31 May 2020 16:32:45 +0300 Subject: [PATCH] Mark old utf8 conversion with deprecation error (#4199) --- backend.native/tests/build.gradle | 2 +- backend.native/tests/runtime/text/utf8.kt | 31 +++--------- runtime/src/main/kotlin/kotlin/Exceptions.kt | 2 +- runtime/src/main/kotlin/kotlin/native/Text.kt | 48 +++++++++++++------ 4 files changed, 43 insertions(+), 40 deletions(-) diff --git a/backend.native/tests/build.gradle b/backend.native/tests/build.gradle index 08cd109c036..00596832604 100644 --- a/backend.native/tests/build.gradle +++ b/backend.native/tests/build.gradle @@ -2288,7 +2288,7 @@ task utf8(type: KonanLocalTest) { // Cannot be executed in the two-stage mode due to KT-33175. // Uses exceptions so cannot run on wasm. enabled = !twoStageEnabled && (project.testTarget != 'wasm32') - goldValue = "Hello\nПривет\n\uD800\uDC00\n\n\uFFFD\uFFFD\n\uFFFD12\n\uFFFD12\n12\uFFFD\n\uD83D\uDE25\n\uD83D\uDE25\n\uD83D\uDE25\n" + goldValue = "Hello\nПривет\n\uD800\uDC00\n\n\uFFFD\uFFFD\n\uFFFD12\n\uFFFD12\n12\uFFFD\n\uD83D\uDE25\n\uD83D\uDE25\n" source = "runtime/text/utf8.kt" } diff --git a/backend.native/tests/runtime/text/utf8.kt b/backend.native/tests/runtime/text/utf8.kt index 531293c2e85..ffbeabf8ccc 100644 --- a/backend.native/tests/runtime/text/utf8.kt +++ b/backend.native/tests/runtime/text/utf8.kt @@ -29,11 +29,9 @@ fun checkUtf16to8(string: String, expected: IntArray, conversion: String.() -> B // Utils for checking successful UTF-16 to UTF-8 conversion. fun checkUtf16to8Replacing(string: String, expected: IntArray) { - checkUtf16to8(string, expected) { toUtf8() } checkUtf16to8(string, expected) { encodeToByteArray() } } fun checkUtf16to8Throwing(string: String, expected: IntArray) { - checkUtf16to8(string, expected) { toUtf8OrThrow() } checkUtf16to8(string, expected) { encodeToByteArray(throwOnInvalidSequence = true) } } fun checkValidUtf16to8(string: String, expected: IntArray) { @@ -42,11 +40,9 @@ fun checkValidUtf16to8(string: String, expected: IntArray) { } fun checkUtf16to8Replacing(string: String, expected: IntArray, start: Int, size: Int) { - checkUtf16to8(string, expected) { toUtf8(start, size) } checkUtf16to8(string, expected) { encodeToByteArray(start, start + size) } } fun checkUtf16to8Throwing(string: String, expected: IntArray, start: Int, size: Int) { - checkUtf16to8(string, expected) { toUtf8OrThrow(start, size) } checkUtf16to8(string, expected) { encodeToByteArray(start, start + size, true) } } fun checkValidUtf16to8(string: String, expected: IntArray, start: Int, size: Int) { @@ -70,22 +66,20 @@ fun checkUtf8to16(expected: String, array: IntArray, conversion: ByteArray.() -> } fun checkZeroTerminatedUtf8to16Replacing(expected: String, array: IntArray) { - checkUtf8to16(expected, array) { stringFromUtf8() } checkUtf8to16(expected, array) { toKString() } + checkUtf8to16(expected, array.copyOf(array.size + 1)) { toKString() } } fun checkUtf8to16Replacing(expected: String, array: IntArray) { - checkUtf8to16(expected, array) { stringFromUtf8() } + checkUtf8to16(expected, array) { decodeToString() } checkZeroTerminatedUtf8to16Replacing(expected, array) - checkZeroTerminatedUtf8to16Replacing(expected, array.copyOf(array.size + 1)) } fun checkZeroTerminatedUtf8to16Throwing(expected: String, array: IntArray) { - checkUtf8to16(expected, array) { stringFromUtf8OrThrow() } checkUtf8to16(expected, array) { toKString(throwOnInvalidSequence = true) } + checkUtf8to16(expected, array.copyOf(array.size + 1)) { toKString(throwOnInvalidSequence = true) } } fun checkUtf8to16Throwing(expected: String, array: IntArray) { checkUtf8to16(expected, array) { decodeToString(throwOnInvalidSequence = true) } checkZeroTerminatedUtf8to16Throwing(expected, array) - checkZeroTerminatedUtf8to16Throwing(expected, array.copyOf(array.size + 1)) } fun checkValidUtf8to16(expected: String, array: IntArray) { checkUtf8to16Replacing(expected, array) @@ -97,22 +91,20 @@ fun checkValidZeroTerminatedUtf8to16(expected: String, array: IntArray) { } fun checkZeroTerminatedUtf8to16Replacing(expected: String, array: IntArray, start: Int, size: Int) { - checkUtf8to16(expected, array) { stringFromUtf8(start, size) } checkUtf8to16(expected, array) { toKString(start, start + size) } + checkUtf8to16(expected, array.copyOf(array.size + 1)) { toKString(start, start + size) } } fun checkUtf8to16Replacing(expected: String, array: IntArray, start: Int, size: Int) { checkUtf8to16(expected, array) { decodeToString(start, start + size) } checkZeroTerminatedUtf8to16Replacing(expected, array, start, size) - checkZeroTerminatedUtf8to16Replacing(expected, array.copyOf(array.size + 1), start, size) } fun checkZeroTerminatedUtf8to16Throwing(expected: String, array: IntArray, start: Int, size: Int) { - checkUtf8to16(expected, array) { stringFromUtf8OrThrow(start, size) } checkUtf8to16(expected, array) { toKString(start, start + size, true) } + checkUtf8to16(expected, array.copyOf(array.size + 1)) { toKString(start, start + size, true) } } fun checkUtf8to16Throwing(expected: String, array: IntArray, start: Int, size: Int) { checkUtf8to16(expected, array) { decodeToString(start, start + size, true) } checkZeroTerminatedUtf8to16Throwing(expected, array, start, size) - checkZeroTerminatedUtf8to16Throwing(expected, array.copyOf(array.size + 1), start, size) } fun checkValidUtf8to16(expected: String, array: IntArray, start: Int, size: Int) { checkUtf8to16Replacing(expected, array, start, size) @@ -141,11 +133,9 @@ fun checkThrows(e: KClass, string: String, action: () -> Unit) { } fun checkUtf16to8Throws(string: String) { - checkThrows(IllegalCharacterConversionException::class, string) { string.toUtf8OrThrow() } checkThrows(CharacterCodingException::class, string) { string.encodeToByteArray(throwOnInvalidSequence = true) } } fun checkUtf16to8Throws(string: String, start: Int, size: Int) { - checkThrows(IllegalCharacterConversionException::class, string) { string.toUtf8OrThrow(start, size) } checkThrows(CharacterCodingException::class, string) { string.encodeToByteArray(start, start + size, true) } } @@ -161,22 +151,20 @@ fun checkUtf8to16Throws(e: KClass, string: String, array: IntArray, } fun checkZeroTerminatedUtf8to16Throws(string: String, array: IntArray) { - checkUtf8to16Throws(IllegalCharacterConversionException::class, string, array) { stringFromUtf8OrThrow() } checkUtf8to16Throws(CharacterCodingException::class, string, array) { toKString(throwOnInvalidSequence = true) } + checkUtf8to16Throws(CharacterCodingException::class, string, array.copyOf(array.size + 1)) { toKString(throwOnInvalidSequence = true) } } fun checkUtf8to16Throws(string: String, array: IntArray) { checkUtf8to16Throws(CharacterCodingException::class, string, array) { decodeToString(throwOnInvalidSequence = true) } checkZeroTerminatedUtf8to16Throws(string, array) - checkZeroTerminatedUtf8to16Throws(string, array.copyOf(array.size + 1)) } fun checkZeroTerminatedUtf8to16Throws(string: String, array: IntArray, start: Int, size: Int) { - checkUtf8to16Throws(IllegalCharacterConversionException::class, string, array) { stringFromUtf8OrThrow(start, size) } checkUtf8to16Throws(CharacterCodingException::class, string, array) { toKString(start, start + size, true) } + checkUtf8to16Throws(CharacterCodingException::class, string, array.copyOf(array.size + 1)) { toKString(start, start + size, true) } } fun checkUtf8to16Throws(string: String, array: IntArray, start: Int, size: Int) { checkUtf8to16Throws(CharacterCodingException::class, string, array) { decodeToString(start, start + size, true) } checkZeroTerminatedUtf8to16Throws(string, array, start, size) - checkZeroTerminatedUtf8to16Throws(string, array.copyOf(array.size + 1), start, size) } @@ -192,11 +180,9 @@ fun checkFloatConversionThrows(string: String) = checkThrows(NumberFormatExcepti // Utils for checking invalid-bounds-exception thrown by UTF-16 to UTF-8 conversion. fun checkOutOfBoundsUtf16to8Replacing(e: KClass, string: String, start: Int, size: Int) { - checkThrows(e, string) { string.toUtf8(start, size) } checkThrows(e, string) { string.encodeToByteArray(start, start + size) } } fun checkOutOfBoundsUtf16to8Throwing(e: KClass, string: String, start: Int, size: Int) { - checkThrows(e, string) { string.toUtf8OrThrow(start, size) } checkThrows(e, string) { string.encodeToByteArray(start, start + size, true) } } fun checkOutOfBoundsUtf16to8(e: KClass, string: String, start: Int, size: Int) { @@ -207,7 +193,6 @@ fun checkOutOfBoundsUtf16to8(e: KClass, string: String, start: Int, // Utils for checking invalid-bounds-exception thrown by UTF-8 to UTF-16 conversion. fun checkOutOfBoundsZeroTerminatedUtf8to16Replacing(e: KClass, string: String, byteArray: ByteArray, start: Int, size: Int) { - checkThrows(e, string) { byteArray.stringFromUtf8(start, size) } checkThrows(e, string) { byteArray.toKString(start, start + size) } } fun checkOutOfBoundsUtf8to16Replacing(e: KClass, string: String, byteArray: ByteArray, start: Int, size: Int) { @@ -215,7 +200,6 @@ fun checkOutOfBoundsUtf8to16Replacing(e: KClass, string: String, byt checkOutOfBoundsZeroTerminatedUtf8to16Replacing(e, string, byteArray, start, size) } fun checkOutOfBoundsZeroTerminatedUtf8to16Throwing(e: KClass, string: String, byteArray: ByteArray, start: Int, size: Int) { - checkThrows(e, string) { byteArray.stringFromUtf8OrThrow(start, size) } checkThrows(e, string) { byteArray.toKString(start, start + size, true) } } fun checkOutOfBoundsUtf8to16Throwing(e: KClass, string: String, byteArray: ByteArray, start: Int, size: Int) { @@ -234,7 +218,6 @@ fun checkOutOfBoundsZeroTerminatedUtf8to16(e: KClass, string: String // Util for performing action on result of UTF-8 to UTF-16 conversion. fun convertUtf8to16(byteArray: ByteArray, action: (String) -> Unit) { - byteArray.stringFromUtf8().let { action(it) } byteArray.decodeToString().let { action(it) } byteArray.toKString().let { action(it) } } diff --git a/runtime/src/main/kotlin/kotlin/Exceptions.kt b/runtime/src/main/kotlin/kotlin/Exceptions.kt index 6393c12ca1a..db829929c1c 100644 --- a/runtime/src/main/kotlin/kotlin/Exceptions.kt +++ b/runtime/src/main/kotlin/kotlin/Exceptions.kt @@ -166,7 +166,7 @@ public actual open class NumberFormatException : IllegalArgumentException { actual constructor(message: String?) : super(message) } -@Deprecated("Use CharacterCodingException instead", ReplaceWith("CharacterCodingException")) +@Deprecated("Use CharacterCodingException instead", ReplaceWith("CharacterCodingException"), DeprecationLevel.ERROR) public open class IllegalCharacterConversionException : IllegalArgumentException { constructor(): super() diff --git a/runtime/src/main/kotlin/kotlin/native/Text.kt b/runtime/src/main/kotlin/kotlin/native/Text.kt index 9738b6b759a..dca59618736 100644 --- a/runtime/src/main/kotlin/kotlin/native/Text.kt +++ b/runtime/src/main/kotlin/kotlin/native/Text.kt @@ -12,10 +12,11 @@ import kotlinx.cinterop.toKString */ @Deprecated( "Use toKString or decodeToString instead", - ReplaceWith("toKString()", "kotlinx.cinterop.toKString") + ReplaceWith("toKString()", "kotlinx.cinterop.toKString"), + DeprecationLevel.ERROR ) public fun ByteArray.stringFromUtf8() : String { - @Suppress("DEPRECATION") + @Suppress("DEPRECATION_ERROR") return this.stringFromUtf8(0, this.size) } @@ -24,7 +25,8 @@ public fun ByteArray.stringFromUtf8() : String { */ @Deprecated( "Use toKString or decodeToString instead", - ReplaceWith("toKString(start, start + size)", "kotlinx.cinterop.toKString") + ReplaceWith("toKString(start, start + size)", "kotlinx.cinterop.toKString"), + DeprecationLevel.ERROR ) public fun ByteArray.stringFromUtf8(start: Int = 0, size: Int = this.size) : String { return toKString(start, start + size) @@ -36,10 +38,11 @@ public fun ByteArray.stringFromUtf8(start: Int = 0, size: Int = this.size) : Str */ @Deprecated( "Use toKString or decodeToString instead", - ReplaceWith("toKString(throwOnInvalidSequence = true)", "kotlinx.cinterop.toKString") + ReplaceWith("toKString(throwOnInvalidSequence = true)", "kotlinx.cinterop.toKString"), + DeprecationLevel.ERROR ) public fun ByteArray.stringFromUtf8OrThrow() : String { - @Suppress("DEPRECATION") + @Suppress("DEPRECATION_ERROR") return this.stringFromUtf8OrThrow(0, this.size) } @@ -49,13 +52,14 @@ public fun ByteArray.stringFromUtf8OrThrow() : String { */ @Deprecated( "Use toKString or decodeToString instead", - ReplaceWith("toKString(start, start + size, throwOnInvalidSequence = true)", "kotlinx.cinterop.toKString") + ReplaceWith("toKString(start, start + size, throwOnInvalidSequence = true)", "kotlinx.cinterop.toKString"), + DeprecationLevel.ERROR ) public fun ByteArray.stringFromUtf8OrThrow(start: Int = 0, size: Int = this.size) : String { try { return toKString(start, start + size, throwOnInvalidSequence = true) } catch (e: CharacterCodingException) { - @Suppress("DEPRECATION") + @Suppress("DEPRECATION_ERROR") throw IllegalCharacterConversionException() } } @@ -63,16 +67,24 @@ public fun ByteArray.stringFromUtf8OrThrow(start: Int = 0, size: Int = this.size /** * Converts a [String] into an UTF-8 array. Replaces invalid input sequences with a default character. */ -@Deprecated("Use encodeToByteArray instead", ReplaceWith("encodeToByteArray()")) +@Deprecated( + "Use encodeToByteArray instead", + ReplaceWith("encodeToByteArray()"), + DeprecationLevel.ERROR +) public fun String.toUtf8() : ByteArray { - @Suppress("DEPRECATION") + @Suppress("DEPRECATION_ERROR") return this.toUtf8(0, this.length) } /** * Converts a [String] into an UTF-8 array. Replaces invalid input sequences with a default character. */ -@Deprecated("Use encodeToByteArray instead", ReplaceWith("encodeToByteArray(start, start + size)")) +@Deprecated( + "Use encodeToByteArray instead", + ReplaceWith("encodeToByteArray(start, start + size)"), + DeprecationLevel.ERROR +) public fun String.toUtf8(start: Int = 0, size: Int = this.length) : ByteArray { checkBoundsIndexes(start, start + size, this.length) return unsafeStringToUtf8(start, size) @@ -82,9 +94,13 @@ public fun String.toUtf8(start: Int = 0, size: Int = this.length) : ByteArray { * Converts a [String] into an UTF-8 array. * @throws [IllegalCharacterConversionException] if the input is invalid. */ -@Deprecated("Use encodeToByteArray instead", ReplaceWith("encodeToByteArray(throwOnInvalidSequence = true)")) +@Deprecated( + "Use encodeToByteArray instead", + ReplaceWith("encodeToByteArray(throwOnInvalidSequence = true)"), + DeprecationLevel.ERROR +) public fun String.toUtf8OrThrow() : ByteArray { - @Suppress("DEPRECATION") + @Suppress("DEPRECATION_ERROR") return this.toUtf8OrThrow(0, this.length) } @@ -92,13 +108,17 @@ public fun String.toUtf8OrThrow() : ByteArray { * Converts a [String] into an UTF-8 array. * @throws [IllegalCharacterConversionException] if the input is invalid. */ -@Deprecated("Use encodeToByteArray instead", ReplaceWith("encodeToByteArray(start, start + size, throwOnInvalidSequence = true)")) +@Deprecated( + "Use encodeToByteArray instead", + ReplaceWith("encodeToByteArray(start, start + size, throwOnInvalidSequence = true)"), + DeprecationLevel.ERROR +) public fun String.toUtf8OrThrow(start: Int = 0, size: Int = this.length) : ByteArray { checkBoundsIndexes(start, start + size, this.length) try { return unsafeStringToUtf8OrThrow(start, size) } catch (e: CharacterCodingException) { - @Suppress("DEPRECATION") + @Suppress("DEPRECATION_ERROR") throw IllegalCharacterConversionException() } }