Преобразование строки на LPCWSTR для CreateFile () для решения последовательного порта
-
05-10-2019 - |
Вопрос
Кажется, я имею немного задачи текста / Unicode при использовании функции Windows CreateFile для адресации последовательного порта. Может кто-нибудь, пожалуйста, помогите указать на мою ошибку?
Я пишу приложение консоли Win32 в VC ++ с использованием VS 2008.
Я могу создать ручку для решения последовательного порта, как это:
#include <iostream>
#include <windows.h>
#include <string>
int main()
{
HANDLE hSerial;
hSerial = CreateFile( L"\\\\.\\COM20",
GENERIC_READ | GENERIC_WRITE,
0,
0,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);`
return 0;
}
Это работает просто хорошо ( \\\\.\\
Бит требуется для Comports больше, чем COM9 и работает для тех, кто до COM9 также работает). Проблема в том, что мой компорут не всегда будет COM20, поэтому я хотел бы указать пользователь, что это такое.
Вот некоторые вещи, которые я пробовал:
#include <iostream>
#include <windows.h>
#include <string>
int main()
{
std::string comNum;
std::cout << "\n\nEnter the port (ex: COM20): ";
std::cin >> comNum;
std::string comPrefix = "\\\\.\\";
std::string comID = comPrefix+comNum;
HANDLE hSerial;
hSerial = CreateFile( comID,
GENERIC_READ | GENERIC_WRITE,
0,
0,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);`
return 0;
}
Это не скомпилируется и возвращает ошибку: Ошибка C2664: «CreateFileW»: не удается преобразовать параметр 1 из «std :: string 'на' lpcwstr '
Я думал, что, возможно, уточнение CreateFilea будет работать тогда, но это дало в основном ту же ошибку.
Я также пробовал:
/*
everything else the same
*/
hSerial = CreateFile( TEXT(comID),
GENERIC_READ | GENERIC_WRITE,
0,
0,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);`
который также не скомпилируется и возвращает: Ошибка C2065: «LCOMID»: неразделенный идентификатор
Я не большой эксперта, но я сейчас работаю над этим. Может кто-нибудь сказать мне, как заменить L"\\\\.\\COM20"
Таким образом, пользователь может указать компорт, и чтобы CreateFile все равно будет работать? Спасибо!
Решение
Вы можете либо использовать std::wstring
а также std::wcin
, std::wcout
Чтобы выполнить вход непосредственно в «Unicode Strings», или вы можете посмотреть в Microsoft's Функции преобразования.
Если вы идете на 1-й вариант (рекомендуется), вам все еще нужно использовать c_str()
функция, чтобы получить доступ к LPCWSTR
значение (указатель на const wchar_t
).
Примерное решение (также не использовать CreateFileW
синтаксис, чтобы предотвратить проблемы с UNICODE
Макрос):
#include <iostream>
#include <windows.h>
#include <string>
int main()
{
std::wstring comNum;
std::wcout << L"\n\nEnter the port (ex: COM20): ";
std::wcin >> comNum;
std::wstring comPrefix = L"\\\\.\\";
std::wstring comID = comPrefix+comNum;
HANDLE hSerial;
hSerial = CreateFileW( comID.c_str(),
GENERIC_READ | GENERIC_WRITE,
0,
0,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);`
return 0;
}
Другие советы
Если вы хотите продолжить использование std::string
, затем используйте его c_str()
Метод при вызове CreateFileA()
, например:
hSerial = CreateFileA( comID.c_str(), ...);
В качестве дополнительной справки посмотрите на макросы преобразований ATL (например, CA2CW и т. Д.). Эти (если использоваться должным образом) может справиться почти все простые конверсионные чехлы, с небольшим количеством суеты.
В вашем примере вы можете использовать STD :: String, затем использовать:
CreateFile( CA2CT( comID.c_str() ), ... );
Если (по какой-то причине) вы решите продолжать работать с строками ANSI, а затем посмотрите на MultiByteToWideChar
функция. Но струны ANSI в значительной степени устарели.
Я побежал в этом недавно. Я просто отключил Unicode, так как Unicode был полностью из-за приложения для этого приложения.
Общая информация о конверсиях строки здесь: http://www.codeproject.com/kb/string/cppstringguide2.aspx.