Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit fb2db193 authored by Ioannis Ilkos's avatar Ioannis Ilkos Committed by Automerger Merge Worker
Browse files

Merge "Per process DMA-BUF stats" into sc-dev am: 50d4ba03

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/13988962

Change-Id: Iabb28779cd1a79c60fcf2f0c45b151a5ea0de148
parents a6538d7b 50d4ba03
Loading
Loading
Loading
Loading
+51 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2021 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.
 */

package com.android.internal.os;

import android.annotation.Nullable;

/** Wrapper around libdmabufinfo. */
public final class DmabufInfoReader {
    private DmabufInfoReader() {}

    /** Process dma-buf stats. */
    public static final class ProcessDmabuf {
        /** Size of buffers retained by the process. */
        public final int retainedSizeKb;
        /** Number of buffers retained by the process. */
        public final int retainedBuffersCount;
        /** Size of buffers mapped to the address space. */
        public final int mappedSizeKb;
        /** Count of buffers mapped to the address space. */
        public final int mappedBuffersCount;

        ProcessDmabuf(int retainedSizeKb, int retainedBuffersCount,
                int mappedSizeKb, int mappedBuffersCount) {
            this.retainedSizeKb = retainedSizeKb;
            this.retainedBuffersCount = retainedBuffersCount;
            this.mappedSizeKb = mappedSizeKb;
            this.mappedBuffersCount = mappedBuffersCount;
        }
    }

