Loading cmds/dumpstate/dumpstate.cpp +51 −19 Original line number Diff line number Diff line Loading @@ -246,7 +246,7 @@ static const std::string DUMP_NETSTATS_PROTO_TASK = "DUMP NETSTATS PROTO"; static const std::string DUMP_HALS_TASK = "DUMP HALS"; static const std::string DUMP_BOARD_TASK = "dumpstate_board()"; static const std::string DUMP_CHECKINS_TASK = "DUMP CHECKINS"; static const std::string POST_PROCESS_UI_TRACES_TASK = "POST-PROCESS UI TRACES"; static const std::string SERIALIZE_PERFETTO_TRACE_TASK = "SERIALIZE PERFETTO TRACE"; namespace android { namespace os { Loading Loading @@ -1086,11 +1086,11 @@ static void DumpNetstatsProto() { static void MaybeAddSystemTraceToZip() { // This function copies into the .zip the system trace that was snapshotted // by the early call to MaybeSnapshotSystemTrace(), if any background // by the early call to MaybeSnapshotSystemTraceAsync(), if any background // tracing was happening. bool system_trace_exists = access(SYSTEM_TRACE_SNAPSHOT, F_OK) == 0; if (!system_trace_exists) { // No background trace was happening at the time MaybeSnapshotSystemTrace() was invoked. // No background trace was happening at the time MaybeSnapshotSystemTraceAsync() was invoked if (!PropertiesHelper::IsUserBuild()) { MYLOGI( "No system traces found. Check for previously uploaded traces by looking for " Loading Loading @@ -1641,7 +1641,7 @@ Dumpstate::RunStatus Dumpstate::dumpstate() { // Enqueue slow functions into the thread pool, if the parallel run is enabled. std::future<std::string> dump_hals, dump_incident_report, dump_board, dump_checkins, dump_netstats_report, post_process_ui_traces; dump_netstats_report; if (ds.dump_pool_) { // Pool was shutdown in DumpstateDefaultAfterCritical method in order to // drop root user. Restarts it. Loading Loading @@ -3077,8 +3077,9 @@ void Dumpstate::Cancel() { } void Dumpstate::PreDumpUiData() { MaybeSnapshotSystemTrace(); auto snapshot_system_trace = MaybeSnapshotSystemTraceAsync(); MaybeSnapshotUiTraces(); MaybeWaitForSnapshotSystemTrace(std::move(snapshot_system_trace)); } /* Loading Loading @@ -3264,13 +3265,15 @@ Dumpstate::RunStatus Dumpstate::RunInternal(int32_t calling_uid, // duration is logged into MYLOG instead. PrintHeader(); std::future<std::string> snapshot_system_trace; bool is_dumpstate_restricted = options_->telephony_only || options_->wifi_only || options_->limited_only; if (!is_dumpstate_restricted) { // Snapshot the system trace now (if running) to avoid that dumpstate's // own activity pushes out interesting data from the trace ring buffer. // The trace file is added to the zip by MaybeAddSystemTraceToZip(). MaybeSnapshotSystemTrace(); snapshot_system_trace = MaybeSnapshotSystemTraceAsync(); // Invoke critical dumpsys to preserve system state, before doing anything else. RunDumpsysCritical(); Loading @@ -3281,6 +3284,7 @@ Dumpstate::RunStatus Dumpstate::RunInternal(int32_t calling_uid, } MaybeTakeEarlyScreenshot(); MaybeWaitForSnapshotSystemTrace(std::move(snapshot_system_trace)); onUiIntensiveBugreportDumpsFinished(calling_uid); MaybeCheckUserConsent(calling_uid, calling_package); if (options_->telephony_only) { Loading Loading @@ -3376,20 +3380,35 @@ void Dumpstate::MaybeTakeEarlyScreenshot() { TakeScreenshot(); } void Dumpstate::MaybeSnapshotSystemTrace() { std::future<std::string> Dumpstate::MaybeSnapshotSystemTraceAsync() { // When capturing traces via bugreport handler (BH), this function will be invoked twice: // 1) When BH invokes IDumpstate::PreDumpUiData() // 2) When BH invokes IDumpstate::startBugreport(flags = BUGREPORT_USE_PREDUMPED_UI_DATA) // In this case we don't want to re-invoke perfetto in step 2. // In all other standard invocation states, this function is invoked once // without the flag BUGREPORT_USE_PREDUMPED_UI_DATA. // This function must run asynchronously to avoid delaying MaybeTakeEarlyScreenshot() in the // standard invocation states (b/316110955). if (options_->use_predumped_ui_data) { return; return {}; } // Create temporary file for the command's output std::string outPath = ds.bugreport_internal_dir_ + "/tmp_serialize_perfetto_trace"; auto outFd = android::base::unique_fd(TEMP_FAILURE_RETRY( open(outPath.c_str(), O_WRONLY | O_CREAT | O_TRUNC | O_CLOEXEC | O_NOFOLLOW, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH))); if (outFd < 0) { MYLOGE("Could not open %s to serialize perfetto trace.\n", outPath.c_str()); return {}; } // If a stale file exists already, remove it. unlink(SYSTEM_TRACE_SNAPSHOT); MYLOGI("Launching async '%s'", SERIALIZE_PERFETTO_TRACE_TASK.c_str()) return std::async( std::launch::async, [this, outPath = std::move(outPath), outFd = std::move(outFd)] { // If a background system trace is happening and is marked as "suitable for // bugreport" (i.e. bugreport_score > 0 in the trace config), this command // will stop it and serialize into SYSTEM_TRACE_SNAPSHOT. In the (likely) Loading @@ -3397,10 +3416,23 @@ void Dumpstate::MaybeSnapshotSystemTrace() { // Note: this should not be enqueued as we need to freeze the trace before // dumpstate starts. Otherwise the trace ring buffers will contain mostly // the dumpstate's own activity which is irrelevant. RunCommand("SERIALIZE PERFETTO TRACE", {"perfetto", "--save-for-bugreport"}, CommandOptions::WithTimeout(10).DropRoot().CloseAllFileDescriptorsOnExec().Build()); RunCommand( SERIALIZE_PERFETTO_TRACE_TASK, {"perfetto", "--save-for-bugreport"}, CommandOptions::WithTimeout(10).DropRoot().CloseAllFileDescriptorsOnExec().Build(), false, outFd); // MaybeAddSystemTraceToZip() will take care of copying the trace in the zip // file in the later stages. return outPath; }); } void Dumpstate::MaybeWaitForSnapshotSystemTrace(std::future<std::string> task) { if (!task.valid()) { return; } WaitForTask(std::move(task), SERIALIZE_PERFETTO_TRACE_TASK, STDOUT_FILENO); } void Dumpstate::MaybeSnapshotUiTraces() { Loading cmds/dumpstate/dumpstate.h +2 −1 Original line number Diff line number Diff line Loading @@ -567,7 +567,8 @@ class Dumpstate { RunStatus dumpstate(); void MaybeTakeEarlyScreenshot(); void MaybeSnapshotSystemTrace(); std::future<std::string> MaybeSnapshotSystemTraceAsync(); void MaybeWaitForSnapshotSystemTrace(std::future<std::string> task); void MaybeSnapshotUiTraces(); void MaybeAddUiTracesToZip(); Loading include/input/InputTransport.h +14 −0 Original line number Diff line number Diff line Loading @@ -283,6 +283,13 @@ public: */ status_t receiveMessage(InputMessage* msg); /* Tells whether there is a message in the channel available to be received. * * This is only a performance hint and may return false negative results. Clients should not * rely on availability of the message based on the return value. */ bool probablyHasInput() const; /* Return a new object that has a duplicate of this channel's fd. */ std::unique_ptr<InputChannel> dup() const; Loading Loading @@ -518,6 +525,13 @@ public: */ int32_t getPendingBatchSource() const; /* Returns true when there is *likely* a pending batch or a pending event in the channel. * * This is only a performance hint and may return false negative results. Clients should not * rely on availability of the message based on the return value. */ bool probablyHasInput() const; std::string dump() const; private: Loading libs/binder/ndk/include_cpp/android/persistable_bundle_aidl.h +38 −20 Original line number Diff line number Diff line Loading @@ -31,7 +31,11 @@ namespace aidl::android::os { */ class PersistableBundle { public: PersistableBundle() noexcept : mPBundle(APersistableBundle_new()) {} PersistableBundle() noexcept { if (__builtin_available(android __ANDROID_API_V__, *)) { mPBundle = APersistableBundle_new(); } } // takes ownership of the APersistableBundle* PersistableBundle(APersistableBundle* _Nonnull bundle) noexcept : mPBundle(bundle) {} // takes ownership of the APersistableBundle* Loading @@ -57,7 +61,7 @@ class PersistableBundle { if (__builtin_available(android __ANDROID_API_V__, *)) { return APersistableBundle_readFromParcel(parcel, &mPBundle); } else { return STATUS_FAILED_TRANSACTION; return STATUS_INVALID_OPERATION; } } Loading @@ -68,7 +72,7 @@ class PersistableBundle { if (__builtin_available(android __ANDROID_API_V__, *)) { return APersistableBundle_writeToParcel(mPBundle, parcel); } else { return STATUS_FAILED_TRANSACTION; return STATUS_INVALID_OPERATION; } } Loading Loading @@ -327,20 +331,32 @@ class PersistableBundle { } bool getBooleanVector(const std::string& key, std::vector<bool>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<bool>(&APersistableBundle_getBooleanVector, mPBundle, key.c_str(), vec); } return false; } bool getIntVector(const std::string& key, std::vector<int32_t>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<int32_t>(&APersistableBundle_getIntVector, mPBundle, key.c_str(), vec); } return false; } bool getLongVector(const std::string& key, std::vector<int64_t>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<int64_t>(&APersistableBundle_getLongVector, mPBundle, key.c_str(), vec); } return false; } bool getDoubleVector(const std::string& key, std::vector<double>* _Nonnull vec) { return getVecInternal<double>(&APersistableBundle_getDoubleVector, mPBundle, key.c_str(), vec); if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<double>(&APersistableBundle_getDoubleVector, mPBundle, key.c_str(), vec); } return false; } // Takes ownership of and frees the char** and its elements. Loading @@ -361,17 +377,19 @@ class PersistableBundle { } bool getStringVector(const std::string& key, std::vector<std::string>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { int32_t bytes = APersistableBundle_getStringVector(mPBundle, key.c_str(), nullptr, 0, &stringAllocator, nullptr); if (bytes > 0) { char** strings = (char**)malloc(bytes); if (strings) { bytes = APersistableBundle_getStringVector(mPBundle, key.c_str(), strings, bytes, &stringAllocator, nullptr); bytes = APersistableBundle_getStringVector(mPBundle, key.c_str(), strings, bytes, &stringAllocator, nullptr); *vec = moveStringsInternal<std::vector<std::string>>(strings, bytes); return true; } } } return false; } Loading libs/binder/ndk/stability.cpp +1 −1 Original line number Diff line number Diff line Loading @@ -27,7 +27,7 @@ using ::android::internal::Stability; #error libbinder_ndk should only be built in a system context #endif #ifdef __ANDROID_VENDOR__ #if defined(__ANDROID_VENDOR__) && !defined(__TRUSTY__) #error libbinder_ndk should only be built in a system context #endif Loading Loading
cmds/dumpstate/dumpstate.cpp +51 −19 Original line number Diff line number Diff line Loading @@ -246,7 +246,7 @@ static const std::string DUMP_NETSTATS_PROTO_TASK = "DUMP NETSTATS PROTO"; static const std::string DUMP_HALS_TASK = "DUMP HALS"; static const std::string DUMP_BOARD_TASK = "dumpstate_board()"; static const std::string DUMP_CHECKINS_TASK = "DUMP CHECKINS"; static const std::string POST_PROCESS_UI_TRACES_TASK = "POST-PROCESS UI TRACES"; static const std::string SERIALIZE_PERFETTO_TRACE_TASK = "SERIALIZE PERFETTO TRACE"; namespace android { namespace os { Loading Loading @@ -1086,11 +1086,11 @@ static void DumpNetstatsProto() { static void MaybeAddSystemTraceToZip() { // This function copies into the .zip the system trace that was snapshotted // by the early call to MaybeSnapshotSystemTrace(), if any background // by the early call to MaybeSnapshotSystemTraceAsync(), if any background // tracing was happening. bool system_trace_exists = access(SYSTEM_TRACE_SNAPSHOT, F_OK) == 0; if (!system_trace_exists) { // No background trace was happening at the time MaybeSnapshotSystemTrace() was invoked. // No background trace was happening at the time MaybeSnapshotSystemTraceAsync() was invoked if (!PropertiesHelper::IsUserBuild()) { MYLOGI( "No system traces found. Check for previously uploaded traces by looking for " Loading Loading @@ -1641,7 +1641,7 @@ Dumpstate::RunStatus Dumpstate::dumpstate() { // Enqueue slow functions into the thread pool, if the parallel run is enabled. std::future<std::string> dump_hals, dump_incident_report, dump_board, dump_checkins, dump_netstats_report, post_process_ui_traces; dump_netstats_report; if (ds.dump_pool_) { // Pool was shutdown in DumpstateDefaultAfterCritical method in order to // drop root user. Restarts it. Loading Loading @@ -3077,8 +3077,9 @@ void Dumpstate::Cancel() { } void Dumpstate::PreDumpUiData() { MaybeSnapshotSystemTrace(); auto snapshot_system_trace = MaybeSnapshotSystemTraceAsync(); MaybeSnapshotUiTraces(); MaybeWaitForSnapshotSystemTrace(std::move(snapshot_system_trace)); } /* Loading Loading @@ -3264,13 +3265,15 @@ Dumpstate::RunStatus Dumpstate::RunInternal(int32_t calling_uid, // duration is logged into MYLOG instead. PrintHeader(); std::future<std::string> snapshot_system_trace; bool is_dumpstate_restricted = options_->telephony_only || options_->wifi_only || options_->limited_only; if (!is_dumpstate_restricted) { // Snapshot the system trace now (if running) to avoid that dumpstate's // own activity pushes out interesting data from the trace ring buffer. // The trace file is added to the zip by MaybeAddSystemTraceToZip(). MaybeSnapshotSystemTrace(); snapshot_system_trace = MaybeSnapshotSystemTraceAsync(); // Invoke critical dumpsys to preserve system state, before doing anything else. RunDumpsysCritical(); Loading @@ -3281,6 +3284,7 @@ Dumpstate::RunStatus Dumpstate::RunInternal(int32_t calling_uid, } MaybeTakeEarlyScreenshot(); MaybeWaitForSnapshotSystemTrace(std::move(snapshot_system_trace)); onUiIntensiveBugreportDumpsFinished(calling_uid); MaybeCheckUserConsent(calling_uid, calling_package); if (options_->telephony_only) { Loading Loading @@ -3376,20 +3380,35 @@ void Dumpstate::MaybeTakeEarlyScreenshot() { TakeScreenshot(); } void Dumpstate::MaybeSnapshotSystemTrace() { std::future<std::string> Dumpstate::MaybeSnapshotSystemTraceAsync() { // When capturing traces via bugreport handler (BH), this function will be invoked twice: // 1) When BH invokes IDumpstate::PreDumpUiData() // 2) When BH invokes IDumpstate::startBugreport(flags = BUGREPORT_USE_PREDUMPED_UI_DATA) // In this case we don't want to re-invoke perfetto in step 2. // In all other standard invocation states, this function is invoked once // without the flag BUGREPORT_USE_PREDUMPED_UI_DATA. // This function must run asynchronously to avoid delaying MaybeTakeEarlyScreenshot() in the // standard invocation states (b/316110955). if (options_->use_predumped_ui_data) { return; return {}; } // Create temporary file for the command's output std::string outPath = ds.bugreport_internal_dir_ + "/tmp_serialize_perfetto_trace"; auto outFd = android::base::unique_fd(TEMP_FAILURE_RETRY( open(outPath.c_str(), O_WRONLY | O_CREAT | O_TRUNC | O_CLOEXEC | O_NOFOLLOW, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH))); if (outFd < 0) { MYLOGE("Could not open %s to serialize perfetto trace.\n", outPath.c_str()); return {}; } // If a stale file exists already, remove it. unlink(SYSTEM_TRACE_SNAPSHOT); MYLOGI("Launching async '%s'", SERIALIZE_PERFETTO_TRACE_TASK.c_str()) return std::async( std::launch::async, [this, outPath = std::move(outPath), outFd = std::move(outFd)] { // If a background system trace is happening and is marked as "suitable for // bugreport" (i.e. bugreport_score > 0 in the trace config), this command // will stop it and serialize into SYSTEM_TRACE_SNAPSHOT. In the (likely) Loading @@ -3397,10 +3416,23 @@ void Dumpstate::MaybeSnapshotSystemTrace() { // Note: this should not be enqueued as we need to freeze the trace before // dumpstate starts. Otherwise the trace ring buffers will contain mostly // the dumpstate's own activity which is irrelevant. RunCommand("SERIALIZE PERFETTO TRACE", {"perfetto", "--save-for-bugreport"}, CommandOptions::WithTimeout(10).DropRoot().CloseAllFileDescriptorsOnExec().Build()); RunCommand( SERIALIZE_PERFETTO_TRACE_TASK, {"perfetto", "--save-for-bugreport"}, CommandOptions::WithTimeout(10).DropRoot().CloseAllFileDescriptorsOnExec().Build(), false, outFd); // MaybeAddSystemTraceToZip() will take care of copying the trace in the zip // file in the later stages. return outPath; }); } void Dumpstate::MaybeWaitForSnapshotSystemTrace(std::future<std::string> task) { if (!task.valid()) { return; } WaitForTask(std::move(task), SERIALIZE_PERFETTO_TRACE_TASK, STDOUT_FILENO); } void Dumpstate::MaybeSnapshotUiTraces() { Loading
cmds/dumpstate/dumpstate.h +2 −1 Original line number Diff line number Diff line Loading @@ -567,7 +567,8 @@ class Dumpstate { RunStatus dumpstate(); void MaybeTakeEarlyScreenshot(); void MaybeSnapshotSystemTrace(); std::future<std::string> MaybeSnapshotSystemTraceAsync(); void MaybeWaitForSnapshotSystemTrace(std::future<std::string> task); void MaybeSnapshotUiTraces(); void MaybeAddUiTracesToZip(); Loading
include/input/InputTransport.h +14 −0 Original line number Diff line number Diff line Loading @@ -283,6 +283,13 @@ public: */ status_t receiveMessage(InputMessage* msg); /* Tells whether there is a message in the channel available to be received. * * This is only a performance hint and may return false negative results. Clients should not * rely on availability of the message based on the return value. */ bool probablyHasInput() const; /* Return a new object that has a duplicate of this channel's fd. */ std::unique_ptr<InputChannel> dup() const; Loading Loading @@ -518,6 +525,13 @@ public: */ int32_t getPendingBatchSource() const; /* Returns true when there is *likely* a pending batch or a pending event in the channel. * * This is only a performance hint and may return false negative results. Clients should not * rely on availability of the message based on the return value. */ bool probablyHasInput() const; std::string dump() const; private: Loading
libs/binder/ndk/include_cpp/android/persistable_bundle_aidl.h +38 −20 Original line number Diff line number Diff line Loading @@ -31,7 +31,11 @@ namespace aidl::android::os { */ class PersistableBundle { public: PersistableBundle() noexcept : mPBundle(APersistableBundle_new()) {} PersistableBundle() noexcept { if (__builtin_available(android __ANDROID_API_V__, *)) { mPBundle = APersistableBundle_new(); } } // takes ownership of the APersistableBundle* PersistableBundle(APersistableBundle* _Nonnull bundle) noexcept : mPBundle(bundle) {} // takes ownership of the APersistableBundle* Loading @@ -57,7 +61,7 @@ class PersistableBundle { if (__builtin_available(android __ANDROID_API_V__, *)) { return APersistableBundle_readFromParcel(parcel, &mPBundle); } else { return STATUS_FAILED_TRANSACTION; return STATUS_INVALID_OPERATION; } } Loading @@ -68,7 +72,7 @@ class PersistableBundle { if (__builtin_available(android __ANDROID_API_V__, *)) { return APersistableBundle_writeToParcel(mPBundle, parcel); } else { return STATUS_FAILED_TRANSACTION; return STATUS_INVALID_OPERATION; } } Loading Loading @@ -327,20 +331,32 @@ class PersistableBundle { } bool getBooleanVector(const std::string& key, std::vector<bool>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<bool>(&APersistableBundle_getBooleanVector, mPBundle, key.c_str(), vec); } return false; } bool getIntVector(const std::string& key, std::vector<int32_t>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<int32_t>(&APersistableBundle_getIntVector, mPBundle, key.c_str(), vec); } return false; } bool getLongVector(const std::string& key, std::vector<int64_t>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<int64_t>(&APersistableBundle_getLongVector, mPBundle, key.c_str(), vec); } return false; } bool getDoubleVector(const std::string& key, std::vector<double>* _Nonnull vec) { return getVecInternal<double>(&APersistableBundle_getDoubleVector, mPBundle, key.c_str(), vec); if (__builtin_available(android __ANDROID_API_V__, *)) { return getVecInternal<double>(&APersistableBundle_getDoubleVector, mPBundle, key.c_str(), vec); } return false; } // Takes ownership of and frees the char** and its elements. Loading @@ -361,17 +377,19 @@ class PersistableBundle { } bool getStringVector(const std::string& key, std::vector<std::string>* _Nonnull vec) { if (__builtin_available(android __ANDROID_API_V__, *)) { int32_t bytes = APersistableBundle_getStringVector(mPBundle, key.c_str(), nullptr, 0, &stringAllocator, nullptr); if (bytes > 0) { char** strings = (char**)malloc(bytes); if (strings) { bytes = APersistableBundle_getStringVector(mPBundle, key.c_str(), strings, bytes, &stringAllocator, nullptr); bytes = APersistableBundle_getStringVector(mPBundle, key.c_str(), strings, bytes, &stringAllocator, nullptr); *vec = moveStringsInternal<std::vector<std::string>>(strings, bytes); return true; } } } return false; } Loading
libs/binder/ndk/stability.cpp +1 −1 Original line number Diff line number Diff line Loading @@ -27,7 +27,7 @@ using ::android::internal::Stability; #error libbinder_ndk should only be built in a system context #endif #ifdef __ANDROID_VENDOR__ #if defined(__ANDROID_VENDOR__) && !defined(__TRUSTY__) #error libbinder_ndk should only be built in a system context #endif Loading