Skip to content

Commit

Permalink
AS fixes
Browse files Browse the repository at this point in the history
  • Loading branch information
tuxudo committed Dec 12, 2022
1 parent cf273d3 commit f64a02f
Showing 1 changed file with 108 additions and 69 deletions.
177 changes: 108 additions & 69 deletions scripts/power
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,10 @@ def get_battery_profiler():
elif item == 'sppower_ups_installed':
batteryprofiler['UPSInstalled'] = obj[item]
elif item == 'sppower_battery_health_info':
batteryprofiler['condition'] = obj['sppower_battery_health_info']['sppower_battery_health']
try:
batteryprofiler['condition'] = obj['sppower_battery_health_info']['sppower_battery_health']
except:
pass
elif item == 'sppower_battery_installed' and obj['sppower_battery_installed'] == "FALSE":
batteryprofiler['condition'] = "No Battery"
elif item == 'sppower_battery_charge_info':
Expand Down Expand Up @@ -120,17 +123,19 @@ def get_battery_stats():
plist = plistlib.loads(output)
batteryxml = plist[0]

cpu_arch = os.uname()[3].lower()

batteryinfo = get_battery_profiler()
for item in batteryxml:
if item == 'DesignCapacity':
batteryinfo['DesignCapacity'] = batteryxml[item]
elif item == 'MaxCapacity' and platform.processor() == 'i386':
elif item == 'MaxCapacity' and (cpu_arch == 'i386' or cpu_arch == 'x86_64'):
batteryinfo['MaxCapacity'] = batteryxml[item]
elif item == 'AppleRawMaxCapacity' and platform.processor() == 'arm':
elif item == 'AppleRawMaxCapacity' and (cpu_arch == 'arm' or cpu_arch == 'arm64'):
batteryinfo['MaxCapacity'] = batteryxml[item]
elif item == 'CurrentCapacity' and platform.processor() == 'i386':
elif item == 'CurrentCapacity' and (cpu_arch == 'i386' or cpu_arch == 'x86_64'):
batteryinfo['CurrentCapacity'] = batteryxml[item]
elif item == 'AppleRawCurrentCapacity' and platform.processor() == 'arm':
elif item == 'AppleRawCurrentCapacity' and (cpu_arch == 'arm' or cpu_arch == 'arm64'):
batteryinfo['CurrentCapacity'] = batteryxml[item]
elif item == 'Temperature':
batteryinfo['Temperature'] = batteryxml[item]
Expand All @@ -154,6 +159,7 @@ def get_battery_stats():
batteryinfo['condition'] = "No Battery"
elif item == 'Serial': # macOS 11+ battery serial is here
batteryinfo['BatterySerialNumber'] = batteryxml[item]
batteryinfo['ManufactureDate'] = process_manufacture_date(batteryxml[item])
elif item == 'BatteryData':
if 'CellVoltage' in batteryxml[item]: # macOS 11+ stores cell voltage here
cells = []
Expand All @@ -162,61 +168,24 @@ def get_battery_stats():
cells.append(str(float(cell)/1000)+"v")
batteryinfo['CellVoltage'] = (', '.join(map(str,(cells))))

# BatteryData values exist prior to Big Sur, but doesn't include the serial number in the dict.
# Only run this routine if Big Sur (Darwin 20) or later.
if getDarwinVersion() > 19:
# The format for battery manufacturing date changed in Big Sur.
# Apple suggested parsing the SerialNumber that contains the manufacture date.
# A SN of XXX1234ZZZZZZZZZZ has the manufacturing date as the values of 1234.
# The first digit is the last digit of the year. 9 would be 2019.
# Note: they reset every decade. So you need to figure out if 9 is 2019 or 2029
battery_serial_number = batteryxml[item]['Serial']
battery_year_sn_digit = int(battery_serial_number[3])
# The next two digits are the week number of the year
battery_week_sn_digit = int(battery_serial_number[4:6])
# The last digit is the day offset: 1 is Monday 7 is Sunday.
battery_day_sn_digit = int(battery_serial_number[6])

# Determine the decade for the battery year
current_decade = datetime.date.today().year - datetime.date.today().year % 10
battery_year = current_decade + battery_year_sn_digit
if (battery_year, battery_week_sn_digit) > datetime.date.today().isocalendar()[:2]:
battery_year -= 10

# Set the variable of the date to year-Wweek-day:
# For example: 2018-10-20 = 2018-W42-5
battery_date_data = str(battery_year) + '-W' + str(battery_week_sn_digit) + '-' + str(battery_day_sn_digit)

# Python's evaluation of the week number does not respect the ISO week numbers.
# Reference: https://community.dataiku.com/t5/Using-Dataiku-DSS/Converting-week-and-year-to-datetime-stamp-using-Python-function/m-p/11310
# This is addressed in Python 3.6+ with using the datetime strptime format of '%G %V %w'
# To be backward compatible with 2.7 the additional work will need to exist.
def iso_year_start(iso_year):
"The gregorian calendar date of the first day of the given ISO year"
fourth_jan = datetime.date(iso_year, 1, 4)
delta = datetime.timedelta(fourth_jan.isoweekday()-1)
return fourth_jan - delta

