From 58d80579d90f8752fc15d7d8f9a81247d8b6c600 Mon Sep 17 00:00:00 2001 From: Jie Song Date: Mon, 27 Mar 2017 19:19:34 -0700 Subject: [PATCH] Add wahoo dumpstate and sepolicy with smlog Bug: 33820081 Test: Verify dumpstate service running Change-Id: I2dffdb063aa3291b1c9ee95df903977d6a928d1e --- BoardConfig.mk | 2 - device.mk | 4 + dumpstate/Android.mk | 43 ++++++ dumpstate/DumpstateDevice.cpp | 136 ++++++++++++++++++ dumpstate/DumpstateDevice.h | 49 +++++++ ...id.hardware.dumpstate@1.0-service.wahoo.rc | 4 + dumpstate/service.cpp | 43 ++++++ manifest.xml | 6 + sepolicy/dumpstate.te | 4 + sepolicy/file.te | 3 + sepolicy/file_contexts | 1 + sepolicy/hal_dumpstate_impl.te | 32 +++++ sepolicy/rild.te | 4 + sepolicy/smlog_dump.te | 23 +++ 14 files changed, 352 insertions(+), 2 deletions(-) create mode 100644 dumpstate/Android.mk create mode 100755 dumpstate/DumpstateDevice.cpp create mode 100644 dumpstate/DumpstateDevice.h create mode 100644 dumpstate/android.hardware.dumpstate@1.0-service.wahoo.rc create mode 100644 dumpstate/service.cpp create mode 100644 sepolicy/dumpstate.te create mode 100644 sepolicy/hal_dumpstate_impl.te create mode 100644 sepolicy/smlog_dump.te diff --git a/BoardConfig.mk b/BoardConfig.mk index 5d374ea4..b1ced854 100644 --- a/BoardConfig.mk +++ b/BoardConfig.mk @@ -63,8 +63,6 @@ ENABLE_CPUSETS := true TARGET_COPY_OUT_VENDOR := vendor -BOARD_HAL_STATIC_LIBRARIES := libdumpstate.$(TARGET_BOOTLOADER_BOARD_NAME) - # Install odex files into the other system image BOARD_USES_SYSTEM_OTHER_ODEX := true diff --git a/device.mk b/device.mk index f5112f73..aa76088e 100644 --- a/device.mk +++ b/device.mk @@ -429,3 +429,7 @@ PRODUCT_PACKAGES += \ ifneq (,$(filter userdebug eng, $(TARGET_BUILD_VARIANT))) PRODUCT_PROPERTY_OVERRIDES += ro.logd.size=1M endif + +# Dumpstate HAL +PRODUCT_PACKAGES += \ + android.hardware.dumpstate@1.0-service.wahoo diff --git a/dumpstate/Android.mk b/dumpstate/Android.mk new file mode 100644 index 00000000..6607bf85 --- /dev/null +++ b/dumpstate/Android.mk @@ -0,0 +1,43 @@ +# +# Copyright 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) +LOCAL_MODULE := android.hardware.dumpstate@1.0-service.wahoo +LOCAL_INIT_RC := android.hardware.dumpstate@1.0-service.wahoo.rc +LOCAL_MODULE_RELATIVE_PATH := hw + +LOCAL_SRC_FILES := \ + DumpstateDevice.cpp \ + service.cpp + +LOCAL_SHARED_LIBRARIES := \ + android.hardware.dumpstate@1.0 \ + libbase \ + libcutils \ + libdumpstateutil \ + libhidlbase \ + libhidltransport \ + libhwbinder \ + liblog \ + libutils + +LOCAL_CFLAGS := -Werror -Wall + +LOCAL_MODULE_TAGS := optional +LOCAL_PROPRIETARY_MODULE := true + +include $(BUILD_EXECUTABLE) diff --git a/dumpstate/DumpstateDevice.cpp b/dumpstate/DumpstateDevice.cpp new file mode 100755 index 00000000..9a6fe720 --- /dev/null +++ b/dumpstate/DumpstateDevice.cpp @@ -0,0 +1,136 @@ +/* + * Copyright 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. + */ + +#define LOG_TAG "dumpstate" + +#include "DumpstateDevice.h" + +#include +#include +#include +#include +#include +#include + +#include "DumpstateUtil.h" + +#define MODEM_LOG_PREFIX_PROPERTY "ro.radio.log_prefix" +#define MODEM_LOG_LOC_PROPERTY "ro.radio.log_loc" +#define MODEM_LOGGING_SWITCH "persist.radio.smlog_switch" + +using android::os::dumpstate::CommandOptions; +using android::os::dumpstate::DumpFileToFd; +using android::os::dumpstate::PropertiesHelper; +using android::os::dumpstate::RunCommandToFd; + +namespace android { +namespace hardware { +namespace dumpstate { +namespace V1_0 { +namespace implementation { + +namespace { + +static void getModemLogs(int fd) +{ + bool modemLogsEnabled = 0; + std::string modemLogDir = android::base::GetProperty(MODEM_LOG_LOC_PROPERTY, ""); + if (modemLogDir.empty()) { + ALOGD("No modem log place is set\n"); + return; + } + /* Check if smlog_dump tool exist */ + if (!PropertiesHelper::IsUserBuild() && !access("/vendor/bin/smlog_dump", X_OK)) { + modemLogsEnabled = android::base::GetBoolProperty(MODEM_LOGGING_SWITCH, false); + + /* Execute SMLOG DUMP if SMLOG is enabled */ + if (modemLogsEnabled) { + CommandOptions options = CommandOptions::WithTimeout(120).Build(); + std::string modemLogAllDir = modemLogDir + "/modem_log"; + std::vector rilAndNetmgrLogs + { + "/data/misc/radio/ril_log", + "/data/misc/radio/ril_log_old", + "/data/misc/netmgr/netmgr_log", + "/data/misc/netmgr/netmgr_log_old" + }; + std::string modemLogMkDirCmd= "/system/bin/mkdir " + modemLogAllDir; + RunCommandToFd(fd, "MKDIR MODEM LOG", { "/system/bin/sh", "-c", modemLogMkDirCmd.c_str()}, options); + RunCommandToFd(fd, "SMLOG DUMP", { "smlog_dump", "-d", "-o", modemLogAllDir.c_str() }, options); + for (std::string logFile : rilAndNetmgrLogs) + { + std::string copyCmd= "/system/bin/cp " + logFile + " " + modemLogAllDir; + RunCommandToFd(fd, "MV MODEM LOG", { "/system/bin/sh", "-c", copyCmd.c_str()}, options); + } + std::string filePrefix = android::base::GetProperty(MODEM_LOG_PREFIX_PROPERTY, ""); + if (!filePrefix.empty()) { + std::string modemLogCombined = modemLogDir + "/" + filePrefix + "all.tar"; + std::string modemLogTarCmd= "/system/bin/tar cvf " + modemLogCombined + " -C " + modemLogAllDir + " ."; + RunCommandToFd(fd, "TAR LOG", { "/system/bin/sh", "-c", modemLogTarCmd.c_str()}, options); + std::string modemLogPermCmd= "/system/bin/chmod a+rw " + modemLogCombined; + RunCommandToFd(fd, "CHG PERM", { "/system/bin/sh", "-c", modemLogPermCmd.c_str()}, options); + std::string modemLogClearCmd= "/system/bin/rm -r " + modemLogAllDir; + RunCommandToFd(fd, "RM MODEM DIR", { "/system/bin/sh", "-c", modemLogClearCmd.c_str()}, options); + } + } + } +} + +} // unnamed namespace + + +// Methods from ::android::hardware::dumpstate::V1_0::IDumpstateDevice follow. +Return DumpstateDevice::dumpstateBoard(const hidl_handle& handle) { + if (handle->numFds < 1) { + ALOGE("no FDs\n"); + return Void(); + } + + int fd = handle->data[0]; + if (fd < 0) { + ALOGE("invalid FD: %d\n", handle->data[0]); + return Void(); + } + + getModemLogs(fd); + DumpFileToFd(fd, "CPU present", "/sys/devices/system/cpu/present"); + DumpFileToFd(fd, "CPU online", "/sys/devices/system/cpu/online"); + DumpFileToFd(fd, "INTERRUPTS", "/proc/interrupts"); + DumpFileToFd(fd, "RPM Stats", "/d/rpm_stats"); + DumpFileToFd(fd, "Power Management Stats", "/d/rpm_master_stats"); + DumpFileToFd(fd, "SMD Log", "/d/ipc_logging/smd/log"); + RunCommandToFd(fd, "ION HEAPS", {"/system/bin/sh", "-c", "for d in $(ls -d /d/ion/*); do for f in $(ls $d); do echo --- $d/$f; cat $d/$f; done; done"}); + DumpFileToFd(fd, "dmabuf info", "/d/dma_buf/bufinfo"); + RunCommandToFd(fd, "Temperatures", {"/system/bin/sh", "-c", "for f in `ls /sys/class/thermal` ; do type=`cat /sys/class/thermal/$f/type` ; temp=`cat /sys/class/thermal/$f/temp` ; echo \"$type: $temp\" ; done"}); + DumpFileToFd(fd, "cpu0-1 time-in-state", "/sys/devices/system/cpu/cpu0/cpufreq/stats/time_in_state"); + RunCommandToFd(fd, "cpu0-1 cpuidle", {"/system/bin/sh", "-c", "for d in $(ls -d /sys/devices/system/cpu/cpu0/cpuidle/state*); do echo \"$d: `cat $d/name` `cat $d/desc` `cat $d/time` `cat $d/usage`\"; done"}); + DumpFileToFd(fd, "cpu2-3 time-in-state", "/sys/devices/system/cpu/cpu2/cpufreq/stats/time_in_state"); + RunCommandToFd(fd, "cpu2-3 cpuidle", {"/system/bin/sh", "-c", "for d in $(ls -d /sys/devices/system/cpu/cpu2/cpuidle/state*); do echo \"$d: `cat $d/name` `cat $d/desc` `cat $d/time` `cat $d/usage`\"; done"}); + DumpFileToFd(fd, "MDP xlogs", "/d/mdp/xlog/dump"); + + /* Check if qsee_logger tool exists */ + if (!access("/system/bin/qsee_logger", X_OK)) { + RunCommandToFd(fd, "FP LOGS", {"qsee_logger", "-d"}); + } + + return Void(); +}; + +} // namespace implementation +} // namespace V1_0 +} // namespace dumpstate +} // namespace hardware +} // namespace android diff --git a/dumpstate/DumpstateDevice.h b/dumpstate/DumpstateDevice.h new file mode 100644 index 00000000..9237b3b1 --- /dev/null +++ b/dumpstate/DumpstateDevice.h @@ -0,0 +1,49 @@ +/* + * 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. + */ +#ifndef ANDROID_HARDWARE_DUMPSTATE_V1_0_DUMPSTATEDEVICE_H +#define ANDROID_HARDWARE_DUMPSTATE_V1_0_DUMPSTATEDEVICE_H + +#include +#include +#include + +namespace android { +namespace hardware { +namespace dumpstate { +namespace V1_0 { +namespace implementation { + +using ::android::hardware::dumpstate::V1_0::IDumpstateDevice; +using ::android::hardware::hidl_array; +using ::android::hardware::hidl_handle; +using ::android::hardware::hidl_string; +using ::android::hardware::hidl_vec; +using ::android::hardware::Return; +using ::android::hardware::Void; +using ::android::sp; + +struct DumpstateDevice : public IDumpstateDevice { + // Methods from ::android::hardware::dumpstate::V1_0::IDumpstateDevice follow. + Return dumpstateBoard(const hidl_handle& h) override; +}; + +} // namespace implementation +} // namespace V1_0 +} // namespace dumpstate +} // namespace hardware +} // namespace android + +#endif // ANDROID_HARDWARE_DUMPSTATE_V1_0_DUMPSTATEDEVICE_H diff --git a/dumpstate/android.hardware.dumpstate@1.0-service.wahoo.rc b/dumpstate/android.hardware.dumpstate@1.0-service.wahoo.rc new file mode 100644 index 00000000..924782f0 --- /dev/null +++ b/dumpstate/android.hardware.dumpstate@1.0-service.wahoo.rc @@ -0,0 +1,4 @@ +service dumpstate-1-0 /vendor/bin/hw/android.hardware.dumpstate@1.0-service.wahoo + class hal + user system + group system diff --git a/dumpstate/service.cpp b/dumpstate/service.cpp new file mode 100644 index 00000000..e5091660 --- /dev/null +++ b/dumpstate/service.cpp @@ -0,0 +1,43 @@ +/* + * 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. + */ +#define LOG_TAG "android.hardware.dumpstate@1.0-service.wahoo" + +#include +#include + +#include "DumpstateDevice.h" + +using ::android::hardware::configureRpcThreadpool; +using ::android::hardware::dumpstate::V1_0::IDumpstateDevice; +using ::android::hardware::dumpstate::V1_0::implementation::DumpstateDevice; +using ::android::hardware::joinRpcThreadpool; +using ::android::sp; + + +int main(int /* argc */, char* /* argv */ []) { + sp dumpstate = new DumpstateDevice; + configureRpcThreadpool(1, true); + + android::status_t status = dumpstate->registerAsService(); + + if (status != android::OK) + { + ALOGE("Could not register DumpstateDevice service (%d).", status); + return -1; + } + + joinRpcThreadpool(); +} diff --git a/manifest.xml b/manifest.xml index 2212b5a8..b2e62ec1 100644 --- a/manifest.xml +++ b/manifest.xml @@ -48,6 +48,12 @@ passthrough 1.0 + + + android.hardware.dumpstate + hwbinder + + 1.0 android.hardware.memtrack diff --git a/sepolicy/dumpstate.te b/sepolicy/dumpstate.te new file mode 100644 index 00000000..5047acb9 --- /dev/null +++ b/sepolicy/dumpstate.te @@ -0,0 +1,4 @@ +userdebug_or_eng(` + allow dumpstate smlog_dump_file:dir create_dir_perms; + allow dumpstate smlog_dump_file:file create_file_perms; +') diff --git a/sepolicy/file.te b/sepolicy/file.te index 3e04200d..dc58bfd3 100644 --- a/sepolicy/file.te +++ b/sepolicy/file.te @@ -10,6 +10,9 @@ type sysfs_soc, sysfs_type, fs_type; type debugfs_rmt_storage, debugfs_type, fs_type; type debugfs_kgsl, debugfs_type, fs_type; +type smlog_dump_file, file_type, data_file_type; + + # /proc type proc_wifi_dbg, fs_type; diff --git a/sepolicy/file_contexts b/sepolicy/file_contexts index 4be639c1..49e77abe 100644 --- a/sepolicy/file_contexts +++ b/sepolicy/file_contexts @@ -94,6 +94,7 @@ /system/bin/ramdump u:object_r:ramdump_exec:s0 # files in /vendor +/vendor/bin/hw/android\.hardware\.dumpstate@1\.0-service.wahoo u:object_r:hal_dumpstate_impl_exec:s0 /vendor/bin/perfd u:object_r:perfd_exec:s0 /vendor/bin/thermal-engine u:object_r:thermal-engine_exec:s0 /vendor/bin/sensors.qcom u:object_r:sensors_exec:s0 diff --git a/sepolicy/hal_dumpstate_impl.te b/sepolicy/hal_dumpstate_impl.te new file mode 100644 index 00000000..1455755e --- /dev/null +++ b/sepolicy/hal_dumpstate_impl.te @@ -0,0 +1,32 @@ +type hal_dumpstate_impl, domain; +hal_server_domain(hal_dumpstate_impl, hal_dumpstate) + +type hal_dumpstate_impl_exec, exec_type, file_type; +init_daemon_domain(hal_dumpstate_impl) + +# Execute dump scripts +allow hal_dumpstate_impl shell_exec:file rx_file_perms; +allow hal_dumpstate_impl toolbox_exec:file rx_file_perms; + +# Temp exception :TODO fix via /36736902 +typeattribute hal_dumpstate_impl coredata_in_vendor_violators; + +userdebug_or_eng(` + # smlog_dump + domain_auto_trans(hal_dumpstate_impl, smlog_dump_exec, smlog_dump) + allow hal_dumpstate_impl smlog_dump_file:dir create_dir_perms; + allow hal_dumpstate_impl smlog_dump_file:file create_file_perms; + allow hal_dumpstate_impl radio_data_file:dir r_dir_perms; + allow hal_dumpstate_impl netmgr_data_file:dir r_dir_perms; + allow hal_dumpstate_impl radio_data_file:file r_file_perms; + allow hal_dumpstate_impl netmgr_data_file:file r_file_perms; +') + +allow hal_dumpstate_impl uio_device:chr_file rw_file_perms; +r_dir_file(hal_dumpstate_impl, sysfs_uio) +r_dir_file(hal_dumpstate_impl, sysfs_rmtfs) +r_dir_file(hal_dumpstate_impl, sysfs_msm_subsys) + +# Access to files for dumping +allow hal_dumpstate_impl sysfs:dir r_dir_perms; +# rpm stat diff --git a/sepolicy/rild.te b/sepolicy/rild.te index e556e268..e2ed1af7 100644 --- a/sepolicy/rild.te +++ b/sepolicy/rild.te @@ -15,3 +15,7 @@ allowxperm rild self:socket ioctl msm_sock_ipc_ioctls; # TODO(b/36613472): Remove this once system_server, mediaserver, radio, and bluetooth no longer # communicate with rild over sockets. typeattribute rild socket_between_core_and_vendor_violators; + +userdebug_or_eng(` + domain_auto_trans(rild, smlog_dump_exec, smlog_dump) +') diff --git a/sepolicy/smlog_dump.te b/sepolicy/smlog_dump.te new file mode 100644 index 00000000..7105ca1a --- /dev/null +++ b/sepolicy/smlog_dump.te @@ -0,0 +1,23 @@ +type smlog_dump_exec, exec_type, file_type; + +userdebug_or_eng(` + type smlog_dump, domain; + allow smlog_dump smlog_dump_file:dir r_dir_perms; + allow smlog_dump smlog_dump_file:file create_file_perms; + r_dir_file(smlog_dump, sysfs_uio) + r_dir_file(smlog_dump, sysfs_rmtfs) + + allow smlog_dump diag_device:chr_file rw_file_perms; + allow smlog_dump radio_data_file:file { append read write }; + allow smlog_dump rild:fd use; + allow smlog_dump rild:fifo_file { read write }; + allow smlog_dump rild:unix_stream_socket { read write }; + allow smlog_dump self:socket create_socket_perms; + allowxperm smlog_dump self:socket ioctl msm_sock_ipc_ioctls; + allow smlog_dump sysfs:dir r_dir_perms; + allow smlog_dump sysfs_msm_subsys:dir r_dir_perms; + allow smlog_dump sysfs_msm_subsys:file r_file_perms; + allow smlog_dump sysfs_msm_subsys:lnk_file read; + allow smlog_dump sysfs_soc:dir search; + allow smlog_dump sysfs_soc:file r_file_perms; +')