2 * Copyright (c) 2000-2002 Apple Computer, Inc. All rights reserved.
4 * @APPLE_LICENSE_HEADER_START@
6 * The contents of this file constitute Original Code as defined in and
7 * are subject to the Apple Public Source License Version 1.1 (the
8 * "License"). You may not use this file except in compliance with the
9 * License. Please obtain a copy of the License at
10 * http://www.apple.com/publicsource and read it before using this file.
12 * This Original Code and all software distributed under the License are
13 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
14 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
15 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
17 * License for the specific language governing rights and limitations
20 * @APPLE_LICENSE_HEADER_END@
24 * Modification History
26 * June 1, 2001 Allan Nathanson <ajn@apple.com>
27 * - public API conversion
29 * March 24, 2000 Allan Nathanson <ajn@apple.com>
39 isMySessionKey(CFStringRef sessionKey
, CFStringRef key
)
42 CFStringRef storeSessionKey
;
44 dict
= CFDictionaryGetValue(storeData
, key
);
46 /* if key no longer exists */
50 storeSessionKey
= CFDictionaryGetValue(dict
, kSCDSession
);
51 if (!storeSessionKey
) {
52 /* if this is not a session key */
56 if (!CFEqual(sessionKey
, storeSessionKey
)) {
57 /* if this is not "my" session key */
66 __SCDynamicStoreClose(SCDynamicStoreRef
*store
)
68 SCDynamicStorePrivateRef storePrivate
= (SCDynamicStorePrivateRef
)*store
;
70 CFStringRef sessionKey
;
73 serverSessionRef mySession
;
75 SCLog(_configd_verbose
, LOG_DEBUG
, CFSTR("__SCDynamicStoreClose:"));
77 if ((*store
== NULL
) || (storePrivate
->server
== MACH_PORT_NULL
)) {
78 return kSCStatusNoStoreSession
; /* you must have an open session to play */
81 /* Remove notification keys */
82 keyCnt
= CFSetGetCount(storePrivate
->keys
);
84 const void **watchedKeys
;
85 CFArrayRef keysToRemove
;
88 watchedKeys
= CFAllocatorAllocate(NULL
, keyCnt
* sizeof(CFStringRef
), 0);
89 CFSetGetValues(storePrivate
->keys
, watchedKeys
);
90 keysToRemove
= CFArrayCreate(NULL
, watchedKeys
, keyCnt
, &kCFTypeArrayCallBacks
);
91 CFAllocatorDeallocate(NULL
, watchedKeys
);
92 for (i
=0; i
<keyCnt
; i
++) {
93 (void) __SCDynamicStoreRemoveWatchedKey(*store
,
94 CFArrayGetValueAtIndex(keysToRemove
, i
),
97 CFRelease(keysToRemove
);
100 /* Remove regex notification keys */
101 keyCnt
= CFSetGetCount(storePrivate
->reKeys
);
103 const void **watchedKeys
;
104 CFArrayRef keysToRemove
;
107 watchedKeys
= CFAllocatorAllocate(NULL
, keyCnt
* sizeof(CFStringRef
), 0);
108 CFSetGetValues(storePrivate
->reKeys
, watchedKeys
);
109 keysToRemove
= CFArrayCreate(NULL
, watchedKeys
, keyCnt
, &kCFTypeArrayCallBacks
);
110 CFAllocatorDeallocate(NULL
, watchedKeys
);
111 for (i
=0; i
<keyCnt
; i
++) {
112 (void) __SCDynamicStoreRemoveWatchedKey(*store
,
113 CFArrayGetValueAtIndex(keysToRemove
, i
),
116 CFRelease(keysToRemove
);
119 /* Remove/cancel any outstanding notification requests. */
120 (void) __SCDynamicStoreNotifyCancel(*store
);
122 /* Remove any session keys */
123 sessionKey
= CFStringCreateWithFormat(NULL
, NULL
, CFSTR("%d"), storePrivate
->server
);
124 dict
= CFDictionaryGetValue(sessionData
, sessionKey
);
125 keys
= CFDictionaryGetValue(dict
, kSCDSessionKeys
);
126 if (keys
&& ((keyCnt
= CFArrayGetCount(keys
)) > 0)) {
131 * if necessary, claim a lock to ensure that we inform
132 * any processes that a session key was removed.
134 wasLocked
= (storeLocked
> 0);
136 (void) __SCDynamicStoreLock(*store
, FALSE
);
139 /* remove keys from "locked" store" */
140 for (i
=0; i
<keyCnt
; i
++) {
141 if (isMySessionKey(sessionKey
, CFArrayGetValueAtIndex(keys
, i
))) {
142 (void) __SCDynamicStoreRemoveValue(*store
, CFArrayGetValueAtIndex(keys
, i
));
147 /* remove keys from "unlocked" store" */
148 _swapLockedStoreData();
149 for (i
=0; i
<keyCnt
; i
++) {
150 if (isMySessionKey(sessionKey
, CFArrayGetValueAtIndex(keys
, i
)))
151 (void) __SCDynamicStoreRemoveValue(*store
, CFArrayGetValueAtIndex(keys
, i
));
153 _swapLockedStoreData();
157 * Note: everyone who calls __SCDynamicStoreClose() ends
158 * up removing this sessions dictionary. As such,
159 * we don't need to worry about the session keys.
162 CFRelease(sessionKey
);
164 /* release the lock */
165 if (storePrivate
->locked
) {
166 (void) __SCDynamicStoreUnlock(*store
, FALSE
);
170 * Remove the run loop source on the server port (for this
171 * client). Then, invalidate and release the port.
173 mySession
= getSession(storePrivate
->server
);
174 if (mySession
->serverRunLoopSource
) {
175 CFRunLoopRemoveSource(CFRunLoopGetCurrent(),
176 mySession
->serverRunLoopSource
,
177 kCFRunLoopDefaultMode
);
178 CFRelease(mySession
->serverRunLoopSource
);
180 CFMachPortInvalidate(mySession
->serverPort
);
181 CFRelease(mySession
->serverPort
);
183 storePrivate
->server
= MACH_PORT_NULL
;
192 _configclose(mach_port_t server
, int *sc_status
)
194 serverSessionRef mySession
= getSession(server
);
196 SCLog(_configd_verbose
, LOG_DEBUG
, CFSTR("Close session."));
197 SCLog(_configd_verbose
, LOG_DEBUG
, CFSTR(" server = %d"), server
);
202 *sc_status
= __SCDynamicStoreClose(&mySession
->store
);
203 if (*sc_status
!= kSCStatusOK
) {
204 SCLog(_configd_verbose
, LOG_DEBUG
, CFSTR(" __SCDynamicStoreClose(): %s"), SCErrorString(*sc_status
));
209 * Remove the session entry.
211 removeSession(server
);