def iso_to_gregorian(iso_year, iso_week, iso_day):
"Gregorian calendar date for the given ISO year, week and day"
year_start = iso_year_start(iso_year)
return year_start + datetime.timedelta(days=iso_day-1, weeks=iso_week-1)

dt = iso_to_gregorian(battery_year, battery_week_sn_digit, battery_day_sn_digit)
battery_date = dt.strftime("%Y-%m-%d")
# Calculate the date based off the year-week-day with a datetime value in the format YYYY-MM-DD
#battery_date = datetime.datetime.strptime(battery_date_data, "%Y-W%W-%w")

# Convert the date values to binary format
binary_date_day = '{0:05b}'.format(int(battery_date.split("-")[2]))
binary_date_month = '{0:04b}'.format(int(battery_date.split("-")[1]))
binary_date_year = '{0:07b}'.format(int(battery_year) - 1980)
# Combine the binary values into one long string of YYYYYYYMMMMDDDDD
# to match the legacy battery ManufactureDate format
binary_full_date = binary_date_year + binary_date_month + binary_date_day
packed_date = int(binary_full_date, 2)

batteryinfo['ManufactureDate'] = packed_date
if 'Serial' in batteryxml[item]: # Battery serial is sometimes here
batteryinfo['BatterySerialNumber'] = batteryxml[item]
batteryinfo['ManufactureDate'] = process_manufacture_date(batteryxml[item])

if 'LifetimeData' in batteryxml[item]:
if "MaximumChargeCurrent" in batteryxml[item]['LifetimeData']:
batteryinfo['max_charge_current'] = batteryxml[item]['LifetimeData']['MaximumChargeCurrent']
if "MaximumDischargeCurrent" in batteryxml[item]['LifetimeData']:
batteryinfo['max_discharge_current'] = batteryxml[item]['LifetimeData']['MaximumDischargeCurrent']
if "MaximumPackVoltage" in batteryxml[item]['LifetimeData']:
batteryinfo['max_pack_voltage'] = batteryxml[item]['LifetimeData']['MaximumPackVoltage']
if "MinimumPackVoltage" in batteryxml[item]['LifetimeData']:
batteryinfo['min_pack_voltage'] = batteryxml[item]['LifetimeData']['MinimumPackVoltage']
if "MaximumTemperature" in batteryxml[item]['LifetimeData']:
batteryinfo['max_temperature'] = batteryxml[item]['LifetimeData']['MaximumTemperature']
if "MinimumTemperature" in batteryxml[item]['LifetimeData']:
batteryinfo['min_temperature'] = batteryxml[item]['LifetimeData']['MinimumTemperature']

elif item == 'ManufactureDate': # 10.15- has Manufacture Date here
batteryinfo['ManufactureDate'] = batteryxml[item]
elif item == 'Voltage':
Expand All @@ -232,11 +201,15 @@ def get_battery_stats():
batteryinfo['adapter_current'] = format((float(batteryxml[item]['Current'])/1000),'.3f')
if 'Voltage' in batteryxml[item]:
batteryinfo['adapter_voltage'] = format((float(batteryxml[item]['Voltage'])/1000),'.3f')
if 'Description' in batteryxml[item]:
batteryinfo['adapter_description'] = batteryxml[item]['Description']
elif item == 'ChargerData':
if 'ChargingCurrent' in batteryxml[item]:
batteryinfo['charging_current'] = format((float(batteryxml[item]['ChargingCurrent'])/1000),'.3f')
if 'ChargingVoltage' in batteryxml[item]:
batteryinfo['charging_voltage'] = format((float(batteryxml[item]['ChargingVoltage'])/1000),'.3f')
if 'Description' in batteryxml[item]:
batteryinfo['adapter_description'] = batteryxml[item]['Description']
return batteryinfo
except:
return get_battery_profiler()
Expand Down Expand Up @@ -321,11 +294,11 @@ def get_pmset_therm():
output = output.decode().replace("CPU_Scheduler_Limit", "\nCPU_Scheduler_Limit")

for item in output.split("\n"):
if "CPU_Scheduler_Limit = " in item:
if "CPU_Scheduler_Limit" in item:
therminfo['CPUSchedulerLimit'] = re.sub('[^0-9]','', item.strip())
elif " CPU_Available_CPUs = " in item:
elif "CPU_Available_CPUs" in item:
therminfo['CPUAvailableCPUs'] = re.sub('[^0-9]','', item.strip())
elif " CPU_Speed_Limit = " in item:
elif "CPU_Speed_Limit" in item:
therminfo['CPUSpeedLimit'] = re.sub('[^0-9]','', item.strip())
return therminfo

