Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
19c3a09b
Commit
19c3a09b
authored
Jul 09, 2007
by
Juan Lang
Committed by
Alexandre Julliard
Jul 10, 2007
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
crypt32: Implement CryptSIPLoad.
parent
da23ed6e
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
194 additions
and
32 deletions
+194
-32
crypt32_private.h
dlls/crypt32/crypt32_private.h
+1
-0
main.c
dlls/crypt32/main.c
+1
-0
sip.c
dlls/crypt32/sip.c
+171
-2
sip.c
dlls/crypt32/tests/sip.c
+21
-30
No files found.
dlls/crypt32/crypt32_private.h
View file @
19c3a09b
...
...
@@ -50,6 +50,7 @@ HCRYPTPROV CRYPT_GetDefaultProvider(void);
void
crypt_oid_init
(
HINSTANCE
hinst
);
void
crypt_oid_free
(
void
);
void
crypt_sip_free
(
void
);
/* Some typedefs that make it easier to abstract which type of context we're
* working with.
...
...
dlls/crypt32/main.c
View file @
19c3a09b
...
...
@@ -43,6 +43,7 @@ BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD fdwReason, PVOID pvReserved)
break
;
case
DLL_PROCESS_DETACH
:
crypt_oid_free
();
crypt_sip_free
();
if
(
hDefProv
)
CryptReleaseContext
(
hDefProv
,
0
);
break
;
}
...
...
dlls/crypt32/sip.c
View file @
19c3a09b
...
...
@@ -30,6 +30,7 @@
#include "winuser.h"
#include "wine/debug.h"
#include "wine/list.h"
WINE_DEFAULT_DEBUG_CHANNEL
(
crypt
);
...
...
@@ -354,6 +355,165 @@ cleanup3:
return
bRet
;
}
static
LONG
CRYPT_OpenSIPFunctionKey
(
const
GUID
*
guid
,
LPCWSTR
function
,
HKEY
*
key
)
{
WCHAR
szFullKey
[
0x100
];
lstrcpyW
(
szFullKey
,
szOID
);
lstrcatW
(
szFullKey
,
function
);
CRYPT_guid2wstr
(
guid
,
&
szFullKey
[
lstrlenW
(
szFullKey
)]);
return
RegOpenKeyExW
(
HKEY_LOCAL_MACHINE
,
szFullKey
,
0
,
KEY_READ
,
key
);
}
/* Loads the function named function for the SIP specified by pgSubject, and
* returns it if found. Returns NULL on error. If the function is loaded,
* *pLib is set to the library in which it is found.
*/
static
void
*
CRYPT_LoadSIPFunc
(
const
GUID
*
pgSubject
,
LPCWSTR
function
,
HMODULE
*
pLib
)
{
LONG
r
;
HKEY
key
=
NULL
;
DWORD
size
;
WCHAR
dllName
[
MAX_PATH
];
char
functionName
[
MAX_PATH
];
HMODULE
lib
;
void
*
func
=
NULL
;
TRACE
(
"(%s, %s)
\n
"
,
debugstr_guid
(
pgSubject
),
debugstr_w
(
function
));
r
=
CRYPT_OpenSIPFunctionKey
(
pgSubject
,
function
,
&
key
);
if
(
r
)
goto
error
;
/* Read the DLL entry */
size
=
sizeof
(
dllName
);
r
=
RegQueryValueExW
(
key
,
szDllName
,
NULL
,
NULL
,
(
LPBYTE
)
dllName
,
&
size
);
if
(
r
)
goto
error
;
/* Read the Function entry */
size
=
sizeof
(
functionName
);
r
=
RegQueryValueExA
(
key
,
"FuncName"
,
NULL
,
NULL
,
(
LPBYTE
)
functionName
,
&
size
);
if
(
r
)
goto
error
;
lib
=
LoadLibraryW
(
dllName
);
if
(
!
lib
)
goto
error
;
func
=
GetProcAddress
(
lib
,
functionName
);
if
(
func
)
*
pLib
=
lib
;
else
FreeLibrary
(
lib
);
error:
RegCloseKey
(
key
);
TRACE
(
"returning %p
\n
"
,
func
);
return
func
;
}
typedef
struct
_WINE_SIP_PROVIDER
{
GUID
subject
;
SIP_DISPATCH_INFO
info
;
struct
list
entry
;
}
WINE_SIP_PROVIDER
;
static
struct
list
providers
=
{
&
providers
,
&
providers
};
static
CRITICAL_SECTION
providers_cs
;
static
CRITICAL_SECTION_DEBUG
providers_cs_debug
=
{
0
,
0
,
&
providers_cs
,
{
&
providers_cs_debug
.
ProcessLocksList
,
&
providers_cs_debug
.
ProcessLocksList
},
0
,
0
,
{
(
DWORD_PTR
)(
__FILE__
": providers_cs"
)
}
};
static
CRITICAL_SECTION
providers_cs
=
{
&
providers_cs_debug
,
-
1
,
0
,
0
,
0
,
0
};
static
void
CRYPT_CacheSIP
(
const
GUID
*
pgSubject
,
SIP_DISPATCH_INFO
*
info
)
{
WINE_SIP_PROVIDER
*
prov
=
CryptMemAlloc
(
sizeof
(
WINE_SIP_PROVIDER
));
if
(
prov
)
{
memcpy
(
&
prov
->
subject
,
pgSubject
,
sizeof
(
prov
->
subject
));
memcpy
(
&
prov
->
info
,
info
,
sizeof
(
prov
->
info
));
EnterCriticalSection
(
&
providers_cs
);
list_add_tail
(
&
providers
,
&
prov
->
entry
);
LeaveCriticalSection
(
&
providers_cs
);
}
}
static
WINE_SIP_PROVIDER
*
CRYPT_GetCachedSIP
(
const
GUID
*
pgSubject
)
{
WINE_SIP_PROVIDER
*
provider
=
NULL
,
*
ret
=
NULL
;
EnterCriticalSection
(
&
providers_cs
);
LIST_FOR_EACH_ENTRY
(
provider
,
&
providers
,
WINE_SIP_PROVIDER
,
entry
)
{
if
(
IsEqualGUID
(
pgSubject
,
&
provider
->
subject
))
break
;
}
if
(
provider
&&
IsEqualGUID
(
pgSubject
,
&
provider
->
subject
))
ret
=
provider
;
LeaveCriticalSection
(
&
providers_cs
);
return
ret
;
}
static
inline
BOOL
CRYPT_IsSIPCached
(
const
GUID
*
pgSubject
)
{
return
CRYPT_GetCachedSIP
(
pgSubject
)
!=
NULL
;
}
void
crypt_sip_free
(
void
)
{
WINE_SIP_PROVIDER
*
prov
,
*
next
;
LIST_FOR_EACH_ENTRY_SAFE
(
prov
,
next
,
&
providers
,
WINE_SIP_PROVIDER
,
entry
)
{
list_remove
(
&
prov
->
entry
);
FreeLibrary
(
prov
->
info
.
hSIP
);
CryptMemFree
(
prov
);
}
}
/* Loads the SIP for pgSubject into the global cache. Returns FALSE if the
* SIP isn't registered or is invalid.
*/
static
BOOL
CRYPT_LoadSIP
(
const
GUID
*
pgSubject
)
{
SIP_DISPATCH_INFO
sip
=
{
0
};
HMODULE
lib
,
temp
=
NULL
;
sip
.
pfGet
=
CRYPT_LoadSIPFunc
(
pgSubject
,
szGetSigned
,
&
lib
);
if
(
!
sip
.
pfGet
)
goto
error
;
sip
.
pfPut
=
CRYPT_LoadSIPFunc
(
pgSubject
,
szPutSigned
,
&
temp
);
if
(
!
sip
.
pfPut
||
temp
!=
lib
)
goto
error
;
FreeLibrary
(
temp
);
sip
.
pfCreate
=
CRYPT_LoadSIPFunc
(
pgSubject
,
szCreate
,
&
temp
);
if
(
!
sip
.
pfCreate
||
temp
!=
lib
)
goto
error
;
FreeLibrary
(
temp
);
sip
.
pfVerify
=
CRYPT_LoadSIPFunc
(
pgSubject
,
szVerify
,
&
temp
);
if
(
!
sip
.
pfVerify
||
temp
!=
lib
)
goto
error
;
FreeLibrary
(
temp
);
sip
.
pfRemove
=
CRYPT_LoadSIPFunc
(
pgSubject
,
szRemoveSigned
,
&
temp
);
if
(
!
sip
.
pfRemove
||
temp
!=
lib
)
goto
error
;
FreeLibrary
(
temp
);
sip
.
hSIP
=
lib
;
CRYPT_CacheSIP
(
pgSubject
,
&
sip
);
return
TRUE
;
error:
FreeLibrary
(
lib
);
FreeLibrary
(
temp
);
SetLastError
(
TRUST_E_SUBJECT_FORM_UNKNOWN
);
return
FALSE
;
}
/***********************************************************************
* CryptSIPLoad (CRYPT32.@)
*
...
...
@@ -382,15 +542,24 @@ cleanup3:
BOOL
WINAPI
CryptSIPLoad
(
const
GUID
*
pgSubject
,
DWORD
dwFlags
,
SIP_DISPATCH_INFO
*
pSipDispatch
)
{
FIXME
(
"(%s %d %p) stub!
\n
"
,
debugstr_guid
(
pgSubject
),
dwFlags
,
pSipDispatch
);
TRACE
(
"(%s %d %p)
\n
"
,
debugstr_guid
(
pgSubject
),
dwFlags
,
pSipDispatch
);
if
(
!
pgSubject
||
dwFlags
!=
0
||
!
pSipDispatch
)
{
SetLastError
(
ERROR_INVALID_PARAMETER
);
return
FALSE
;
}
if
(
!
CRYPT_IsSIPCached
(
pgSubject
)
&&
!
CRYPT_LoadSIP
(
pgSubject
))
return
FALSE
;
return
FALSE
;
pSipDispatch
->
hSIP
=
NULL
;
pSipDispatch
->
pfGet
=
CryptSIPGetSignedDataMsg
;
pSipDispatch
->
pfPut
=
CryptSIPPutSignedDataMsg
;
pSipDispatch
->
pfCreate
=
CryptSIPCreateIndirectData
;
pSipDispatch
->
pfVerify
=
CryptSIPVerifyIndirectData
;
pSipDispatch
->
pfRemove
=
CryptSIPRemoveSignedDataMsg
;
return
TRUE
;
}
/***********************************************************************
...
...
dlls/crypt32/tests/sip.c
View file @
19c3a09b
...
...
@@ -283,9 +283,8 @@ static void test_SIPLoad(void)
sdi
.
pfGet
=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
;
ret
=
CryptSIPLoad
(
&
dummySubject
,
0
,
&
sdi
);
ok
(
!
ret
,
"Expected CryptSIPLoad to fail
\n
"
);
todo_wine
ok
(
GetLastError
()
==
TRUST_E_SUBJECT_FORM_UNKNOWN
,
"Expected TRUST_E_SUBJECT_FORM_UNKNOWN, got 0x%08x
\n
"
,
GetLastError
());
ok
(
GetLastError
()
==
TRUST_E_SUBJECT_FORM_UNKNOWN
,
"Expected TRUST_E_SUBJECT_FORM_UNKNOWN, got 0x%08x
\n
"
,
GetLastError
());
ok
(
sdi
.
pfGet
==
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
,
"Expected no change to the function pointer
\n
"
);
hCrypt
=
LoadLibraryA
(
"crypt32.dll"
);
...
...
@@ -306,16 +305,13 @@ static void test_SIPLoad(void)
sdi
.
cbSize
=
sizeof
(
SIP_DISPATCH_INFO
);
sdi
.
pfGet
=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
;
ret
=
CryptSIPLoad
(
&
unknown
,
0
,
&
sdi
);
todo_wine
{
ok
(
ret
,
"Expected CryptSIPLoad to succeed
\n
"
);
/* On native the last error will always be ERROR_PROC_NOT_FOUND as native searches for the function DllCanUnloadNow
* in WINTRUST.DLL (in this case). This function is not available in WINTRUST.DLL.
* For now there's no need to implement this is Wine as I doubt any program will rely on
* this last error when the call succeeded.
*/
ok
(
sdi
.
pfGet
!=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
,
"Expected a function pointer to be loaded.
\n
"
);
}
ok
(
ret
,
"Expected CryptSIPLoad to succeed
\n
"
);
/* On native the last error will always be ERROR_PROC_NOT_FOUND as native searches for the function DllCanUnloadNow
* in WINTRUST.DLL (in this case). This function is not available in WINTRUST.DLL.
* For now there's no need to implement this is Wine as I doubt any program will rely on
* this last error when the call succeeded.
*/
ok
(
sdi
.
pfGet
!=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
,
"Expected a function pointer to be loaded.
\n
"
);
/* The function addresses returned by CryptSIPLoad are actually the addresses of
* crypt32's own functions. A function calling these addresses will end up first
...
...
@@ -324,13 +320,12 @@ static void test_SIPLoad(void)
*/
if
(
funcCryptSIPGetSignedDataMsg
&&
funcCryptSIPPutSignedDataMsg
&&
funcCryptSIPCreateIndirectData
&&
funcCryptSIPVerifyIndirectData
&&
funcCryptSIPRemoveSignedDataMsg
)
todo_wine
ok
(
sdi
.
pfGet
==
funcCryptSIPGetSignedDataMsg
&&
sdi
.
pfPut
==
funcCryptSIPPutSignedDataMsg
&&
sdi
.
pfCreate
==
funcCryptSIPCreateIndirectData
&&
sdi
.
pfVerify
==
funcCryptSIPVerifyIndirectData
&&
sdi
.
pfRemove
==
funcCryptSIPRemoveSignedDataMsg
,
"Expected function addresses to be from crypt32
\n
"
);
ok
(
sdi
.
pfGet
==
funcCryptSIPGetSignedDataMsg
&&
sdi
.
pfPut
==
funcCryptSIPPutSignedDataMsg
&&
sdi
.
pfCreate
==
funcCryptSIPCreateIndirectData
&&
sdi
.
pfVerify
==
funcCryptSIPVerifyIndirectData
&&
sdi
.
pfRemove
==
funcCryptSIPRemoveSignedDataMsg
,
"Expected function addresses to be from crypt32
\n
"
);
else
trace
(
"Couldn't load function pointers
\n
"
);
...
...
@@ -340,16 +335,12 @@ static void test_SIPLoad(void)
sdi
.
cbSize
=
sizeof
(
SIP_DISPATCH_INFO
);
sdi
.
pfGet
=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
;
ret
=
CryptSIPLoad
(
&
unknown2
,
0
,
&
sdi
);
todo_wine
{
ok
(
ret
,
"Expected CryptSIPLoad to succeed
\n
"
);
/* This call on its own would have resulted in an ERROR_PROC_NOT_FOUND, but the previous
* call to CryptSIPLoad already loaded wintrust.dll. As this information is cached,
* CryptSIPLoad will not try to search for the already mentioned DllCanUnloadNow.
*/
}
todo_wine
ok
(
sdi
.
pfGet
!=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
,
"Expected a function pointer to be loaded.
\n
"
);
ok
(
ret
,
"Expected CryptSIPLoad to succeed
\n
"
);
/* This call on its own would have resulted in an ERROR_PROC_NOT_FOUND, but the previous
* call to CryptSIPLoad already loaded wintrust.dll. As this information is cached,
* CryptSIPLoad will not try to search for the already mentioned DllCanUnloadNow.
*/
ok
(
sdi
.
pfGet
!=
(
pCryptSIPGetSignedDataMsg
)
0xdeadbeef
,
"Expected a function pointer to be loaded.
\n
"
);
/* All OK, but other SIP */
SetLastError
(
0xdeadbeef
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment