Merge "Don't use bare `noreturn` in log.h."
diff --git a/init/Android.mk b/init/Android.mk
index ecdf5db..111fe89 100644
--- a/init/Android.mk
+++ b/init/Android.mk
@@ -54,7 +54,7 @@
service.cpp \
util.cpp \
-LOCAL_STATIC_LIBRARIES := libbase libselinux liblog libprocessgroup
+LOCAL_STATIC_LIBRARIES := libbase libselinux liblog libprocessgroup libnl
LOCAL_WHOLE_STATIC_LIBRARIES := libcap
LOCAL_MODULE := libinit
LOCAL_SANITIZE := integer
@@ -103,7 +103,8 @@
libdl \
libsparse_static \
libz \
- libprocessgroup
+ libprocessgroup \
+ libnl \
# Create symlinks.
LOCAL_POST_INSTALL_CMD := $(hide) mkdir -p $(TARGET_ROOT_OUT)/sbin; \
diff --git a/init/log.cpp b/init/log.cpp
index 8618340..6b32526 100644
--- a/init/log.cpp
+++ b/init/log.cpp
@@ -19,6 +19,8 @@
#include <fcntl.h>
#include <string.h>
+#include <linux/audit.h>
+#include <netlink/netlink.h>
#include <selinux/selinux.h>
void InitKernelLogging(char* argv[]) {
@@ -38,6 +40,24 @@
android::base::InitLogging(argv, &android::base::KernelLogger);
}
+static void selinux_avc_log(char* buf, size_t buf_len) {
+ size_t str_len = strnlen(buf, buf_len);
+
+ // trim newline at end of string
+ buf[str_len - 1] = '\0';
+
+ struct nl_sock* sk = nl_socket_alloc();
+ if (sk == NULL) {
+ return;
+ }
+ nl_connect(sk, NETLINK_AUDIT);
+ int result;
+ do {
+ result = nl_send_simple(sk, AUDIT_USER_AVC, 0, buf, str_len);
+ } while (result == -NLE_INTR);
+ nl_socket_free(sk);
+}
+
int selinux_klog_callback(int type, const char *fmt, ...) {
android::base::LogSeverity severity = android::base::ERROR;
if (type == SELINUX_WARNING) {
@@ -48,8 +68,15 @@
char buf[1024];
va_list ap;
va_start(ap, fmt);
- vsnprintf(buf, sizeof(buf), fmt, ap);
+ int res = vsnprintf(buf, sizeof(buf), fmt, ap);
va_end(ap);
- android::base::KernelLogger(android::base::MAIN, severity, "selinux", nullptr, 0, buf);
+ if (res <= 0) {
+ return 0;
+ }
+ if (type == SELINUX_AVC) {
+ selinux_avc_log(buf, sizeof(buf));
+ } else {
+ android::base::KernelLogger(android::base::MAIN, severity, "selinux", nullptr, 0, buf);
+ }
return 0;
}
diff --git a/init/service.cpp b/init/service.cpp
index 7cff348..0f7f62f 100644
--- a/init/service.cpp
+++ b/init/service.cpp
@@ -582,12 +582,15 @@
console_ = default_console;
}
- bool have_console = (access(console_.c_str(), R_OK | W_OK) != -1);
- if (!have_console) {
- PLOG(ERROR) << "service '" << name_ << "' cannot gain read/write access to console '" << console_ << "'";
+ // Make sure that open call succeeds to ensure a console driver is
+ // properly registered for the device node
+ int console_fd = open(console_.c_str(), O_RDWR | O_CLOEXEC);
+ if (console_fd < 0) {
+ PLOG(ERROR) << "service '" << name_ << "' couldn't open console '" << console_ << "'";
flags_ |= SVC_DISABLED;
return false;
}
+ close(console_fd);
}
struct stat sb;
diff --git a/logd/LogAudit.cpp b/logd/LogAudit.cpp
index aa05932..11ffcb7 100644
--- a/logd/LogAudit.cpp
+++ b/logd/LogAudit.cpp
@@ -47,6 +47,10 @@
logbuf(buf),
reader(reader),
fdDmesg(fdDmesg),
+ main(__android_logger_property_get_bool("ro.logd.auditd.main",
+ BOOL_DEFAULT_TRUE)),
+ events(__android_logger_property_get_bool("ro.logd.auditd.events",
+ BOOL_DEFAULT_TRUE)),
initialized(false) {
static const char auditd_message[] = { KMSG_PRIORITY(LOG_INFO),
'l', 'o', 'g', 'd', '.', 'a', 'u', 'd', 'i', 't', 'd', ':',
@@ -94,6 +98,13 @@
}
char *cp;
+ // Work around kernels missing
+ // https://github.com/torvalds/linux/commit/b8f89caafeb55fba75b74bea25adc4e4cd91be67
+ // Such kernels improperly add newlines inside audit messages.
+ while ((cp = strchr(str, '\n'))) {
+ *cp = ' ';
+ }
+
while ((cp = strstr(str, " "))) {
memmove(cp, cp + 1, strlen(cp + 1) + 1);
}
@@ -172,6 +183,11 @@
}
}
+ if (!main && !events) {
+ free(str);
+ return 0;
+ }
+
pid_t pid = getpid();
pid_t tid = gettid();
uid_t uid = AID_LOGD;
@@ -222,7 +238,7 @@
bool notify = false;
- { // begin scope for event buffer
+ if (events) { // begin scope for event buffer
uint32_t buffer[(n + sizeof(uint32_t) - 1) / sizeof(uint32_t)];
android_log_event_string_t *event
@@ -277,7 +293,7 @@
size_t e = strnlen(ecomm, LOGGER_ENTRY_MAX_PAYLOAD - b);
n = b + e + l + 2;
- { // begin scope for main buffer
+ if (main) { // begin scope for main buffer
char newstr[n];
*newstr = info ? ANDROID_LOG_INFO : ANDROID_LOG_WARN;
diff --git a/logd/LogAudit.h b/logd/LogAudit.h
index ab30e28..844951d 100644
--- a/logd/LogAudit.h
+++ b/logd/LogAudit.h
@@ -26,7 +26,9 @@
class LogAudit : public SocketListener {
LogBuffer *logbuf;
LogReader *reader;
- int fdDmesg;
+ int fdDmesg; // fdDmesg >= 0 is functionally bool dmesg
+ bool main;
+ bool events;
bool initialized;
public:
diff --git a/logd/README.property b/logd/README.property
index 791b1d5..de6767a 100644
--- a/logd/README.property
+++ b/logd/README.property
@@ -2,8 +2,9 @@
name type default description
ro.logd.auditd bool true Enable selinux audit daemon
-ro.logd.auditd.dmesg bool true selinux audit messages duplicated and
- sent on to dmesg log
+ro.logd.auditd.dmesg bool true selinux audit messages sent to dmesg.
+ro.logd.auditd.main bool true selinux audit messages sent to main.
+ro.logd.auditd.events bool true selinux audit messages sent to events.
persist.logd.security bool false Enable security buffer.
ro.device_owner bool false Override persist.logd.security to false
ro.logd.kernel bool+ svelte+ Enable klogd daemon
diff --git a/logd/main.cpp b/logd/main.cpp
index c3343d7..5878f15 100644
--- a/logd/main.cpp
+++ b/logd/main.cpp
@@ -451,9 +451,8 @@
pthread_attr_destroy(&attr);
}
- bool auditd = __android_logger_property_get_bool("logd.auditd",
- BOOL_DEFAULT_TRUE |
- BOOL_DEFAULT_FLAG_PERSIST);
+ bool auditd = __android_logger_property_get_bool("ro.logd.auditd",
+ BOOL_DEFAULT_TRUE);
if (drop_privs(klogd, auditd) != 0) {
return -1;
}
@@ -513,8 +512,8 @@
if (auditd) {
al = new LogAudit(logBuf, reader,
__android_logger_property_get_bool(
- "logd.auditd.dmesg",
- BOOL_DEFAULT_TRUE | BOOL_DEFAULT_FLAG_PERSIST)
+ "ro.logd.auditd.dmesg",
+ BOOL_DEFAULT_TRUE)
? fdDmesg
: -1);
}