Expand Down Expand Up @@ -362,11 +335,11 @@ def get_pmset_ups():
upsinfo = get_pmset_sched()

for item in output.decode().split("\n"):
if " haltlevel " in item:
if "haltlevel" in item:
upsinfo['haltlevel'] = re.sub('[^0-9]','', item.strip())
elif " haltafter " in item:
elif "haltafter" in item:
upsinfo['haltafter'] = re.sub('[^0-9]','', item.strip())
elif " haltremain " in item:
elif "haltremain" in item:
upsinfo['haltremain'] = re.sub('[^0-9]','', item.strip())
return upsinfo

Expand Down Expand Up @@ -427,17 +400,84 @@ def get_pmset_general():

return powerinfo

def process_manufacture_date(serial):

try:
try:
# The format for battery manufacturing date changed in Big Sur.
# Apple suggested parsing the SerialNumber that contains the manufacture date.
# A SN of XXX1234ZZZZZZZZZZ has the manufacturing date as the values of 1234.
# The first digit is the last digit of the year. 9 would be 2019.
# Note: they reset every decade. So you need to figure out if 9 is 2019 or 2029
battery_serial_number = serial
battery_year_sn_digit = int(battery_serial_number[3])
# The next two digits are the week number of the year
battery_week_sn_digit = int(battery_serial_number[4:6])
# The last digit is the day offset: 1 is Monday 7 is Sunday.
battery_day_sn_digit = int(battery_serial_number[6])
except:
# The serial may also be shifted
battery_serial_number = serial
battery_year_sn_digit = int(battery_serial_number[2])
# The next two digits are the week number of the year
battery_week_sn_digit = int(battery_serial_number[3:5])
# The last digit is the day offset: 1 is Monday 7 is Sunday.
battery_day_sn_digit = int(battery_serial_number[5])

# Determine the decade for the battery year
current_decade = datetime.date.today().year - datetime.date.today().year % 10
battery_year = current_decade + battery_year_sn_digit
if (battery_year, battery_week_sn_digit) > datetime.date.today().isocalendar()[:2]:
battery_year -= 10

# Set the variable of the date to year-Wweek-day:
# For example: 2018-10-20 = 2018-W42-5
battery_date_data = str(battery_year) + '-W' + str(battery_week_sn_digit) + '-' + str(battery_day_sn_digit)

# Python's evaluation of the week number does not respect the ISO week numbers.
# Reference: https://community.dataiku.com/t5/Using-Dataiku-DSS/Converting-week-and-year-to-datetime-stamp-using-Python-function/m-p/11310
# This is addressed in Python 3.6+ with using the datetime strptime format of '%G %V %w'
# To be backward compatible with 2.7 the additional work will need to exist.
def iso_year_start(iso_year):
"The gregorian calendar date of the first day of the given ISO year"
fourth_jan = datetime.date(iso_year, 1, 4)
delta = datetime.timedelta(fourth_jan.isoweekday()-1)
return fourth_jan - delta

def iso_to_gregorian(iso_year, iso_week, iso_day):
"Gregorian calendar date for the given ISO year, week and day"
year_start = iso_year_start(iso_year)
return year_start + datetime.timedelta(days=iso_day-1, weeks=iso_week-1)

dt = iso_to_gregorian(battery_year, battery_week_sn_digit, battery_day_sn_digit)
battery_date = dt.strftime("%Y-%m-%d")
# Calculate the date based off the year-week-day with a datetime value in the format YYYY-MM-DD
#battery_date = datetime.datetime.strptime(battery_date_data, "%Y-W%W-%w")

# Convert the date values to binary format
binary_date_day = '{0:05b}'.format(int(battery_date.split("-")[2]))
binary_date_month = '{0:04b}'.format(int(battery_date.split("-")[1]))
binary_date_year = '{0:07b}'.format(int(battery_year) - 1980)
# Combine the binary values into one long string of YYYYYYYMMMMDDDDD
# to match the legacy battery ManufactureDate format
binary_full_date = binary_date_year + binary_date_month + binary_date_day
packed_date = int(binary_full_date, 2)

return packed_date
except:
return ""

def remove_all(substr, str):
return str.replace(substr, "")

def getDarwinVersion():
"""Returns the Darwin version."""
# Catalina -> 10.15.7 -> 19.6.0 -> 19
# os_version_tuple = platform.mac_ver()[0].split('.')
# return int(os_version_tuple[1])
darwin_version_tuple = platform.release().split('.')
return int(darwin_version_tuple[0])

def main():

"""Main"""
Expand All @@ -457,6 +497,5 @@ def main():
with open(output_plist, 'wb') as fp:
plistlib.dump(info, fp, fmt=plistlib.FMT_XML)


if __name__ == "__main__":
main()

0 comments on commit f64a02f

Please sign in to comment.