2 * Copyright (c) 2000-2004,2011-2012,2014 Apple Inc. All Rights Reserved.
4 * @APPLE_LICENSE_HEADER_START@
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
21 * @APPLE_LICENSE_HEADER_END@
26 // attachment - CSSM module attachment objects
28 #include "attachment.h"
31 #include "cssmcontext.h"
32 #include <security_cdsa_utilities/cssmbridge.h>
35 // Construct an Attachment object.
36 // This constructor does almost all the work: it initializes the Attachment
37 // object, calls the plugin's attach function, and initializes everything.
38 // The only job left for the subclass's constructor is to take the spiFunctionTable
39 // field and extract from it the plugin's dispatch table in suitable form.
41 Attachment::Attachment(Module
*parent
,
42 const CSSM_VERSION
&version
,
44 CSSM_SERVICE_TYPE ssType
,
45 const CSSM_API_MEMORY_FUNCS
&memoryOps
,
46 CSSM_ATTACH_FLAGS attachFlags
,
47 CSSM_KEY_HIERARCHY keyHierarchy
)
48 : CssmMemoryFunctionsAllocator(memoryOps
), module(*parent
)
53 mSubserviceType
= ssType
;
54 mAttachFlags
= attachFlags
;
55 mKeyHierarchy
= keyHierarchy
;
57 // we are not (yet) attached to our plugin
60 // build the upcalls table
61 // (we could do this once in a static, but then we'd have to lock on it)
62 upcalls
.malloc_func
= upcallMalloc
;
63 upcalls
.free_func
= upcallFree
;
64 upcalls
.realloc_func
= upcallRealloc
;
65 upcalls
.calloc_func
= upcallCalloc
;
66 upcalls
.CcToHandle_func
= upcallCcToHandle
;
67 upcalls
.GetModuleInfo_func
= upcallGetModuleInfo
;
69 // tell the module to create an attachment
70 spiFunctionTable
= NULL
; // preset invalid
71 if (CSSM_RETURN err
= module.plugin
->attach(&module.myGuid(),
78 &gGuidCssm
, // CSSM's Guid
79 &gGuidCssm
, // module manager Guid
80 &module.cssm
.callerGuid(), // caller Guid
83 // attach rejected by module
84 secdebug("cssm", "attach of module %p(%s) failed",
85 &module, module.name().c_str());
86 CssmError::throwMe(err
);
89 if (spiFunctionTable
== NULL
|| spiFunctionTable
->ServiceType
!= subserviceType())
90 CssmError::throwMe(CSSMERR_CSSM_INVALID_ADDIN_FUNCTION_TABLE
);
91 mIsActive
= true; // now officially attached to plugin
92 secdebug("cssm", "%p attached module %p(%s) (ssid %ld type %ld)",
93 this, parent
, parent
->name().c_str(), (long)ssId
, (long)ssType
);
94 // subclass is responsible for taking spiFunctionTable and build
95 // whatever dispatch is needed
97 module.plugin
->detach(handle()); // with extreme prejudice
104 // Detach an attachment.
105 // This is the polite way to detach from the plugin. It may be refused safely
106 // (though perhaps not meaningfully).
107 // THREADS: mLock is locked on entry IFF isLocked, and will be unlocked on exit.
109 void Attachment::detach(bool isLocked
)
111 StLock
<Mutex
> locker(*this, isLocked
); // pre-state locker
112 locker
.lock(); // make sure it's locked
116 CssmError::throwMe(CSSM_ERRCODE_FUNCTION_FAILED
); //@#attachment busy
117 if (CSSM_RETURN error
= module.plugin
->detach(handle()))
118 CssmError::throwMe(error
); // I'm sorry Dave, ...
119 secdebug("cssm", "%p detach module %p(%s)", this,
120 &module, module.name().c_str());
128 // Destroy the Attachment object
130 Attachment::~Attachment()
135 // too bad - you're dead
142 // These do not lock the attachment object. The attachment can't go away
143 // because we incremented the busy count on entry to the plugin; and these
144 // fields are quite constant for the life of the Attachment.
146 void *Attachment::upcallMalloc(CSSM_HANDLE handle
, size_t size
)
149 return HandleObject::find
<Attachment
>(handle
, CSSMERR_CSSM_INVALID_ADDIN_HANDLE
).malloc(size
);
153 void Attachment::upcallFree(CSSM_HANDLE handle
, void *mem
)
156 return HandleObject::find
<Attachment
>(handle
, CSSMERR_CSSM_INVALID_ADDIN_HANDLE
).free(mem
);
160 void *Attachment::upcallRealloc(CSSM_HANDLE handle
, void *mem
, size_t size
)
163 return HandleObject::find
<Attachment
>(handle
, CSSMERR_CSSM_INVALID_ADDIN_HANDLE
).realloc(mem
, size
);
167 void *Attachment::upcallCalloc(CSSM_HANDLE handle
, size_t num
, size_t size
)
170 return HandleObject::find
<Attachment
>(handle
, CSSMERR_CSSM_INVALID_ADDIN_HANDLE
).calloc(size
, num
);
174 CSSM_RETURN
Attachment::upcallCcToHandle(CSSM_CC_HANDLE handle
,
175 CSSM_MODULE_HANDLE
*modHandle
)
178 #warning Cast from CSSM_CC_HANDLE to CSSM_HANDLE
179 Required(modHandle
) = HandleObject::find
<HandleContext
>((CSSM_HANDLE
)handle
, CSSMERR_CSSM_INVALID_ADDIN_HANDLE
).attachment
.handle();
183 CSSM_RETURN
Attachment::upcallGetModuleInfo(CSSM_MODULE_HANDLE handle
,
185 CSSM_VERSION_PTR version
,
186 uint32
*subserviceId
,
187 CSSM_SERVICE_TYPE
*subserviceType
,
188 CSSM_ATTACH_FLAGS
*attachFlags
,
189 CSSM_KEY_HIERARCHY
*keyHierarchy
,
190 CSSM_API_MEMORY_FUNCS_PTR memoryOps
,
191 CSSM_FUNC_NAME_ADDR_PTR FunctionTable
,
195 Attachment
&attachment
= HandleObject::find
<Attachment
>(handle
, CSSMERR_CSSM_INVALID_ADDIN_HANDLE
);
196 Required(guid
) = attachment
.myGuid();
197 Required(version
) = attachment
.mVersion
;
198 Required(subserviceId
) = attachment
.mSubserviceId
;
199 Required(subserviceType
) = attachment
.mSubserviceType
;
200 Required(attachFlags
) = attachment
.mAttachFlags
;
201 Required(keyHierarchy
) = attachment
.mKeyHierarchy
;
202 Required(memoryOps
) = attachment
;
204 attachment
.resolveSymbols(FunctionTable
, NumFunctions
);