Windows APIでWindows API、つまりRegCreateKeyEx
関数を使用して新しいレジストリキーを作成し、GetSecurityInfo
を使用してそのDACLを取得しようとしています。無効なハンドル値エラー(エラー6)を返すGetSecurityInfo
関数呼び出しになるまで、すべてのアサートは円滑に進みます。私は間違って何をしていますか?C++ windows API GetSecurityInfo無効なハンドルが指定されました
これは、私が唯一与えるより精巧なプロジェクトの一部である(または私はそれが何を考えて、私はあまりにも休息を追加することができます)ここに関連部分:出力を作るためにRegCreateKeyEx
にラッパー
協力し、発生したエラーを設定する方が簡単:
inline extern auto RegCreateKeyEx_safe(
_In_ const HKEY hKey,
_In_ const LPCTSTR lpSubKey,
_Reserved_ const DWORD Reserved,
_In_opt_ const LPTSTR lpClass,
_In_ const DWORD dwOptions,
_In_ const REGSAM samDesired,
_In_opt_ const LPSECURITY_ATTRIBUTES lpSecurityAttributes,
_Out_ const PHKEY phkResult,
_Out_opt_ const LPDWORD lpdwDisposition)
{
const auto result =
RegCreateKeyEx(
hKey,
lpSubKey,
Reserved,
lpClass,
dwOptions,
samDesired,
lpSecurityAttributes,
phkResult,
lpdwDisposition);
if (result != ERROR_SUCCESS)
SetLastError(result);
return result == ERROR_SUCCESS;
}
ラッパー、それが有効であるかどうかをチェックした後、作成したキーのハンドルを返す必要があります上記の機能に:
inline extern auto CreateNewRegKey(
HKEY hKey,
LPCTSTR lpSubKey,
DWORD Reserved,
LPTSTR lpClass,
DWORD dwOptions,
REGSAM samDesired,
LPSECURITY_ATTRIBUTES lpSecurityAttributes,
LPDWORD lpdwDisposition)
{
auto createdKey = static_cast<PHKEY>(malloc(sizeof HKEY));
assert(
RegCreateKeyEx_safe(
hKey,
lpSubKey,
Reserved,
lpClass,
dwOptions,
samDesired,
lpSecurityAttributes,
createdKey,
lpdwDisposition));
assert(createdKey != INVALID_HANDLE_VALUE);
return createdKey;
}
そしてRegCreateKey
バージョンとしてGetSecurityInfo
のラッパー、同じ理由と機能:
inline extern auto GetSecurityInfo_safe(
_In_ const HANDLE handle,
_In_ const SE_OBJECT_TYPE ObjectType,
_In_ const SECURITY_INFORMATION SecurityInfo,
_Out_opt_ PSID* ppsidOwner,
_Out_opt_ PSID* ppsidGroup,
_Out_opt_ PACL* ppDacl,
_Out_opt_ PACL* ppSacl,
_Out_opt_ PSECURITY_DESCRIPTOR* ppSecurityDescriptor)
{
const auto result =
GetSecurityInfo(
handle,
ObjectType,
SecurityInfo,
ppsidOwner,
ppsidGroup,
ppDacl,
ppSacl,
ppSecurityDescriptor);
if (result != ERROR_SUCCESS)
SetLastError(result);
return result == EXIT_SUCCESS;
}
次のように今、これらの関数を呼び出すコードは次のとおりです。
const auto newRegKey =
CreateNewRegKey(
HKEY_CURRENT_USER,
SUBKEY_PATH,
NULL,
nullptr,
REG_OPTION_NON_VOLATILE,
KEY_ALL_ACCESS,
NULL, //securityAttributes,
nullptr);
assert(
GetSecurityInfo_safe(
newRegKey,
SE_REGISTRY_KEY,
DACL_SECURITY_INFORMATION,
NULL,
NULL,
oldDacl,
NULL,
NULL));
出力が問題である場合にはかなり明確です(条件を確認した後、条件が満たされなかった場合のエラーテキストと共に、条件をチェックした後にそれを表示するというやや詳細なアサーションを実装しました):
SUCCESS: RegCreateKeyEx_safe(hKey, lpSubKey, Reserved, lpClass, dwOptions, samDesired, lpSecurityAttributes, createdKey, lpdwDisposition)
SUCCESS: createdKey != INVALID_HANDLE_VALUE
FAILURE: GetSecurityInfo_safe(newRegKey, SE_REGISTRY_KEY, DACL_SECURITY_INFORMATION, NULL, NULL, oldDacl, NULL, NULL)
ERROR-6: The handle is invalid.
アサート:
#define _VERBOSE (1)
#define assert(cond) if((cond) == TRUE) \
{ if (_VERBOSE) cout << "SUCCESS:\t" << #cond << endl; } \
else \
{cout << "FAILURE:\t" << #cond << "\n\nERROR-" << GetLastError() << ":\t" << GetLastErrorAsString() << "\n\n"; exit(EXIT_FAILURE); }
は、事前にありがとうございます!
このラッパーでは、作業をより難しくする意味はなんですか? 'SetLastError'はここでは必要ありません - Reg APIはtrue/falseの代わりにエラーコードを返します。本当にはるかに優れたデザインで使いやすいです。 – RbMm
@RbMmこれらのコードは、コードがより精巧なプロジェクトの一部であり、より大きなコードベースで作業するほうが簡単です:) –
エラーコードを返す関数での作業 - 真/偽を返し、最後のエラーを返す関数よりはるかに簡単です – RbMm