-
-
Notifications
You must be signed in to change notification settings - Fork 5.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
decouple Windows APIs from UTF16String type #15033
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -131,13 +131,13 @@ end | |
end | ||
systemerror(:OpenClipboard, 0==ccall((:OpenClipboard, "user32"), stdcall, Cint, (Ptr{Void},), C_NULL)) | ||
systemerror(:EmptyClipboard, 0==ccall((:EmptyClipboard, "user32"), stdcall, Cint, ())) | ||
x_u16 = utf16(x) | ||
x_u16 = cwstring(x) | ||
# copy data to locked, allocated space | ||
p = ccall((:GlobalAlloc, "kernel32"), stdcall, Ptr{UInt16}, (UInt16, Int32), 2, sizeof(x_u16)+2) | ||
p = ccall((:GlobalAlloc, "kernel32"), stdcall, Ptr{UInt16}, (UInt16, Int32), 2, sizeof(x_u16)) | ||
systemerror(:GlobalAlloc, p==C_NULL) | ||
plock = ccall((:GlobalLock, "kernel32"), stdcall, Ptr{UInt16}, (Ptr{UInt16},), p) | ||
systemerror(:GlobalLock, plock==C_NULL) | ||
ccall(:memcpy, Ptr{UInt16}, (Ptr{UInt16},Ptr{UInt16},Int), plock, x_u16, sizeof(x_u16)+2) | ||
ccall(:memcpy, Ptr{UInt16}, (Ptr{UInt16},Ptr{UInt16},Int), plock, x_u16, sizeof(x_u16)) | ||
systemerror(:GlobalUnlock, 0==ccall((:GlobalUnlock, "kernel32"), stdcall, Cint, (Ptr{Void},), plock)) | ||
pdata = ccall((:SetClipboardData, "user32"), stdcall, Ptr{UInt16}, (UInt32, Ptr{UInt16}), 13, p) | ||
systemerror(:SetClipboardData, pdata!=p) | ||
|
@@ -152,7 +152,9 @@ end | |
systemerror(:CloseClipboard, 0==ccall((:CloseClipboard, "user32"), stdcall, Cint, ())) | ||
plock = ccall((:GlobalLock, "kernel32"), stdcall, Ptr{UInt16}, (Ptr{UInt16},), pdata) | ||
systemerror(:GlobalLock, plock==C_NULL) | ||
s = utf8(utf16(plock)) | ||
len = 0 | ||
while unsafe_load(plock, len+1) != 0; len += 1; end | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Maybe @windows_only utf16to8(p::Ptr{UInt16}, len=ccall(:wcslen, Csize_t, (Ptr{UInt16},), p)) = utf16to8(pointer_to_array(p, len)) method? |
||
s = UTF8String(utf16to8(pointer_to_array(plock, len))) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. this could use comments explaining what's going on There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. still not obvious, still needs comments |
||
systemerror(:GlobalUnlock, 0==ccall((:GlobalUnlock, "kernel32"), stdcall, Cint, (Ptr{UInt16},), plock)) | ||
return s | ||
end | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -124,36 +124,31 @@ normpath(a::AbstractString, b::AbstractString...) = normpath(joinpath(a,b...)) | |
abspath(a::AbstractString) = normpath(isabspath(a) ? a : joinpath(pwd(),a)) | ||
abspath(a::AbstractString, b::AbstractString...) = abspath(joinpath(a,b...)) | ||
|
||
@windows_only realpath(path::AbstractString) = realpath(utf16(path)) | ||
@windows_only function realpath(path::UTF16String) | ||
p::UInt32 = sizeof(path)>>1 | ||
@windows_only function realpath(path::AbstractString) | ||
path = cwstring(path) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. not type-stable ( |
||
buf = zeros(UInt16, length(path)) | ||
while true | ||
buf = zeros(UInt16, p + 1) | ||
p = ccall((:GetFullPathNameW, "kernel32"), stdcall, | ||
UInt32, (Cwstring, UInt32, Ptr{UInt16}, Ptr{Void}), | ||
n = ccall((:GetFullPathNameW, "kernel32"), stdcall, | ||
UInt32, (Ptr{UInt16}, UInt32, Ptr{UInt16}, Ptr{Void}), | ||
path, length(buf), buf, C_NULL) | ||
systemerror(:realpath, p == 0) | ||
if (p < length(buf)) | ||
resize!(buf, p + 1) | ||
return utf8(UTF16String(buf)) | ||
end | ||
systemerror(:realpath, n == 0) | ||
x = n < length(buf) # is the buffer big enough? | ||
resize!(buf, n) # shrink if x, grow if !x | ||
x && return UTF8String(utf16to8(buf)) | ||
end | ||
end | ||
|
||
@windows_only longpath(path::AbstractString) = longpath(utf16(path)) | ||
@windows_only function longpath(path::UTF16String) | ||
p::UInt32 = sizeof(path)>>1 | ||
@windows_only function longpath(path::AbstractString) | ||
path = cwstring(path) | ||
buf = zeros(UInt16, length(path)) | ||
while true | ||
buf = zeros(UInt16, p + 1) | ||
p = ccall((:GetLongPathNameW, "kernel32"), stdcall, UInt32, | ||
(Cwstring, Ptr{UInt16}, UInt32), | ||
n = ccall((:GetLongPathNameW, "kernel32"), stdcall, | ||
UInt32, (Ptr{UInt16}, Ptr{UInt16}, UInt32), | ||
path, buf, length(buf)) | ||
systemerror(:longpath, p == 0) | ||
# Buffer wasn't big enough, in which case `p` is the necessary buffer size | ||
if (p < length(buf)) | ||
resize!(buf, p + 1) | ||
return utf8(UTF16String(buf)) | ||
end | ||
systemerror(:longpath, n == 0) | ||
x = n < length(buf) # is the buffer big enough? | ||
resize!(buf, n) # shrink if x, grow if !x | ||
x && return UTF8String(utf16to8(buf)) | ||
end | ||
end | ||
|
||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What's the obstacle to using the
Cwstring
conversion forccall
arguments?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I forget the details, but
unsafe_convert
andcconvert
were not cooperative. I spent an hour or so going back and forth with @yuyichao and @vtjnash and it didn't lead to anything workable. That would be the right solution, rather than exposing these internal conversion functions.