1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.server; 18 19 import static android.os.HardwarePropertiesManager.DEVICE_TEMPERATURE_BATTERY; 20 import static android.os.HardwarePropertiesManager.DEVICE_TEMPERATURE_CPU; 21 import static android.os.HardwarePropertiesManager.DEVICE_TEMPERATURE_GPU; 22 import static android.os.HardwarePropertiesManager.DEVICE_TEMPERATURE_SKIN; 23 import static android.os.HardwarePropertiesManager.TEMPERATURE_CURRENT; 24 import static android.os.HardwarePropertiesManager.TEMPERATURE_SHUTDOWN; 25 import static android.os.HardwarePropertiesManager.TEMPERATURE_THROTTLING; 26 import static android.os.HardwarePropertiesManager.TEMPERATURE_THROTTLING_BELOW_VR_MIN; 27 28 import android.Manifest; 29 import android.app.AppOpsManager; 30 import android.app.admin.DevicePolicyManager; 31 import android.content.Context; 32 import android.content.pm.PackageManager; 33 import android.os.Binder; 34 import android.os.CpuUsageInfo; 35 import android.os.IHardwarePropertiesManager; 36 import android.os.UserHandle; 37 38 import com.android.internal.util.DumpUtils; 39 import com.android.server.vr.VrManagerInternal; 40 41 import java.io.FileDescriptor; 42 import java.io.PrintWriter; 43 import java.util.Arrays; 44 45 /** 46 * Service for {@link HardwarePropertiesManager} 47 */ 48 public class HardwarePropertiesManagerService extends IHardwarePropertiesManager.Stub { 49 50 private static final String TAG = "HardwarePropertiesManagerService"; nativeInit()51 private static native void nativeInit(); 52 nativeGetFanSpeeds()53 private static native float[] nativeGetFanSpeeds(); nativeGetDeviceTemperatures(int type, int source)54 private static native float[] nativeGetDeviceTemperatures(int type, int source); nativeGetCpuUsages()55 private static native CpuUsageInfo[] nativeGetCpuUsages(); 56 57 private final Context mContext; 58 private final Object mLock = new Object(); 59 private final AppOpsManager mAppOps; 60 HardwarePropertiesManagerService(Context context)61 public HardwarePropertiesManagerService(Context context) { 62 mContext = context; 63 mAppOps = (AppOpsManager)mContext.getSystemService(Context.APP_OPS_SERVICE); 64 synchronized (mLock) { 65 nativeInit(); 66 } 67 } 68 69 // TODO - Make HardwarePropertiesManager APIs require a userId to verifiy 70 // cross user permission - b/63697518 71 @Override getDeviceTemperatures(String callingPackage, int type, int source)72 public float[] getDeviceTemperatures(String callingPackage, int type, int source) 73 throws SecurityException { 74 enforceHardwarePropertiesRetrievalAllowed(callingPackage); 75 synchronized (mLock) { 76 return nativeGetDeviceTemperatures(type, source); 77 } 78 } 79 80 // TODO - Make HardwarePropertiesManager APIs require a userId to verifiy 81 // cross user permission - b/63697518 82 @Override getCpuUsages(String callingPackage)83 public CpuUsageInfo[] getCpuUsages(String callingPackage) throws SecurityException { 84 enforceHardwarePropertiesRetrievalAllowed(callingPackage); 85 synchronized (mLock) { 86 return nativeGetCpuUsages(); 87 } 88 } 89 90 // TODO - Make HardwarePropertiesManager APIs require a userId to verifiy 91 // cross user permission - b/63697518 92 @Override getFanSpeeds(String callingPackage)93 public float[] getFanSpeeds(String callingPackage) throws SecurityException { 94 enforceHardwarePropertiesRetrievalAllowed(callingPackage); 95 synchronized (mLock) { 96 return nativeGetFanSpeeds(); 97 } 98 } 99 getCallingPackageName()100 private String getCallingPackageName() { 101 final PackageManager pm = mContext.getPackageManager(); 102 final int uid = Binder.getCallingUid(); 103 final String[] packages = pm.getPackagesForUid(uid); 104 if (packages != null && packages.length > 0) { 105 return packages[0]; 106 } 107 final String name = pm.getNameForUid(uid); 108 if (name != null) { 109 return name; 110 } 111 return String.valueOf(uid); 112 } 113 dumpTempValues(String pkg, PrintWriter pw, int type, String typeLabel)114 private void dumpTempValues(String pkg, PrintWriter pw, int type, 115 String typeLabel) { 116 dumpTempValues(pkg, pw, type, typeLabel, "temperatures: ", 117 TEMPERATURE_CURRENT); 118 dumpTempValues(pkg, pw, type, typeLabel, "throttling temperatures: ", 119 TEMPERATURE_THROTTLING); 120 dumpTempValues(pkg, pw, type, typeLabel, "shutdown temperatures: ", 121 TEMPERATURE_SHUTDOWN); 122 dumpTempValues(pkg, pw, type, typeLabel, "vr throttling temperatures: ", 123 TEMPERATURE_THROTTLING_BELOW_VR_MIN); 124 } 125 dumpTempValues(String pkg, PrintWriter pw, int type, String typeLabel, String subLabel, int valueType)126 private void dumpTempValues(String pkg, PrintWriter pw, int type, 127 String typeLabel, String subLabel, int valueType) { 128 pw.println(typeLabel + subLabel + Arrays.toString(getDeviceTemperatures( 129 pkg, type, valueType))); 130 } 131 132 @Override dump(FileDescriptor fd, PrintWriter pw, String[] args)133 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 134 if (!DumpUtils.checkDumpPermission(mContext, TAG, pw)) return; 135 pw.println("****** Dump of HardwarePropertiesManagerService ******"); 136 137 final String PKG = getCallingPackageName(); 138 dumpTempValues(PKG, pw, DEVICE_TEMPERATURE_CPU, "CPU "); 139 dumpTempValues(PKG, pw, DEVICE_TEMPERATURE_GPU, "GPU "); 140 dumpTempValues(PKG, pw, DEVICE_TEMPERATURE_BATTERY, "Battery "); 141 dumpTempValues(PKG, pw, DEVICE_TEMPERATURE_SKIN, "Skin "); 142 143 float[] fanSpeeds = getFanSpeeds(PKG); 144 pw.println("Fan speed: " + Arrays.toString(fanSpeeds) + "\n"); 145 146 CpuUsageInfo[] cpuUsageInfos = getCpuUsages(PKG); 147 int core = 0; 148 for (int i = 0; i < cpuUsageInfos.length; i++) { 149 pw.println("Cpu usage of core: " + i + 150 ", active = " + cpuUsageInfos[i].getActive() + 151 ", total = " + cpuUsageInfos[i].getTotal()); 152 } 153 pw.println("****** End of HardwarePropertiesManagerService dump ******"); 154 } 155 156 /** 157 * Throws SecurityException if the calling package is not allowed to retrieve information 158 * provided by the service. 159 * 160 * @param callingPackage The calling package name. 161 * 162 * @throws SecurityException if something other than the device owner, the current VR service, 163 * or a caller holding the {@link Manifest.permission#DEVICE_POWER} permission tries to 164 * retrieve information provided by this service. 165 */ enforceHardwarePropertiesRetrievalAllowed(String callingPackage)166 private void enforceHardwarePropertiesRetrievalAllowed(String callingPackage) 167 throws SecurityException { 168 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 169 final int userId = UserHandle.getUserId(Binder.getCallingUid()); 170 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 171 final DevicePolicyManager dpm = mContext.getSystemService(DevicePolicyManager.class); 172 if (!dpm.isDeviceOwnerApp(callingPackage) 173 && mContext.checkCallingOrSelfPermission(Manifest.permission.DEVICE_POWER) 174 != PackageManager.PERMISSION_GRANTED 175 && (vrService == null || !vrService.isCurrentVrListener(callingPackage, userId))) { 176 throw new SecurityException("The caller is neither a device owner" 177 + ", nor holding the DEVICE_POWER permission, nor the current VrListener."); 178 } 179 } 180 } 181 182 183