1 /*
2  * Copyright (C) 2021 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.android.server.stats.bootstrap;
17 
18 import android.content.Context;
19 import android.os.IStatsBootstrapAtomService;
20 import android.os.StatsBootstrapAtom;
21 import android.os.StatsBootstrapAtomValue;
22 import android.util.Slog;
23 import android.util.StatsEvent;
24 import android.util.StatsLog;
25 
26 import com.android.server.SystemService;
27 
28 /**
29  * Proxy service for logging pushed atoms to statsd
30  *
31  * @hide
32  */
33 public class StatsBootstrapAtomService extends IStatsBootstrapAtomService.Stub {
34 
35     private static final String TAG = "StatsBootstrapAtomService";
36     private static final boolean DEBUG = false;
37 
38     @Override
reportBootstrapAtom(StatsBootstrapAtom atom)39     public void reportBootstrapAtom(StatsBootstrapAtom atom) {
40         if (atom.atomId < 1 || atom.atomId >= 10000) {
41             Slog.e(TAG, "Atom ID " + atom.atomId + " is not a valid atom ID");
42             return;
43         }
44         StatsEvent.Builder builder = StatsEvent.newBuilder().setAtomId(atom.atomId);
45         for (StatsBootstrapAtomValue value : atom.values) {
46             switch (value.getTag()) {
47                 case StatsBootstrapAtomValue.boolValue:
48                     builder.writeBoolean(value.getBoolValue());
49                     break;
50                 case StatsBootstrapAtomValue.intValue:
51                     builder.writeInt(value.getIntValue());
52                     break;
53                 case StatsBootstrapAtomValue.longValue:
54                     builder.writeLong(value.getLongValue());
55                     break;
56                 case StatsBootstrapAtomValue.floatValue:
57                     builder.writeFloat(value.getFloatValue());
58                     break;
59                 case StatsBootstrapAtomValue.stringValue:
60                     builder.writeString(value.getStringValue());
61                     break;
62                 case StatsBootstrapAtomValue.bytesValue:
63                     builder.writeByteArray(value.getBytesValue());
64                     break;
65                 default:
66                     Slog.e(TAG, "Unexpected value type " + value.getTag()
67                             + " when logging atom " + atom.atomId);
68                     return;
69 
70             }
71         }
72         StatsLog.write(builder.usePooledBuffer().build());
73     }
74 
75     /**
76      * Lifecycle and related code
77      */
78     public static final class Lifecycle extends SystemService {
79         private StatsBootstrapAtomService mStatsBootstrapAtomService;
80 
Lifecycle(Context context)81         public Lifecycle(Context context) {
82             super(context);
83         }
84 
85         @Override
onStart()86         public void onStart() {
87             mStatsBootstrapAtomService = new StatsBootstrapAtomService();
88             try {
89                 publishBinderService(Context.STATS_BOOTSTRAP_ATOM_SERVICE,
90                         mStatsBootstrapAtomService);
91                 if (DEBUG) Slog.d(TAG, "Published " + Context.STATS_BOOTSTRAP_ATOM_SERVICE);
92             } catch (Exception e) {
93                 Slog.e(TAG, "Failed to publishBinderService", e);
94             }
95         }
96     }
97 
98 }
99