/* * Copyright (c) 2003 Apple Computer, Inc. All rights reserved. * * @APPLE_LICENSE_HEADER_START@ * * This file contains Original Code and/or Modifications of Original Code * as defined in and that are subject to the Apple Public Source License * Version 2.0 (the 'License'). You may not use this file except in * compliance with the License. Please obtain a copy of the License at * http://www.opensource.apple.com/apsl/ and read it before using this * file. * * The Original Code and all software distributed under the License are * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. * Please see the License for the specific language governing rights and * limitations under the License. * * @APPLE_LICENSE_HEADER_END@ */ #import "PolicyUser.h" // ---------------------------------------------------------------------------------------- #pragma mark - #pragma mark C API #pragma mark - // ---------------------------------------------------------------------------------------- // ---------------------------------------------------------------------------------------- // ConvertXMLPolicyToSpaceDelimited // // Returns: -1 fail, or 0 success. // <outPolicyStr> is malloc'd memory, caller must free. // ---------------------------------------------------------------------------------------- int ConvertXMLPolicyToSpaceDelimited( const char *inXMLDataStr, char **outPolicyStr ) { PolicyUser *userPolicyObj = nil; CFStringRef userPolicyString = NULL; CFIndex needSize = 0; int result = 0; if ( inXMLDataStr == NULL || outPolicyStr == NULL ) return -1; *outPolicyStr = NULL; userPolicyObj = [[PolicyUser alloc] initWithUTF8String:inXMLDataStr]; if ( userPolicyObj != nil ) { userPolicyString = [userPolicyObj policyAsSpaceDelimitedDataCopy]; if ( userPolicyString != NULL ) { needSize = CFStringGetMaximumSizeForEncoding( CFStringGetLength(userPolicyString), kCFStringEncodingUTF8 ); *outPolicyStr = (char *) malloc( needSize + 1 ); if ( *outPolicyStr != NULL ) { if ( CFStringGetCString(userPolicyString, *outPolicyStr, needSize + 1, kCFStringEncodingUTF8) ) result = 1; } CFRelease( userPolicyString ); } [userPolicyObj free]; } // clean up on failure if ( result == 0 && *outPolicyStr != NULL ) { free( *outPolicyStr ); *outPolicyStr = NULL; } return result; } // ---------------------------------------------------------------------------------------- // ConvertSpaceDelimitedPolicyToXML // // Returns: -1 fail, or 0 success. // <outXMLDataStr> is malloc'd memory, caller must free. // ---------------------------------------------------------------------------------------- int ConvertSpaceDelimitedPolicyToXML( const char *inPolicyStr, char **outXMLDataStr ) { return ConvertSpaceDelimitedPoliciesToXML( inPolicyStr, NO, outXMLDataStr ); } int ConvertSpaceDelimitedPoliciesToXML( const char *inPolicyStr, int inPreserveStateInfo, char **outXMLDataStr ) { PWAccessFeatures policies; PWMoreAccessFeatures morePolicies = {0}; PolicyUser *userPolicyObj = nil; if ( inPolicyStr == NULL || outXMLDataStr == NULL ) return -1; *outXMLDataStr = NULL; GetDefaultUserPolicies( &policies ); if ( ! StringToPWAccessFeaturesExtra( inPolicyStr, &policies, &morePolicies ) ) return -1; userPolicyObj = [[PolicyUser alloc] init]; if ( userPolicyObj != nil ) { [userPolicyObj addMiscPolicies:inPolicyStr]; [userPolicyObj setPolicy:&policies extraPolicy:&morePolicies]; *outXMLDataStr = [userPolicyObj policyAsXMLDataCopy:(BOOL)inPreserveStateInfo]; [userPolicyObj free]; } return (*outXMLDataStr == NULL) ? -1 : 0; } @implementation PolicyUser -(void)getPolicy:(PWAccessFeatures *)outPolicy extraPolicy:(PWMoreAccessFeatures *)outExtraPolicy { memcpy(outPolicy, &mUserPolicy, sizeof(PWAccessFeatures)); memcpy(outExtraPolicy, &mMoreUserPolicy, sizeof(PWMoreAccessFeatures)); } -(void)setPolicy:(PWAccessFeatures *)inPolicy { memcpy(&mUserPolicy, inPolicy, sizeof(PWAccessFeatures)); } -(void)setPolicy:(PWAccessFeatures *)inPolicy extraPolicy:(PWMoreAccessFeatures *)inExtraPolicy { [self setPolicy:inPolicy]; memcpy(&mMoreUserPolicy, inExtraPolicy, sizeof(PWMoreAccessFeatures)); } //------------------------------------------------------------------------------------------------ // addMiscPolicies // // warnOfExpirationMinutes, warnOfDisableMinutes //------------------------------------------------------------------------------------------------ -(void)addMiscPolicies:(const char *)inPolicyStr { const char *warnOfExpirationMinutes = strstr( inPolicyStr, kPWPolicyStr_warnOfExpirationMinutes ); const char *warnOfDisableMinutes = strstr( inPolicyStr, kPWPolicyStr_warnOfDisableMinutes ); unsigned long value; if ( StringToPWAccessFeatures_GetValue( warnOfExpirationMinutes, &value ) ) mWarnOfExpirationMinutes = value; if ( StringToPWAccessFeatures_GetValue( warnOfDisableMinutes, &value ) ) mWarnOfDisableMinutes = value; } -(void)convertDictToStruct:(CFDictionaryRef)policyDict { int historyCount = [self intValueForKey:CFSTR(kPWPolicyStr_usingHistory) inDictionary:policyDict]; mUserPolicy.usingHistory = (historyCount != 0); mUserPolicy.historyCount = historyCount - 1; mUserPolicy.canModifyPasswordforSelf = 1; if ( CFDictionaryContainsKey(policyDict, CFSTR(kPWPolicyStr_canModifyPasswordforSelf)) ) mUserPolicy.canModifyPasswordforSelf = [self intValueForKey:CFSTR(kPWPolicyStr_canModifyPasswordforSelf) inDictionary:policyDict]; mUserPolicy.usingExpirationDate = [self intValueForKey:CFSTR(kPWPolicyStr_expirationDateGMT) inDictionary:policyDict]; mUserPolicy.usingHardExpirationDate = [self intValueForKey:CFSTR(kPWPolicyStr_hardExpireDateGMT) inDictionary:policyDict]; mUserPolicy.requiresAlpha = [self intValueForKey:CFSTR(kPWPolicyStr_requiresAlpha) inDictionary:policyDict]; mUserPolicy.requiresNumeric = [self intValueForKey:CFSTR(kPWPolicyStr_requiresNumeric) inDictionary:policyDict]; mUserPolicy.passwordCannotBeName = [self intValueForKey:CFSTR(kPWPolicyStr_passwordCannotBeName) inDictionary:policyDict]; mMoreUserPolicy.requiresMixedCase = [self intValueForKey:CFSTR(kPWPolicyStr_requiresMixedCase) inDictionary:policyDict]; mMoreUserPolicy.requiresSymbol = [self intValueForKey:CFSTR(kPWPolicyStr_requiresSymbol) inDictionary:policyDict]; mUserPolicy.newPasswordRequired = [self intValueForKey:CFSTR(kPWPolicyStr_newPasswordRequired) inDictionary:policyDict]; pwsf_ConvertCFDateToBSDTime( [self dateValueForKey:CFSTR(kPWPolicyStr_expirationDateGMT) inDictionary:policyDict], (struct tm *)&mUserPolicy.expirationDateGMT ); pwsf_ConvertCFDateToBSDTime( [self dateValueForKey:CFSTR(kPWPolicyStr_hardExpireDateGMT) inDictionary:policyDict], (struct tm *)&mUserPolicy.hardExpireDateGMT ); mUserPolicy.maxMinutesUntilChangePassword = [self intValueForKey:CFSTR(kPWPolicyStr_maxMinutesUntilChangePW) inDictionary:policyDict]; mUserPolicy.maxMinutesUntilDisabled = [self intValueForKey:CFSTR(kPWPolicyStr_maxMinutesUntilDisabled) inDictionary:policyDict]; mUserPolicy.maxMinutesOfNonUse = [self intValueForKey:CFSTR(kPWPolicyStr_maxMinutesOfNonUse) inDictionary:policyDict]; mUserPolicy.maxFailedLoginAttempts = [self intValueForKey:CFSTR(kPWPolicyStr_maxFailedLoginAttempts) inDictionary:policyDict]; mUserPolicy.minChars = [self intValueForKey:CFSTR(kPWPolicyStr_minChars) inDictionary:policyDict]; mUserPolicy.maxChars = [self intValueForKey:CFSTR(kPWPolicyStr_maxChars) inDictionary:policyDict]; mMoreUserPolicy.minutesUntilFailedLoginReset = [self intValueForKey:CFSTR(kPWPolicyStr_minutesUntilFailedLoginReset) inDictionary:policyDict]; mMoreUserPolicy.notGuessablePattern = [self intValueForKey:CFSTR(kPWPolicyStr_notGuessablePattern) inDictionary:policyDict]; mMoreUserPolicy.isComputerAccount = [self intValueForKey:CFSTR(kPWPolicyStr_isComputerAccount) inDictionary:policyDict]; } -(CFMutableDictionaryRef)convertStructToDict; { CFMutableDictionaryRef policyDict; int historyNumber; CFDateRef expirationDateGMTRef; CFDateRef hardExpireDateGMTRef; unsigned int aBoolVal; CFNumberRef warnOfExpirationRef = NULL; CFNumberRef warnOfDisableRef = NULL; policyDict = CFDictionaryCreateMutable( kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks ); if ( policyDict != NULL ) { // prep historyNumber = (mUserPolicy.usingHistory != 0); if ( historyNumber > 0 ) historyNumber += mUserPolicy.historyCount; pwsf_ConvertBSDTimeToCFDate( (struct tm *)&(mUserPolicy.expirationDateGMT), &expirationDateGMTRef ); pwsf_ConvertBSDTimeToCFDate( (struct tm *)&(mUserPolicy.hardExpireDateGMT), &hardExpireDateGMTRef ); CFNumberRef usingHistoryRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &historyNumber ); aBoolVal = (mUserPolicy.canModifyPasswordforSelf != 0); CFNumberRef canModifyPasswordforSelfRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.usingExpirationDate != 0); CFNumberRef usingExpirationDateRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.usingHardExpirationDate != 0); CFNumberRef usingHardExpirationDateRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.requiresAlpha != 0); CFNumberRef requiresAlphaRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.requiresNumeric != 0); CFNumberRef requiresNumericRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mMoreUserPolicy.requiresMixedCase != 0); CFNumberRef requiresMixedCaseRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mMoreUserPolicy.requiresSymbol != 0); CFNumberRef requiresSymbolRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); CFNumberRef notGuessablePatternRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &(mMoreUserPolicy.notGuessablePattern) ); CFNumberRef minutesUntilFailedLoginResetRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &(mMoreUserPolicy.minutesUntilFailedLoginReset) ); aBoolVal = (mUserPolicy.passwordCannotBeName != 0); CFNumberRef passwordCannotBeNameRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.isSessionKeyAgent != 0); CFNumberRef isSessionKeyAgentRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mMoreUserPolicy.isComputerAccount != 0); CFNumberRef isComputerAccountRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); CFNumberRef maxMinutesUntilChangePasswordRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &mUserPolicy.maxMinutesUntilChangePassword ); CFNumberRef maxMinutesUntilDisabledRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &mUserPolicy.maxMinutesUntilDisabled ); CFNumberRef maxMinutesOfNonUseRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &mUserPolicy.maxMinutesOfNonUse ); CFNumberRef maxFailedLoginAttemptsRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberShortType, &mUserPolicy.maxFailedLoginAttempts ); CFNumberRef minCharsRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberShortType, &mUserPolicy.minChars ); CFNumberRef maxCharsRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberShortType, &mUserPolicy.maxChars ); if ( mWarnOfExpirationMinutes > 0 ) warnOfExpirationRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &mWarnOfExpirationMinutes ); if ( mWarnOfDisableMinutes > 0 ) warnOfDisableRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberLongType, &mWarnOfDisableMinutes ); if ( usingHistoryRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_usingHistory), usingHistoryRef ); CFRelease( usingHistoryRef ); } if ( canModifyPasswordforSelfRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_canModifyPasswordforSelf), canModifyPasswordforSelfRef ); CFRelease( canModifyPasswordforSelfRef ); } if ( usingExpirationDateRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_usingExpirationDate), usingExpirationDateRef ); CFRelease( usingExpirationDateRef ); } if ( usingHardExpirationDateRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_usingHardExpirationDate), usingHardExpirationDateRef ); CFRelease( usingHardExpirationDateRef ); } if ( requiresAlphaRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_requiresAlpha), requiresAlphaRef ); CFRelease( requiresAlphaRef ); } if ( requiresNumericRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_requiresNumeric), requiresNumericRef ); CFRelease( requiresNumericRef ); } if ( requiresMixedCaseRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_requiresMixedCase), requiresMixedCaseRef ); CFRelease( requiresMixedCaseRef ); } if ( requiresSymbolRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_requiresSymbol), requiresSymbolRef ); CFRelease( requiresSymbolRef ); } if ( notGuessablePatternRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_notGuessablePattern), notGuessablePatternRef ); CFRelease( notGuessablePatternRef ); } if ( minutesUntilFailedLoginResetRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_minutesUntilFailedLoginReset), minutesUntilFailedLoginResetRef ); CFRelease( minutesUntilFailedLoginResetRef ); } if ( expirationDateGMTRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_expirationDateGMT), expirationDateGMTRef ); CFRelease( expirationDateGMTRef ); } if ( hardExpireDateGMTRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_hardExpireDateGMT), hardExpireDateGMTRef ); CFRelease( hardExpireDateGMTRef ); } if ( maxMinutesUntilChangePasswordRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_maxMinutesUntilChangePW), maxMinutesUntilChangePasswordRef ); CFRelease( maxMinutesUntilChangePasswordRef ); } if ( maxMinutesUntilDisabledRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_maxMinutesUntilDisabled), maxMinutesUntilDisabledRef ); CFRelease( maxMinutesUntilDisabledRef ); } if ( maxMinutesOfNonUseRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_maxMinutesOfNonUse), maxMinutesOfNonUseRef ); CFRelease( maxMinutesOfNonUseRef ); } if ( maxFailedLoginAttemptsRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_maxFailedLoginAttempts), maxFailedLoginAttemptsRef ); CFRelease( maxFailedLoginAttemptsRef ); } if ( minCharsRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_minChars), minCharsRef ); CFRelease( minCharsRef ); } if ( maxCharsRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_maxChars), maxCharsRef ); CFRelease( maxCharsRef ); } if ( passwordCannotBeNameRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_passwordCannotBeName), passwordCannotBeNameRef ); CFRelease( passwordCannotBeNameRef ); } if ( isSessionKeyAgentRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_isSessionKeyAgent), isSessionKeyAgentRef ); CFRelease( isSessionKeyAgentRef ); } if ( isComputerAccountRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_isComputerAccount), isComputerAccountRef ); CFRelease( isComputerAccountRef ); } if ( warnOfExpirationRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_warnOfExpirationMinutes), warnOfExpirationRef ); CFRelease( warnOfExpirationRef ); } if ( warnOfDisableRef != NULL ) { CFDictionaryAddValue( policyDict, CFSTR(kPWPolicyStr_warnOfDisableMinutes), warnOfDisableRef ); CFRelease( warnOfDisableRef ); } } return policyDict; } -(CFMutableDictionaryRef)convertStructToDictWithState { unsigned int aBoolVal; aBoolVal = (mUserPolicy.isDisabled != 0); CFNumberRef isDisabledRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.isAdminUser != 0); CFNumberRef isAdminUserRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); aBoolVal = (mUserPolicy.newPasswordRequired != 0); CFNumberRef newPasswordRequiredRef = CFNumberCreate( kCFAllocatorDefault, kCFNumberIntType, &aBoolVal ); CFMutableDictionaryRef theDict = [self convertStructToDict]; if ( theDict != NULL ) { if ( isDisabledRef != NULL ) { CFDictionaryAddValue( theDict, CFSTR(kPWPolicyStr_isDisabled), isDisabledRef ); CFRelease( isDisabledRef ); } if ( isAdminUserRef != NULL ) { CFDictionaryAddValue( theDict, CFSTR(kPWPolicyStr_isAdminUser), isAdminUserRef ); CFRelease( isAdminUserRef ); } if ( newPasswordRequiredRef != NULL ) { CFDictionaryAddValue( theDict, CFSTR(kPWPolicyStr_newPasswordRequired), newPasswordRequiredRef ); CFRelease( newPasswordRequiredRef ); } } return theDict; } @end