2 * Copyright (c) 2000-2001 Apple Computer, Inc. All Rights Reserved.
4 * The contents of this file constitute Original Code as defined in and are
5 * subject to the Apple Public Source License Version 1.2 (the 'License').
6 * You may not use this file except in compliance with the License. Please obtain
7 * a copy of the License at http://www.apple.com/publicsource and read it before
10 * This Original Code and all software distributed under the License are
11 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS
12 * OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, INCLUDING WITHOUT
13 * LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
14 * PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. Please see the License for the
15 * specific language governing rights and limitations under the License.
27 #include "cssmdatetime.h"
29 #include "StorageManager.h"
30 #include <CoreServices/../Frameworks/CarbonCore.framework/Headers/MacErrors.h>
32 using namespace KeychainCore
;
33 using namespace CssmClient
;
34 using namespace CSSMDateTimeUtils
;
39 KCCursorImpl::KCCursorImpl(const DbCursor
&dbCursor
, SecItemClass itemClass
, const SecKeychainAttributeList
*attrList
)
42 if (!attrList
) // No additional selectionPredicates: we are done
46 mDbCursor
->recordType(Schema::recordTypeFor(itemClass
));
48 mDbCursor
->conjunctive(CSSM_DB_AND
);
49 const SecKeychainAttribute
*end
=&attrList
->attr
[attrList
->count
];
50 // Add all the attrs in attrs list to the cursor.
51 for (const SecKeychainAttribute
*attr
=attrList
->attr
; attr
!= end
; ++attr
)
53 const CssmDbAttributeInfo
&info
= Schema::attributeInfo(attr
->tag
);
54 void *buf
= attr
->data
;
55 UInt32 length
= attr
->length
;
58 // XXX This code is duplicated in NewItemImpl::setAttribute()
59 // Convert a 4 or 8 byte TIME_DATE to a CSSM_DB_ATTRIBUTE_FORMAT_TIME_DATE
60 // style attribute value.
61 if (info
.format() == CSSM_DB_ATTRIBUTE_FORMAT_TIME_DATE
)
63 if (length
== sizeof(UInt32
))
65 MacSecondsToTimeString(*reinterpret_cast<const UInt32
*>(buf
),
70 else if (length
== sizeof(SInt64
))
72 MacLongDateTimeToTimeString(*reinterpret_cast<const SInt64
*>(buf
),
78 mDbCursor
->add(CSSM_DB_EQUAL
,info
, CssmData(buf
,length
));
82 KCCursorImpl::KCCursorImpl(const DbCursor
&dbCursor
, const SecKeychainAttributeList
*attrList
)
85 if (!attrList
) // No additional selectionPredicates: we are done
88 mDbCursor
->conjunctive(CSSM_DB_AND
);
89 bool foundClassAttribute
=false;
90 const SecKeychainAttribute
*end
=&attrList
->attr
[attrList
->count
];
91 // Add all the attrs in attrs list to the cursor.
92 for (const SecKeychainAttribute
*attr
=attrList
->attr
; attr
!= end
; ++attr
)
94 if (attr
->tag
!=kSecClassItemAttr
) // a regular attribute
96 const CssmDbAttributeInfo
&info
= Schema::attributeInfo(attr
->tag
);
97 void *buf
= attr
->data
;
98 UInt32 length
= attr
->length
;
101 // XXX This code is duplicated in NewItemImpl::setAttribute()
102 // Convert a 4 or 8 byte TIME_DATE to a CSSM_DB_ATTRIBUTE_FORMAT_TIME_DATE
103 // style attribute value.
104 if (info
.format() == CSSM_DB_ATTRIBUTE_FORMAT_TIME_DATE
)
106 if (length
== sizeof(UInt32
))
108 MacSecondsToTimeString(*reinterpret_cast<const UInt32
*>(buf
),
113 else if (length
== sizeof(SInt64
))
115 MacLongDateTimeToTimeString(*reinterpret_cast<const SInt64
*>(buf
),
121 mDbCursor
->add(CSSM_DB_EQUAL
,info
, CssmData(buf
,length
));
126 // the class attribute
127 if (foundClassAttribute
|| attr
->length
!= sizeof(SecItemClass
))
128 MacOSError::throwMe(paramErr
); // We have 2 different 'clas' attributes
130 mDbCursor
->recordType(Schema
131 ::recordTypeFor(*reinterpret_cast<SecItemClass
*>(attr
->data
)));
132 foundClassAttribute
=true;
136 KCCursorImpl::~KCCursorImpl()
141 KCCursorImpl::next(Item
&item
)
143 DbAttributes dbAttributes
;
144 DbUniqueRecord uniqueId
;
146 MacOSError::throwMe(errSecInvalidSearchRef
);
150 if (!mDbCursor
->next(&dbAttributes
, NULL
, uniqueId
))
152 // Forget my resources.
153 mDbCursor
= DbCursor();
157 // Skip records that we don't have a matching itemClass for,
158 // since we can't do anything with them.
159 if (Schema::itemClassFor(dbAttributes
.recordType()))
163 Keychain keychain
= globals().storageManager
.keychain(uniqueId
->database()->dlDbIdentifier());
164 // Go though Keychain since item might already exist.
165 item
= keychain
->item(dbAttributes
.recordType(), uniqueId
);