1 /*
2  * Copyright (C) 2023 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 
17 package com.android.keyguard.logging
18 
19 import androidx.annotation.IntDef
20 import com.android.keyguard.CarrierTextManager.CarrierTextCallbackInfo
21 import com.android.systemui.log.LogBuffer
22 import com.android.systemui.log.core.LogLevel
23 import com.android.systemui.log.dagger.CarrierTextManagerLog
24 import javax.inject.Inject
25 
26 /** Logger adapter for [CarrierTextManager] to add detailed messages in a [LogBuffer] */
27 class CarrierTextManagerLogger @Inject constructor(@CarrierTextManagerLog val buffer: LogBuffer) {
28     /**
29      * To help disambiguate carrier text manager instances, set a location string here which will
30      * propagate to [logUpdate] and [logUpdateCarrierTextForReason]
31      */
32     var location: String? = null
33 
34     /**
35      * This method and the methods below trace the execution of CarrierTextManager.updateCarrierText
36      */
37     fun logUpdate(numSubs: Int) {
38         buffer.log(
39             TAG,
40             LogLevel.VERBOSE,
41             { int1 = numSubs },
42             { "updateCarrierText: location=${location ?: "(unknown)"} numSubs=$int1" },
43         )
44     }
45 
46     fun logUpdateLoopStart(sub: Int, simState: Int, carrierName: String) {
47         buffer.log(
48             TAG,
49             LogLevel.VERBOSE,
50             {
51                 int1 = sub
52                 int2 = simState
53                 str1 = carrierName
54             },
55             { "┣ updateCarrierText: updating sub=$int1 simState=$int2 carrierName=$str1" },
56         )
57     }
58 
59     fun logUpdateWfcCheck() {
60         buffer.log(
61             TAG,
62             LogLevel.VERBOSE,
63             {},
64             { "┣ updateCarrierText: found WFC state" },
65         )
66     }
67 
68     fun logUpdateFromStickyBroadcast(plmn: String?, spn: String?) {
69         buffer.log(
70             TAG,
71             LogLevel.VERBOSE,
72             {
73                 str1 = plmn
74                 str2 = spn
75             },
76             { "┣ updateCarrierText: getting PLMN/SPN sticky brdcst. plmn=$str1, spn=$str1" },
77         )
78     }
79 
80     /** De-structures the info object so that we don't have to generate new strings */
81     fun logCallbackSentFromUpdate(info: CarrierTextCallbackInfo) {
82         buffer.log(
83             TAG,
84             LogLevel.VERBOSE,
85             {
86                 str1 = "${info.carrierText}"
87                 bool1 = info.anySimReady
88                 bool2 = info.airplaneMode
89             },
90             {
91                 "┗ updateCarrierText: " +
92                     "result=(carrierText=$str1, anySimReady=$bool1, airplaneMode=$bool2)"
93             },
94         )
95     }
96 
97     /**
98      * Used to log the starting point for _why_ the carrier text is updating. In order to keep us
99      * from holding on to too many objects, we'll just use simple ints for reasons here
100      */
101     fun logUpdateCarrierTextForReason(@CarrierTextRefreshReason reason: Int) {
102         buffer.log(
103             TAG,
104             LogLevel.DEBUG,
105             { int1 = reason },
106             {
107                 "refreshing carrier info for reason: ${reason.reasonMessage()}" +
108                     " location=${location ?: "(unknown)"}"
109             }
110         )
111     }
112 
113     companion object {
114         const val REASON_REFRESH_CARRIER_INFO = 1
115         const val REASON_ON_TELEPHONY_CAPABLE = 2
116         const val REASON_ON_SIM_STATE_CHANGED = 3
117         const val REASON_ACTIVE_DATA_SUB_CHANGED = 4
118 
119         @Retention(AnnotationRetention.SOURCE)
120         @IntDef(
121             value =
122                 [
123                     REASON_REFRESH_CARRIER_INFO,
124                     REASON_ON_TELEPHONY_CAPABLE,
125                     REASON_ON_SIM_STATE_CHANGED,
126                     REASON_ACTIVE_DATA_SUB_CHANGED,
127                 ]
128         )
129         annotation class CarrierTextRefreshReason
130 
131         private fun @receiver:CarrierTextRefreshReason Int.reasonMessage() =
132             when (this) {
133                 REASON_REFRESH_CARRIER_INFO -> "REFRESH_CARRIER_INFO"
134                 REASON_ON_TELEPHONY_CAPABLE -> "ON_TELEPHONY_CAPABLE"
135                 REASON_ON_SIM_STATE_CHANGED -> "SIM_STATE_CHANGED"
136                 REASON_ACTIVE_DATA_SUB_CHANGED -> "ACTIVE_DATA_SUB_CHANGED"
137                 else -> "unknown"
138             }
139     }
140 }
141 
142 private const val TAG = "CarrierTextManagerLog"
143