160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad/* 260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * Copyright 2014, The Android Open Source Project 360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * 460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * Licensed under the Apache License, Version 2.0 (the "License"); 560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * you may not use this file except in compliance with the License. 660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * You may obtain a copy of the License at 760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * 860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * http://www.apache.org/licenses/LICENSE-2.0 960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * 1060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * Unless required by applicable law or agreed to in writing, software 1160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * distributed under the License is distributed on an "AS IS" BASIS, 1260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * See the License for the specific language governing permissions and 1460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * limitations under the License. 1560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad */ 1660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 17ef9f6f957d897ea0ed82114185b8fa3fefd4917bTyler Gunnpackage android.telecom; 1860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 194fb372fe169c6abd463a620b56dd6b05b5ff1e7aBrad Ebingerimport android.content.Context; 203c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordonimport android.net.Uri; 21e362e501ee5d8f892d705c0762eff0a584cfb439Hall Liuimport android.os.AsyncTask; 22b3cd7b51d330caa1f54710741b73a63043515b82youhei.x.miyoshiimport android.os.Build; 2351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebingerimport android.telecom.Logging.EventManager; 2451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebingerimport android.telecom.Logging.Session; 2551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebingerimport android.telecom.Logging.SessionManager; 263c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordonimport android.telephony.PhoneNumberUtils; 273c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordonimport android.text.TextUtils; 28e362e501ee5d8f892d705c0762eff0a584cfb439Hall Liu 2951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebingerimport com.android.internal.annotations.VisibleForTesting; 3051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebingerimport com.android.internal.util.IndentingPrintWriter; 3151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 3260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awadimport java.security.MessageDigest; 3360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awadimport java.security.NoSuchAlgorithmException; 3460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awadimport java.util.IllegalFormatException; 3560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awadimport java.util.Locale; 3660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 3760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad/** 3860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * Manages logging for the entire module. 3960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * 4060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad * @hide 4160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad */ 4251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebingerpublic class Log { 4351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 4451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static final long EXTENDED_LOGGING_DURATION_MILLIS = 60000 * 30; // 30 minutes 4551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 4651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static final int EVENTS_TO_CACHE = 10; 4751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static final int EVENTS_TO_CACHE_DEBUG = 20; 4860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 4951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Generic tag for all Telecom logging 5051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger @VisibleForTesting 5151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static String TAG = "TelecomFramework"; 520c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger public static boolean DEBUG = isLoggable(android.util.Log.DEBUG); 530c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger public static boolean INFO = isLoggable(android.util.Log.INFO); 540c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger public static boolean VERBOSE = isLoggable(android.util.Log.VERBOSE); 550c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger public static boolean WARN = isLoggable(android.util.Log.WARN); 560c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger public static boolean ERROR = isLoggable(android.util.Log.ERROR); 5760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 5851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static final boolean FORCE_LOGGING = false; /* STOP SHIP if true */ 595ab024333065c60620867e58eaa27f27dfa85752Jeff Sharkey private static final boolean USER_BUILD = Build.IS_USER; 6060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 6151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Used to synchronize singleton logging lazy initialization 6251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static final Object sSingletonSync = new Object(); 6351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static EventManager sEventManager; 6451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static SessionManager sSessionManager; 65e362e501ee5d8f892d705c0762eff0a584cfb439Hall Liu 6651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger /** 6751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * Tracks whether user-activated extended logging is enabled. 6851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger */ 6951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static boolean sIsUserExtendedLoggingEnabled = false; 7060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 7151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger /** 7251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * The time when user-activated extended logging should be ended. Used to determine when 7351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * extended logging should automatically be disabled. 7451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger */ 7551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static long sUserExtendedLoggingStopTime = 0; 76e362e501ee5d8f892d705c0762eff0a584cfb439Hall Liu 7751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private Log() { 7860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 7960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 8060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void d(String prefix, String format, Object... args) { 8151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sIsUserExtendedLoggingEnabled) { 8251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger maybeDisableLogging(); 8351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.i(TAG, buildMessage(prefix, format, args)); 8451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else if (DEBUG) { 8551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.d(TAG, buildMessage(prefix, format, args)); 8660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 8760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 8860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 8960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void d(Object objectPrefix, String format, Object... args) { 9051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sIsUserExtendedLoggingEnabled) { 9151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger maybeDisableLogging(); 9251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.i(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args)); 9351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else if (DEBUG) { 9451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.d(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args)); 9560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 9660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 9760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 9860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void i(String prefix, String format, Object... args) { 9960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (INFO) { 10051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.i(TAG, buildMessage(prefix, format, args)); 10160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 10260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 10360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 10460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void i(Object objectPrefix, String format, Object... args) { 10560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (INFO) { 10651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.i(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args)); 10760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 10860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 10960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 11060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void v(String prefix, String format, Object... args) { 11151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sIsUserExtendedLoggingEnabled) { 11251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger maybeDisableLogging(); 11351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.i(TAG, buildMessage(prefix, format, args)); 11451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else if (VERBOSE) { 11551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.v(TAG, buildMessage(prefix, format, args)); 11660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 11760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 11860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 11960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void v(Object objectPrefix, String format, Object... args) { 12051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sIsUserExtendedLoggingEnabled) { 12151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger maybeDisableLogging(); 12251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.i(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args)); 12351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else if (VERBOSE) { 12451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.v(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args)); 12560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 12660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 12760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 12860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void w(String prefix, String format, Object... args) { 12960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (WARN) { 13051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.w(TAG, buildMessage(prefix, format, args)); 13160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 13260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 13360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 13460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void w(Object objectPrefix, String format, Object... args) { 13560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (WARN) { 13651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.w(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args)); 13760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 13860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 13960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 14060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void e(String prefix, Throwable tr, String format, Object... args) { 14160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (ERROR) { 14251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.e(TAG, buildMessage(prefix, format, args), tr); 14360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 14460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 14560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 14660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void e(Object objectPrefix, Throwable tr, String format, Object... args) { 14760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (ERROR) { 14851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.e(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args), 14960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad tr); 15060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 15160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 15260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 15360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void wtf(String prefix, Throwable tr, String format, Object... args) { 15451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.wtf(TAG, buildMessage(prefix, format, args), tr); 15560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 15660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 15760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void wtf(Object objectPrefix, Throwable tr, String format, Object... args) { 15851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.wtf(TAG, buildMessage(getPrefixFromObject(objectPrefix), format, args), 15960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad tr); 16060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 16160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 16260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void wtf(String prefix, String format, Object... args) { 16360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad String msg = buildMessage(prefix, format, args); 16451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.wtf(TAG, msg, new IllegalStateException(msg)); 16560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 16660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 16760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad public static void wtf(Object objectPrefix, String format, Object... args) { 16860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad String msg = buildMessage(getPrefixFromObject(objectPrefix), format, args); 16951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger android.util.Slog.wtf(TAG, msg, new IllegalStateException(msg)); 17060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 17160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 17260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad /** 17351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * The ease of use methods below only act mostly as proxies to the Session and Event Loggers. 17451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * They also control the lazy loaders of the singleton instances, which will never be loaded if 17551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * the proxy methods aren't used. 17651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * 17751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * Please see each method's documentation inside of their respective implementations in the 17851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * loggers. 17960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad */ 18051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 1814fb372fe169c6abd463a620b56dd6b05b5ff1e7aBrad Ebinger public static void setSessionContext(Context context) { 1824fb372fe169c6abd463a620b56dd6b05b5ff1e7aBrad Ebinger getSessionManager().setContext(context); 1834fb372fe169c6abd463a620b56dd6b05b5ff1e7aBrad Ebinger } 1844fb372fe169c6abd463a620b56dd6b05b5ff1e7aBrad Ebinger 18551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void startSession(String shortMethodName) { 18651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getSessionManager().startSession(shortMethodName, null); 18751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 18851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 1893445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger public static void startSession(Session.Info info, String shortMethodName) { 1903445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger getSessionManager().startSession(info, shortMethodName, null); 1913445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger } 1923445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger 19351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void startSession(String shortMethodName, String callerIdentification) { 19451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getSessionManager().startSession(shortMethodName, callerIdentification); 19551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 19651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 197a0dc9765d339ee69da4a1adc3bd6863126267b08Brad Ebinger public static void startSession(Session.Info info, String shortMethodName, 198a0dc9765d339ee69da4a1adc3bd6863126267b08Brad Ebinger String callerIdentification) { 199a0dc9765d339ee69da4a1adc3bd6863126267b08Brad Ebinger getSessionManager().startSession(info, shortMethodName, callerIdentification); 200a0dc9765d339ee69da4a1adc3bd6863126267b08Brad Ebinger } 201a0dc9765d339ee69da4a1adc3bd6863126267b08Brad Ebinger 20251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static Session createSubsession() { 20351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return getSessionManager().createSubsession(); 20451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 20551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 2063445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger public static Session.Info getExternalSession() { 2073445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger return getSessionManager().getExternalSession(); 2083445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger } 2093445f829077cea72da77e31f0a2f6ccce3af295bBrad Ebinger 21051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void cancelSubsession(Session subsession) { 21151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getSessionManager().cancelSubsession(subsession); 21251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 21351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 21451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void continueSession(Session subsession, String shortMethodName) { 21551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getSessionManager().continueSession(subsession, shortMethodName); 21651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 21751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 21851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void endSession() { 21951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getSessionManager().endSession(); 22051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 22151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 222836efade0c24ec235fe3470198509f5040655642Brad Ebinger public static void registerSessionListener(SessionManager.ISessionListener l) { 223836efade0c24ec235fe3470198509f5040655642Brad Ebinger getSessionManager().registerSessionListener(l); 224836efade0c24ec235fe3470198509f5040655642Brad Ebinger } 225836efade0c24ec235fe3470198509f5040655642Brad Ebinger 22651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static String getSessionId() { 22751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // If the Session logger has not been initialized, then there have been no sessions logged. 22851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Don't load it now! 22951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger synchronized (sSingletonSync) { 23051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sSessionManager != null) { 23151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return getSessionManager().getSessionId(); 23251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else { 23351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return ""; 23451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 23551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 23651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 23751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 23851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void addEvent(EventManager.Loggable recordEntry, String event) { 23951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getEventManager().event(recordEntry, event, null); 24051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 24151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 24251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void addEvent(EventManager.Loggable recordEntry, String event, Object data) { 24351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getEventManager().event(recordEntry, event, data); 24451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 24551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 24651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void addEvent(EventManager.Loggable recordEntry, String event, String format, 24751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger Object... args) { 24851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getEventManager().event(recordEntry, event, format, args); 24951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 25051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 25151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void registerEventListener(EventManager.EventListener e) { 25251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getEventManager().registerEventListener(e); 25351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 25451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 25551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void addRequestResponsePair(EventManager.TimedEventPair p) { 25651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getEventManager().addRequestResponsePair(p); 25751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 25851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 25951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void dumpEvents(IndentingPrintWriter pw) { 26051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // If the Events logger has not been initialized, then there have been no events logged. 26151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Don't load it now! 26251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger synchronized (sSingletonSync) { 26351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sEventManager != null) { 26451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger getEventManager().dumpEvents(pw); 26551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else { 2662db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn pw.println("No Historical Events Logged."); 2672db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn } 2682db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn } 2692db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn } 2702db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn 2712db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn /** 2722db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn * Dumps the events in a timeline format. 2732db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn * @param pw The {@link IndentingPrintWriter} to write to. 2742db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn * @hide 2752db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn */ 2762db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn public static void dumpEventsTimeline(IndentingPrintWriter pw) { 2772db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn // If the Events logger has not been initialized, then there have been no events logged. 2782db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn // Don't load it now! 2792db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn synchronized (sSingletonSync) { 2802db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn if (sEventManager != null) { 2812db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn getEventManager().dumpEventsTimeline(pw); 2822db81b599b342de99fd80001ed1a131b9fc67f6aTyler Gunn } else { 28351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger pw.println("No Historical Events Logged."); 28451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 28551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 28651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 28751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 28851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger /** 28951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * Enable or disable extended telecom logging. 29051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * 29151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * @param isExtendedLoggingEnabled {@code true} if extended logging should be enabled, 29251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * {@code false} if it should be disabled. 29351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger */ 29451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void setIsExtendedLoggingEnabled(boolean isExtendedLoggingEnabled) { 29551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // If the state hasn't changed, bail early. 29651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sIsUserExtendedLoggingEnabled == isExtendedLoggingEnabled) { 29751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return; 29851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 29951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 30051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sEventManager != null) { 30151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sEventManager.changeEventCacheSize(isExtendedLoggingEnabled ? 30251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger EVENTS_TO_CACHE_DEBUG : EVENTS_TO_CACHE); 30351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 30451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 30551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sIsUserExtendedLoggingEnabled = isExtendedLoggingEnabled; 30651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sIsUserExtendedLoggingEnabled) { 30751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sUserExtendedLoggingStopTime = System.currentTimeMillis() 30851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger + EXTENDED_LOGGING_DURATION_MILLIS; 30951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else { 31051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sUserExtendedLoggingStopTime = 0; 31151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 31251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 31351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 31451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static EventManager getEventManager() { 31551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Checking for null again outside of synchronization because we only need to synchronize 31651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // during the lazy loading of the events logger. We don't need to synchronize elsewhere. 31751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sEventManager == null) { 31851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger synchronized (sSingletonSync) { 31951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sEventManager == null) { 32051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sEventManager = new EventManager(Log::getSessionId); 32151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return sEventManager; 32251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 32351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 32451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 32551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return sEventManager; 32651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 32751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 3288adafe786cf548543d721602ea35969afcdc295fBrad Ebinger @VisibleForTesting 3298adafe786cf548543d721602ea35969afcdc295fBrad Ebinger public static SessionManager getSessionManager() { 33051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Checking for null again outside of synchronization because we only need to synchronize 33151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // during the lazy loading of the session logger. We don't need to synchronize elsewhere. 33251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sSessionManager == null) { 33351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger synchronized (sSingletonSync) { 33451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sSessionManager == null) { 33551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sSessionManager = new SessionManager(); 33651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return sSessionManager; 33751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 33851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 33951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 34051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return sSessionManager; 34151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 34251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 34351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static void setTag(String tag) { 34451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger TAG = tag; 3450c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger DEBUG = isLoggable(android.util.Log.DEBUG); 3460c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger INFO = isLoggable(android.util.Log.INFO); 3470c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger VERBOSE = isLoggable(android.util.Log.VERBOSE); 3480c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger WARN = isLoggable(android.util.Log.WARN); 3490c3541be65fa87519a879c053a7cf4b4526be5dbBrad Ebinger ERROR = isLoggable(android.util.Log.ERROR); 35051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 35151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 35251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger /** 35351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * If user enabled extended logging is enabled and the time limit has passed, disables the 35451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * extended logging. 35551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger */ 35651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger private static void maybeDisableLogging() { 35751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (!sIsUserExtendedLoggingEnabled) { 35851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return; 35951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 36051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 36151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (sUserExtendedLoggingStopTime < System.currentTimeMillis()) { 36251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sUserExtendedLoggingStopTime = 0; 36351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sIsUserExtendedLoggingEnabled = false; 36451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 36551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 36651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 36751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static boolean isLoggable(int level) { 36851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return FORCE_LOGGING || android.util.Log.isLoggable(TAG, level); 36951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 37051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 37151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static String piiHandle(Object pii) { 37260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad if (pii == null || VERBOSE) { 37360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad return String.valueOf(pii); 37460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 37560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 3763c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon StringBuilder sb = new StringBuilder(); 37751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (pii instanceof Uri) { 37851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger Uri uri = (Uri) pii; 37951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger String scheme = uri.getScheme(); 38051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 38151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (!TextUtils.isEmpty(scheme)) { 38251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sb.append(scheme).append(":"); 38351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 38451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 38551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger String textToObfuscate = uri.getSchemeSpecificPart(); 38651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (PhoneAccount.SCHEME_TEL.equals(scheme)) { 38751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger for (int i = 0; i < textToObfuscate.length(); i++) { 38851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger char c = textToObfuscate.charAt(i); 38951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sb.append(PhoneNumberUtils.isDialable(c) ? "*" : c); 39051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 39151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else if (PhoneAccount.SCHEME_SIP.equals(scheme)) { 39251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger for (int i = 0; i < textToObfuscate.length(); i++) { 39351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger char c = textToObfuscate.charAt(i); 39451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (c != '@' && c != '.') { 39551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger c = '*'; 39651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 3973c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon sb.append(c); 3983c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon } 39951b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } else { 40051b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger sb.append(pii(pii)); 4013c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon } 4023c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon } 40351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 4043c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon return sb.toString(); 40551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 4063c20d633731a3a2f6ea03012cb4b1d4903a31520Santos Cordon 40751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger /** 40851b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger * Redact personally identifiable information for production users. 409b3cd7b51d330caa1f54710741b73a63043515b82youhei.x.miyoshi * If we are running in verbose mode, return the original string, 410f784b29c9dce6361dd2f1f45c92df30d4a6d3c7cBrad Ebinger * and return "***" otherwise. 41151b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger */ 41251b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger public static String pii(Object pii) { 41351b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger if (pii == null || VERBOSE) { 41451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return String.valueOf(pii); 41551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger } 416f784b29c9dce6361dd2f1f45c92df30d4a6d3c7cBrad Ebinger return "***"; 41760ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 41860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 41960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad private static String getPrefixFromObject(Object obj) { 42060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad return obj == null ? "<null>" : obj.getClass().getSimpleName(); 42160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 42260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad 42360ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad private static String buildMessage(String prefix, String format, Object... args) { 42451b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger // Incorporate thread ID and calling method into prefix 42551b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger String sessionName = getSessionId(); 42651b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger String sessionPostfix = TextUtils.isEmpty(sessionName) ? "" : ": " + sessionName; 42751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger 42860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad String msg; 42960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad try { 43060ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad msg = (args == null || args.length == 0) ? format 43160ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad : String.format(Locale.US, format, args); 43260ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } catch (IllegalFormatException ife) { 4334fb372fe169c6abd463a620b56dd6b05b5ff1e7aBrad Ebinger e(TAG, ife, "Log: IllegalFormatException: formatString='%s' numArgs=%d", format, 43460ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad args.length); 43560ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad msg = format + " (An error occurred while formatting the message.)"; 43660ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 43751b9834180db6ecaf4edaf38fb12d5d408f2c1ceBrad Ebinger return String.format(Locale.US, "%s: %s%s", prefix, msg, sessionPostfix); 43860ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad } 43960ac30bb8a30fa7283d592c12ddf2da9447adf14Ihab Awad} 440