Boolean _SCNetworkSetSetSetID(SCNetworkSetRef set, CFStringRef newSetID) { SCNetworkSetRef currentSet = NULL; SCNetworkSetPrivateRef currentSetPrivate = NULL; CFDictionaryRef entity; CFStringRef newPath; Boolean ok = FALSE; CFStringRef oldPath = NULL; SCNetworkSetPrivateRef setPrivate = (SCNetworkSetPrivateRef)set; Boolean updateCurrentSet = FALSE; if (!isA_SCNetworkSet(set)) { _SCErrorSet(kSCStatusInvalidArgument); return FALSE; } if (!isA_CFString(newSetID)) { _SCErrorSet(kSCStatusInvalidArgument); return FALSE; } // If newSetID is equal to current setID, our work is done if (CFEqual(newSetID, setPrivate->setID)) { return TRUE; } newPath = SCPreferencesPathKeyCreateSet(NULL, newSetID); entity = SCPreferencesPathGetValue(setPrivate->prefs, newPath); if (isA_CFDictionary(entity)) { // if the new set already exists _SCErrorSet(kSCStatusKeyExists); goto done; } oldPath = SCPreferencesPathKeyCreateSet(NULL, setPrivate->setID); entity = SCPreferencesPathGetValue(setPrivate->prefs, oldPath); if (!isA_CFDictionary(entity)) { // if the set has already been removed _SCErrorSet(kSCStatusNoKey); goto done; } ok = SCPreferencesPathSetValue(setPrivate->prefs, newPath, entity); if (!ok) { goto done; } ok = SCPreferencesPathRemoveValue(setPrivate->prefs, oldPath); if (!ok) { goto done; } // update current set (if needed) currentSet = SCNetworkSetCopyCurrent(setPrivate->prefs); if (currentSet != NULL) { currentSetPrivate = (SCNetworkSetPrivateRef)currentSet; if (CFEqual(currentSetPrivate->setID, setPrivate->setID)) { updateCurrentSet = TRUE; } CFRelease(currentSet); } CFRetain(newSetID); CFRelease(setPrivate->setID); setPrivate->setID = newSetID; if (updateCurrentSet) { SCNetworkSetSetCurrent(set); } done: if (oldPath != NULL) { CFRelease(oldPath); } if (newPath != NULL) { CFRelease(newPath); } return ok; }
static Boolean establishNewPreferences() { CFBundleRef bundle; SCNetworkSetRef current = NULL; CFStringRef new_model; Boolean ok = FALSE; int sc_status = kSCStatusFailed; SCNetworkSetRef set = NULL; CFStringRef setName = NULL; Boolean updated = FALSE; while (TRUE) { ok = SCPreferencesLock(prefs, TRUE); if (ok) { break; } sc_status = SCError(); if (sc_status == kSCStatusStale) { SCPreferencesSynchronize(prefs); } else { SCLog(TRUE, LOG_ERR, CFSTR("Could not acquire network configuration lock: %s"), SCErrorString(sc_status)); return FALSE; } } /* Ensure that the preferences has the new model */ new_model = _SC_hw_model(FALSE); /* Need to regenerate the new configuration for new model */ if (new_model != NULL) { CFStringRef old_model; old_model = SCPreferencesGetValue(prefs, MODEL); if ((old_model != NULL) && !_SC_CFEqual(old_model, new_model)) { CFIndex count; CFIndex index; CFArrayRef keys; keys = SCPreferencesCopyKeyList(prefs); count = (keys != NULL) ? CFArrayGetCount(keys) : 0; // if new hardware for (index = 0; index < count; index++) { CFStringRef existing_key; existing_key = CFArrayGetValueAtIndex(keys, index); if (isA_CFString(existing_key) != NULL) { CFStringRef new_key; CFPropertyListRef value; /* If it already contains a Model or if it already contains a MODEL:KEY key skip it*/ if (CFEqual(existing_key, MODEL) || CFStringFind(existing_key, CFSTR(":"), 0).location != kCFNotFound) { continue; } value = SCPreferencesGetValue(prefs, existing_key); /* Create a new key as OLD_MODEL:OLD_KEY */ new_key = CFStringCreateWithFormat(NULL, NULL, CFSTR("%@:%@"), old_model, existing_key); SCPreferencesSetValue(prefs, new_key, value); if (!CFEqual(existing_key, kSCPrefSystem)) { /* preserve existing host names */ SCPreferencesRemoveValue(prefs, existing_key); } CFRelease(new_key); } } if (keys != NULL) { CFRelease(keys); } } /* Set the new model */ SCPreferencesSetValue(prefs, MODEL, new_model); } current = SCNetworkSetCopyCurrent(prefs); if (current != NULL) { set = current; } if (set == NULL) { set = SCNetworkSetCreate(prefs); if (set == NULL) { ok = FALSE; sc_status = SCError(); goto done; } bundle = _SC_CFBundleGet(); if (bundle != NULL) { setName = CFBundleCopyLocalizedString(bundle, CFSTR("DEFAULT_SET_NAME"), CFSTR("Automatic"), NULL); } ok = SCNetworkSetSetName(set, (setName != NULL) ? setName : CFSTR("Automatic")); if (!ok) { sc_status = SCError(); goto done; } ok = SCNetworkSetSetCurrent(set); if (!ok) { sc_status = SCError(); goto done; } } ok = SCNetworkSetEstablishDefaultConfiguration(set); if (!ok) { sc_status = SCError(); goto done; } done : if (ok) { ok = SCPreferencesCommitChanges(prefs); if (ok) { SCLog(TRUE, LOG_NOTICE, CFSTR("New network configuration saved")); updated = TRUE; } else { sc_status = SCError(); if (sc_status == EROFS) { /* a read-only fileysstem is OK */ ok = TRUE; /* ... but we don't want to synchronize */ rofs = TRUE; } } /* apply (committed or temporary/read-only) changes */ (void) SCPreferencesApplyChanges(prefs); } else if ((current == NULL) && (set != NULL)) { (void) SCNetworkSetRemove(set); } if (!ok) { SCLog(TRUE, LOG_ERR, CFSTR("Could not establish network configuration: %s"), SCErrorString(sc_status)); } (void)SCPreferencesUnlock(prefs); if (setName != NULL) CFRelease(setName); if (set != NULL) CFRelease(set); return updated; }