Snap for 8720775 from b2ca6f29c64e8efd11cee852562a4054368dcf81 to mainline-sdkext-release
Change-Id: I6685401e78e5ccee306047c7da037ff507020ca1
diff --git a/liblog/logger_write.cpp b/liblog/logger_write.cpp
index 08ab6e2..9a9a126 100644
--- a/liblog/logger_write.cpp
+++ b/liblog/logger_write.cpp
@@ -60,7 +60,7 @@
static int check_log_uid_permissions() {
uid_t uid = getuid();
- /* Matches clientHasLogCredentials() in logd */
+ /* Matches clientCanWriteSecurityLog() in logd */
if ((uid != AID_SYSTEM) && (uid != AID_ROOT) && (uid != AID_LOG)) {
uid = geteuid();
if ((uid != AID_SYSTEM) && (uid != AID_ROOT) && (uid != AID_LOG)) {
@@ -81,7 +81,8 @@
}
num_groups = getgroups(num_groups, groups);
while (num_groups > 0) {
- if (groups[num_groups - 1] == AID_LOG) {
+ if (groups[num_groups - 1] == AID_LOG ||
+ groups[num_groups - 1] == AID_SECURITY_LOG_WRITER) {
break;
}
--num_groups;
diff --git a/logd/LogListener.cpp b/logd/LogListener.cpp
index ae74796..182567d 100644
--- a/logd/LogListener.cpp
+++ b/logd/LogListener.cpp
@@ -103,10 +103,13 @@
return;
}
- if ((logId == LOG_ID_SECURITY) &&
- (!__android_log_security() ||
- !clientHasLogCredentials(cred->uid, cred->gid, cred->pid))) {
- return;
+ if (logId == LOG_ID_SECURITY) {
+ if (!__android_log_security()) {
+ return;
+ }
+ if (!clientCanWriteSecurityLog(cred->uid, cred->gid, cred->pid)) {
+ return;
+ }
}
char* msg = ((char*)buffer) + sizeof(android_log_header_t);
diff --git a/logd/LogPermissions.cpp b/logd/LogPermissions.cpp
index 31e145a..b8b0bd0 100644
--- a/logd/LogPermissions.cpp
+++ b/logd/LogPermissions.cpp
@@ -26,7 +26,7 @@
#include <private/android_filesystem_config.h>
-static bool groupIsLog(char* buf) {
+static bool checkGroup(char* buf, gid_t gidToCheck) {
char* ptr;
static const char ws[] = " \n";
@@ -36,7 +36,7 @@
if (errno != 0) {
return false;
}
- if (Gid == AID_LOG) {
+ if (Gid == gidToCheck) {
return true;
}
}
@@ -54,17 +54,12 @@
// This function introduces races especially since status
// can change 'shape' while reading, the net result is err
// on lack of permission.
-bool clientHasLogCredentials(uid_t uid, gid_t gid, pid_t pid) {
- if (UserIsPrivileged(uid) || UserIsPrivileged(gid)) {
- return true;
- }
-
- // FYI We will typically be here for 'adb logcat'
+static bool checkSupplementaryGroup(uid_t uid, gid_t gid, pid_t pid, gid_t gidToCheck) {
char filename[256];
snprintf(filename, sizeof(filename), "/proc/%u/status", pid);
bool ret;
- bool foundLog = false;
+ bool foundGroup = false;
bool foundGid = false;
bool foundUid = false;
@@ -83,8 +78,7 @@
// doubt, but we expect the falses should be reduced significantly as
// three times is a charm.
//
- for (int retry = 3; !(ret = foundGid && foundUid && foundLog) && retry;
- --retry) {
+ for (int retry = 3; !(ret = foundGid && foundUid && foundGroup) && retry; --retry) {
FILE* file = fopen(filename, "re");
if (!file) {
continue;
@@ -98,8 +92,8 @@
static const char gid_string[] = "Gid:\t";
if (strncmp(groups_string, line, sizeof(groups_string) - 1) == 0) {
- if (groupIsLog(line + sizeof(groups_string) - 1)) {
- foundLog = true;
+ if (checkGroup(line + sizeof(groups_string) - 1, gidToCheck)) {
+ foundGroup = true;
}
} else if (strncmp(uid_string, line, sizeof(uid_string) - 1) == 0) {
uid_t u[4] = { (uid_t)-1, (uid_t)-1, (uid_t)-1, (uid_t)-1 };
@@ -132,6 +126,22 @@
return ret;
}
+bool clientCanWriteSecurityLog(uid_t uid, gid_t gid, pid_t pid) {
+ if (UserIsPrivileged(uid) || UserIsPrivileged(gid)) {
+ return true;
+ }
+ return checkSupplementaryGroup(uid, gid, pid, AID_SECURITY_LOG_WRITER) ||
+ checkSupplementaryGroup(uid, gid, pid, AID_LOG);
+}
+
+bool clientHasLogCredentials(uid_t uid, gid_t gid, pid_t pid) {
+ if (UserIsPrivileged(uid) || UserIsPrivileged(gid)) {
+ return true;
+ }
+ // FYI We will typically be here for 'adb logcat'
+ return checkSupplementaryGroup(uid, gid, pid, AID_LOG);
+}
+
bool clientHasLogCredentials(SocketClient* cli) {
if (UserIsPrivileged(cli->getUid()) || UserIsPrivileged(cli->getGid())) {
return true;
diff --git a/logd/LogPermissions.h b/logd/LogPermissions.h
index 7065d9f..34a8607 100644
--- a/logd/LogPermissions.h
+++ b/logd/LogPermissions.h
@@ -22,4 +22,5 @@
bool clientHasLogCredentials(uid_t uid, gid_t gid, pid_t pid);
bool clientHasLogCredentials(SocketClient* cli);
+bool clientCanWriteSecurityLog(uid_t uid, gid_t gid, pid_t pid);
bool clientIsExemptedFromUserConsent(SocketClient* cli);
diff --git a/logd/TrustyLog.cpp b/logd/TrustyLog.cpp
index 213533d..b04587a 100644
--- a/logd/TrustyLog.cpp
+++ b/logd/TrustyLog.cpp
@@ -73,6 +73,7 @@
bool TrustyLog::onDataAvailable(SocketClient* cli) {
char buffer[4096];
ssize_t len = 0;
+ bool need_newline = false;
for (;;) {
ssize_t retval = 0;
if (len < (ssize_t)(sizeof(buffer) - 1)) {
@@ -104,10 +105,17 @@
len -= TRUSTY_LINE_BUFFER_SIZE;
} else {
if (len) {
+ if (need_newline) {
+ // still no newline after reading more, log what we have
+ // and return
+ LogMsg(linestart, len);
+ return true;
+ }
// there's some unterminated data left at the end of the
// buffer. Move it to the front and try to append more in
// the outer loop.
memmove(buffer, linestart, len);
+ need_newline = true;
}
break;
}
diff --git a/logd/main.cpp b/logd/main.cpp
index e405544..f8be2dc 100644
--- a/logd/main.cpp
+++ b/logd/main.cpp
@@ -307,6 +307,8 @@
delete al;
}
+ TrustyLog::create(log_buffer);
+
TEMP_FAILURE_RETRY(pause());
return EXIT_SUCCESS;