Dennis
Dennis

Reputation: 63

Windows API function CredUIPromptForWindowsCredentials also returns an error of 31

When I use the function CredUIPromptForWindowsCredentials to display a windows security authentication dialog, the return result is always 31 and the dialog doesn't display.
What's wrong with the code below?

CREDUI_INFO credui;  
credui.pszCaptionText = "Enter Network Password";  
credui.pszMessageText = ("Enter your password to connect to: " + strDbPath).c_str();  
credui.cbSize = sizeof(credui);  
credui.hbmBanner = nullptr;  
ULONG authPackage = 0;  
LPVOID outCredBuffer = nullptr;  
ULONG outCredSize = 0;  
BOOL save = false;  
int result = CredUIPromptForWindowsCredentials(&credui, 0, &authPackage, nullptr, 0, &outCredBuffer, &outCredSize, &save, 1);               

Upvotes: 5

Views: 3338

Answers (1)

Remy Lebeau
Remy Lebeau

Reputation: 596477

31 is ERROR_GEN_FAILURE. If you read the documentation, there is a comment that says:

I'm not sure why but it seems that CredUIPromptForWindowsCredentialsA always return ERROR_GEN_FAILURE (0x1E). Only Unicode version works.

You are, in fact, calling the Ansi version of CredUIPromptForWindowsCredentials() (as evident by the fact that you are assigning char* data to the CREDUI_INFO struct). Try calling the Unicode version instead.

Also, you are not assigning a value to the credui.hwndParent field, and you are not zeroing out credui before populating it, so the hwndParent has an indeterminate value. You must specify a valid HWND. If you don't have one, you can use NULL.

Also, you are assigning a char* pointer from a temporary string to credui.pszMessageText. That string goes out of scope and gets destroyed before CredUIPromptForWindowsCredentials() is called. You need to use a local variable to hold the message text until CredUIPromptForWindowsCredentials() is done using it.

Try this:

std::wstring strDbPath = ...;
std::wstring strMsg = L"Enter your password to connect to: " + strDbPath;

CREDUI_INFOW credui = {};
credui.cbSize = sizeof(credui);  
credui.hwndParent = nullptr;
credui.pszMessageText = strMsg.c_str();
credui.pszCaptionText = L"Enter Network Password";
credui.hbmBanner = nullptr;

ULONG authPackage = 0;  
LPVOID outCredBuffer = nullptr;  
ULONG outCredSize = 0;  
BOOL save = false;  

int result = CredUIPromptForWindowsCredentialsW(&credui, 0, &authPackage, nullptr, 0, &outCredBuffer, &outCredSize, &save, 1);

Upvotes: 7

Related Questions