Fix a bunch of repeated reads of a ro.* property

SystemProperties.get() is not particularly fast,
especially if a string is returned. Since ro.* values
are unable to be changed, there's no need to
continously re-query them. Cache the value at
static init time to trivially fix this.

Test: refactoring CL.
Change-Id: Iccb021d3cb2ba3a4a1d0048ddec6811bb7409eec
(cherry picked from commit aa67f684ff)
This commit is contained in:
John Reck
2016-09-20 14:24:21 -07:00
committed by Andreas Gampe
parent b8bbd30203
commit ed065024a5
9 changed files with 117 additions and 21 deletions

View File

@@ -32,6 +32,7 @@ import android.os.IBinder;
import android.os.ParcelFileDescriptor;
import com.android.internal.app.procstats.ProcessStats;
import com.android.internal.os.RoSystemProperties;
import com.android.internal.os.TransferPipe;
import com.android.internal.util.FastPrintWriter;
@@ -895,7 +896,7 @@ public class ActivityManager {
/** @hide */
public static boolean isLowRamDeviceStatic() {
return "true".equals(SystemProperties.get("ro.config.low_ram", "false"));
return RoSystemProperties.CONFIG_LOW_RAM;
}
/**

View File

@@ -18,6 +18,8 @@ package android.net;
import android.os.SystemProperties;
import android.util.Log;
import com.android.internal.os.RoSystemProperties;
import com.android.org.conscrypt.OpenSSLContextImpl;
import com.android.org.conscrypt.OpenSSLSocketImpl;
import com.android.org.conscrypt.SSLClientSessionCache;
@@ -221,8 +223,8 @@ public class SSLCertificateSocketFactory extends SSLSocketFactory {
}
private static boolean isSslCheckRelaxed() {
return "1".equals(SystemProperties.get("ro.debuggable")) &&
"yes".equals(SystemProperties.get("socket.relaxsslcheck"));
return RoSystemProperties.DEBUGGABLE &&
SystemProperties.getBoolean("socket.relaxsslcheck", false);
}
private synchronized SSLSocketFactory getDelegate() {

View File

@@ -16,6 +16,8 @@
package android.os;
import com.android.internal.os.RoSystemProperties;
/**
* Provides support for in-place factory test functions.
*
@@ -36,7 +38,7 @@ public final class FactoryTest {
* or {@link #FACTORY_TEST_HIGH_LEVEL}.
*/
public static int getMode() {
return SystemProperties.getInt("ro.factorytest", FACTORY_TEST_OFF);
return RoSystemProperties.FACTORYTEST;
}
/**

View File

@@ -16,7 +16,13 @@
package android.os;
import android.util.Log;
import android.util.MutableInt;
import com.android.internal.annotations.GuardedBy;
import java.util.ArrayList;
import java.util.HashMap;
/**
@@ -25,13 +31,45 @@ import java.util.ArrayList;
*
* {@hide}
*/
public class SystemProperties
{
public class SystemProperties {
private static final String TAG = "SystemProperties";
private static final boolean TRACK_KEY_ACCESS = false;
public static final int PROP_NAME_MAX = 31;
public static final int PROP_VALUE_MAX = 91;
private static final ArrayList<Runnable> sChangeCallbacks = new ArrayList<Runnable>();
@GuardedBy("sRoReads")
private static final HashMap<String, MutableInt> sRoReads;
static {
if (TRACK_KEY_ACCESS) {
sRoReads = new HashMap<>();
} else {
sRoReads = null;
}
}
private static void onKeyAccess(String key) {
if (!TRACK_KEY_ACCESS) return;
if (key != null && key.startsWith("ro.")) {
synchronized (sRoReads) {
MutableInt numReads = sRoReads.getOrDefault(key, null);
if (numReads == null) {
numReads = new MutableInt(0);
sRoReads.put(key, numReads);
}
numReads.value++;
if (numReads.value > 3) {
Log.d(TAG, "Repeated read (count=" + numReads.value
+ ") of a read-only system property '" + key + "'",
new Exception());
}
}
}
}
private static native String native_get(String key);
private static native String native_get(String key, String def);
private static native int native_get_int(String key, int def);
@@ -50,6 +88,7 @@ public class SystemProperties
if (key.length() > PROP_NAME_MAX) {
throw new IllegalArgumentException("key.length > " + PROP_NAME_MAX);
}
if (TRACK_KEY_ACCESS) onKeyAccess(key);
return native_get(key);
}
@@ -62,6 +101,7 @@ public class SystemProperties
if (key.length() > PROP_NAME_MAX) {
throw new IllegalArgumentException("key.length > " + PROP_NAME_MAX);
}
if (TRACK_KEY_ACCESS) onKeyAccess(key);
return native_get(key, def);
}
@@ -77,6 +117,7 @@ public class SystemProperties
if (key.length() > PROP_NAME_MAX) {
throw new IllegalArgumentException("key.length > " + PROP_NAME_MAX);
}
if (TRACK_KEY_ACCESS) onKeyAccess(key);
return native_get_int(key, def);
}
@@ -92,6 +133,7 @@ public class SystemProperties
if (key.length() > PROP_NAME_MAX) {
throw new IllegalArgumentException("key.length > " + PROP_NAME_MAX);
}
if (TRACK_KEY_ACCESS) onKeyAccess(key);
return native_get_long(key, def);
}
@@ -112,6 +154,7 @@ public class SystemProperties
if (key.length() > PROP_NAME_MAX) {
throw new IllegalArgumentException("key.length > " + PROP_NAME_MAX);
}
if (TRACK_KEY_ACCESS) onKeyAccess(key);
return native_get_boolean(key, def);
}
@@ -128,6 +171,7 @@ public class SystemProperties
throw new IllegalArgumentException("val.length > " +
PROP_VALUE_MAX);
}
if (TRACK_KEY_ACCESS) onKeyAccess(key);
native_set(key, val);
}

