Don\'t demangle symbol names.
am: fbbc744
* commit 'fbbc744130c85538a754d245e958d7d79f24309c':
Don't demangle symbol names.
diff --git a/adb/usb_linux_client.cpp b/adb/usb_linux_client.cpp
index 18289e2..f3db346 100644
--- a/adb/usb_linux_client.cpp
+++ b/adb/usb_linux_client.cpp
@@ -64,6 +64,14 @@
struct usb_endpoint_descriptor_no_audio sink;
} __attribute__((packed));
+struct ss_func_desc {
+ struct usb_interface_descriptor intf;
+ struct usb_endpoint_descriptor_no_audio source;
+ struct usb_ss_ep_comp_descriptor source_comp;
+ struct usb_endpoint_descriptor_no_audio sink;
+ struct usb_ss_ep_comp_descriptor sink_comp;
+} __attribute__((packed));
+
struct desc_v1 {
struct usb_functionfs_descs_head_v1 {
__le32 magic;
@@ -79,7 +87,9 @@
// The rest of the structure depends on the flags in the header.
__le32 fs_count;
__le32 hs_count;
+ __le32 ss_count;
struct func_desc fs_descs, hs_descs;
+ struct ss_func_desc ss_descs;
} __attribute__((packed));
struct func_desc fs_descriptors = {
@@ -136,6 +146,41 @@
},
};
+static struct ss_func_desc ss_descriptors = {
+ .intf = {
+ .bLength = sizeof(ss_descriptors.intf),
+ .bDescriptorType = USB_DT_INTERFACE,
+ .bInterfaceNumber = 0,
+ .bNumEndpoints = 2,
+ .bInterfaceClass = ADB_CLASS,
+ .bInterfaceSubClass = ADB_SUBCLASS,
+ .bInterfaceProtocol = ADB_PROTOCOL,
+ .iInterface = 1, /* first string from the provided table */
+ },
+ .source = {
+ .bLength = sizeof(ss_descriptors.source),
+ .bDescriptorType = USB_DT_ENDPOINT,
+ .bEndpointAddress = 1 | USB_DIR_OUT,
+ .bmAttributes = USB_ENDPOINT_XFER_BULK,
+ .wMaxPacketSize = MAX_PACKET_SIZE_SS,
+ },
+ .source_comp = {
+ .bLength = sizeof(ss_descriptors.source_comp),
+ .bDescriptorType = USB_DT_SS_ENDPOINT_COMP,
+ },
+ .sink = {
+ .bLength = sizeof(ss_descriptors.sink),
+ .bDescriptorType = USB_DT_ENDPOINT,
+ .bEndpointAddress = 2 | USB_DIR_IN,
+ .bmAttributes = USB_ENDPOINT_XFER_BULK,
+ .wMaxPacketSize = MAX_PACKET_SIZE_SS,
+ },
+ .sink_comp = {
+ .bLength = sizeof(ss_descriptors.sink_comp),
+ .bDescriptorType = USB_DT_SS_ENDPOINT_COMP,
+ },
+};
+
#define STR_INTERFACE_ "ADB Interface"
static const struct {
@@ -279,11 +324,14 @@
v2_descriptor.header.magic = cpu_to_le32(FUNCTIONFS_DESCRIPTORS_MAGIC_V2);
v2_descriptor.header.length = cpu_to_le32(sizeof(v2_descriptor));
- v2_descriptor.header.flags = FUNCTIONFS_HAS_FS_DESC | FUNCTIONFS_HAS_HS_DESC;
+ v2_descriptor.header.flags = FUNCTIONFS_HAS_FS_DESC | FUNCTIONFS_HAS_HS_DESC |
+ FUNCTIONFS_HAS_SS_DESC;
v2_descriptor.fs_count = 3;
v2_descriptor.hs_count = 3;
+ v2_descriptor.ss_count = 5;
v2_descriptor.fs_descs = fs_descriptors;
v2_descriptor.hs_descs = hs_descriptors;
+ v2_descriptor.ss_descs = ss_descriptors;
if (h->control < 0) { // might have already done this before
D("OPENING %s\n", USB_FFS_ADB_EP0);
diff --git a/debuggerd/debuggerd.cpp b/debuggerd/debuggerd.cpp
index b84a4e5..9c8a41e 100644
--- a/debuggerd/debuggerd.cpp
+++ b/debuggerd/debuggerd.cpp
@@ -538,7 +538,7 @@
return 1;
fcntl(s, F_SETFD, FD_CLOEXEC);
- ALOGI("debuggerd: " __DATE__ " " __TIME__ "\n");
+ ALOGI("debuggerd: starting\n");
for (;;) {
sockaddr addr;
diff --git a/fastboot/fastboot.cpp b/fastboot/fastboot.cpp
index be80cce..de4c0ea 100644
--- a/fastboot/fastboot.cpp
+++ b/fastboot/fastboot.cpp
@@ -279,17 +279,22 @@
" flashall flash boot, system, vendor and if found,\n"
" recovery\n"
" flash <partition> [ <filename> ] write a file to a flash partition\n"
- " flashing lock locks the device. Prevents flashing"
+ " flashing lock locks the device. Prevents flashing\n"
" partitions\n"
- " flashing unlock unlocks the device. Allows user to"
- " flash any partition except the ones"
+ " flashing unlock unlocks the device. Allows user to\n"
+ " flash any partition except the ones\n"
" that are related to bootloader\n"
- " flashing lock_critical Prevents flashing bootloader related"
+ " flashing lock_critical Prevents flashing bootloader related\n"
" partitions\n"
- " flashing unlock_critical Enables flashing bootloader related"
+ " flashing unlock_critical Enables flashing bootloader related\n"
" partitions\n"
- " flashing get_unlock_ability Queries bootloader to see if the"
+ " flashing get_unlock_ability Queries bootloader to see if the\n"
" device is unlocked\n"
+ " flashing get_unlock_bootloader_nonce Queries the bootloader to get the\n"
+ " unlock nonce\n"
+ " flashing unlock_bootloader <request> Issue unlock bootloader using request\n"
+ " flashing lock_bootloader Locks the bootloader to prevent\n"
+ " bootloader version rollback\n"
" erase <partition> erase a flash partition\n"
" format[:[<fs type>][:[<size>]] <partition> format a flash partition.\n"
" Can override the fs type and/or\n"
@@ -831,6 +836,27 @@
#define skip(n) do { argc -= (n); argv += (n); } while (0)
#define require(n) do { if (argc < (n)) {usage(); exit(1);}} while (0)
+int do_bypass_unlock_command(int argc, char **argv)
+{
+ unsigned sz;
+ void *data;
+
+ if (argc <= 2) return 0;
+ skip(2);
+
+ /*
+ * Process unlock_bootloader, we have to load the message file
+ * and send that to the remote device.
+ */
+ require(1);
+ data = load_file(*argv, &sz);
+ if (data == 0) die("could not load '%s': %s", *argv, strerror(errno));
+ fb_queue_download("unlock_message", data, sz);
+ fb_queue_command("flashing unlock_bootloader", "unlocking bootloader");
+ skip(1);
+ return 0;
+}
+
int do_oem_command(int argc, char **argv)
{
char command[256];
@@ -1230,12 +1256,18 @@
wants_reboot = 1;
} else if(!strcmp(*argv, "oem")) {
argc = do_oem_command(argc, argv);
- } else if(!strcmp(*argv, "flashing") && argc == 2) {
- if(!strcmp(*(argv+1), "unlock") || !strcmp(*(argv+1), "lock")
- || !strcmp(*(argv+1), "unlock_critical")
- || !strcmp(*(argv+1), "lock_critical")
- || !strcmp(*(argv+1), "get_unlock_ability")) {
- argc = do_oem_command(argc, argv);
+ } else if(!strcmp(*argv, "flashing")) {
+ if (argc == 2 && (!strcmp(*(argv+1), "unlock") ||
+ !strcmp(*(argv+1), "lock") ||
+ !strcmp(*(argv+1), "unlock_critical") ||
+ !strcmp(*(argv+1), "lock_critical") ||
+ !strcmp(*(argv+1), "get_unlock_ability") ||
+ !strcmp(*(argv+1), "get_unlock_bootloader_nonce") ||
+ !strcmp(*(argv+1), "lock_bootloader"))) {
+ argc = do_oem_command(argc, argv);
+ } else
+ if (argc == 3 && !strcmp(*(argv+1), "unlock_bootloader")) {
+ argc = do_bypass_unlock_command(argc, argv);
} else {
usage();
return 1;
diff --git a/fs_mgr/fs_mgr_verity.c b/fs_mgr/fs_mgr_verity.c
index 2d1abbe..a9e3358 100644
--- a/fs_mgr/fs_mgr_verity.c
+++ b/fs_mgr/fs_mgr_verity.c
@@ -47,6 +47,8 @@
#define VERITY_METADATA_SIZE 32768
#define VERITY_TABLE_RSA_KEY "/verity_key"
+#define VERITY_TABLE_HASH_IDX 8
+#define VERITY_TABLE_SALT_IDX 9
#define METADATA_MAGIC 0x01564c54
#define METADATA_TAG_MAX_LENGTH 63
@@ -141,6 +143,33 @@
return retval;
}
+static int invalidate_table(char *table, int table_length)
+{
+ int n = 0;
+ int idx = 0;
+ int cleared = 0;
+
+ while (n < table_length) {
+ if (table[n++] == ' ') {
+ ++idx;
+ }
+
+ if (idx != VERITY_TABLE_HASH_IDX && idx != VERITY_TABLE_SALT_IDX) {
+ continue;
+ }
+
+ while (n < table_length && table[n] != ' ') {
+ table[n++] = '0';
+ }
+
+ if (++cleared == 2) {
+ return 0;
+ }
+ }
+
+ return -1;
+}
+
static int squashfs_get_target_device_size(char *blk_device, uint64_t *device_size)
{
struct squashfs_info sq_info;
@@ -859,6 +888,7 @@
int fs_mgr_update_verity_state(fs_mgr_verity_state_callback callback)
{
_Alignas(struct dm_ioctl) char buffer[DM_BUF_SIZE];
+ bool use_state = true;
char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
char *mount_point;
char propbuf[PROPERTY_VALUE_MAX];
@@ -875,7 +905,10 @@
property_get("ro.boot.veritymode", propbuf, "");
if (*propbuf != '\0') {
- return 0; /* state is kept by the bootloader */
+ if (fs_mgr_load_verity_state(&mode) == -1) {
+ return -1;
+ }
+ use_state = false; /* state is kept by the bootloader */
}
fd = TEMP_FAILURE_RETRY(open("/dev/device-mapper", O_RDWR | O_CLOEXEC));
@@ -900,9 +933,11 @@
continue;
}
- if (get_verity_state_offset(&fstab->recs[i], &offset) < 0 ||
- read_verity_state(fstab->recs[i].verity_loc, offset, &mode) < 0) {
- continue;
+ if (use_state) {
+ if (get_verity_state_offset(&fstab->recs[i], &offset) < 0 ||
+ read_verity_state(fstab->recs[i].verity_loc, offset, &mode) < 0) {
+ continue;
+ }
}
mount_point = basename(fstab->recs[i].mount_point);
@@ -916,7 +951,7 @@
status = &buffer[io->data_start + sizeof(struct dm_target_spec)];
- if (*status == 'C') {
+ if (use_state && *status == 'C') {
if (write_verity_state(fstab->recs[i].verity_loc, offset,
VERITY_MODE_LOGGING) < 0) {
continue;
@@ -951,6 +986,7 @@
char *verity_blk_name = 0;
char *verity_table = 0;
char *verity_table_signature = 0;
+ int verity_table_length = 0;
uint64_t device_size = 0;
_Alignas(struct dm_ioctl) char buffer[DM_BUF_SIZE];
@@ -977,6 +1013,7 @@
}
retval = FS_MGR_SETUP_VERITY_FAIL;
+ verity_table_length = strlen(verity_table);
// get the device mapper fd
if ((fd = open("/dev/device-mapper", O_RDWR)) < 0) {
@@ -996,13 +1033,6 @@
goto out;
}
- // verify the signature on the table
- if (verify_table(verity_table_signature,
- verity_table,
- strlen(verity_table)) < 0) {
- goto out;
- }
-
if (load_verity_state(fstab, &mode) < 0) {
/* if accessing or updating the state failed, switch to the default
* safe mode. This makes sure the device won't end up in an endless
@@ -1011,6 +1041,22 @@
mode = VERITY_MODE_EIO;
}
+ // verify the signature on the table
+ if (verify_table(verity_table_signature,
+ verity_table,
+ verity_table_length) < 0) {
+ if (mode == VERITY_MODE_LOGGING) {
+ // the user has been warned, allow mounting without dm-verity
+ retval = FS_MGR_SETUP_VERITY_SUCCESS;
+ goto out;
+ }
+
+ // invalidate root hash and salt to trigger device-specific recovery
+ if (invalidate_table(verity_table, verity_table_length) < 0) {
+ goto out;
+ }
+ }
+
INFO("Enabling dm-verity for %s (mode %d)\n", mount_point, mode);
// load the verity mapping table
diff --git a/healthd/BatteryMonitor.cpp b/healthd/BatteryMonitor.cpp
index 7ea8250..396dfef 100644
--- a/healthd/BatteryMonitor.cpp
+++ b/healthd/BatteryMonitor.cpp
@@ -24,11 +24,13 @@
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
+#include <sys/types.h>
#include <unistd.h>
+
#include <batteryservice/BatteryService.h>
#include <cutils/klog.h>
#include <cutils/properties.h>
-#include <sys/types.h>
+#include <log/log_read.h>
#include <utils/Errors.h>
#include <utils/String8.h>
#include <utils/Vector.h>
@@ -37,6 +39,7 @@
#define POWER_SUPPLY_SYSFS_PATH "/sys/class/" POWER_SUPPLY_SUBSYSTEM
#define FAKE_BATTERY_CAPACITY 42
#define FAKE_BATTERY_TEMPERATURE 424
+#define ALWAYS_PLUGGED_CAPACITY 100
namespace android {
@@ -181,6 +184,7 @@
props.chargerWirelessOnline = false;
props.batteryStatus = BATTERY_STATUS_UNKNOWN;
props.batteryHealth = BATTERY_HEALTH_UNKNOWN;
+ props.maxChargingCurrent = 0;
if (!mHealthdConfig->batteryPresentPath.isEmpty())
props.batteryPresent = getBooleanField(mHealthdConfig->batteryPresentPath);
@@ -196,6 +200,15 @@
mBatteryFixedTemperature :
getIntField(mHealthdConfig->batteryTemperaturePath);
+ // For devices which do not have battery and are always plugged
+ // into power souce.
+ if (mAlwaysPluggedDevice) {
+ props.chargerAcOnline = true;
+ props.batteryPresent = true;
+ props.batteryStatus = BATTERY_STATUS_CHARGING;
+ props.batteryHealth = BATTERY_HEALTH_GOOD;
+ }
+
const int SIZE = 128;
char buf[SIZE];
String8 btech;
@@ -235,6 +248,15 @@
KLOG_WARNING(LOG_TAG, "%s: Unknown power supply type\n",
mChargerNames[i].string());
}
+ path.clear();
+ path.appendFormat("%s/%s/current_max", POWER_SUPPLY_SYSFS_PATH,
+ mChargerNames[i].string());
+ if (access(path.string(), R_OK) == 0) {
+ int maxChargingCurrent = getIntField(path);
+ if (props.maxChargingCurrent < maxChargingCurrent) {
+ props.maxChargingCurrent = maxChargingCurrent;
+ }
+ }
}
}
}
@@ -265,10 +287,32 @@
"battery none");
}
- KLOG_WARNING(LOG_TAG, "%s chg=%s%s%s\n", dmesgline,
- props.chargerAcOnline ? "a" : "",
- props.chargerUsbOnline ? "u" : "",
- props.chargerWirelessOnline ? "w" : "");
+ size_t len = strlen(dmesgline);
+ snprintf(dmesgline + len, sizeof(dmesgline) - len, " chg=%s%s%s",
+ props.chargerAcOnline ? "a" : "",
+ props.chargerUsbOnline ? "u" : "",
+ props.chargerWirelessOnline ? "w" : "");
+
+ log_time realtime(CLOCK_REALTIME);
+ time_t t = realtime.tv_sec;
+ struct tm *tmp = gmtime(&t);
+ if (tmp) {
+ static const char fmt[] = " %Y-%m-%d %H:%M:%S.XXXXXXXXX UTC";
+ len = strlen(dmesgline);
+ if ((len < (sizeof(dmesgline) - sizeof(fmt) - 8)) // margin
+ && strftime(dmesgline + len, sizeof(dmesgline) - len,
+ fmt, tmp)) {
+ char *usec = strchr(dmesgline + len, 'X');
+ if (usec) {
+ len = usec - dmesgline;
+ snprintf(dmesgline + len, sizeof(dmesgline) - len,
+ "%09u", realtime.tv_nsec);
+ usec[9] = ' ';
+ }
+ }
+ }
+
+ KLOG_WARNING(LOG_TAG, "%s\n", dmesgline);
}
healthd_mode_ops->battery_update(&props);
@@ -341,9 +385,9 @@
int v;
char vs[128];
- snprintf(vs, sizeof(vs), "ac: %d usb: %d wireless: %d\n",
+ snprintf(vs, sizeof(vs), "ac: %d usb: %d wireless: %d current_max: %d\n",
props.chargerAcOnline, props.chargerUsbOnline,
- props.chargerWirelessOnline);
+ props.chargerWirelessOnline, props.maxChargingCurrent);
write(fd, vs, strlen(vs));
snprintf(vs, sizeof(vs), "status: %d health: %d present: %d\n",
props.batteryStatus, props.batteryHealth, props.batteryPresent);
@@ -508,8 +552,15 @@
closedir(dir);
}
- if (!mChargerNames.size())
+ // This indicates that there is no charger driver registered.
+ // Typically the case for devices which do not have a battery and
+ // and are always plugged into AC mains.
+ if (!mChargerNames.size()) {
KLOG_ERROR(LOG_TAG, "No charger supplies found\n");
+ mBatteryFixedCapacity = ALWAYS_PLUGGED_CAPACITY;
+ mBatteryFixedTemperature = FAKE_BATTERY_TEMPERATURE;
+ mAlwaysPluggedDevice = true;
+ }
if (!mBatteryDevicePresent) {
KLOG_WARNING(LOG_TAG, "No battery devices found\n");
hc->periodic_chores_interval_fast = -1;
diff --git a/healthd/BatteryMonitor.h b/healthd/BatteryMonitor.h
index 3425f27..a61171f 100644
--- a/healthd/BatteryMonitor.h
+++ b/healthd/BatteryMonitor.h
@@ -46,6 +46,7 @@
struct healthd_config *mHealthdConfig;
Vector<String8> mChargerNames;
bool mBatteryDevicePresent;
+ bool mAlwaysPluggedDevice;
int mBatteryFixedCapacity;
int mBatteryFixedTemperature;
struct BatteryProperties props;
diff --git a/init/bootchart.cpp b/init/bootchart.cpp
index 95687cb..df8359d 100644
--- a/init/bootchart.cpp
+++ b/init/bootchart.cpp
@@ -89,7 +89,7 @@
if (out == NULL) {
return;
}
- fprintf(out, "version = Android init 0.8 " __TIME__ "\n");
+ fprintf(out, "version = Android init 0.8\n");
fprintf(out, "title = Boot chart for Android (%s)\n", date);
fprintf(out, "system.uname = %s %s %s %s\n", uts.sysname, uts.release, uts.version, uts.machine);
fprintf(out, "system.release = %s\n", fingerprint);
diff --git a/init/builtins.cpp b/init/builtins.cpp
index 9e5f9ff..8eb5b5b 100644
--- a/init/builtins.cpp
+++ b/init/builtins.cpp
@@ -803,9 +803,9 @@
return -1;
}
-int do_load_all_props(int nargs, char **args) {
+int do_load_system_props(int nargs, char **args) {
if (nargs == 1) {
- load_all_props();
+ load_system_props();
return 0;
}
return -1;
@@ -833,18 +833,31 @@
return 0;
}
+static bool is_file_crypto() {
+ char prop_value[PROP_VALUE_MAX] = {0};
+ property_get("ro.crypto.type", prop_value);
+ return strcmp(prop_value, "file") == 0;
+}
+
int do_installkey(int nargs, char **args)
{
if (nargs != 2) {
return -1;
}
-
- char prop_value[PROP_VALUE_MAX] = {0};
- property_get("ro.crypto.type", prop_value);
- if (strcmp(prop_value, "file")) {
+ if (!is_file_crypto()) {
return 0;
}
-
return e4crypt_create_device_key(args[1],
do_installkeys_ensure_dir_exists);
}
+
+int do_setusercryptopolicies(int nargs, char **args)
+{
+ if (nargs != 2) {
+ return -1;
+ }
+ if (!is_file_crypto()) {
+ return 0;
+ }
+ return e4crypt_set_user_crypto_policies(args[1]);
+}
diff --git a/init/init_parser.cpp b/init/init_parser.cpp
index 666a86e..9bab67d 100644
--- a/init/init_parser.cpp
+++ b/init/init_parser.cpp
@@ -159,7 +159,7 @@
case 'l':
if (!strcmp(s, "oglevel")) return K_loglevel;
if (!strcmp(s, "oad_persist_props")) return K_load_persist_props;
- if (!strcmp(s, "oad_all_props")) return K_load_all_props;
+ if (!strcmp(s, "oad_system_props")) return K_load_system_props;
break;
case 'm':
if (!strcmp(s, "kdir")) return K_mkdir;
@@ -187,6 +187,7 @@
if (!strcmp(s, "etenv")) return K_setenv;
if (!strcmp(s, "etprop")) return K_setprop;
if (!strcmp(s, "etrlimit")) return K_setrlimit;
+ if (!strcmp(s, "etusercryptopolicies")) return K_setusercryptopolicies;
if (!strcmp(s, "ocket")) return K_socket;
if (!strcmp(s, "tart")) return K_start;
if (!strcmp(s, "top")) return K_stop;
@@ -571,7 +572,7 @@
list_for_each(node, &action_list) {
act = node_to_item(node, struct action, alist);
- match = !name;
+ match = !name;
list_for_each(node2, &act->triggers) {
cur_trigger = node_to_item(node2, struct trigger, nlist);
if (!strncmp(cur_trigger->name, "property:", strlen("property:"))) {
@@ -585,29 +586,28 @@
match = true;
continue;
}
- } else {
- const char* equals = strchr(test, '=');
- if (equals) {
- char prop_name[PROP_NAME_MAX + 1];
- char value[PROP_VALUE_MAX];
- int length = equals - test;
- if (length <= PROP_NAME_MAX) {
- int ret;
- memcpy(prop_name, test, length);
- prop_name[length] = 0;
+ }
+ const char* equals = strchr(test, '=');
+ if (equals) {
+ char prop_name[PROP_NAME_MAX + 1];
+ char value[PROP_VALUE_MAX];
+ int length = equals - test;
+ if (length <= PROP_NAME_MAX) {
+ int ret;
+ memcpy(prop_name, test, length);
+ prop_name[length] = 0;
- /* does the property exist, and match the trigger value? */
- ret = property_get(prop_name, value);
- if (ret > 0 && (!strcmp(equals + 1, value) ||
- !strcmp(equals + 1, "*"))) {
- continue;
- }
- }
- }
- }
- }
- match = false;
- break;
+ /* does the property exist, and match the trigger value? */
+ ret = property_get(prop_name, value);
+ if (ret > 0 && (!strcmp(equals + 1, value) ||
+ !strcmp(equals + 1, "*"))) {
+ continue;
+ }
+ }
+ }
+ }
+ match = false;
+ break;
}
if (match) {
action_add_queue_tail(act);
diff --git a/init/keywords.h b/init/keywords.h
index e637d7d..0910f60 100644
--- a/init/keywords.h
+++ b/init/keywords.h
@@ -22,6 +22,7 @@
int do_rmdir(int nargs, char **args);
int do_setprop(int nargs, char **args);
int do_setrlimit(int nargs, char **args);
+int do_setusercryptopolicies(int nargs, char **args);
int do_start(int nargs, char **args);
int do_stop(int nargs, char **args);
int do_swapon_all(int nargs, char **args);
@@ -34,7 +35,7 @@
int do_chmod(int nargs, char **args);
int do_loglevel(int nargs, char **args);
int do_load_persist_props(int nargs, char **args);
-int do_load_all_props(int nargs, char **args);
+int do_load_system_props(int nargs, char **args);
int do_verity_load_state(int nargs, char **args);
int do_verity_update_state(int nargs, char **args);
int do_wait(int nargs, char **args);
@@ -66,7 +67,7 @@
KEYWORD(installkey, COMMAND, 1, do_installkey)
KEYWORD(ioprio, OPTION, 0, 0)
KEYWORD(keycodes, OPTION, 0, 0)
- KEYWORD(load_all_props, COMMAND, 0, do_load_all_props)
+ KEYWORD(load_system_props, COMMAND, 0, do_load_system_props)
KEYWORD(load_persist_props, COMMAND, 0, do_load_persist_props)
KEYWORD(loglevel, COMMAND, 1, do_loglevel)
KEYWORD(mkdir, COMMAND, 1, do_mkdir)
@@ -86,6 +87,7 @@
KEYWORD(setenv, OPTION, 2, 0)
KEYWORD(setprop, COMMAND, 2, do_setprop)
KEYWORD(setrlimit, COMMAND, 3, do_setrlimit)
+ KEYWORD(setusercryptopolicies, COMMAND, 1, do_setusercryptopolicies)
KEYWORD(socket, OPTION, 0, 0)
KEYWORD(start, COMMAND, 1, do_start)
KEYWORD(stop, COMMAND, 1, do_stop)
diff --git a/init/property_service.cpp b/init/property_service.cpp
index c2881ae..52f6b98 100644
--- a/init/property_service.cpp
+++ b/init/property_service.cpp
@@ -560,16 +560,10 @@
close(fd);
}
-void load_all_props() {
+void load_system_props() {
load_properties_from_file(PROP_PATH_SYSTEM_BUILD, NULL);
load_properties_from_file(PROP_PATH_VENDOR_BUILD, NULL);
load_properties_from_file(PROP_PATH_FACTORY, "ro.*");
-
- load_override_properties();
-
- /* Read persistent properties after all default values have been loaded. */
- load_persistent_properties();
-
load_recovery_id_prop();
}
diff --git a/init/property_service.h b/init/property_service.h
index a27053d..303f251 100644
--- a/init/property_service.h
+++ b/init/property_service.h
@@ -23,7 +23,7 @@
extern void property_init(void);
extern void property_load_boot_defaults(void);
extern void load_persist_props(void);
-extern void load_all_props(void);
+extern void load_system_props(void);
extern void start_property_service(void);
void get_property_workspace(int *fd, int *sz);
extern int __property_get(const char *name, char *value);
diff --git a/libbacktrace/BacktraceCurrent.cpp b/libbacktrace/BacktraceCurrent.cpp
index 2714d93..d339550 100644
--- a/libbacktrace/BacktraceCurrent.cpp
+++ b/libbacktrace/BacktraceCurrent.cpp
@@ -93,6 +93,10 @@
static pthread_mutex_t g_sigaction_mutex = PTHREAD_MUTEX_INITIALIZER;
+static void SignalLogOnly(int, siginfo_t*, void*) {
+ BACK_LOGE("pid %d, tid %d: Received a spurious signal %d\n", getpid(), gettid(), THREAD_SIGNAL);
+}
+
static void SignalHandler(int, siginfo_t*, void* sigcontext) {
ThreadEntry* entry = ThreadEntry::Get(getpid(), gettid(), false);
if (!entry) {
@@ -151,9 +155,21 @@
// that we are waiting for the first Wake() call made by the thread.
bool wait_completed = entry->Wait(1);
+ if (!wait_completed && oldact.sa_sigaction == nullptr) {
+ // If the wait failed, it could be that the signal could not be delivered
+ // within the timeout. Add a signal handler that's simply going to log
+ // something so that we don't crash if the signal eventually gets
+ // delivered. Only do this if there isn't already an action set up.
+ memset(&act, 0, sizeof(act));
+ act.sa_sigaction = SignalLogOnly;
+ act.sa_flags = SA_RESTART | SA_SIGINFO | SA_ONSTACK;
+ sigemptyset(&act.sa_mask);
+ sigaction(THREAD_SIGNAL, &act, nullptr);
+ } else {
+ sigaction(THREAD_SIGNAL, &oldact, nullptr);
+ }
// After the thread has received the signal, allow other unwinders to
// continue.
- sigaction(THREAD_SIGNAL, &oldact, nullptr);
pthread_mutex_unlock(&g_sigaction_mutex);
bool unwind_done = false;
diff --git a/logd/FlushCommand.cpp b/logd/FlushCommand.cpp
index d584925..823a842 100644
--- a/logd/FlushCommand.cpp
+++ b/logd/FlushCommand.cpp
@@ -72,7 +72,7 @@
return;
}
entry = new LogTimeEntry(mReader, client, mNonBlock, mTail, mLogMask, mPid, mStart);
- times.push_back(entry);
+ times.push_front(entry);
}
client->incRef();
diff --git a/logd/LogBuffer.cpp b/logd/LogBuffer.cpp
index 0f5071b..d72a78c 100644
--- a/logd/LogBuffer.cpp
+++ b/logd/LogBuffer.cpp
@@ -217,29 +217,42 @@
return len;
}
-// If we're using more than 256K of memory for log entries, prune
-// at least 10% of the log entries.
+// Prune at most 10% of the log entries or 256, whichever is less.
//
// mLogElementsLock must be held when this function is called.
void LogBuffer::maybePrune(log_id_t id) {
size_t sizes = stats.sizes(id);
- if (sizes > log_buffer_size(id)) {
- size_t sizeOver90Percent = sizes - ((log_buffer_size(id) * 9) / 10);
+ unsigned long maxSize = log_buffer_size(id);
+ if (sizes > maxSize) {
+ size_t sizeOver = sizes - ((maxSize * 9) / 10);
size_t elements = stats.elements(id);
- unsigned long pruneRows = elements * sizeOver90Percent / sizes;
- elements /= 10;
- if (pruneRows <= elements) {
- pruneRows = elements;
+ size_t minElements = elements / 10;
+ unsigned long pruneRows = elements * sizeOver / sizes;
+ if (pruneRows <= minElements) {
+ pruneRows = minElements;
+ }
+ if (pruneRows > 256) {
+ pruneRows = 256;
}
prune(id, pruneRows);
}
}
-LogBufferElementCollection::iterator LogBuffer::erase(LogBufferElementCollection::iterator it) {
+LogBufferElementCollection::iterator LogBuffer::erase(
+ LogBufferElementCollection::iterator it, bool engageStats) {
LogBufferElement *e = *it;
+ log_id_t id = e->getLogId();
+ LogBufferIteratorMap::iterator f = mLastWorstUid[id].find(e->getUid());
+ if ((f != mLastWorstUid[id].end()) && (it == f->second)) {
+ mLastWorstUid[id].erase(f);
+ }
it = mLogElements.erase(it);
- stats.subtract(e);
+ if (engageStats) {
+ stats.subtract(e);
+ } else {
+ stats.erase(e);
+ }
delete e;
return it;
@@ -316,7 +329,51 @@
// prune "pruneRows" of type "id" from the buffer.
//
+// This garbage collection task is used to expire log entries. It is called to
+// remove all logs (clear), all UID logs (unprivileged clear), or every
+// 256 or 10% of the total logs (whichever is less) to prune the logs.
+//
+// First there is a prep phase where we discover the reader region lock that
+// acts as a backstop to any pruning activity to stop there and go no further.
+//
+// There are three major pruning loops that follow. All expire from the oldest
+// entries. Since there are multiple log buffers, the Android logging facility
+// will appear to drop entries 'in the middle' when looking at multiple log
+// sources and buffers. This effect is slightly more prominent when we prune
+// the worst offender by logging source. Thus the logs slowly loose content
+// and value as you move back in time. This is preferred since chatty sources
+// invariably move the logs value down faster as less chatty sources would be
+// expired in the noise.
+//
+// The first loop performs blacklisting and worst offender pruning. Falling
+// through when there are no notable worst offenders and have not hit the
+// region lock preventing further worst offender pruning. This loop also looks
+// after managing the chatty log entries and merging to help provide
+// statistical basis for blame. The chatty entries are not a notification of
+// how much logs you may have, but instead represent how much logs you would
+// have had in a virtual log buffer that is extended to cover all the in-memory
+// logs without loss. They last much longer than the represented pruned logs
+// since they get multiplied by the gains in the non-chatty log sources.
+//
+// The second loop get complicated because an algorithm of watermarks and
+// history is maintained to reduce the order and keep processing time
+// down to a minimum at scale. These algorithms can be costly in the face
+// of larger log buffers, or severly limited processing time granted to a
+// background task at lowest priority.
+//
+// This second loop does straight-up expiration from the end of the logs
+// (again, remember for the specified log buffer id) but does some whitelist
+// preservation. Thus whitelist is a Hail Mary low priority, blacklists and
+// spam filtration all take priority. This second loop also checks if a region
+// lock is causing us to buffer too much in the logs to help the reader(s),
+// and will tell the slowest reader thread to skip log entries, and if
+// persistent and hits a further threshold, kill the reader thread.
+//
+// The third thread is optional, and only gets hit if there was a whitelist
+// and more needs to be pruned against the backstop of the region lock.
+//
// mLogElementsLock must be held when this function is called.
+//
void LogBuffer::prune(log_id_t id, unsigned long pruneRows, uid_t caller_uid) {
LogTimeEntry *oldest = NULL;
@@ -378,7 +435,10 @@
worst_sizes = sorted[0]->getSizes();
// Calculate threshold as 12.5% of available storage
size_t threshold = log_buffer_size(id) / 8;
- if (worst_sizes > threshold) {
+ if ((worst_sizes > threshold)
+ // Allow time horizon to extend roughly tenfold, assume
+ // average entry length is 100 characters.
+ && (worst_sizes > (10 * sorted[0]->getDropped()))) {
worst = sorted[0]->getKey();
second_worst_sizes = sorted[1]->getSizes();
if (second_worst_sizes < threshold) {
@@ -396,8 +456,28 @@
bool kick = false;
bool leading = true;
+ it = mLogElements.begin();
+ // Perform at least one mandatory garbage collection cycle in following
+ // - clear leading chatty tags
+ // - merge chatty tags
+ // - check age-out of preserved logs
+ bool gc = pruneRows <= 1;
+ if (!gc && (worst != (uid_t) -1)) {
+ LogBufferIteratorMap::iterator f = mLastWorstUid[id].find(worst);
+ if ((f != mLastWorstUid[id].end())
+ && (f->second != mLogElements.end())) {
+ leading = false;
+ it = f->second;
+ }
+ }
+ static const timespec too_old = {
+ EXPIRE_HOUR_THRESHOLD * 60 * 60, 0
+ };
+ LogBufferElementCollection::iterator lastt;
+ lastt = mLogElements.end();
+ --lastt;
LogBufferElementLast last;
- for(it = mLogElements.begin(); it != mLogElements.end();) {
+ while (it != mLogElements.end()) {
LogBufferElement *e = *it;
if (oldest && (oldest->mStart <= e->getSequence())) {
@@ -419,9 +499,7 @@
// merge any drops
if (dropped && last.merge(e, dropped)) {
- it = mLogElements.erase(it);
- stats.erase(e);
- delete e;
+ it = erase(it, false);
continue;
}
@@ -447,25 +525,24 @@
continue;
}
+ if ((e->getRealTime() < ((*lastt)->getRealTime() - too_old))
+ || (e->getRealTime() > (*lastt)->getRealTime())) {
+ break;
+ }
+
+ // unmerged drop message
if (dropped) {
last.add(e);
+ if ((!gc && (e->getUid() == worst))
+ || (mLastWorstUid[id].find(e->getUid())
+ == mLastWorstUid[id].end())) {
+ mLastWorstUid[id][e->getUid()] = it;
+ }
++it;
continue;
}
if (e->getUid() != worst) {
- if (leading) {
- static const timespec too_old = {
- EXPIRE_HOUR_THRESHOLD * 60 * 60, 0
- };
- LogBufferElementCollection::iterator last;
- last = mLogElements.end();
- --last;
- if ((e->getRealTime() < ((*last)->getRealTime() - too_old))
- || (e->getRealTime() > (*last)->getRealTime())) {
- break;
- }
- }
leading = false;
last.clear(e);
++it;
@@ -488,11 +565,13 @@
stats.drop(e);
e->setDropped(1);
if (last.merge(e, 1)) {
- it = mLogElements.erase(it);
- stats.erase(e);
- delete e;
+ it = erase(it, false);
} else {
last.add(e);
+ if (!gc || (mLastWorstUid[id].find(worst)
+ == mLastWorstUid[id].end())) {
+ mLastWorstUid[id][worst] = it;
+ }
++it;
}
}
diff --git a/logd/LogBuffer.h b/logd/LogBuffer.h
index a13fded..4769a6c 100644
--- a/logd/LogBuffer.h
+++ b/logd/LogBuffer.h
@@ -19,9 +19,10 @@
#include <sys/types.h>
+#include <list>
+
#include <log/log.h>
#include <sysutils/SocketClient.h>
-#include <utils/List.h>
#include <private/android_filesystem_config.h>
@@ -30,7 +31,7 @@
#include "LogStatistics.h"
#include "LogWhiteBlackList.h"
-typedef android::List<LogBufferElement *> LogBufferElementCollection;
+typedef std::list<LogBufferElement *> LogBufferElementCollection;
class LogBuffer {
LogBufferElementCollection mLogElements;
@@ -39,6 +40,11 @@
LogStatistics stats;
PruneList mPrune;
+ // watermark of any worst/chatty uid processing
+ typedef std::unordered_map<uid_t,
+ LogBufferElementCollection::iterator>
+ LogBufferIteratorMap;
+ LogBufferIteratorMap mLastWorstUid[LOG_ID_MAX];
unsigned long mMaxSize[LOG_ID_MAX];
@@ -81,7 +87,8 @@
private:
void maybePrune(log_id_t id);
void prune(log_id_t id, unsigned long pruneRows, uid_t uid = AID_ROOT);
- LogBufferElementCollection::iterator erase(LogBufferElementCollection::iterator it);
+ LogBufferElementCollection::iterator erase(
+ LogBufferElementCollection::iterator it, bool engageStats = true);
};
#endif // _LOGD_LOG_BUFFER_H__
diff --git a/logd/LogKlog.cpp b/logd/LogKlog.cpp
index d578c04..0a5df24 100644
--- a/logd/LogKlog.cpp
+++ b/logd/LogKlog.cpp
@@ -43,10 +43,12 @@
if (!isdigit(*s++)) {
return NULL;
}
+ static const size_t max_prio_len = 4;
+ size_t len = 0;
char c;
- while ((c = *s++)) {
+ while (((c = *s++)) && (++len <= max_prio_len)) {
if (!isdigit(c)) {
- return (c == '>') ? s : NULL;
+ return ((c == '>') && (*s == '[')) ? s : NULL;
}
}
return NULL;
@@ -73,7 +75,7 @@
}
// Like strtok_r with "\r\n" except that we look for log signatures (regex)
-// \(\(<[0-9]+>\)\([[] *[0-9]+[.][0-9]+[]] \)\{0,1\}\|[[] *[0-9]+[.][0-9]+[]] \)
+// \(\(<[0-9]\{1,4\}>\)\([[] *[0-9]+[.][0-9]+[]] \)\{0,1\}\|[[] *[0-9]+[.][0-9]+[]] \)
// and split if we see a second one without a newline.
#define SIGNATURE_MASK 0xF0
@@ -165,7 +167,7 @@
break;
}
}
- /* NOTREACHED */
+ // NOTREACHED
}
log_time LogKlog::correction = log_time(CLOCK_REALTIME) - log_time(CLOCK_MONOTONIC);
@@ -254,6 +256,7 @@
if ((cp = now.strptime(*buf, "[ %s.%q]"))) {
static const char suspend[] = "PM: suspend entry ";
static const char resume[] = "PM: suspend exit ";
+ static const char healthd[] = "healthd: battery ";
static const char suspended[] = "Suspended for ";
if (isspace(*cp)) {
@@ -263,6 +266,15 @@
calculateCorrection(now, cp + sizeof(suspend) - 1);
} else if (!strncmp(cp, resume, sizeof(resume) - 1)) {
calculateCorrection(now, cp + sizeof(resume) - 1);
+ } else if (!strncmp(cp, healthd, sizeof(healthd) - 1)) {
+ // look for " 2???-??-?? ??:??:??.????????? ???"
+ const char *tp;
+ for (tp = cp + sizeof(healthd) - 1; *tp && (*tp != '\n'); ++tp) {
+ if ((tp[0] == ' ') && (tp[1] == '2') && (tp[5] == '-')) {
+ calculateCorrection(now, tp + 1);
+ break;
+ }
+ }
} else if (!strncmp(cp, suspended, sizeof(suspended) - 1)) {
log_time real;
char *endp;
@@ -284,6 +296,22 @@
}
}
+pid_t LogKlog::sniffPid(const char *cp) {
+ while (*cp) {
+ // Mediatek kernels with modified printk
+ if (*cp == '[') {
+ int pid = 0;
+ char dummy;
+ if (sscanf(cp, "[%d:%*[a-z_./0-9:A-Z]]%c", &pid, &dummy) == 2) {
+ return pid;
+ }
+ break; // Only the first one
+ }
+ ++cp;
+ }
+ return 0;
+}
+
// Passed the entire SYSLOG_ACTION_READ_ALL buffer and interpret a
// compensated start time.
void LogKlog::synchronize(const char *buf) {
@@ -407,9 +435,9 @@
// sniff for start marker
const char klogd_message[] = "logd.klogd: ";
- if (!strncmp(buf, klogd_message, sizeof(klogd_message) - 1)) {
- char *endp;
- uint64_t sig = strtoll(buf + sizeof(klogd_message) - 1, &endp, 10);
+ const char *start = strstr(buf, klogd_message);
+ if (start) {
+ uint64_t sig = strtoll(start + sizeof(klogd_message) - 1, NULL, 10);
if (sig == signature.nsec()) {
if (initialized) {
enableLogging = true;
@@ -425,10 +453,10 @@
return 0;
}
- // Parse pid, tid and uid (not possible)
- const pid_t pid = 0;
- const pid_t tid = 0;
- const uid_t uid = 0;
+ // Parse pid, tid and uid
+ const pid_t pid = sniffPid(buf);
+ const pid_t tid = pid;
+ const uid_t uid = pid ? logbuf->pidToUid(pid) : 0;
// Parse (rules at top) to pull out a tag from the incoming kernel message.
// Some may view the following as an ugly heuristic, the desire is to
@@ -440,7 +468,7 @@
if (!*buf) {
return 0;
}
- const char *start = buf;
+ start = buf;
const char *tag = "";
const char *etag = tag;
if (!isspace(*buf)) {
@@ -451,7 +479,14 @@
// <PRI>[<TIME>] "[INFO]"<tag> ":" message
bt = buf + 6;
}
- for(et = bt; *et && (*et != ':') && !isspace(*et); ++et);
+ for(et = bt; *et && (*et != ':') && !isspace(*et); ++et) {
+ // skip ':' within [ ... ]
+ if (*et == '[') {
+ while (*et && *et != ']') {
+ ++et;
+ }
+ }
+ }
for(cp = et; isspace(*cp); ++cp);
size_t size;
@@ -465,7 +500,7 @@
if (strncmp(bt, cp, size)) {
// <PRI>[<TIME>] <tag>_host '<tag>.<num>' : message
if (!strncmp(bt + size - 5, "_host", 5)
- && !strncmp(bt, cp, size - 5)) {
+ && !strncmp(bt, cp, size - 5)) {
const char *b = cp;
cp += size - 5;
if (*cp == '.') {
@@ -535,16 +570,30 @@
}
size = etag - tag;
if ((size <= 1)
- || ((size == 2) && (isdigit(tag[0]) || isdigit(tag[1])))
- || ((size == 3) && !strncmp(tag, "CPU", 3))
- || ((size == 7) && !strncmp(tag, "WARNING", 7))
- || ((size == 5) && !strncmp(tag, "ERROR", 5))
- || ((size == 4) && !strncmp(tag, "INFO", 4))) {
+ // register names like x9
+ || ((size == 2) && (isdigit(tag[0]) || isdigit(tag[1])))
+ // register names like x18 but not driver names like en0
+ || ((size == 3) && (isdigit(tag[1]) && isdigit(tag[2])))
+ // blacklist
+ || ((size == 3) && !strncmp(tag, "CPU", 3))
+ || ((size == 7) && !strncmp(tag, "WARNING", 7))
+ || ((size == 5) && !strncmp(tag, "ERROR", 5))
+ || ((size == 4) && !strncmp(tag, "INFO", 4))) {
buf = start;
etag = tag = "";
}
}
- size_t l = etag - tag;
+ // Suppress additional stutter in tag:
+ // eg: [143:healthd]healthd -> [143:healthd]
+ size_t taglen = etag - tag;
+ // Mediatek-special printk induced stutter
+ char *np = strrchr(tag, ']');
+ if (np && (++np < etag)) {
+ size_t s = etag - np;
+ if (((s + s) < taglen) && !strncmp(np, np - 1 - s, s)) {
+ taglen = np - tag;
+ }
+ }
// skip leading space
while (isspace(*buf)) {
++buf;
@@ -555,11 +604,11 @@
--b;
}
// trick ... allow tag with empty content to be logged. log() drops empty
- if (!b && l) {
+ if (!b && taglen) {
buf = " ";
b = 1;
}
- size_t n = 1 + l + 1 + b + 1;
+ size_t n = 1 + taglen + 1 + b + 1;
// Allocate a buffer to hold the interpreted log message
int rc = n;
@@ -568,15 +617,15 @@
rc = -ENOMEM;
return rc;
}
- char *np = newstr;
+ np = newstr;
// Convert priority into single-byte Android logger priority
*np = convertKernelPrioToAndroidPrio(pri);
++np;
// Copy parsed tag following priority
- strncpy(np, tag, l);
- np += l;
+ strncpy(np, tag, taglen);
+ np += taglen;
*np = '\0';
++np;
diff --git a/logd/LogKlog.h b/logd/LogKlog.h
index a898c63..081d344 100644
--- a/logd/LogKlog.h
+++ b/logd/LogKlog.h
@@ -49,6 +49,7 @@
protected:
void sniffTime(log_time &now, const char **buf, bool reverse);
+ pid_t sniffPid(const char *buf);
void calculateCorrection(const log_time &monotonic, const char *real_string);
virtual bool onDataAvailable(SocketClient *cli);
diff --git a/logd/LogTimes.h b/logd/LogTimes.h
index 783bce6..39bcdd4 100644
--- a/logd/LogTimes.h
+++ b/logd/LogTimes.h
@@ -20,8 +20,10 @@
#include <pthread.h>
#include <time.h>
#include <sys/types.h>
+
+#include <list>
+
#include <sysutils/SocketClient.h>
-#include <utils/List.h>
#include <log/log.h>
class LogReader;
@@ -107,6 +109,6 @@
static int FilterSecondPass(const LogBufferElement *element, void *me);
};
-typedef android::List<LogTimeEntry *> LastLogTimes;
+typedef std::list<LogTimeEntry *> LastLogTimes;
-#endif
+#endif // _LOGD_LOG_TIMES_H__
diff --git a/logd/LogWhiteBlackList.cpp b/logd/LogWhiteBlackList.cpp
index 277b3ca..16dd6d2 100644
--- a/logd/LogWhiteBlackList.cpp
+++ b/logd/LogWhiteBlackList.cpp
@@ -50,18 +50,14 @@
}
PruneList::PruneList() : mWorstUidEnabled(true) {
- mNaughty.clear();
- mNice.clear();
}
PruneList::~PruneList() {
PruneCollection::iterator it;
for (it = mNice.begin(); it != mNice.end();) {
- delete (*it);
it = mNice.erase(it);
}
for (it = mNaughty.begin(); it != mNaughty.end();) {
- delete (*it);
it = mNaughty.erase(it);
}
}
@@ -70,11 +66,9 @@
mWorstUidEnabled = true;
PruneCollection::iterator it;
for (it = mNice.begin(); it != mNice.end();) {
- delete (*it);
it = mNice.erase(it);
}
for (it = mNaughty.begin(); it != mNaughty.end();) {
- delete (*it);
it = mNaughty.erase(it);
}
@@ -142,28 +136,28 @@
// insert sequentially into list
PruneCollection::iterator it = list->begin();
while (it != list->end()) {
- Prune *p = *it;
- int m = uid - p->mUid;
+ Prune &p = *it;
+ int m = uid - p.mUid;
if (m == 0) {
- if (p->mPid == p->pid_all) {
+ if (p.mPid == p.pid_all) {
break;
}
- if ((pid == p->pid_all) && (p->mPid != p->pid_all)) {
+ if ((pid == p.pid_all) && (p.mPid != p.pid_all)) {
it = list->erase(it);
continue;
}
- m = pid - p->mPid;
+ m = pid - p.mPid;
}
if (m <= 0) {
if (m < 0) {
- list->insert(it, new Prune(uid,pid));
+ list->insert(it, Prune(uid,pid));
}
break;
}
++it;
}
if (it == list->end()) {
- list->push_back(new Prune(uid,pid));
+ list->push_back(Prune(uid,pid));
}
if (!*str) {
break;
@@ -193,7 +187,7 @@
for (it = mNice.begin(); it != mNice.end(); ++it) {
char *a = NULL;
- (*it)->format(&a);
+ (*it).format(&a);
string.appendFormat(fmt, a);
fmt = nice_format;
@@ -205,7 +199,7 @@
fmt = naughty_format + (*fmt != ' ');
for (it = mNaughty.begin(); it != mNaughty.end(); ++it) {
char *a = NULL;
- (*it)->format(&a);
+ (*it).format(&a);
string.appendFormat(fmt, a);
fmt = naughty_format;
@@ -223,7 +217,7 @@
bool PruneList::naughty(LogBufferElement *element) {
PruneCollection::iterator it;
for (it = mNaughty.begin(); it != mNaughty.end(); ++it) {
- if (!(*it)->cmp(element)) {
+ if (!(*it).cmp(element)) {
return true;
}
}
@@ -233,7 +227,7 @@
bool PruneList::nice(LogBufferElement *element) {
PruneCollection::iterator it;
for (it = mNice.begin(); it != mNice.end(); ++it) {
- if (!(*it)->cmp(element)) {
+ if (!(*it).cmp(element)) {
return true;
}
}
diff --git a/logd/LogWhiteBlackList.h b/logd/LogWhiteBlackList.h
index 5f60801..57cd03b 100644
--- a/logd/LogWhiteBlackList.h
+++ b/logd/LogWhiteBlackList.h
@@ -19,7 +19,7 @@
#include <sys/types.h>
-#include <utils/List.h>
+#include <list>
#include <LogBufferElement.h>
@@ -47,7 +47,7 @@
void format(char **strp);
};
-typedef android::List<Prune *> PruneCollection;
+typedef std::list<Prune> PruneCollection;
class PruneList {
PruneCollection mNaughty;
diff --git a/rootdir/init.rc b/rootdir/init.rc
index b71908c..317207c 100644
--- a/rootdir/init.rc
+++ b/rootdir/init.rc
@@ -7,6 +7,7 @@
import /init.environ.rc
import /init.usb.rc
import /init.${ro.hardware}.rc
+import /init.usb.configfs.rc
import /init.${ro.zygote}.rc
import /init.trace.rc
@@ -88,10 +89,17 @@
write /proc/sys/kernel/panic_on_oops 1
write /proc/sys/kernel/hung_task_timeout_secs 0
write /proc/cpu/alignment 4
+
+ # scheduler tunables
+ # Disable auto-scaling of scheduler tunables with hotplug. The tunables
+ # will vary across devices in unpredictable ways if allowed to scale with
+ # cpu cores.
+ write /proc/sys/kernel/sched_tunable_scaling 0
write /proc/sys/kernel/sched_latency_ns 10000000
write /proc/sys/kernel/sched_wakeup_granularity_ns 2000000
write /proc/sys/kernel/sched_compat_yield 1
write /proc/sys/kernel/sched_child_runs_first 0
+
write /proc/sys/kernel/randomize_va_space 2
write /proc/sys/kernel/kptr_restrict 2
write /proc/sys/vm/mmap_min_addr 32768
@@ -132,21 +140,37 @@
# sets up initial cpusets for ActivityManager
mkdir /dev/cpuset
mount cpuset none /dev/cpuset
- mkdir /dev/cpuset/foreground
- mkdir /dev/cpuset/background
+
# this ensures that the cpusets are present and usable, but the device's
# init.rc must actually set the correct cpus
+ mkdir /dev/cpuset/foreground
write /dev/cpuset/foreground/cpus 0
- write /dev/cpuset/background/cpus 0
write /dev/cpuset/foreground/mems 0
+ mkdir /dev/cpuset/foreground/boost
+ write /dev/cpuset/foreground/boost/cpus 0
+ write /dev/cpuset/foreground/boost/mems 0
+ mkdir /dev/cpuset/background
+ write /dev/cpuset/background/cpus 0
write /dev/cpuset/background/mems 0
+
+ # system-background is for system tasks that should only run on
+ # little cores, not on bigs
+ # to be used only by init, so don't change system-bg permissions
+ mkdir /dev/cpuset/system-background
+ write /dev/cpuset/system-background/cpus 0
+ write /dev/cpuset/system-background/mems 0
+
+ # change permissions for all cpusets we'll touch at runtime
chown system system /dev/cpuset
chown system system /dev/cpuset/foreground
+ chown system system /dev/cpuset/foreground/boost
chown system system /dev/cpuset/background
chown system system /dev/cpuset/tasks
chown system system /dev/cpuset/foreground/tasks
+ chown system system /dev/cpuset/foreground/boost/tasks
chown system system /dev/cpuset/background/tasks
chmod 0664 /dev/cpuset/foreground/tasks
+ chmod 0664 /dev/cpuset/foreground/boost/tasks
chmod 0664 /dev/cpuset/background/tasks
chmod 0664 /dev/cpuset/tasks
@@ -182,8 +206,11 @@
trigger late-init
# Load properties from /system/ + /factory after fs mount.
-on load_all_props_action
- load_all_props
+on load_system_props_action
+ load_system_props
+
+on load_persist_props_action
+ load_persist_props
start logd
start logd-reinit
@@ -196,12 +223,16 @@
trigger early-fs
trigger fs
trigger post-fs
- trigger post-fs-data
# Load properties from /system/ + /factory after fs mount. Place
# this in another action so that the load will be scheduled after the prior
# issued fs triggers have completed.
- trigger load_all_props_action
+ trigger load_system_props_action
+
+ # Now we can mount /data. File encryption requires keymaster to decrypt
+ # /data, which in turn can only be loaded when system properties are present
+ trigger post-fs-data
+ trigger load_persist_props_action
# Remove a file to wake up anything waiting for firmware.
trigger firmware_mounts_complete
@@ -352,6 +383,8 @@
mkdir /data/system/heapdump 0700 system system
mkdir /data/user 0711 system system
+ setusercryptopolicies /data/user
+
# Reload policy from /data/security if present.
setprop selinux.reload_policy 1
@@ -525,9 +558,11 @@
socket logdr seqpacket 0666 logd logd
socket logdw dgram 0222 logd logd
group root system
+ writepid /dev/cpuset/system-background/tasks
service logd-reinit /system/bin/logd --reinit
oneshot
+ writepid /dev/cpuset/system-background/tasks
disabled
service healthd /sbin/healthd
@@ -562,6 +597,7 @@
class core
critical
socket lmkd seqpacket 0660 system system
+ writepid /dev/cpuset/system-background/tasks
service servicemanager /system/bin/servicemanager
class core
@@ -591,9 +627,11 @@
service debuggerd /system/bin/debuggerd
class main
+ writepid /dev/cpuset/system-background/tasks
service debuggerd64 /system/bin/debuggerd64
class main
+ writepid /dev/cpuset/system-background/tasks
service ril-daemon /system/bin/rild
class main
@@ -608,6 +646,7 @@
user system
group graphics drmrpc
onrestart restart zygote
+ writepid /dev/cpuset/system-background/tasks
service drm /system/bin/drmserver
class main
@@ -628,7 +667,7 @@
# encryption) or trigger_restart_min_framework (other encryption)
# One shot invocation to encrypt unencrypted volumes
-service encrypt /system/bin/vdc --wait cryptfs enablecrypto inplace default
+service encrypt /system/bin/vdc --wait cryptfs enablecrypto inplace default noui
disabled
oneshot
# vold will set vold.decrypt to trigger_restart_framework (default
@@ -702,6 +741,7 @@
class late_start
user root
oneshot
+ writepid /dev/cpuset/system-background/tasks
on property:persist.logd.logpersistd=logcatd
# all exec/services are called with umask(077), so no gain beyond 0700
@@ -716,3 +756,4 @@
# logd for write to /data/misc/logd, log group for read from log daemon
user logd
group log
+ writepid /dev/cpuset/system-background/tasks
diff --git a/rootdir/init.usb.configfs.rc b/rootdir/init.usb.configfs.rc
new file mode 100644
index 0000000..186384b
--- /dev/null
+++ b/rootdir/init.usb.configfs.rc
@@ -0,0 +1,175 @@
+on property:sys.usb.config=none && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/UDC "none"
+ stop adbd
+ write /config/usb_gadget/g1/bDeviceClass 0
+ write /config/usb_gadget/g1/bDeviceSubClass 0
+ write /config/usb_gadget/g1/bDeviceProtocol 0
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=mtp && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "mtp"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/mtp.gs0 /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=mtp,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=mtp,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "mtp_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/mtp.gs0 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=ptp && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "ptp"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/ptp.gs1 /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=ptp,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=ptp,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "ptp_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/ptp.gs1 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=accessory && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "accessory"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/accessory.gs2 /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=accessory,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=accessory,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "accessory_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/accessory.gs2 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=audio_source && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "audiosource"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/audio_source.gs2 /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=audio_source,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=audio_source,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "audiosource_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/audio_source.gs2 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=accessory,audio_source && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "accessory_audiosource"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/accessory.gs2 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/audio_source.gs3 /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=accessory,audio_source,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=accessory,audio_source,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "accessory_audiosource_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/accessory.gs2 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/audio_source.gs3 /config/usb_gadget/g1/configs/b.1/f2
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f3
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=midi && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "midi"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/midi.gs5 /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=midi,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=midi,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "midi_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/midi.gs5 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=rndis && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "rndis"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/rndis.gs4 /config/usb_gadget/g1/configs/b.1/f1
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
+
+on property:sys.usb.config=rndis,adb && property:sys.usb.configfs=1
+ start adbd
+
+on property:sys.usb.ffs.ready=1 && property:sys.usb.config=rndis,adb && property:sys.usb.configfs=1
+ write /config/usb_gadget/g1/configs/b.1/strings/0x409/configuration "rndis_adb"
+ rm /config/usb_gadget/g1/configs/b.1/f1
+ rm /config/usb_gadget/g1/configs/b.1/f2
+ rm /config/usb_gadget/g1/configs/b.1/f3
+ symlink /config/usb_gadget/g1/functions/rndis.gs4 /config/usb_gadget/g1/configs/b.1/f1
+ symlink /config/usb_gadget/g1/functions/ffs.adb /config/usb_gadget/g1/configs/b.1/f2
+ write /config/usb_gadget/g1/UDC ${sys.usb.controller}
+ setprop sys.usb.state ${sys.usb.config}
diff --git a/rootdir/init.usb.rc b/rootdir/init.usb.rc
index e290ca4..a105afe 100644
--- a/rootdir/init.usb.rc
+++ b/rootdir/init.usb.rc
@@ -9,8 +9,11 @@
chown system system /sys/class/android_usb/android0/f_rndis/ethaddr
chmod 0660 /sys/class/android_usb/android0/f_rndis/ethaddr
+on boot
+ setprop sys.usb.configfs 0
+
# Used to disable USB when switching states
-on property:sys.usb.config=none
+on property:sys.usb.config=none && property:sys.usb.configfs=0
stop adbd
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/bDeviceClass 0
@@ -19,7 +22,7 @@
# adb only USB configuration
# This is the fallback configuration if the
# USB manager fails to set a standard configuration
-on property:sys.usb.config=adb
+on property:sys.usb.config=adb && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 4EE7
@@ -29,7 +32,7 @@
setprop sys.usb.state ${sys.usb.config}
# USB accessory configuration
-on property:sys.usb.config=accessory
+on property:sys.usb.config=accessory && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 2d00
@@ -38,7 +41,7 @@
setprop sys.usb.state ${sys.usb.config}
# USB accessory configuration, with adb
-on property:sys.usb.config=accessory,adb
+on property:sys.usb.config=accessory,adb && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 2d01
@@ -48,7 +51,7 @@
setprop sys.usb.state ${sys.usb.config}
# audio accessory configuration
-on property:sys.usb.config=audio_source
+on property:sys.usb.config=audio_source && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 2d02
@@ -57,7 +60,7 @@
setprop sys.usb.state ${sys.usb.config}
# audio accessory configuration, with adb
-on property:sys.usb.config=audio_source,adb
+on property:sys.usb.config=audio_source,adb && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 2d03
@@ -67,7 +70,7 @@
setprop sys.usb.state ${sys.usb.config}
# USB and audio accessory configuration
-on property:sys.usb.config=accessory,audio_source
+on property:sys.usb.config=accessory,audio_source && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 2d04
@@ -76,7 +79,7 @@
setprop sys.usb.state ${sys.usb.config}
# USB and audio accessory configuration, with adb
-on property:sys.usb.config=accessory,audio_source,adb
+on property:sys.usb.config=accessory,audio_source,adb && property:sys.usb.configfs=0
write /sys/class/android_usb/android0/enable 0
write /sys/class/android_usb/android0/idVendor 18d1
write /sys/class/android_usb/android0/idProduct 2d05
@@ -89,3 +92,34 @@
# when changing the default configuration
on property:persist.sys.usb.config=*
setprop sys.usb.config ${persist.sys.usb.config}
+
+#
+# USB type C
+#
+
+# USB mode changes
+on property:sys.usb.typec.mode=dfp
+ write /sys/class/dual_role_usb/otg_default/mode ${sys.usb.typec.mode}
+ setprop sys.usb.typec.state ${sys.usb.typec.mode}
+
+on property:sys.usb.typec.mode=ufp
+ write /sys/class/dual_role_usb/otg_default/mode ${sys.usb.typec.mode}
+ setprop sys.usb.typec.state ${sys.usb.typec.mode}
+
+# USB data role changes
+on property:sys.usb.typec.data_role=device
+ write /sys/class/dual_role_usb/otg_default/data_role ${sys.usb.typec.data_role}
+ setprop sys.usb.typec.state ${sys.usb.typec.data_role}
+
+on property:sys.usb.typec.data_role=host
+ write /sys/class/dual_role_usb/otg_default/data_role ${sys.usb.typec.data_role}
+ setprop sys.usb.typec.state ${sys.usb.typec.data_role}
+
+# USB power role changes
+on property:sys.usb.typec.power_role=source
+ write /sys/class/dual_role_usb/otg_default/power_role ${sys.usb.typec.power_role}
+ setprop sys.usb.typec.state ${sys.usb.typec.power_role}
+
+on property:sys.usb.typec.power_role=sink
+ write /sys/class/dual_role_usb/otg_default/power_role ${sys.usb.typec.power_role}
+ setprop sys.usb.typec.state ${sys.usb.typec.power_role}
diff --git a/rootdir/init.zygote32.rc b/rootdir/init.zygote32.rc
index 75961e6..ff25ac2 100644
--- a/rootdir/init.zygote32.rc
+++ b/rootdir/init.zygote32.rc
@@ -5,4 +5,4 @@
onrestart write /sys/power/state on
onrestart restart media
onrestart restart netd
-
+ writepid /dev/cpuset/foreground/tasks
diff --git a/rootdir/init.zygote32_64.rc b/rootdir/init.zygote32_64.rc
index 68c0668..29bb1cf 100644
--- a/rootdir/init.zygote32_64.rc
+++ b/rootdir/init.zygote32_64.rc
@@ -5,8 +5,10 @@
onrestart write /sys/power/state on
onrestart restart media
onrestart restart netd
+ writepid /dev/cpuset/foreground/tasks
service zygote_secondary /system/bin/app_process64 -Xzygote /system/bin --zygote --socket-name=zygote_secondary
class main
socket zygote_secondary stream 660 root system
onrestart restart zygote
+ writepid /dev/cpuset/foreground/tasks
\ No newline at end of file
diff --git a/rootdir/init.zygote64.rc b/rootdir/init.zygote64.rc
index afb6d63..5497524 100644
--- a/rootdir/init.zygote64.rc
+++ b/rootdir/init.zygote64.rc
@@ -5,4 +5,4 @@
onrestart write /sys/power/state on
onrestart restart media
onrestart restart netd
-
+ writepid /dev/cpuset/foreground/tasks
diff --git a/rootdir/init.zygote64_32.rc b/rootdir/init.zygote64_32.rc
index 979ab3b..8ed5e9e 100644
--- a/rootdir/init.zygote64_32.rc
+++ b/rootdir/init.zygote64_32.rc
@@ -5,8 +5,10 @@
onrestart write /sys/power/state on
onrestart restart media
onrestart restart netd
+ writepid /dev/cpuset/foreground/tasks
service zygote_secondary /system/bin/app_process32 -Xzygote /system/bin --zygote --socket-name=zygote_secondary
class main
socket zygote_secondary stream 660 root system
onrestart restart zygote
+ writepid /dev/cpuset/foreground/tasks
\ No newline at end of file
diff --git a/sdcard/sdcard.c b/sdcard/sdcard.c
index a79e2dd..06452aa 100644
--- a/sdcard/sdcard.c
+++ b/sdcard/sdcard.c
@@ -507,6 +507,16 @@
}
}
+static void derive_permissions_recursive_locked(struct fuse* fuse, struct node *parent) {
+ struct node *node;
+ for (node = parent->child; node; node = node->next) {
+ derive_permissions_locked(fuse, parent, node);
+ if (node->child) {
+ derive_permissions_recursive_locked(fuse, node);
+ }
+ }
+}
+
/* Kernel has already enforced everything we returned through
* derive_permissions_locked(), so this is used to lock down access
* even further, such as enforcing that apps hold sdcard_rw. */
@@ -1145,6 +1155,8 @@
res = rename_node_locked(child_node, new_name, new_actual_name);
if (!res) {
remove_node_from_parent_locked(child_node);
+ derive_permissions_locked(fuse, new_parent_node, child_node);
+ derive_permissions_recursive_locked(fuse, child_node);
add_node_to_parent_locked(child_node, new_parent_node);
}
goto done;
@@ -1663,6 +1675,10 @@
TRACE("read_package_list: found %zu packages\n",
hashmapSize(global->package_to_appid));
fclose(file);
+
+ /* Regenerate ownership details using newly loaded mapping */
+ derive_permissions_recursive_locked(global->fuse_default, &global->root);
+
pthread_mutex_unlock(&global->lock);
return 0;
}