Skip to content

Commit

Permalink
Fix: leverage String.each_utf16_char instead of external C call
Browse files Browse the repository at this point in the history
  • Loading branch information
ysbaddaden committed Jun 13, 2024
1 parent a54c848 commit 5541f6e
Showing 1 changed file with 18 additions and 4 deletions.
22 changes: 18 additions & 4 deletions src/crystal/system/print_error.cr
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,25 @@ module Crystal::System
end

{% if flag?(:win32) %}
# Helper to print wide char slices (UTF-16) from the Win32 API as multibyte (UTF-8).
# Print a UTF-16 slice as multibyte (UTF-8).
def self.print_error(bytes : Slice(UInt16)) : Nil
utf8 = uninitialized UInt8[256]
len = LibC.WideCharToMultiByte(LibC::CP_UTF8, 0, bytes, bytes.size, utf8, utf8.size, nil, nil)
print_error utf8.to_slice[0...len]
utf8 = uninitialized UInt8[512]
len = 0

String.each_utf16_char(bytes) do |char|
# avoid buffer overun and splitting an unicode char
if len > utf8.size - char.bytesize
print_error utf8.to_slice
len = 0
end

char.each_byte do |byte]
utf8.to_unsafe[len] = byte
len &+= 1
end
end

print_error utf8.to_slice[0...len] if len > 0
end
{% end %}

Expand Down

0 comments on commit 5541f6e

Please sign in to comment.