View File

@@ -42,6 +42,7 @@ import android.telephony.TelephonyManager;
import android.view.WindowManager.LayoutParams;
import com.android.internal.R;
import com.android.internal.os.RoSystemProperties;
import java.io.IOException;
import java.lang.annotation.Retention;
@@ -761,7 +762,7 @@ public class UserManager {
* a single owner user. see @link {android.os.UserHandle#USER_OWNER}
*/
public static boolean isSplitSystemUser() {
return SystemProperties.getBoolean("ro.fw.system_user_split", false);
return RoSystemProperties.FW_SYSTEM_USER_SPLIT;
}
/**

View File

@@ -44,6 +44,7 @@ import android.util.Pair;
import android.util.Slog;
import android.util.SparseArray;
import com.android.internal.os.RoSystemProperties;
import com.android.internal.os.SomeArgs;
import com.android.internal.util.Preconditions;
@@ -1167,8 +1168,7 @@ public class StorageManager {
* false not encrypted and not encryptable
*/
public static boolean isEncryptable() {
final String state = SystemProperties.get("ro.crypto.state", "unsupported");
return !"unsupported".equalsIgnoreCase(state);
return RoSystemProperties.CRYPTO_ENCRYPTABLE;
}
/** {@hide}
@@ -1177,8 +1177,7 @@ public class StorageManager {
* false not encrypted
*/
public static boolean isEncrypted() {
final String state = SystemProperties.get("ro.crypto.state", "");
return "encrypted".equalsIgnoreCase(state);
return RoSystemProperties.CRYPTO_ENCRYPTED;
}
/** {@hide}
@@ -1190,9 +1189,7 @@ public class StorageManager {
if (!isEncrypted()) {
return false;
}
final String status = SystemProperties.get("ro.crypto.type", "");
return "file".equalsIgnoreCase(status);
return RoSystemProperties.CRYPTO_FILE_ENCRYPTED;
}
/** {@hide}
@@ -1204,8 +1201,7 @@ public class StorageManager {
if (!isEncrypted()) {
return false;
}
final String status = SystemProperties.get("ro.crypto.type", "");
return "block".equalsIgnoreCase(status);
return RoSystemProperties.CRYPTO_BLOCK_ENCRYPTED;
}
/** {@hide}

View File

@@ -0,0 +1,51 @@
/*
* Copyright (C) 2016 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.internal.os;
import android.os.SystemProperties;
/**
* This is a cache of various ro.* properties so that they can be read just once
* at class init time.
*/
public class RoSystemProperties {
public static final boolean DEBUGGABLE =
SystemProperties.getInt("ro.debuggable", 0) == 1;
public static final int FACTORYTEST =
SystemProperties.getInt("ro.factorytest", 0);
// ------ ro.config.* -------- //
public static final boolean CONFIG_LOW_RAM =
SystemProperties.getBoolean("ro.config.low_ram", false);
// ------ ro.fw.* ------------ //
public static final boolean FW_SYSTEM_USER_SPLIT =
SystemProperties.getBoolean("ro.fw.system_user_split", false);
// ------ ro.crypto.* -------- //
public static final String CRYPTO_STATE = SystemProperties.get("ro.crypto.state");
public static final String CRYPTO_TYPE = SystemProperties.get("ro.crypto.type");
// These are pseudo-properties
public static final boolean CRYPTO_ENCRYPTABLE =
!CRYPTO_STATE.isEmpty() && !"unsupported".equals(CRYPTO_STATE);
public static final boolean CRYPTO_ENCRYPTED =
"encrypted".equalsIgnoreCase(CRYPTO_STATE);
public static final boolean CRYPTO_FILE_ENCRYPTED =
"file".equalsIgnoreCase(CRYPTO_TYPE);
public static final boolean CRYPTO_BLOCK_ENCRYPTED =
"block".equalsIgnoreCase(CRYPTO_TYPE);
}

View File

@@ -24,6 +24,7 @@ import static android.system.OsConstants.STDOUT_FILENO;
import android.net.Credentials;
import android.net.LocalSocket;
import android.os.FactoryTest;
import android.os.Process;
import android.os.SELinux;
import android.os.SystemProperties;
@@ -642,13 +643,10 @@ class ZygoteConnection {
throws ZygoteSecurityException {
if (peer.getUid() == Process.SYSTEM_UID) {
String factoryTest = SystemProperties.get("ro.factorytest");
boolean uidRestricted;
/* In normal operation, SYSTEM_UID can only specify a restricted
* set of UIDs. In factory test mode, SYSTEM_UID may specify any uid.
*/
uidRestricted = !(factoryTest.equals("1") || factoryTest.equals("2"));
boolean uidRestricted = FactoryTest.getMode() == FactoryTest.FACTORY_TEST_OFF;
if (uidRestricted && args.uidSpecified && (args.uid < Process.SYSTEM_UID)) {
throw new ZygoteSecurityException(
@@ -678,7 +676,7 @@ class ZygoteConnection {
* @param args non-null; zygote spawner args
*/
public static void applyDebuggerSystemProperty(Arguments args) {
if ("1".equals(SystemProperties.get("ro.debuggable"))) {
if (RoSystemProperties.DEBUGGABLE) {
args.debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER;
}
}

View File

@@ -2542,6 +2542,7 @@ com.android.internal.os.RuntimeInit$1
com.android.internal.os.RuntimeInit$Arguments
com.android.internal.os.RuntimeInit$KillApplicationHandler
com.android.internal.os.RuntimeInit$LoggingHandler
com.android.internal.os.RoSystemProperties
com.android.internal.os.SamplingProfilerIntegration
com.android.internal.os.SomeArgs
com.android.internal.os.Zygote