@@ -25,7 +25,7 @@ function iconv_open(tocode, fromcode)
2525 elseif errno () == EINVAL
2626 error (" conversion from $fromcode to $tocode not supported by iconv implementation, check that specified encodings are correct" )
2727 else
28- error (" iconv_open error $(errno ()) : $(strerror (errno ())) " )
28+ error (" iconv_open error $(errno ()) : $(strerror (errno ())) " )
2929 end
3030end
3131
@@ -57,6 +57,15 @@ type StringDecoder{S<:IO} <: IO
5757 skip:: Int
5858end
5959
60+ # This is called during GC, just make sure C memory is returned, don't throw errors
61+ function finalize (s:: Union{StringEncoder, StringDecoder} )
62+ if s. cd != C_NULL
63+ iconv_close (s. cd)
64+ s. cd = C_NULL
65+ end
66+ nothing
67+ end
68+
6069function iconv! (cd:: Ptr{Void} , inbuf:: Vector{UInt8} , outbuf:: Vector{UInt8} ,
6170 inbufptr:: Ref{Ptr{UInt8}} , outbufptr:: Ref{Ptr{UInt8}} ,
6271 inbytesleft:: Ref{Csize_t} , outbytesleft:: Ref{Csize_t} )
@@ -70,7 +79,7 @@ function iconv!(cd::Ptr{Void}, inbuf::Vector{UInt8}, outbuf::Vector{UInt8},
7079 (Ptr{Void}, Ptr{Ptr{UInt8}}, Ref{Csize_t}, Ptr{Ptr{UInt8}}, Ref{Csize_t}),
7180 cd, inbufptr, inbytesleft, outbufptr, outbytesleft)
7281
73- if ret == reinterpret (Csize_t, - 1 )
82+ if ret == - 1 % Csize_t
7483 err = errno ()
7584
7685 # Should never happen unless a very small buffer is used
@@ -102,7 +111,7 @@ function iconv_reset!(s::Union{StringEncoder, StringDecoder})
102111 (Ptr{Void}, Ptr{Ptr{UInt8}}, Ref{Csize_t}, Ptr{Ptr{UInt8}}, Ref{Csize_t}),
103112 s. cd, C_NULL , C_NULL , s. outbufptr, s. outbytesleft)
104113
105- if ret == reinterpret (Csize_t, - 1 )
114+ if ret == - 1 % Csize_t
106115 err = errno ()
107116 if err == EINVAL
108117 error (" iconv error: incomplete byte sequence at end of input" )
@@ -135,7 +144,7 @@ function StringEncoder(ostream::IO, to::ASCIIString, from::ASCIIString="UTF-8")
135144 s = StringEncoder (ostream, cd, inbuf, outbuf,
136145 Ref {Ptr{UInt8}} (pointer (inbuf)), Ref {Ptr{UInt8}} (pointer (outbuf)),
137146 Ref {Csize_t} (0 ), Ref {Csize_t} (BUFSIZE))
138- finalizer (s, close )
147+ finalizer (s, finalize )
139148 s
140149end
141150
@@ -157,11 +166,10 @@ function flush(s::StringEncoder)
157166end
158167
159168function close (s:: StringEncoder )
160- s. cd == C_NULL && return s
161169 flush (s)
162170 iconv_reset! (s)
163- iconv_close (s . cd)
164- s . cd = C_NULL
171+ # Make sure C memory/resources are returned
172+ finalize (s)
165173 # flush() wasn't able to empty input buffer, which cannot happen with correct data
166174 s. inbytesleft[] == 0 || error (" iconv error: incomplete byte sequence at end of input" )
167175end
@@ -188,7 +196,7 @@ function StringDecoder(istream::IO, from::ASCIIString, to::ASCIIString="UTF-8")
188196 s = StringDecoder (istream, cd, inbuf, outbuf,
189197 Ref {Ptr{UInt8}} (pointer (inbuf)), Ref {Ptr{UInt8}} (pointer (outbuf)),
190198 Ref {Csize_t} (0 ), Ref {Csize_t} (BUFSIZE), 0 )
191- finalizer (s, close )
199+ finalizer (s, finalize )
192200 s
193201end
194202
@@ -221,10 +229,10 @@ function eof(s::StringDecoder)
221229end
222230
223231function close (s:: StringDecoder )
224- s . cd == C_NULL && return s
225- iconv_close (s . cd)
226- s . cd = C_NULL
227- # fill_buffer !() wasn't able to empty input buffer, which cannot happen with correct data
232+ iconv_reset! (s)
233+ # Make sure C memory/resources are returned
234+ finalize (s)
235+ # iconv_reset !() wasn't able to empty input buffer, which cannot happen with correct data
228236 s. inbytesleft[] == 0 || error (" iconv error: incomplete byte sequence at end of input" )
229237end
230238
240248# # Functions to encode/decode strings
241249
242250encoding_string (:: Type{ASCIIString} ) = " ASCII"
243- encoding_string (:: Type{UTF8String} ) = " UTF-8"
244- encoding_string (:: Type{UTF16String} ) = " UTF-16LE"
245- encoding_string (:: Type{UTF32String} ) = " UTF-32LE"
251+ encoding_string (:: Type{UTF8String} ) = " UTF-8"
252+ encoding_string (:: Type{UTF16String} ) = ( ENDIAN_BOM == 0x04030201 ) ? " UTF-16LE" : " UTF-16BE "
253+ encoding_string (:: Type{UTF32String} ) = ( ENDIAN_BOM == 0x04030201 ) ? " UTF-32LE" : " UTF-32BE "
246254
247255"""
248256 decode(a::Vector{UInt8}, enc::ASCIIString)
0 commit comments