简体   繁体   中英

How can I override default encoding when marshalling strings?

I have a Delphi 2007 DLL with this export:

function TestSignString(s, Sign: PChar): LongBool; stdcall;

I am calling it in .NET Core v7 C# using this import:

[DllImport(@"LibraryName.dll")]
[return:MarshalAs(UnmanagedType.Bool)]
internal static extern bool TestSignString(string s, string sign);

I am passing s and sign params, when the run-time system has default encoding (EXPECTED) WIN1250 everything goes fine as expected, however when it's not, there's default system encoding involved and passed chars are encoded using default encoding (for example to WIN1252).

So my question is, how to override default encoding when marshaling strings in C#? I mean both ways - as a input params and output as well, please.

I have tried altering the import to:

[DllImport(@"LockBoxLibrary.dll", CharSet = CharSet.Ansi)]

but no luck, I am missing code page (1250) specification.

I have a "dirty" solution as it's probably memory leaking. Let me know if you know better way, please. I have two extension methods for string conversion to nint and vice versa.

private static string FromAnsiPtrToUtf8Str(this nint n)
{
    var length = 0;

    while (Marshal.ReadByte(n + length) != 0)
    {
        length++;
    }

    var strbuf = new byte[length];
    Marshal.Copy(n, strbuf, 0, length);
    
    return Encoding.GetEncoding(1250).GetString(strbuf);
}

private static nint FromUtf8StrToAnsiPtr(this string s) => GCHandle.Alloc(Encoding.GetEncoding(1250).GetBytes(s), GCHandleType.Pinned).AddrOfPinnedObject();

Import changed to: private static extern bool TestSignString(nint s, nint sign);

Method call: TestSignString(s.FromUtf8StrToAnsiPtr(), sign.FromUtf8StrToAnsiPtr());

Try to change TestSignString to take a UTF-16 string, or introduce a widestring (W) version, it is 2023:-)

function TestSignStringW(s, Sign: PWideChar): LongBool; stdcall;

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM