#include <mach/mach.h>
#include <mach/mach_error.h>
#include <SystemConfiguration/SystemConfiguration.h>
#include <SystemConfiguration/SCPrivate.h>
#include "SCDynamicStoreInternal.h"
#include "config.h"
CFDictionaryRef
SCDynamicStoreCopyMultiple(SCDynamicStoreRef store,
CFArrayRef keys,
CFArrayRef patterns)
{
SCDynamicStorePrivateRef storePrivate = (SCDynamicStorePrivateRef)store;
kern_return_t status;
CFDataRef xmlKeys = NULL;
xmlData_t myKeysRef = NULL;
CFIndex myKeysLen = 0;
CFDataRef xmlPatterns = NULL;
xmlData_t myPatternsRef = NULL;
CFIndex myPatternsLen = 0;
xmlDataOut_t xmlDictRef;
CFIndex xmlDictLen;
CFDataRef xmlDict;
CFDictionaryRef dict;
int sc_status;
CFStringRef xmlError;
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("SCDynamicStoreCopyMultiple:"));
SCLog(_sc_verbose, LOG_DEBUG, CFSTR(" keys = %@"), keys);
SCLog(_sc_verbose, LOG_DEBUG, CFSTR(" patterns = %@"), patterns);
if (!store) {
_SCErrorSet(kSCStatusNoStoreSession);
return NULL;
}
if (storePrivate->server == MACH_PORT_NULL) {
_SCErrorSet(kSCStatusNoStoreServer);
return NULL;
}
if (keys) {
xmlKeys = CFPropertyListCreateXMLData(NULL, keys);
myKeysRef = (xmlData_t)CFDataGetBytePtr(xmlKeys);
myKeysLen = CFDataGetLength(xmlKeys);
}
if (patterns) {
xmlPatterns = CFPropertyListCreateXMLData(NULL, patterns);
myPatternsRef = (xmlData_t)CFDataGetBytePtr(xmlPatterns);
myPatternsLen = CFDataGetLength(xmlPatterns);
}
status = configget_m(storePrivate->server,
myKeysRef,
myKeysLen,
myPatternsRef,
myPatternsLen,
&xmlDictRef,
(int *)&xmlDictLen,
(int *)&sc_status);
if (xmlKeys) CFRelease(xmlKeys);
if (xmlPatterns) CFRelease(xmlPatterns);
if (status != KERN_SUCCESS) {
if (status != MACH_SEND_INVALID_DEST)
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("configget_m(): %s"), mach_error_string(status));
(void) mach_port_destroy(mach_task_self(), storePrivate->server);
storePrivate->server = MACH_PORT_NULL;
_SCErrorSet(status);
return NULL;
}
if (sc_status != kSCStatusOK) {
status = vm_deallocate(mach_task_self(), (vm_address_t)xmlDictRef, xmlDictLen);
if (status != KERN_SUCCESS) {
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("vm_deallocate(): %s"), mach_error_string(status));
}
_SCErrorSet(sc_status);
return NULL;
}
xmlDict = CFDataCreate(NULL, xmlDictRef, xmlDictLen);
status = vm_deallocate(mach_task_self(), (vm_address_t)xmlDictRef, xmlDictLen);
if (status != KERN_SUCCESS) {
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("vm_deallocate(): %s"), mach_error_string(status));
}
dict = CFPropertyListCreateFromXMLData(NULL,
xmlDict,
kCFPropertyListImmutable,
&xmlError);
CFRelease(xmlDict);
if (!dict) {
if (xmlError) {
SCLog(_sc_verbose, LOG_DEBUG,
CFSTR("CFPropertyListCreateFromXMLData() dict: %@"),
xmlError);
CFRelease(xmlError);
}
_SCErrorSet(kSCStatusFailed);
return NULL;
}
SCLog(_sc_verbose, LOG_DEBUG, CFSTR(" value = %@"), dict);
return dict;
}
CFPropertyListRef
SCDynamicStoreCopyValue(SCDynamicStoreRef store, CFStringRef key)
{
SCDynamicStorePrivateRef storePrivate = (SCDynamicStorePrivateRef)store;
kern_return_t status;
CFDataRef xmlKey;
xmlData_t myKeyRef;
CFIndex myKeyLen;
xmlDataOut_t xmlDataRef;
CFIndex xmlDataLen;
CFDataRef xmlData;
CFPropertyListRef data;
int newInstance;
int sc_status;
CFStringRef xmlError;
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("SCDynamicStoreCopyValue:"));
SCLog(_sc_verbose, LOG_DEBUG, CFSTR(" key = %@"), key);
if (!store) {
_SCErrorSet(kSCStatusNoStoreSession);
return NULL;
}
if (storePrivate->server == MACH_PORT_NULL) {
_SCErrorSet(kSCStatusNoStoreServer);
return NULL;
}
xmlKey = CFPropertyListCreateXMLData(NULL, key);
myKeyRef = (xmlData_t)CFDataGetBytePtr(xmlKey);
myKeyLen = CFDataGetLength(xmlKey);
status = configget(storePrivate->server,
myKeyRef,
myKeyLen,
&xmlDataRef,
(int *)&xmlDataLen,
&newInstance,
(int *)&sc_status);
CFRelease(xmlKey);
if (status != KERN_SUCCESS) {
if (status != MACH_SEND_INVALID_DEST)
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("configget(): %s"), mach_error_string(status));
(void) mach_port_destroy(mach_task_self(), storePrivate->server);
storePrivate->server = MACH_PORT_NULL;
_SCErrorSet(status);
return NULL;
}
if (sc_status != kSCStatusOK) {
status = vm_deallocate(mach_task_self(), (vm_address_t)xmlDataRef, xmlDataLen);
if (status != KERN_SUCCESS) {
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("vm_deallocate(): %s"), mach_error_string(status));
}
_SCErrorSet(sc_status);
return NULL;
}
xmlData = CFDataCreate(NULL, xmlDataRef, xmlDataLen);
status = vm_deallocate(mach_task_self(), (vm_address_t)xmlDataRef, xmlDataLen);
if (status != KERN_SUCCESS) {
SCLog(_sc_verbose, LOG_DEBUG, CFSTR("vm_deallocate(): %s"), mach_error_string(status));
}
data = CFPropertyListCreateFromXMLData(NULL,
xmlData,
kCFPropertyListImmutable,
&xmlError);
CFRelease(xmlData);
if (!data) {
if (xmlError) {
SCLog(_sc_verbose, LOG_DEBUG,
CFSTR("CFPropertyListCreateFromXMLData() data: %@"),
xmlError);
CFRelease(xmlError);
}
_SCErrorSet(kSCStatusFailed);
return NULL;
}
SCLog(_sc_verbose, LOG_DEBUG, CFSTR(" value = %@"), data);
return data;
}