#include <security_cdsa_client/mdsclient.h>
#include <Security/mdspriv.h>
namespace Security {
namespace MDSClient {
ModuleNexus<Directory> mds;
Directory::Directory()
: mMemoryFunctions(Allocator::standard())
{
StLock<Mutex> _(mInitLock);
CssmError::check(MDS_Initialize(&mCallerGuid, &mMemoryFunctions,
this, &mCDSA.DLHandle));
mCDSA.DBHandle = CSSM_INVALID_HANDLE;
}
Directory::~Directory()
{
if (mCDSA.DBHandle)
CssmError::check(DbClose(mCDSA));
CssmError::check(MDS_Terminate(mds()));
}
const MDS_DB_HANDLE &Directory::cdsa() const
{
if (mCDSA.DBHandle == CSSM_INVALID_HANDLE) {
StLock<Mutex> _(mInitLock);
if (mCDSA.DBHandle == CSSM_INVALID_HANDLE)
CssmError::check(DbOpen(mCDSA.DLHandle, MDS_CDSA_DIRECTORY_NAME, NULL,
CSSM_DB_ACCESS_READ, NULL, NULL, &mCDSA.DBHandle));
}
return mCDSA;
}
CSSM_HANDLE Directory::dlGetFirst(const CSSM_QUERY &query, CSSM_DB_RECORD_ATTRIBUTE_DATA &attributes,
CSSM_DATA *data, CSSM_DB_UNIQUE_RECORD *&id)
{
CSSM_HANDLE result;
switch (CSSM_RETURN rc = DataGetFirst(cdsa(), &query, &result, &attributes, NULL, &id)) {
case CSSM_OK:
if (data)
*data = CssmData();
return result;
case CSSMERR_DL_ENDOFDATA:
return CSSM_INVALID_HANDLE;
default:
CssmError::throwMe(rc);
return CSSM_INVALID_HANDLE; }
}
bool Directory::dlGetNext(CSSM_HANDLE handle, CSSM_DB_RECORD_ATTRIBUTE_DATA &attributes,
CSSM_DATA *data, CSSM_DB_UNIQUE_RECORD *&id)
{
CSSM_RETURN rc = DataGetNext(cdsa(), handle, &attributes, NULL, &id);
switch (rc) {
case CSSM_OK:
if (data)
*data = CssmData();
return true;
case CSSMERR_DL_ENDOFDATA:
return false;
default:
CssmError::throwMe(rc);
return false; }
}
void Directory::dlAbortQuery(CSSM_HANDLE handle)
{
CssmError::check(DataAbortQuery(cdsa(), handle));
}
void Directory::dlFreeUniqueId(CSSM_DB_UNIQUE_RECORD *id)
{
CssmError::check(FreeUniqueRecord(cdsa(), id));
}
void Directory::dlDeleteRecord(CSSM_DB_UNIQUE_RECORD *id)
{
CssmError::check(DataDelete(cdsa(), id));
}
Allocator &Directory::allocator()
{
return Allocator::standard();
}
void Directory::install()
{
CssmError::check(MDS_Install(this->mds()));
}
void Directory::install(const MDS_InstallDefaults *defaults,
const char *path, const char *subdir, const char *file)
{
CssmError::check(MDS_InstallFile(this->mds(), defaults, path, subdir, file));
}
void Directory::uninstall(const char *guid, uint32 ssid)
{
CssmError::check(MDS_RemoveSubservice(this->mds(), guid, ssid));
}
} }