1b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong/*
2b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * Copyright (C) 2014 The Android Open Source Project
3b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong *
4b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * Licensed under the Apache License, Version 2.0 (the "License");
5b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * you may not use this file except in compliance with the License.
6b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * You may obtain a copy of the License at
7b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong *
8b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong *      http://www.apache.org/licenses/LICENSE-2.0
9b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong *
10b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * Unless required by applicable law or agreed to in writing, software
11b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * distributed under the License is distributed on an "AS IS" BASIS,
12b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * See the License for the specific language governing permissions and
14b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong * limitations under the License.
15b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong */
16b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
17b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kongpackage com.android.ex.camera2.portability.debug;
18b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
19b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kongpublic class Log {
20b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger    /**
21b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     * All Camera logging using this class will use this tag prefix.
22b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     * Additionally, the prefix itself is checked in isLoggable and
23b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     * serves as an override. So, to toggle all logs allowed by the
24b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     * current {@link Configuration}, you can set properties:
25b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     *
26b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     * adb shell setprop log.tag.CAM2PORT_ VERBOSE
27b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     * adb shell setprop log.tag.CAM2PORT_ ""
28b52fe84c71ddcf1313c4112393bb4936442d9f13Alan Newberger     */
29b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static final String CAMERA_LOGTAG_PREFIX = "CAM2PORT_";
30b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    private static final Log.Tag TAG = new Log.Tag("Log");
31b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
32b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    /**
33b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong     * This class restricts the length of the log tag to be less than the
34b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong     * framework limit and also prepends the common tag prefix defined by
35b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong     * {@code CAMERA_LOGTAG_PREFIX}.
36b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong     */
37b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static final class Tag {
38b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
39b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        // The length limit from Android framework is 23.
40b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        private static final int MAX_TAG_LEN = 23 - CAMERA_LOGTAG_PREFIX.length();
41b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
42b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        final String mValue;
43b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
44b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        public Tag(String tag) {
45b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            final int lenDiff = tag.length() - MAX_TAG_LEN;
46b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            if (lenDiff > 0) {
47b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong                w(TAG, "Tag " + tag + " is " + lenDiff + " chars longer than limit.");
48b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            }
49b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            mValue = CAMERA_LOGTAG_PREFIX + (lenDiff > 0 ? tag.substring(0, MAX_TAG_LEN) : tag);
50b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        }
51b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
52b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        @Override
53b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        public String toString() {
54b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            return mValue;
55b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        }
56b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
57b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
58b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void d(Tag tag, String msg) {
59f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.DEBUG)) {
60f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.d(tag.toString(), msg);
61f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
62b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
63b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
64b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void d(Tag tag, String msg, Throwable tr) {
65f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.DEBUG)) {
66f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.d(tag.toString(), msg, tr);
67f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
68b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
69b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
70b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void e(Tag tag, String msg) {
71f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.ERROR)) {
72f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.e(tag.toString(), msg);
73f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
74b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
75b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
76b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void e(Tag tag, String msg, Throwable tr) {
77f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.ERROR)) {
78f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.e(tag.toString(), msg, tr);
79f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
80b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
81b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
82b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void i(Tag tag, String msg) {
83f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.INFO)) {
84f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.i(tag.toString(), msg);
85f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
86b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
87b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
88b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void i(Tag tag, String msg, Throwable tr) {
89f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.INFO)) {
90f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.i(tag.toString(), msg, tr);
91f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
92b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
93b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
94b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void v(Tag tag, String msg) {
95f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.VERBOSE)) {
96f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.v(tag.toString(), msg);
97f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
98b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
99b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
100b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void v(Tag tag, String msg, Throwable tr) {
101f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.VERBOSE)) {
102f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.v(tag.toString(), msg, tr);
103f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
104b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
105b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
106b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void w(Tag tag, String msg) {
107f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.WARN)) {
108f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.w(tag.toString(), msg);
109f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
110b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
111b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
112b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    public static void w(Tag tag, String msg, Throwable tr) {
113f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        if (isLoggable(tag, android.util.Log.WARN)) {
114f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            android.util.Log.w(tag.toString(), msg, tr);
115f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger        }
116b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
117b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong
118b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    private static boolean isLoggable(Tag tag, int level) {
119b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        try {
120f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            if (LogHelper.getOverrideLevel() != 0) {
121f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                // Override system log level and output. VERBOSE is smaller than
122f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                // ERROR, so the comparison checks that the override value is smaller
123f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                // than the desired output level. This applies to all tags.
124f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                return LogHelper.getOverrideLevel() <= level;
125f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            } else {
126f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                // The prefix can be used as an override tag to see all camera logs
127f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                return android.util.Log.isLoggable(CAMERA_LOGTAG_PREFIX, level)
128f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger                        || android.util.Log.isLoggable(tag.toString(), level);
129f7a80d935f2e40383237ad4c163b85047f95dc9cAlan Newberger            }
130b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        } catch (IllegalArgumentException ex) {
131b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            e(TAG, "Tag too long:" + tag);
132b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong            return false;
133b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong        }
134b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong    }
135b35ea0d2d494ba7668b0183dfc906cde0708bc55Angus Kong}
136