Выделение ByValTStr как UTF8 - PullRequest
1 голос
/ 04 мая 2020

Я работаю с C DLL и у меня возникают проблемы с сортировкой строк с помощью P / Invoke.

DLL имеет следующую структуру:

typedef struct
{
    char sAddress[256];
    BYTE byUseRtsp;
    WORD wPort;
}INFO,*LPINFO;

My C# Структура выглядит следующим образом:

[StructLayout(LayoutKind.Sequential)]
public struct INFO
{
    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
    public string sAddress;

    public byte byUseRtsp;

    public short wPort;
}

Строка сортировки для sAddress работает с текстом ASCII, но DLL использует кодировку UTF-8 повсюду. Поэтому, как только используются многобайтовые символы, маршаллинг искажает текст. Использование CharSet.Unicode здесь не работает, поскольку это говорит маршаллеру кодировать / декодировать строки как UTF-16 на Windows. Мне нужен CharSet.Utf8, которого, к сожалению, не существует.

У меня есть есть обходной путь, но он уродлив и его следует избегать, если это возможно. Обходной путь должен заменить:

    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
    public string sAddress;

на:

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 256)]
    public byte[] sAddress;

и затем просто переписать мой код, чтобы использовать методы Encoding.UTF8.GetBytes/String() для получения строковых значений. Я также должен сам обработать нулевые терминаторы этим методом.

Есть ли лучший способ сделать это?

1 Ответ

1 голос
/ 04 мая 2020

Есть ли лучший способ сделать это?

Использование встроенных опций для маршалинга того, что вы сделали, вероятно, так же хорошо, как и получается. Возможно, вы захотите написать несколько вспомогательных методов, чтобы управлять этим для вас, но я уверен, что вы живы для этого.

Помимо этого вы можете использовать собственный маршалер. Я не знаю, что на этом топи c доступно большое количество работ. Один из наиболее полных случается с моим вопросом: Как мне написать собственный маршалер, который позволяет передавать данные из нативного в управляемый?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...