invoke DLL on x86/x64

P

Peter Gibbons

Hello,

I'd like to use Windows getuname.dll to get the name of a character
because I haven't found this functionality in the .Net framework. So far
I have done this on x86 with the follwing code, but it crashes on x64
Windows:

Declare Function GetUName Lib "getuname.dll" Alias "GetUName" (ByVal
dwCodePoint As Int32, ByRef lpBuffer As Byte) As Int32

Public Function GetCharName(ByVal myChar As Char) As String
Dim dwCodePoint As Int32 = AscW(myChar)
Dim bytbuf(&H200&) As Byte
Dim strTmp As String = ""
Dim result As Long
result = GetUName(dwCodePoint, bytbuf(0))
strTmp = System.Text.Encoding.GetEncoding(1200).GetChars(bytbuf)
If strTmp.IndexOf(Chr(0)) > 0 Then
strTmp = Left$(strTmp, strTmp.IndexOf(Chr(0)))
End If
Return strTmp
End Function

Applcation eventlog:
Source: .Net Runtime
Type: Error
Code: 1023
..NET Runtime version 2.0.50727.1433 - Fatal Execution Engine Error
(000006427F8A5DC8) (80131506)

And with error reporting enabled also:
Source: .Net Runtime 2.0
Type: Error
Code: 1000
Faulting application txt2txt.exe, version 1.3.0.0, stamp 4899da28,
faulting module mscorwks.dll, version 2.0.50727.1433, stamp 471ed580,
debug? 0, fault address 0x0000000000202016.

It works on x64 when I compile it as a pure x86 application but I want
to use more than 2GB RAM on x64 and don't want to have separate programs
for each platform. Is it possible to late bind in a way that works on
x86 and x64?

Tanks,
Peter
 
M

Mattias Sjögren

Peter,
Declare Function GetUName Lib "getuname.dll" Alias "GetUName" (ByVal
dwCodePoint As Int32, ByRef lpBuffer As Byte) As Int32

Public Function GetCharName(ByVal myChar As Char) As String
Dim dwCodePoint As Int32 = AscW(myChar)
Dim bytbuf(&H200&) As Byte
Dim strTmp As String = ""
Dim result As Long
result = GetUName(dwCodePoint, bytbuf(0))


When a function accepts an array (of Bytes in this case, the lpBuffer
parameter), you can't just pass in the first array element ByRef and
expect it to work. It works "by accident" on x86 but as you've noticed
blows up on x64.

The correct declaration would be

Declare Function GetUName Lib "getuname.dll" Alias "GetUName" (ByVal
dwCodePoint As Int32, ByVal lpBuffer() As Byte) As Int32

or even better so save you the Encoding work

Declare Unicode Function GetUName Lib "getuname.dll" Alias "GetUName"
(ByVal dwCodePoint As Int32, ByVal lpBuffer As StringBuilder) As Int32


Mattias
 
P

Peter Gibbons

Hello,

I changed the code and it works on x86 and x64 Windows:

Declare Unicode Function GetUName Lib "getuname.dll" Alias "GetUName"
(ByVal dwCodePoint As Int32, ByVal lpBuffer As StringBuilder) As Int32

' Alternative data sources for character names:
http://unicode.org/Public/UNIDATA/NamesList.txt /
ftp://ftp.unicode.org/Public/UNIDATA/UnicodeData.txt
'
http://codeka.com/blogs/index.php/dean/2006/01/13/getting_the_name_of_a_unicode_character
' http://www.codeka.com/blogs/media/UnicodeName.zip
' http://blogs.msdn.com/michkap/archive/2006/01/12/511920.aspx

Public Function GetCharName(ByVal myChar As Char) As String
Dim result As Int32
Dim retStr As New StringBuilder(255)
result = GetUName(AscW(myChar), retStr)
Return retStr.ToString
End Function

Console.WriteLine(GetCharName(CChar("☢")))

I took the original code from
http://kmleak.spaces.live.com/blog/cns!1A64EF1CFC75CCA2!273.entry and my
japanese isn't that good ;-) but I should have seen the wrong array
parameter usage.

Thank you Mattias,
Peter.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top