Merge "logd: statistics per-pid filter"
am: f2e88777fb
* commit 'f2e88777fb7d82dc788dc3a5f6b6b3b8e84c2139':
logd: statistics per-pid filter
This commit is contained in:
commit
e39a969808
6 changed files with 103 additions and 34 deletions
|
|
@ -501,6 +501,14 @@ ssize_t android_logger_get_statistics(struct logger_list *logger_list,
|
||||||
remaining -= n;
|
remaining -= n;
|
||||||
cp += n;
|
cp += n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (logger_list->pid) {
|
||||||
|
n = snprintf(cp, remaining, " pid=%u", logger_list->pid);
|
||||||
|
n = min(n, remaining);
|
||||||
|
remaining -= n;
|
||||||
|
cp += n;
|
||||||
|
}
|
||||||
|
|
||||||
return send_log_msg(NULL, NULL, buf, len);
|
return send_log_msg(NULL, NULL, buf, len);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -210,9 +210,20 @@ int CommandListener::GetStatisticsCmd::runCommand(SocketClient *cli,
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int logMask = -1;
|
unsigned int logMask = -1;
|
||||||
|
pid_t pid = 0;
|
||||||
if (argc > 1) {
|
if (argc > 1) {
|
||||||
logMask = 0;
|
logMask = 0;
|
||||||
for (int i = 1; i < argc; ++i) {
|
for (int i = 1; i < argc; ++i) {
|
||||||
|
static const char _pid[] = "pid=";
|
||||||
|
if (!strncmp(argv[i], _pid, sizeof(_pid) - 1)) {
|
||||||
|
pid = atol(argv[i] + sizeof(_pid) - 1);
|
||||||
|
if (pid == 0) {
|
||||||
|
cli->sendMsg("PID Error");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
int id = atoi(argv[i]);
|
int id = atoi(argv[i]);
|
||||||
if ((id < LOG_ID_MIN) || (LOG_ID_MAX <= id)) {
|
if ((id < LOG_ID_MIN) || (LOG_ID_MAX <= id)) {
|
||||||
cli->sendMsg("Range Error");
|
cli->sendMsg("Range Error");
|
||||||
|
|
@ -222,7 +233,8 @@ int CommandListener::GetStatisticsCmd::runCommand(SocketClient *cli,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
cli->sendMsg(package_string(mBuf.formatStatistics(uid, logMask)).c_str());
|
cli->sendMsg(package_string(mBuf.formatStatistics(uid, pid,
|
||||||
|
logMask)).c_str());
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -499,7 +499,8 @@ bool LogBuffer::prune(log_id_t id, unsigned long pruneRows, uid_t caller_uid) {
|
||||||
size_t second_worst_sizes = 0;
|
size_t second_worst_sizes = 0;
|
||||||
|
|
||||||
if (worstUidEnabledForLogid(id) && mPrune.worstUidEnabled()) {
|
if (worstUidEnabledForLogid(id) && mPrune.worstUidEnabled()) {
|
||||||
std::unique_ptr<const UidEntry *[]> sorted = stats.sort(2, id);
|
std::unique_ptr<const UidEntry *[]> sorted = stats.sort(
|
||||||
|
AID_ROOT, (pid_t)0, 2, id);
|
||||||
|
|
||||||
if (sorted.get()) {
|
if (sorted.get()) {
|
||||||
if (sorted[0] && sorted[1]) {
|
if (sorted[0] && sorted[1]) {
|
||||||
|
|
@ -866,10 +867,11 @@ uint64_t LogBuffer::flushTo(
|
||||||
return max;
|
return max;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string LogBuffer::formatStatistics(uid_t uid, unsigned int logMask) {
|
std::string LogBuffer::formatStatistics(uid_t uid, pid_t pid,
|
||||||
|
unsigned int logMask) {
|
||||||
pthread_mutex_lock(&mLogElementsLock);
|
pthread_mutex_lock(&mLogElementsLock);
|
||||||
|
|
||||||
std::string ret = stats.format(uid, logMask);
|
std::string ret = stats.format(uid, pid, logMask);
|
||||||
|
|
||||||
pthread_mutex_unlock(&mLogElementsLock);
|
pthread_mutex_unlock(&mLogElementsLock);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -86,7 +86,7 @@ public:
|
||||||
int setSize(log_id_t id, unsigned long size);
|
int setSize(log_id_t id, unsigned long size);
|
||||||
unsigned long getSizeUsed(log_id_t id);
|
unsigned long getSizeUsed(log_id_t id);
|
||||||
// *strp uses malloc, use free to release.
|
// *strp uses malloc, use free to release.
|
||||||
std::string formatStatistics(uid_t uid, unsigned int logMask);
|
std::string formatStatistics(uid_t uid, pid_t pid, unsigned int logMask);
|
||||||
|
|
||||||
void enableStatistics() {
|
void enableStatistics() {
|
||||||
stats.enableStatistics();
|
stats.enableStatistics();
|
||||||
|
|
|
||||||
|
|
@ -205,7 +205,7 @@ std::string UidEntry::formatHeader(const std::string &name, log_id_t id) const {
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string UidEntry::format(const LogStatistics &stat, log_id_t id) const {
|
std::string UidEntry::format(const LogStatistics &stat, log_id_t id) const {
|
||||||
uid_t uid = getKey();
|
uid_t uid = getUid();
|
||||||
std::string name = android::base::StringPrintf("%u", uid);
|
std::string name = android::base::StringPrintf("%u", uid);
|
||||||
const char *nameTmp = stat.uidToName(uid);
|
const char *nameTmp = stat.uidToName(uid);
|
||||||
if (nameTmp) {
|
if (nameTmp) {
|
||||||
|
|
@ -287,8 +287,8 @@ std::string PidEntry::formatHeader(const std::string &name, log_id_t /* id */) c
|
||||||
|
|
||||||
std::string PidEntry::format(const LogStatistics &stat, log_id_t /* id */) const {
|
std::string PidEntry::format(const LogStatistics &stat, log_id_t /* id */) const {
|
||||||
uid_t uid = getUid();
|
uid_t uid = getUid();
|
||||||
std::string name = android::base::StringPrintf("%5u/%u",
|
pid_t pid = getPid();
|
||||||
getKey(), uid);
|
std::string name = android::base::StringPrintf("%5u/%u", pid, uid);
|
||||||
const char *nameTmp = getName();
|
const char *nameTmp = getName();
|
||||||
if (nameTmp) {
|
if (nameTmp) {
|
||||||
name += android::base::StringPrintf(
|
name += android::base::StringPrintf(
|
||||||
|
|
@ -325,7 +325,7 @@ std::string TidEntry::formatHeader(const std::string &name, log_id_t /* id */) c
|
||||||
std::string TidEntry::format(const LogStatistics &stat, log_id_t /* id */) const {
|
std::string TidEntry::format(const LogStatistics &stat, log_id_t /* id */) const {
|
||||||
uid_t uid = getUid();
|
uid_t uid = getUid();
|
||||||
std::string name = android::base::StringPrintf("%5u/%u",
|
std::string name = android::base::StringPrintf("%5u/%u",
|
||||||
getKey(), uid);
|
getTid(), uid);
|
||||||
const char *nameTmp = getName();
|
const char *nameTmp = getName();
|
||||||
if (nameTmp) {
|
if (nameTmp) {
|
||||||
name += android::base::StringPrintf(
|
name += android::base::StringPrintf(
|
||||||
|
|
@ -388,7 +388,8 @@ std::string TagEntry::format(const LogStatistics & /* stat */, log_id_t /* id */
|
||||||
return formatLine(name, size, pruned);
|
return formatLine(name, size, pruned);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string LogStatistics::format(uid_t uid, unsigned int logMask) const {
|
std::string LogStatistics::format(uid_t uid, pid_t pid,
|
||||||
|
unsigned int logMask) const {
|
||||||
static const unsigned short spaces_total = 19;
|
static const unsigned short spaces_total = 19;
|
||||||
|
|
||||||
// Report on total logging, current and for all time
|
// Report on total logging, current and for all time
|
||||||
|
|
@ -461,24 +462,38 @@ std::string LogStatistics::format(uid_t uid, unsigned int logMask) const {
|
||||||
name = (uid == AID_ROOT)
|
name = (uid == AID_ROOT)
|
||||||
? "Chattiest UIDs in %s log buffer:"
|
? "Chattiest UIDs in %s log buffer:"
|
||||||
: "Logging for your UID in %s log buffer:";
|
: "Logging for your UID in %s log buffer:";
|
||||||
output += uidTable[id].format(*this, uid, name, id);
|
output += uidTable[id].format(*this, uid, pid, name, id);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (enable) {
|
if (enable) {
|
||||||
name = (uid == AID_ROOT) ? "Chattiest PIDs:" : "Logging for this PID:";
|
name = ((uid == AID_ROOT) && !pid)
|
||||||
output += pidTable.format(*this, uid, name);
|
? "Chattiest PIDs:"
|
||||||
name = "Chattiest TIDs:";
|
: "Logging for this PID:";
|
||||||
output += tidTable.format(*this, uid, name);
|
output += pidTable.format(*this, uid, pid, name);
|
||||||
|
name = "Chattiest TIDs";
|
||||||
|
if (pid) {
|
||||||
|
name += android::base::StringPrintf(" for PID %d", pid);
|
||||||
|
}
|
||||||
|
name += ":";
|
||||||
|
output += tidTable.format(*this, uid, pid, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (enable && (logMask & (1 << LOG_ID_EVENTS))) {
|
if (enable && (logMask & (1 << LOG_ID_EVENTS))) {
|
||||||
name = "Chattiest events log buffer TAGs:";
|
name = "Chattiest events log buffer TAGs";
|
||||||
output += tagTable.format(*this, uid, name, LOG_ID_EVENTS);
|
if (pid) {
|
||||||
|
name += android::base::StringPrintf(" for PID %d", pid);
|
||||||
|
}
|
||||||
|
name += ":";
|
||||||
|
output += tagTable.format(*this, uid, pid, name, LOG_ID_EVENTS);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (enable && (logMask & (1 << LOG_ID_SECURITY))) {
|
if (enable && (logMask & (1 << LOG_ID_SECURITY))) {
|
||||||
name = "Chattiest security log buffer TAGs:";
|
name = "Chattiest security log buffer TAGs";
|
||||||
output += securityTagTable.format(*this, uid, name, LOG_ID_SECURITY);
|
if (pid) {
|
||||||
|
name += android::base::StringPrintf(" for PID %d", pid);
|
||||||
|
}
|
||||||
|
name += ":";
|
||||||
|
output += securityTagTable.format(*this, uid, pid, name, LOG_ID_SECURITY);
|
||||||
}
|
}
|
||||||
|
|
||||||
return output;
|
return output;
|
||||||
|
|
|
||||||
|
|
@ -47,7 +47,8 @@ public:
|
||||||
typedef typename std::unordered_map<TKey, TEntry>::iterator iterator;
|
typedef typename std::unordered_map<TKey, TEntry>::iterator iterator;
|
||||||
typedef typename std::unordered_map<TKey, TEntry>::const_iterator const_iterator;
|
typedef typename std::unordered_map<TKey, TEntry>::const_iterator const_iterator;
|
||||||
|
|
||||||
std::unique_ptr<const TEntry *[]> sort(size_t len) const {
|
std::unique_ptr<const TEntry *[]> sort(uid_t uid, pid_t pid,
|
||||||
|
size_t len) const {
|
||||||
if (!len) {
|
if (!len) {
|
||||||
std::unique_ptr<const TEntry *[]> sorted(NULL);
|
std::unique_ptr<const TEntry *[]> sorted(NULL);
|
||||||
return sorted;
|
return sorted;
|
||||||
|
|
@ -58,6 +59,14 @@ public:
|
||||||
|
|
||||||
for(const_iterator it = map.begin(); it != map.end(); ++it) {
|
for(const_iterator it = map.begin(); it != map.end(); ++it) {
|
||||||
const TEntry &entry = it->second;
|
const TEntry &entry = it->second;
|
||||||
|
|
||||||
|
if ((uid != AID_ROOT) && (uid != entry.getUid())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (pid && entry.getPid() && (pid != entry.getPid())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
size_t sizes = entry.getSizes();
|
size_t sizes = entry.getSizes();
|
||||||
ssize_t index = len - 1;
|
ssize_t index = len - 1;
|
||||||
while ((!retval[index] || (sizes > retval[index]->getSizes()))
|
while ((!retval[index] || (sizes > retval[index]->getSizes()))
|
||||||
|
|
@ -118,12 +127,13 @@ public:
|
||||||
std::string format(
|
std::string format(
|
||||||
const LogStatistics &stat,
|
const LogStatistics &stat,
|
||||||
uid_t uid,
|
uid_t uid,
|
||||||
|
pid_t pid,
|
||||||
const std::string &name = std::string(""),
|
const std::string &name = std::string(""),
|
||||||
log_id_t id = LOG_ID_MAX) const {
|
log_id_t id = LOG_ID_MAX) const {
|
||||||
static const size_t maximum_sorted_entries = 32;
|
static const size_t maximum_sorted_entries = 32;
|
||||||
std::string output;
|
std::string output;
|
||||||
std::unique_ptr<const TEntry *[]> sorted = sort(maximum_sorted_entries);
|
std::unique_ptr<const TEntry *[]> sorted = sort(uid, pid,
|
||||||
|
maximum_sorted_entries);
|
||||||
if (!sorted.get()) {
|
if (!sorted.get()) {
|
||||||
return output;
|
return output;
|
||||||
}
|
}
|
||||||
|
|
@ -136,9 +146,6 @@ public:
|
||||||
if (entry->getSizes() <= (sorted[0]->getSizes() / 100)) {
|
if (entry->getSizes() <= (sorted[0]->getSizes() / 100)) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if ((uid != AID_ROOT) && (uid != entry->getUid())) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (!headerPrinted) {
|
if (!headerPrinted) {
|
||||||
output += "\n\n";
|
output += "\n\n";
|
||||||
output += entry->formatHeader(name, id);
|
output += entry->formatHeader(name, id);
|
||||||
|
|
@ -217,14 +224,24 @@ struct EntryBaseDropped : public EntryBase {
|
||||||
|
|
||||||
struct UidEntry : public EntryBaseDropped {
|
struct UidEntry : public EntryBaseDropped {
|
||||||
const uid_t uid;
|
const uid_t uid;
|
||||||
|
pid_t pid;
|
||||||
|
|
||||||
UidEntry(LogBufferElement *element):
|
UidEntry(LogBufferElement *element):
|
||||||
EntryBaseDropped(element),
|
EntryBaseDropped(element),
|
||||||
uid(element->getUid()) {
|
uid(element->getUid()),
|
||||||
|
pid(element->getPid()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
inline const uid_t&getKey() const { return uid; }
|
inline const uid_t&getKey() const { return uid; }
|
||||||
inline const uid_t&getUid() const { return uid; }
|
inline const uid_t&getUid() const { return getKey(); }
|
||||||
|
inline const pid_t&getPid() const { return pid; }
|
||||||
|
|
||||||
|
inline void add(LogBufferElement *element) {
|
||||||
|
if (pid != element->getPid()) {
|
||||||
|
pid = -1;
|
||||||
|
}
|
||||||
|
EntryBase::add(element);
|
||||||
|
}
|
||||||
|
|
||||||
std::string formatHeader(const std::string &name, log_id_t id) const;
|
std::string formatHeader(const std::string &name, log_id_t id) const;
|
||||||
std::string format(const LogStatistics &stat, log_id_t id) const;
|
std::string format(const LogStatistics &stat, log_id_t id) const;
|
||||||
|
|
@ -260,6 +277,7 @@ struct PidEntry : public EntryBaseDropped {
|
||||||
~PidEntry() { free(name); }
|
~PidEntry() { free(name); }
|
||||||
|
|
||||||
const pid_t&getKey() const { return pid; }
|
const pid_t&getKey() const { return pid; }
|
||||||
|
const pid_t&getPid() const { return getKey(); }
|
||||||
const uid_t&getUid() const { return uid; }
|
const uid_t&getUid() const { return uid; }
|
||||||
const char*getName() const { return name; }
|
const char*getName() const { return name; }
|
||||||
|
|
||||||
|
|
@ -291,30 +309,36 @@ struct PidEntry : public EntryBaseDropped {
|
||||||
|
|
||||||
struct TidEntry : public EntryBaseDropped {
|
struct TidEntry : public EntryBaseDropped {
|
||||||
const pid_t tid;
|
const pid_t tid;
|
||||||
|
pid_t pid;
|
||||||
uid_t uid;
|
uid_t uid;
|
||||||
char *name;
|
char *name;
|
||||||
|
|
||||||
TidEntry(pid_t tid):
|
TidEntry(pid_t tid, pid_t pid):
|
||||||
EntryBaseDropped(),
|
EntryBaseDropped(),
|
||||||
tid(tid),
|
tid(tid),
|
||||||
|
pid(pid),
|
||||||
uid(android::pidToUid(tid)),
|
uid(android::pidToUid(tid)),
|
||||||
name(android::tidToName(tid)) {
|
name(android::tidToName(tid)) {
|
||||||
}
|
}
|
||||||
TidEntry(LogBufferElement *element):
|
TidEntry(LogBufferElement *element):
|
||||||
EntryBaseDropped(element),
|
EntryBaseDropped(element),
|
||||||
tid(element->getTid()),
|
tid(element->getTid()),
|
||||||
|
pid(element->getPid()),
|
||||||
uid(element->getUid()),
|
uid(element->getUid()),
|
||||||
name(android::tidToName(tid)) {
|
name(android::tidToName(tid)) {
|
||||||
}
|
}
|
||||||
TidEntry(const TidEntry &element):
|
TidEntry(const TidEntry &element):
|
||||||
EntryBaseDropped(element),
|
EntryBaseDropped(element),
|
||||||
tid(element.tid),
|
tid(element.tid),
|
||||||
|
pid(element.pid),
|
||||||
uid(element.uid),
|
uid(element.uid),
|
||||||
name(element.name ? strdup(element.name) : NULL) {
|
name(element.name ? strdup(element.name) : NULL) {
|
||||||
}
|
}
|
||||||
~TidEntry() { free(name); }
|
~TidEntry() { free(name); }
|
||||||
|
|
||||||
const pid_t&getKey() const { return tid; }
|
const pid_t&getKey() const { return tid; }
|
||||||
|
const pid_t&getTid() const { return getKey(); }
|
||||||
|
const pid_t&getPid() const { return pid; }
|
||||||
const uid_t&getUid() const { return uid; }
|
const uid_t&getUid() const { return uid; }
|
||||||
const char*getName() const { return name; }
|
const char*getName() const { return name; }
|
||||||
|
|
||||||
|
|
@ -330,8 +354,10 @@ struct TidEntry : public EntryBaseDropped {
|
||||||
|
|
||||||
inline void add(LogBufferElement *element) {
|
inline void add(LogBufferElement *element) {
|
||||||
uid_t incomingUid = element->getUid();
|
uid_t incomingUid = element->getUid();
|
||||||
if (getUid() != incomingUid) {
|
pid_t incomingPid = element->getPid();
|
||||||
|
if ((getUid() != incomingUid) || (getPid() != incomingPid)) {
|
||||||
uid = incomingUid;
|
uid = incomingUid;
|
||||||
|
pid = incomingPid;
|
||||||
free(name);
|
free(name);
|
||||||
name = android::tidToName(element->getTid());
|
name = android::tidToName(element->getTid());
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -346,23 +372,28 @@ struct TidEntry : public EntryBaseDropped {
|
||||||
|
|
||||||
struct TagEntry : public EntryBase {
|
struct TagEntry : public EntryBase {
|
||||||
const uint32_t tag;
|
const uint32_t tag;
|
||||||
|
pid_t pid;
|
||||||
uid_t uid;
|
uid_t uid;
|
||||||
|
|
||||||
TagEntry(LogBufferElement *element):
|
TagEntry(LogBufferElement *element):
|
||||||
EntryBase(element),
|
EntryBase(element),
|
||||||
tag(element->getTag()),
|
tag(element->getTag()),
|
||||||
|
pid(element->getPid()),
|
||||||
uid(element->getUid()) {
|
uid(element->getUid()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const uint32_t&getKey() const { return tag; }
|
const uint32_t&getKey() const { return tag; }
|
||||||
|
const pid_t&getPid() const { return pid; }
|
||||||
const uid_t&getUid() const { return uid; }
|
const uid_t&getUid() const { return uid; }
|
||||||
const char*getName() const { return android::tagToName(tag); }
|
const char*getName() const { return android::tagToName(tag); }
|
||||||
|
|
||||||
inline void add(LogBufferElement *element) {
|
inline void add(LogBufferElement *element) {
|
||||||
uid_t incomingUid = element->getUid();
|
if (uid != element->getUid()) {
|
||||||
if (uid != incomingUid) {
|
|
||||||
uid = -1;
|
uid = -1;
|
||||||
}
|
}
|
||||||
|
if (pid != element->getPid()) {
|
||||||
|
pid = -1;
|
||||||
|
}
|
||||||
EntryBase::add(element);
|
EntryBase::add(element);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -416,8 +447,9 @@ public:
|
||||||
--mDroppedElements[log_id];
|
--mDroppedElements[log_id];
|
||||||
}
|
}
|
||||||
|
|
||||||
std::unique_ptr<const UidEntry *[]> sort(size_t len, log_id id) {
|
std::unique_ptr<const UidEntry *[]> sort(uid_t uid, pid_t pid,
|
||||||
return uidTable[id].sort(len);
|
size_t len, log_id id) {
|
||||||
|
return uidTable[id].sort(uid, pid, len);
|
||||||
}
|
}
|
||||||
|
|
||||||
// fast track current value by id only
|
// fast track current value by id only
|
||||||
|
|
@ -429,7 +461,7 @@ public:
|
||||||
size_t sizesTotal(log_id_t id) const { return mSizesTotal[id]; }
|
size_t sizesTotal(log_id_t id) const { return mSizesTotal[id]; }
|
||||||
size_t elementsTotal(log_id_t id) const { return mElementsTotal[id]; }
|
size_t elementsTotal(log_id_t id) const { return mElementsTotal[id]; }
|
||||||
|
|
||||||
std::string format(uid_t uid, unsigned int logMask) const;
|
std::string format(uid_t uid, pid_t pid, unsigned int logMask) const;
|
||||||
|
|
||||||
// helper (must be locked directly or implicitly by mLogElementsLock)
|
// helper (must be locked directly or implicitly by mLogElementsLock)
|
||||||
const char *pidToName(pid_t pid) const;
|
const char *pidToName(pid_t pid) const;
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue