2 * Copyright 2004-2006 Juan Lang
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
23 #include "wine/debug.h"
24 #include "wine/list.h"
25 #include "crypt32_private.h"
27 WINE_DEFAULT_DEBUG_CHANNEL(crypt
);
29 typedef struct _CONTEXT_PROPERTY_LIST
32 struct list properties
;
33 } CONTEXT_PROPERTY_LIST
;
35 typedef struct _CONTEXT_PROPERTY
41 } CONTEXT_PROPERTY
, *PCONTEXT_PROPERTY
;
43 PCONTEXT_PROPERTY_LIST
ContextPropertyList_Create(void)
45 PCONTEXT_PROPERTY_LIST list
= CryptMemAlloc(sizeof(CONTEXT_PROPERTY_LIST
));
49 InitializeCriticalSection(&list
->cs
);
50 list
->cs
.DebugInfo
->Spare
[0] = (DWORD_PTR
)(__FILE__
": PCONTEXT_PROPERTY_LIST->cs");
51 list_init(&list
->properties
);
56 void ContextPropertyList_Free(PCONTEXT_PROPERTY_LIST list
)
58 PCONTEXT_PROPERTY prop
, next
;
60 LIST_FOR_EACH_ENTRY_SAFE(prop
, next
, &list
->properties
, CONTEXT_PROPERTY
,
63 list_remove(&prop
->entry
);
64 CryptMemFree(prop
->pbData
);
67 list
->cs
.DebugInfo
->Spare
[0] = 0;
68 DeleteCriticalSection(&list
->cs
);
72 BOOL
ContextPropertyList_FindProperty(PCONTEXT_PROPERTY_LIST list
, DWORD id
,
73 PCRYPT_DATA_BLOB blob
)
75 PCONTEXT_PROPERTY prop
;
78 TRACE("(%p, %d, %p)\n", list
, id
, blob
);
80 EnterCriticalSection(&list
->cs
);
81 LIST_FOR_EACH_ENTRY(prop
, &list
->properties
, CONTEXT_PROPERTY
, entry
)
83 if (prop
->propID
== id
)
85 blob
->cbData
= prop
->cbData
;
86 blob
->pbData
= prop
->pbData
;
91 LeaveCriticalSection(&list
->cs
);
95 BOOL
ContextPropertyList_SetProperty(PCONTEXT_PROPERTY_LIST list
, DWORD id
,
96 const BYTE
*pbData
, size_t cbData
)
103 data
= CryptMemAlloc(cbData
);
105 memcpy(data
, pbData
, cbData
);
111 PCONTEXT_PROPERTY prop
;
114 EnterCriticalSection(&list
->cs
);
115 LIST_FOR_EACH_ENTRY(prop
, &list
->properties
, CONTEXT_PROPERTY
, entry
)
117 if (prop
->propID
== id
)
125 CryptMemFree(prop
->pbData
);
126 prop
->cbData
= cbData
;
132 prop
= CryptMemAlloc(sizeof(CONTEXT_PROPERTY
));
136 prop
->cbData
= cbData
;
138 list_add_tail(&list
->properties
, &prop
->entry
);
144 LeaveCriticalSection(&list
->cs
);
149 void ContextPropertyList_RemoveProperty(PCONTEXT_PROPERTY_LIST list
, DWORD id
)
151 PCONTEXT_PROPERTY prop
, next
;
153 EnterCriticalSection(&list
->cs
);
154 LIST_FOR_EACH_ENTRY_SAFE(prop
, next
, &list
->properties
, CONTEXT_PROPERTY
,
157 if (prop
->propID
== id
)
159 list_remove(&prop
->entry
);
160 CryptMemFree(prop
->pbData
);
165 LeaveCriticalSection(&list
->cs
);
168 /* Since the properties are stored in a list, this is a tad inefficient
169 * (O(n^2)) since I have to find the previous position every time.
171 DWORD
ContextPropertyList_EnumPropIDs(PCONTEXT_PROPERTY_LIST list
, DWORD id
)
175 EnterCriticalSection(&list
->cs
);
178 PCONTEXT_PROPERTY cursor
= NULL
;
180 LIST_FOR_EACH_ENTRY(cursor
, &list
->properties
, CONTEXT_PROPERTY
, entry
)
182 if (cursor
->propID
== id
)
187 if (cursor
->entry
.next
!= &list
->properties
)
188 ret
= LIST_ENTRY(cursor
->entry
.next
, CONTEXT_PROPERTY
,
196 else if (!list_empty(&list
->properties
))
197 ret
= LIST_ENTRY(list
->properties
.next
, CONTEXT_PROPERTY
,
201 LeaveCriticalSection(&list
->cs
);
205 void ContextPropertyList_Copy(PCONTEXT_PROPERTY_LIST to
,
206 PCONTEXT_PROPERTY_LIST from
)
208 PCONTEXT_PROPERTY prop
;
210 EnterCriticalSection(&from
->cs
);
211 LIST_FOR_EACH_ENTRY(prop
, &from
->properties
, CONTEXT_PROPERTY
, entry
)
213 ContextPropertyList_SetProperty(to
, prop
->propID
, prop
->pbData
,
216 LeaveCriticalSection(&from
->cs
);