Ответ 1
Это не так просто, как кажется. Есть одна информация, которую вы не предоставили: в какой кодировке функция C ожидает путь?
В Linux пути - это "просто" массивы байтов (0 - недопустимый), и приложения обычно не пытаются их декодировать. (Однако им, возможно, придется декодировать их с помощью определенной кодировки, например, чтобы отобразить их пользователю, и в этом случае они обычно будут пытаться декодировать их в соответствии с текущей локалью, которая часто будет использовать кодировку UTF-8.)
В Windows это сложнее, потому что есть варианты функций API, которые используют кодовую страницу "ANSI", и варианты, которые используют "Unicode" (UTF-16). Кроме того, Windows не поддерживает установку UTF-8 в качестве кодовой страницы "ANSI". Это означает, что если библиотека специально не ожидает UTF-8 и не преобразует путь в собственное кодирование, передача его в кодированном UTF-8 пути определенно неверна (хотя может показаться, что она работает для строк, содержащих только символы ASCII).
(Я не знаю о других платформах, но это уже достаточно грязно.)
В Rust Path
- это просто оболочка для OsStr
. OsStr
использует платформо-зависимое представление, которое оказывается совместимым с UTF-8, когда строка действительно является допустимой UTF-8, но строки не-UTF-8 используют неопределенную кодировку (в Windows это фактически использует WTF-8, но это не является договорным, в Linux это просто массив байтов как есть).
Прежде чем передать путь к функции C, вы должны определить, в какой кодировке она ожидает строку, и, если она не соответствует кодировке Rust, вам придется преобразовать ее перед упаковкой в CString
. Rust не позволяет вам преобразовывать Path
или OsStr
во что-либо кроме str
независимо от платформы. Для целей на основе Unix OsStrExt
особенность OsStrExt
которая обеспечивает доступ к OsStr
в виде фрагмента байтов.
Ржавчина используется для обеспечения to_cstring
метод на OsStr
, но это никогда не стабилизируется, и она была устаревшей в Rust 1.6.0, как выяснилось, что поведение было неуместно для Windows ( в это возвратило UTF-8 закодирован путь, но для Windows API, не поддерживаю это!).