Velvet Star Monitor

Standout celebrity highlights with iconic style.

general

Why does the RegQueryValueEx() function return ERROR_FILE_NOT_FOUND while trying to read from a registry key?

Writer Sophia Terry

System: Windows 7 32bit
Language: C++

I have tried to access register HKEY_LOCAL_MACHINE\\HARDWARE\\DEVICEMAP\\Scsi\\Scsi Port 0, key Driver (type REG_SZ) -- no problem.

The same for reading from HKEY_LOCAL_MACHINE\\HARDWARE\\DEVICEMAP\\SERIALCOMM, all keys (types REG_SZ) got slashes, for example \Device\Serial0.

While reading such keys it always returns 2 (no such file) with following example code:

HKEY hKey = 0;
DWORD dwType = REG_SZ;
char buf[255] = {0};
DWORD dwBufSize = sizeof(buf);
if( RegOpenKeyEx( HKEY_LOCAL_MACHINE, TEXT("HARDWARE\\DEVICEMAP\\SERIALCOMM"), 0, KEY_QUERY_VALUE, &hKey ) == ERROR_SUCCESS )
{ auto ret = RegQueryValueEx( hKey, TEXT("\Device\Serial0"), 0, &dwType, (LPBYTE)buf, &dwBufSize ); // ret always == 2 for key with slashes
--- CUT ---

What is the proper way to read key values with slashes in name?


Above has been properly answered by Cody Gray.
Below another issue.

Im getting the same problem when Im using variable instead of a text string.
Iv considered both approaches with single and double slashes:

HKEY hKey = 0;
DWORD keyType = REG_SZ;
TCHAR buf[255] = {0};
DWORD bufSize = sizeof(buf);
QSettings winReg("HKEY_LOCAL_MACHINE\\HARDWARE\\DEVICEMAP\\SERIALCOMM", QSettings::NativeFormat);
auto comsKey = winReg.allKeys();
FOREACH( auto com, comsKey )
{ // FOREACH - boost macro // comsKey = QList<QString> (list of key names) [from Qt framework] // com = QString (single key name) [from Qt framework] if( RegOpenKeyEx(HKEY_LOCAL_MACHINE, TEXT("HARDWARE\\DEVICEMAP\\SERIALCOMM"), 0, KEY_QUERY_VALUE, &hKey ) == ERROR_SUCCESS ) { wchar_t* keyw = new wchar_t(); //com.replace("/", "\\\\"); <- checked both variants commented and not commented; com == /Device/Serial0 so im converting to \\Device\\Serial0 int size = com.size(); mbstowcs( keyw, com.toStdString().data(), size ); //auto ret = RegQueryValueEx( hKey, TEXT("\\Device\\Serial0"), 0, &keyType, (LPBYTE)buf, &bufSize ); // <- this works! auto ret = RegQueryValueExW( hKey, (LPCWSTR)&keyw, 0, &keyType, (LPBYTE)buf, &bufSize ); // <- this one not works!

I have tried all variants with "\Device..", "/Device", "\Device", etc.

2

1 Answer

You have to escape the slashes, just like you did in the first line...

if( RegOpenKeyEx( HKEY_LOCAL_MACHINE, TEXT("HARDWARE\\DEVICEMAP\\SERIALCOMM"), 0, KEY_QUERY_VALUE, &hKey ) == ERROR_SUCCESS )
{ auto ret = RegQueryValueEx( hKey, TEXT("\\Device\\Serial0"), 0, &dwType, (LPBYTE)buf, &dwBufSize ); // ret always == 2 for key with slashes

If you don't, the RegQueryValueEx function can't find the specified key, and it returns ERROR_FILE_NOT_FOUND (== 2).


But there's another problem. You should be declaring the buffer array as type wchar_t (or TCHAR), rather than char:

TCHAR buf[255] = {0};

Otherwise, the RegQueryValueEx function is going to attempt to fill the array with a Unicode string read from the specified registry key, and you're going to get something unreadable.

6

Your Answer

Sign up or log in

Sign up using Google Sign up using Facebook Sign up using Email and Password

Post as a guest

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.