    /**
     * Return stats for DMA-BUFs retained by process pid or null if the DMA-BUF
     * stats could not be read.
     */
    @Nullable
    public static native ProcessDmabuf getProcessStats(int pid);
}
+1 −0
Original line number Diff line number Diff line
@@ -202,6 +202,7 @@ cc_library_shared {
                "com_android_internal_content_om_OverlayConfig.cpp",
                "com_android_internal_net_NetworkUtilsInternal.cpp",
                "com_android_internal_os_ClassLoaderFactory.cpp",
                "com_android_internal_os_DmabufInfoReader.cpp",
                "com_android_internal_os_FuseAppLoop.cpp",
                "com_android_internal_os_KernelCpuBpfTracking.cpp",
                "com_android_internal_os_KernelCpuTotalBpfMapReader.cpp",
+2 −0
Original line number Diff line number Diff line
@@ -191,6 +191,7 @@ extern int register_com_android_internal_content_NativeLibraryHelper(JNIEnv *env
extern int register_com_android_internal_content_om_OverlayConfig(JNIEnv *env);
extern int register_com_android_internal_net_NetworkUtilsInternal(JNIEnv* env);
extern int register_com_android_internal_os_ClassLoaderFactory(JNIEnv* env);
extern int register_com_android_internal_os_DmabufInfoReader(JNIEnv* env);
extern int register_com_android_internal_os_FuseAppLoop(JNIEnv* env);
extern int register_com_android_internal_os_KernelCpuBpfTracking(JNIEnv* env);
extern int register_com_android_internal_os_KernelCpuTotalBpfMapReader(JNIEnv* env);
@@ -1616,6 +1617,7 @@ static const RegJNIRec gRegJNI[] = {
        REG_JNI(register_android_animation_PropertyValuesHolder),
        REG_JNI(register_android_security_Scrypt),
        REG_JNI(register_com_android_internal_content_NativeLibraryHelper),
        REG_JNI(register_com_android_internal_os_DmabufInfoReader),
        REG_JNI(register_com_android_internal_os_FuseAppLoop),
        REG_JNI(register_com_android_internal_os_KernelCpuBpfTracking),
        REG_JNI(register_com_android_internal_os_KernelCpuTotalBpfMapReader),
+60 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2021 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.
 */

#include <dmabufinfo/dmabufinfo.h>
#include "core_jni_helpers.h"

namespace android {

static jobject DmabufInfoReader_getProcessStats(JNIEnv *env, jobject, jint pid) {
    std::vector<dmabufinfo::DmaBuffer> buffers;
    if (!dmabufinfo::ReadDmaBufMapRefs(pid, &buffers)) {
        return nullptr;
    }
    jint mappedSize = 0;
    jint mappedCount = buffers.size();
    for (const auto &buffer : buffers) {
        mappedSize += buffer.size();
    }
    mappedSize /= 1024;

    jint retainedSize = -1;
    jint retainedCount = -1;
    if (dmabufinfo::ReadDmaBufFdRefs(pid, &buffers)) {
        retainedCount = buffers.size();
        retainedSize = 0;
        for (const auto &buffer : buffers) {
            retainedSize += buffer.size();
        }
        retainedSize /= 1024;
    }

    jclass clazz = FindClassOrDie(env, "com/android/internal/os/DmabufInfoReader$ProcessDmabuf");
    jmethodID constructID = GetMethodIDOrDie(env, clazz, "<init>", "(IIII)V");
    return env->NewObject(clazz, constructID, retainedSize, retainedCount, mappedSize, mappedCount);
}

static const JNINativeMethod methods[] = {
        {"getProcessStats", "(I)Lcom/android/internal/os/DmabufInfoReader$ProcessDmabuf;",
         (void *)DmabufInfoReader_getProcessStats},
};

int register_com_android_internal_os_DmabufInfoReader(JNIEnv *env) {
    return RegisterMethodsOrDie(env, "com/android/internal/os/DmabufInfoReader", methods,
                                NELEM(methods));
}

} // namespace android
+43 −0
Original line number Diff line number Diff line
@@ -111,6 +111,7 @@ import android.os.IThermalService;
import android.os.OutcomeReceiver;
import android.os.ParcelFileDescriptor;
import android.os.Parcelable;
import android.os.Process;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.os.StatFs;
@@ -148,6 +149,7 @@ import com.android.internal.os.BackgroundThread;
import com.android.internal.os.BatterySipper;
import com.android.internal.os.BatteryStatsHelper;
import com.android.internal.os.BinderCallsStats.ExportedCallStat;
import com.android.internal.os.DmabufInfoReader;
import com.android.internal.os.KernelCpuBpfTracking;
import com.android.internal.os.KernelCpuThreadReader;
import com.android.internal.os.KernelCpuThreadReaderDiff;
@@ -198,6 +200,7 @@ import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
@@ -528,6 +531,8 @@ public class StatsPullAtomService extends SystemService {
                        synchronized (mProcessSystemIonHeapSizeLock) {
                            return pullProcessSystemIonHeapSizeLocked(atomTag, data);
                        }
                    case FrameworkStatsLog.PROCESS_DMABUF_MEMORY:
                        return pullProcessDmabufMemory(atomTag, data);
                    case FrameworkStatsLog.SYSTEM_MEMORY:
                        return pullSystemMemory(atomTag, data);
                    case FrameworkStatsLog.TEMPERATURE:
@@ -818,6 +823,7 @@ public class StatsPullAtomService extends SystemService {
        registerIonHeapSize();
        registerProcessSystemIonHeapSize();
        registerSystemMemory();
        registerProcessDmabufMemory();
        registerTemperature();
        registerCoolingDevice();
        registerBinderCallsStats();
@@ -2183,6 +2189,43 @@ public class StatsPullAtomService extends SystemService {
        return StatsManager.PULL_SUCCESS;
    }

    private void registerProcessDmabufMemory() {
        int tagId = FrameworkStatsLog.PROCESS_DMABUF_MEMORY;
        mStatsManager.setPullAtomCallback(
                tagId,
                null, // use default PullAtomMetadata values
                DIRECT_EXECUTOR,
                mStatsCallbackImpl
        );
    }

    int pullProcessDmabufMemory(int atomTag, List<StatsEvent> pulledData) {
        List<ProcessMemoryState> managedProcessList =
                LocalServices.getService(ActivityManagerInternal.class)
                        .getMemoryStateForProcesses();
        managedProcessList.sort(Comparator.comparingInt(x -> x.oomScore));
        for (ProcessMemoryState process : managedProcessList) {
            if (process.uid == Process.SYSTEM_UID) {
                continue;
            }
            DmabufInfoReader.ProcessDmabuf proc = DmabufInfoReader.getProcessStats(process.pid);
            if (proc == null || (proc.retainedBuffersCount <= 0 && proc.mappedBuffersCount <= 0)) {
                continue;
            }
            pulledData.add(
                    FrameworkStatsLog.buildStatsEvent(
                            atomTag,
                            process.uid,
                            process.processName,
                            process.oomScore,
                            proc.retainedSizeKb,
                            proc.retainedBuffersCount,
                            proc.mappedSizeKb,
                            proc.mappedBuffersCount));
        }
        return StatsManager.PULL_SUCCESS;
    }

    private void registerSystemMemory() {
        int tagId = FrameworkStatsLog.SYSTEM_MEMORY;
        mStatsManager.setPullAtomCallback(