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

Commit d1371a8b authored by Mark Salyzyn's avatar Mark Salyzyn Committed by Gerrit Code Review
Browse files

Merge "logd: Add TID statistics"

parents 0c6c4150 17ed6797
Loading
Loading
Loading
Loading
+3 −3
Original line number Diff line number Diff line
@@ -58,7 +58,7 @@ uint32_t LogBufferElement::getTag() const {
}

// caller must own and free character string
static char *tidToName(pid_t tid) {
char *android::tidToName(pid_t tid) {
    char *retval = NULL;
    char buffer[256];
    snprintf(buffer, sizeof(buffer), "/proc/%u/comm", tid);
@@ -108,9 +108,9 @@ size_t LogBufferElement::populateDroppedMessage(char *&buffer,
    static const char format_uid[] = "uid=%u%s too chatty%s, expire %u line%s";

    char *name = parent->uidToName(mUid);
    char *commName = tidToName(mTid);
    char *commName = android::tidToName(mTid);
    if (!commName && (mTid != mPid)) {
        commName = tidToName(mPid);
        commName = android::tidToName(mPid);
    }
    if (!commName) {
        commName = parent->pidToName(mPid);
+1 −0
Original line number Diff line number Diff line
@@ -35,6 +35,7 @@ char *uidToName(uid_t uid);

// Furnished in LogStatistics.cpp. Caller must own and free returned value
char *pidToName(pid_t pid);
char *tidToName(pid_t tid);

// Furnished in main.cpp. Thread safe.
const char *tagToName(uint32_t tag);
+60 −0
Original line number Diff line number Diff line
@@ -83,6 +83,7 @@ void LogStatistics::add(LogBufferElement *e) {
    }

    pidTable.add(e->getPid(), e);
    tidTable.add(e->getTid(), e);

    uint32_t tag = e->getTag();
    if (tag) {
@@ -107,6 +108,7 @@ void LogStatistics::subtract(LogBufferElement *e) {
    }

    pidTable.subtract(e->getPid(), e);
    tidTable.subtract(e->getTid(), e);

    uint32_t tag = e->getTag();
    if (tag) {
@@ -128,6 +130,7 @@ void LogStatistics::drop(LogBufferElement *e) {
    }

    pidTable.drop(e->getPid(), e);
    tidTable.drop(e->getTid(), e);
}

// caller must own and free character string
@@ -390,6 +393,63 @@ void LogStatistics::format(char **buf, uid_t uid, unsigned int logMask) {
        }
    }

    if (enable) {
        // Tid table
        bool headerPrinted = false;
        // sort() returns list of references, unique_ptr makes sure self-delete
        std::unique_ptr<const TidEntry *[]> sorted = tidTable.sort(maximum_sorted_entries);
        ssize_t index = -1;
        while ((index = tidTable.next(index, sorted, maximum_sorted_entries)) >= 0) {
            const TidEntry *entry = sorted[index];
            uid_t u = entry->getUid();
            if ((uid != AID_ROOT) && (u != uid)) {
                continue;
            }

            if (!headerPrinted) { // Only print header if we have table to print
                output.appendFormat("\n\n");
                android::String8 name("Chattiest TIDs:");
                android::String8 size("Size");
                android::String8 pruned("Pruned");
                format_line(output, name, size, pruned);

                name.setTo("  TID/UID   COMM");
                size.setTo("BYTES");
                pruned.setTo("LINES");
                format_line(output, name, size, pruned);

                headerPrinted = true;
            }

            android::String8 name("");
            name.appendFormat("%5u/%u", entry->getKey(), u);
            const char *n = entry->getName();
            if (n) {
                name.appendFormat("%*s%s", (int)std::max(12 - name.length(), (size_t)1), "", n);
            } else {
                // if we do not have a PID name, lets punt to try UID name?
                char *un = uidToName(u);
                if (un) {
                    name.appendFormat("%*s%s", (int)std::max(12 - name.length(), (size_t)1), "", un);
                    free(un);
                }
                // We tried, better to not have a name at all, we still
                // have TID/UID by number to report in any case.
            }

            android::String8 size("");
            size.appendFormat("%zu", entry->getSizes());

            android::String8 pruned("");
            size_t dropped = entry->getDropped();
            if (dropped) {
                pruned.appendFormat("%zu", dropped);
            }

            format_line(output, name, size, pruned);
        }
    }

    if (enable && (logMask & (1 << LOG_ID_EVENTS))) {
        // Tag table
        bool headerPrinted = false;
+56 −0
Original line number Diff line number Diff line
@@ -209,6 +209,58 @@ struct PidEntry : public EntryBaseDropped {
    }
};

struct TidEntry : public EntryBaseDropped {
    const pid_t tid;
    uid_t uid;
    char *name;

    TidEntry(pid_t t):
        EntryBaseDropped(),
        tid(t),
        uid(android::pidToUid(t)),
        name(android::tidToName(tid)) { }
    TidEntry(LogBufferElement *e):
        EntryBaseDropped(e),
        tid(e->getTid()),
        uid(e->getUid()),
        name(android::tidToName(e->getTid())) { }
    TidEntry(const TidEntry &c):
        EntryBaseDropped(c),
        tid(c.tid),
        uid(c.uid),
        name(c.name ? strdup(c.name) : NULL) { }
    ~TidEntry() { free(name); }

    const pid_t&getKey() const { return tid; }
    const uid_t&getUid() const { return uid; }
    const char*getName() const { return name; }

    inline void add(pid_t t) {
        if (name && !strncmp(name, "zygote", 6)) {
            free(name);
            name = NULL;
        }
        if (!name) {
            char *n = android::tidToName(t);
            if (n) {
                name = n;
            }
        }
    }

    inline void add(LogBufferElement *e) {
        uid_t u = e->getUid();
        if (getUid() != u) {
            uid = u;
            free(name);
            name = android::tidToName(e->getTid());
        } else {
            add(e->getTid());
        }
        EntryBaseDropped::add(e);
    }
};

struct TagEntry : public EntryBase {
    const uint32_t tag;
    uid_t uid;
@@ -247,6 +299,10 @@ class LogStatistics {
    typedef LogHashtable<pid_t, PidEntry> pidTable_t;
    pidTable_t pidTable;

    // tid to uid list
    typedef LogHashtable<pid_t, TidEntry> tidTable_t;
    tidTable_t tidTable;

    // tag list
    typedef LogHashtable<uint32_t, TagEntry> tagTable_t;
    tagTable_t tagTable;