Last active
April 13, 2017 13:10
-
-
Save joshua-d-miller/969745b4d557990d7f4336bfbd543be0 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/python | |
# pylint:disable=C0103, E0611, E1101, W0703 | |
'''Power User Preferences (With Location Services)''' | |
# This policy will unlock certain system prereference | |
# panes in macOS to allow users who do not have administrative | |
# privileges to access them. | |
# Joshua D. Miller - [email protected] | |
# The Pennsylvania State University | |
# August 31, 2016 - Converted from Bash | |
# April 4, 2017 - Updates Location Services and tested with 10.12.4 | |
from __future__ import print_function | |
from ctypes import CDLL, c_void_p, byref | |
from ctypes.util import find_library | |
from CoreLocation import CLLocationManager | |
from Foundation import (NSBundle, CFPreferencesSetValue, | |
CFPreferencesSynchronize, kCFPreferencesAnyUser, | |
kCFPreferencesCurrentUser, kCFPreferencesCurrentHost) | |
import multiprocessing | |
from platform import mac_ver | |
from distutils import version | |
import objc | |
class power_prefs_with_location(object): | |
'''This is the main class for this script. It will contain all | |
the variables that we need for use throughout this script''' | |
# Get the current version of macOS running on the client | |
macOS_version = mac_ver()[0] | |
macOS_version = version.StrictVersion(macOS_version) | |
# Load Security Framework thanks to Tom burgin | |
# https://gist.github.com/tburgin/ca7cf77767 | |
Security = CDLL(find_library("Security.framework")) | |
AuthorizationRightGet = Security.AuthorizationRightGet | |
AuthorizationRightSet = Security.AuthorizationRightSet | |
AuthorizationCreate = Security.AuthorizationCreate | |
# Set blank uuid variable | |
uuid = '' | |
# Create list of system preferences that we want to modify | |
system_prefs_to_change = [ | |
'system.preferences', 'system.preferences.datetime', | |
'system.preferences.timemachine', 'system.preferences.energysaver'] | |
@classmethod | |
def get_uuid(cls): | |
'''Get the UUID of the computer''' | |
# IOKit Bundle Objective C code from Michael Lynn | |
# https://gist.github.com/pudquick/c7dd1262bd81a32663f0 | |
IOKit_bundle = NSBundle.bundleWithIdentifier_( | |
'com.apple.framework.IOKit') | |
functions = [("IOServiceGetMatchingService", b"II@"), | |
("IOServiceMatching", b"@*"), | |
("IORegistryEntryCreateCFProperty", b"@I@@I"), ] | |
IOKit = dict() | |
objc.loadBundleFunctions(IOKit_bundle, IOKit, functions) | |
# pylint:disable=F0401, E0602, W0232 | |
cls.uuid = IOKit['IORegistryEntryCreateCFProperty']( | |
IOKit['IOServiceGetMatchingService']( | |
0, IOKit['IOServiceMatching']( | |
'IOPlatformExpertDevice')), 'IOPlatformUUID', None, 0) | |
@classmethod | |
def authorization_right_get(cls, right): | |
'''Get Authorization Right thanks to Tom Burgin | |
https://gist.github.com/tburgin/77ebd114d59d368b0b4321ca7cf77767''' | |
db_buffer = c_void_p() | |
cls.AuthorizationRightGet(right, byref(db_buffer)) | |
if db_buffer: | |
# pylint:disable=E1101 | |
return objc.objc_object(c_void_p=db_buffer).mutableCopy() | |
@classmethod | |
def authorization_right_set(cls, right, value): | |
'''Set Authorization Right thanks to Tom Burgin | |
https://gist.github.com/tburgin/77ebd114d59d368b0b4321ca7cf77767''' | |
auth_ref = c_void_p() | |
cls.AuthorizationCreate(None, None, 0, byref(auth_ref)) | |
return cls.AuthorizationRightSet( | |
auth_ref, right, value.__c_void_p__(), None, None, None) | |
@classmethod | |
def location_services(cls): | |
'''This funciton will allow the Mac to change its time zone | |
# based off its location when it is connected to WiFi''' | |
ls_status = CLLocationManager.locationServicesEnabled() | |
if ls_status is False: | |
try: | |
import os | |
import pwd | |
locationd_uid = pwd.getpwnam('_locationd').pw_uid | |
os.setuid(locationd_uid) | |
CFPreferencesSetValue('LocationServicesEnabled', | |
True, 'com.apple.locationd', | |
kCFPreferencesCurrentUser, | |
kCFPreferencesCurrentHost) | |
except Exception as error: | |
print(error) | |
@classmethod | |
def main(cls): | |
'''This function will set the system preferences we have specified | |
and will turn on location services based off WiFi location''' | |
# Enable all users access to the System Preference Panes | |
# we defined above | |
for preference in cls.system_prefs_to_change: | |
if cls.macOS_version < "10.10.0": | |
print('This script will not function on 10.9.5 or below...') | |
exit(0) | |
else: | |
db = power_prefs_with_location.authorization_right_get( | |
preference) | |
if db['group'] == 'admin': | |
db['group'] = 'everyone' | |
if preference == 'system.preferences.datetime': | |
db['shared'] = True | |
power_prefs_with_location.authorization_right_set( | |
preference, db) | |
else: | |
continue | |
# Turn on Location Services and set Time Zone by Location | |
enable_ls = multiprocessing.Process( | |
power_prefs_with_location.location_services()) | |
enable_ls.start() | |
enable_ls.join() | |
# Turn on Auto Timezone | |
CFPreferencesSetValue('Active', True, 'com.apple.timezone.auto', | |
kCFPreferencesAnyUser, kCFPreferencesCurrentHost) | |
# Syncrhonize Preferences for Auto Timezone | |
CFPreferencesSynchronize('com.apple.timezone.auto', | |
kCFPreferencesAnyUser, | |
kCFPreferencesCurrentHost) | |
power_prefs_with_location.main() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment