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

Commit 37dadd10 authored by Kweku Adams's avatar Kweku Adams Committed by Android (Google) Code Review
Browse files

Merge "Log debug and trace tags to statsd." into main

parents 8177bca2 1e466293
Loading
Loading
Loading
Loading
+6 −2
Original line number Diff line number Diff line
@@ -1840,7 +1840,9 @@ public class JobSchedulerService extends com.android.server.SystemService
                    /* isFlexConstraintSatisfied */ false,
                    jobStatus.canApplyTransportAffinities(),
                    jobStatus.getNumAppliedFlexibleConstraints(),
                    jobStatus.getNumDroppedFlexibleConstraints());
                    jobStatus.getNumDroppedFlexibleConstraints(),
                    jobStatus.getFilteredTraceTag(),
                    jobStatus.getFilteredDebugTags());

            // If the job is immediately ready to run, then we can just immediately
            // put it in the pending list and try to schedule it.  This is especially
@@ -2288,7 +2290,9 @@ public class JobSchedulerService extends com.android.server.SystemService
                    cancelled.isConstraintSatisfied(JobStatus.CONSTRAINT_FLEXIBLE),
                    cancelled.canApplyTransportAffinities(),
                    cancelled.getNumAppliedFlexibleConstraints(),
                    cancelled.getNumDroppedFlexibleConstraints());
                    cancelled.getNumDroppedFlexibleConstraints(),
                    cancelled.getFilteredTraceTag(),
                    cancelled.getFilteredDebugTags());
        }
        // If this is a replacement, bring in the new version of the job
        if (incomingJob != null) {
+6 −2
Original line number Diff line number Diff line
@@ -541,7 +541,9 @@ public final class JobServiceContext implements ServiceConnection {
                    job.isConstraintSatisfied(JobStatus.CONSTRAINT_FLEXIBLE),
                    job.canApplyTransportAffinities(),
                    job.getNumAppliedFlexibleConstraints(),
                    job.getNumDroppedFlexibleConstraints());
                    job.getNumDroppedFlexibleConstraints(),
                    job.getFilteredTraceTag(),
                    job.getFilteredDebugTags());
            sEnqueuedJwiAtJobStart.logSampleWithUid(job.getUid(), job.getWorkCount());
            final String sourcePackage = job.getSourcePackageName();
            if (Trace.isTagEnabled(Trace.TRACE_TAG_SYSTEM_SERVER)) {
@@ -1630,7 +1632,9 @@ public final class JobServiceContext implements ServiceConnection {
                completedJob.isConstraintSatisfied(JobStatus.CONSTRAINT_FLEXIBLE),
                completedJob.canApplyTransportAffinities(),
                completedJob.getNumAppliedFlexibleConstraints(),
                completedJob.getNumDroppedFlexibleConstraints());
                completedJob.getNumDroppedFlexibleConstraints(),
                completedJob.getFilteredTraceTag(),
                completedJob.getFilteredDebugTags());
        if (Trace.isTagEnabled(Trace.TRACE_TAG_SYSTEM_SERVER)) {
            Trace.asyncTraceForTrackEnd(Trace.TRACE_TAG_SYSTEM_SERVER, "JobScheduler",
                    getId());
+66 −0
Original line number Diff line number Diff line
@@ -48,6 +48,7 @@ import android.util.ArrayMap;
import android.util.ArraySet;
import android.util.IndentingPrintWriter;
import android.util.Pair;
import android.util.Patterns;
import android.util.Range;
import android.util.Slog;
import android.util.TimeUtils;
@@ -76,6 +77,7 @@ import java.util.Collections;
import java.util.Objects;
import java.util.Random;
import java.util.function.Predicate;
import java.util.regex.Pattern;

/**
 * Uniquely identifies a job internally.
@@ -203,6 +205,17 @@ public final class JobStatus {
    // TODO(b/129954980): ensure this doesn't spam statsd, especially at boot
    private static final boolean STATS_LOG_ENABLED = false;

    /**
     * Simple patterns to match some common forms of PII. This is not intended all-encompassing and
     * any clients should aim to do additional filtering.
     */
    private static final ArrayMap<Pattern, String> BASIC_PII_FILTERS = new ArrayMap<>();

    static {
        BASIC_PII_FILTERS.put(Patterns.EMAIL_ADDRESS, "[EMAIL]");
        BASIC_PII_FILTERS.put(Patterns.PHONE, "[PHONE]");
    }

    // No override.
    public static final int OVERRIDE_NONE = 0;
    // Override to improve sorting order. Does not affect constraint evaluation.
@@ -249,6 +262,18 @@ public final class JobStatus {
    /** An ID that can be used to uniquely identify the job when logging statsd metrics. */
    private final long mLoggingJobId;

    /**
     * List of tags from {@link JobInfo#getDebugTags()}, filtered using {@link #BASIC_PII_FILTERS}.
     * Lazily loaded in {@link #getFilteredDebugTags()}.
     */
    @Nullable
    private String[] mFilteredDebugTags;
    /**
     * Trace tag from {@link JobInfo#getTraceTag()}, filtered using {@link #BASIC_PII_FILTERS}.
     * Lazily loaded in {@link #getFilteredTraceTag()}.
     */
    @Nullable
    private String mFilteredTraceTag;
    /**
     * Tag to identify the wakelock held for this job. Lazily loaded in
     * {@link #getWakelockTag()} since it's not typically needed until the job is about to run.
@@ -1325,6 +1350,47 @@ public final class JobStatus {
        return batteryName;
    }

    @VisibleForTesting
    @NonNull
    static String applyBasicPiiFilters(@NonNull String val) {
        for (int i = BASIC_PII_FILTERS.size() - 1; i >= 0; --i) {
            val = BASIC_PII_FILTERS.keyAt(i).matcher(val).replaceAll(BASIC_PII_FILTERS.valueAt(i));
        }
        return val;
    }

    /**
     * List of tags from {@link JobInfo#getDebugTags()}, filtered using a basic set of PII filters.
     */
    @NonNull
    public String[] getFilteredDebugTags() {
        if (mFilteredDebugTags != null) {
            return mFilteredDebugTags;
        }
        final ArraySet<String> debugTags = job.getDebugTagsArraySet();
        mFilteredDebugTags = new String[debugTags.size()];
        for (int i = 0; i < mFilteredDebugTags.length; ++i) {
            mFilteredDebugTags[i] = applyBasicPiiFilters(debugTags.valueAt(i));
        }
        return mFilteredDebugTags;
    }

    /**
     * Trace tag from {@link JobInfo#getTraceTag()}, filtered using a basic set of PII filters.
     */
    @Nullable
    public String getFilteredTraceTag() {
        if (mFilteredTraceTag != null) {
            return mFilteredTraceTag;
        }
        final String rawTag = job.getTraceTag();
        if (rawTag == null) {
            return null;
        }
        mFilteredTraceTag = applyBasicPiiFilters(rawTag);
        return mFilteredTraceTag;
    }

    /** Return the String to be used as the tag for the wakelock held for this job. */
    @NonNull
    public String getWakelockTag() {
+67 −0
Original line number Diff line number Diff line
@@ -45,6 +45,7 @@ import static com.android.server.job.controllers.JobStatus.CONSTRAINT_WITHIN_QUO
import static com.android.server.job.controllers.JobStatus.NO_EARLIEST_RUNTIME;
import static com.android.server.job.controllers.JobStatus.NO_LATEST_RUNTIME;

import static org.junit.Assert.assertArrayEquals;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
@@ -78,6 +79,7 @@ import org.mockito.quality.Strictness;

import java.time.Clock;
import java.time.ZoneOffset;
import java.util.Arrays;

@RunWith(AndroidJUnit4.class)
public class JobStatusTest {
@@ -137,6 +139,35 @@ public class JobStatusTest {
        }
    }

    @Test
    public void testApplyBasicPiiFilters_email() {
        assertEquals("[EMAIL]", JobStatus.applyBasicPiiFilters("test@email.com"));
        assertEquals("[EMAIL]", JobStatus.applyBasicPiiFilters("test+plus@email.com"));
        assertEquals("[EMAIL]", JobStatus.applyBasicPiiFilters("t.e_st+plus-minus@email.com"));

        assertEquals("prefix:[EMAIL]", JobStatus.applyBasicPiiFilters("prefix:test@email.com"));

        assertEquals("not-an-email", JobStatus.applyBasicPiiFilters("not-an-email"));
    }

    @Test
    public void testApplyBasicPiiFilters_mixture() {
        assertEquals("[PHONE]:[EMAIL]",
                JobStatus.applyBasicPiiFilters("123-456-7890:test+plus@email.com"));
        assertEquals("prefix:[PHONE]:[EMAIL]",
                JobStatus.applyBasicPiiFilters("prefix:123-456-7890:test+plus@email.com"));
    }

    @Test
    public void testApplyBasicPiiFilters_phone() {
        assertEquals("[PHONE]", JobStatus.applyBasicPiiFilters("123-456-7890"));
        assertEquals("[PHONE]", JobStatus.applyBasicPiiFilters("+1-234-567-8900"));

        assertEquals("prefix:[PHONE]", JobStatus.applyBasicPiiFilters("prefix:123-456-7890"));

        assertEquals("not-a-phone-number", JobStatus.applyBasicPiiFilters("not-a-phone-number"));
    }

    @Test
    public void testCanRunInBatterySaver_regular() {
        final JobInfo jobInfo =
@@ -244,6 +275,42 @@ public class JobStatusTest {
        assertEquals(1, js.getNumRequiredFlexibleConstraints());
    }

    @Test
    public void testGetFilteredDebugTags() {
        final JobInfo jobInfo = new JobInfo.Builder(101, new ComponentName("foo", "bar"))
                .addDebugTag("test@email.com")
                .addDebugTag("123-456-7890")
                .addDebugTag("random")
                .build();
        JobStatus job = createJobStatus(jobInfo);
        String[] expected = new String[]{"[EMAIL]", "[PHONE]", "random"};
        String[] result = job.getFilteredDebugTags();
        Arrays.sort(expected);
        Arrays.sort(result);
        assertArrayEquals(expected, result);
    }

    @Test
    public void testGetFilteredTraceTag() {
        JobInfo jobInfo = new JobInfo.Builder(101, new ComponentName("foo", "bar"))
                .setTraceTag("test@email.com")
                .build();
        JobStatus job = createJobStatus(jobInfo);
        assertEquals("[EMAIL]", job.getFilteredTraceTag());

        jobInfo = new JobInfo.Builder(101, new ComponentName("foo", "bar"))
                .setTraceTag("123-456-7890")
                .build();
        job = createJobStatus(jobInfo);
        assertEquals("[PHONE]", job.getFilteredTraceTag());

        jobInfo = new JobInfo.Builder(101, new ComponentName("foo", "bar"))
                .setTraceTag("random")
                .build();
        job = createJobStatus(jobInfo);
        assertEquals("random", job.getFilteredTraceTag());
    }

    @Test
    public void testIsUserVisibleJob() {
        JobInfo jobInfo = new JobInfo.Builder(101, new ComponentName("foo", "bar"))