utils.h revision 91bf6cd47174f5c17265320f7a350722720390a5
1/* 2 * Copyright (C) 2011 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#ifndef ART_SRC_UTILS_H_ 18#define ART_SRC_UTILS_H_ 19 20#include "globals.h" 21#include "logging.h" 22#include "primitive.h" 23#include "stringpiece.h" 24#include "stringprintf.h" 25 26#include <pthread.h> 27#include <string> 28#include <vector> 29 30namespace art { 31 32class Class; 33class DexFile; 34class Field; 35class Method; 36class Object; 37class String; 38 39template<typename T> 40static inline bool IsPowerOfTwo(T x) { 41 return (x & (x - 1)) == 0; 42} 43 44template<int n, typename T> 45static inline bool IsAligned(T x) { 46 COMPILE_ASSERT((n & (n - 1)) == 0, n_not_power_of_two); 47 return (x & (n - 1)) == 0; 48} 49 50template<int n, typename T> 51static inline bool IsAligned(T* x) { 52 return IsAligned<n>(reinterpret_cast<const uintptr_t>(x)); 53} 54 55#define CHECK_ALIGNED(value, alignment) \ 56 CHECK(::art::IsAligned<alignment>(value)) << reinterpret_cast<const void*>(value) 57 58#define DCHECK_ALIGNED(value, alignment) \ 59 DCHECK(::art::IsAligned<alignment>(value)) << reinterpret_cast<const void*>(value) 60 61// Check whether an N-bit two's-complement representation can hold value. 62static inline bool IsInt(int N, word value) { 63 CHECK_LT(0, N); 64 CHECK_LT(N, kBitsPerWord); 65 word limit = static_cast<word>(1) << (N - 1); 66 return (-limit <= value) && (value < limit); 67} 68 69static inline bool IsUint(int N, word value) { 70 CHECK_LT(0, N); 71 CHECK_LT(N, kBitsPerWord); 72 word limit = static_cast<word>(1) << N; 73 return (0 <= value) && (value < limit); 74} 75 76static inline bool IsAbsoluteUint(int N, word value) { 77 CHECK_LT(0, N); 78 CHECK_LT(N, kBitsPerWord); 79 if (value < 0) value = -value; 80 return IsUint(N, value); 81} 82 83static inline int32_t Low16Bits(int32_t value) { 84 return static_cast<int32_t>(value & 0xffff); 85} 86 87static inline int32_t High16Bits(int32_t value) { 88 return static_cast<int32_t>(value >> 16); 89} 90 91static inline int32_t Low32Bits(int64_t value) { 92 return static_cast<int32_t>(value); 93} 94 95static inline int32_t High32Bits(int64_t value) { 96 return static_cast<int32_t>(value >> 32); 97} 98 99template<typename T> 100static inline T RoundDown(T x, int n) { 101 CHECK(IsPowerOfTwo(n)); 102 return (x & -n); 103} 104 105template<typename T> 106static inline T RoundUp(T x, int n) { 107 return RoundDown(x + n - 1, n); 108} 109 110// Implementation is from "Hacker's Delight" by Henry S. Warren, Jr., 111// figure 3-3, page 48, where the function is called clp2. 112static inline uint32_t RoundUpToPowerOfTwo(uint32_t x) { 113 x = x - 1; 114 x = x | (x >> 1); 115 x = x | (x >> 2); 116 x = x | (x >> 4); 117 x = x | (x >> 8); 118 x = x | (x >> 16); 119 return x + 1; 120} 121 122// Implementation is from "Hacker's Delight" by Henry S. Warren, Jr., 123// figure 5-2, page 66, where the function is called pop. 124static inline int CountOneBits(uint32_t x) { 125 x = x - ((x >> 1) & 0x55555555); 126 x = (x & 0x33333333) + ((x >> 2) & 0x33333333); 127 x = (x + (x >> 4)) & 0x0F0F0F0F; 128 x = x + (x >> 8); 129 x = x + (x >> 16); 130 return static_cast<int>(x & 0x0000003F); 131} 132 133#define CLZ(x) __builtin_clz(x) 134 135static inline bool NeedsEscaping(uint16_t ch) { 136 return (ch < ' ' || ch > '~'); 137} 138 139static inline std::string PrintableChar(uint16_t ch) { 140 std::string result; 141 result += '\''; 142 if (NeedsEscaping(ch)) { 143 StringAppendF(&result, "\\u%04x", ch); 144 } else { 145 result += ch; 146 } 147 result += '\''; 148 return result; 149} 150 151// TODO: assume the content is UTF-8, and show code point escapes? 152template<typename StringT> 153static inline std::string PrintableString(const StringT& s) { 154 std::string result; 155 result += '"'; 156 for (typename StringT::const_iterator it = s.begin(); it != s.end(); ++it) { 157 char ch = *it; 158 if (NeedsEscaping(ch)) { 159 StringAppendF(&result, "\\x%02x", ch & 0xff); 160 } else { 161 result += ch; 162 } 163 } 164 result += '"'; 165 return result; 166} 167 168// Tests whether 's' starts with 'prefix'. 169bool StartsWith(const std::string& s, const char* prefix); 170 171// Used to implement PrettyClass, PrettyField, PrettyMethod, and PrettyTypeOf, 172// one of which is probably more useful to you. 173// Returns a human-readable equivalent of 'descriptor'. So "I" would be "int", 174// "[[I" would be "int[][]", "[Ljava/lang/String;" would be 175// "java.lang.String[]", and so forth. 176std::string PrettyDescriptor(const String* descriptor); 177std::string PrettyDescriptor(const std::string& descriptor); 178std::string PrettyDescriptor(Primitive::Type type); 179std::string PrettyDescriptor(const Class* klass); 180 181// Returns a human-readable signature for 'f'. Something like "a.b.C.f" or 182// "int a.b.C.f" (depending on the value of 'with_type'). 183std::string PrettyField(const Field* f, bool with_type = true); 184 185// Returns a human-readable signature for 'm'. Something like "a.b.C.m" or 186// "a.b.C.m(II)V" (depending on the value of 'with_signature'). 187std::string PrettyMethod(const Method* m, bool with_signature = true); 188std::string PrettyMethod(uint32_t method_idx, const DexFile& dex_file, bool with_signature = true); 189 190// Returns a human-readable form of the name of the *class* of the given object. 191// So given an instance of java.lang.String, the output would 192// be "java.lang.String". Given an array of int, the output would be "int[]". 193// Given String.class, the output would be "java.lang.Class<java.lang.String>". 194std::string PrettyTypeOf(const Object* obj); 195 196// Returns a human-readable form of the name of the given class. 197// Given String.class, the output would be "java.lang.Class<java.lang.String>". 198std::string PrettyClass(const Class* c); 199 200// Returns a human-readable form of the name of the given class with its class loader. 201std::string PrettyClassAndClassLoader(const Class* c); 202 203// Returns a human-readable size string. e.g. "1MB" 204std::string PrettySize(size_t size_in_bytes); 205 206// Returns a human-readable time string which prints every nanosecond while trying to limit the 207// number of trailing zeros. Prints using the largest human readable unit up to a second. 208// e.g. "1ms", "1.000000001s", "1.001us" 209std::string PrettyDuration(uint64_t nano_duration); 210 211// Performs JNI name mangling as described in section 11.3 "Linking Native Methods" 212// of the JNI spec. 213std::string MangleForJni(const std::string& s); 214 215// Turn "java.lang.String" into "Ljava/lang/String;". 216std::string DotToDescriptor(const char* class_name); 217 218// Turn "Ljava/lang/String;" into "java.lang.String". 219std::string DescriptorToDot(const char* descriptor); 220 221// Turn "Ljava/lang/String;" into "java/lang/String". 222std::string DescriptorToName(const char* descriptor); 223 224// Tests for whether 's' is a valid class name in the three common forms: 225bool IsValidBinaryClassName(const char* s); // "java.lang.String" 226bool IsValidJniClassName(const char* s); // "java/lang/String" 227bool IsValidDescriptor(const char* s); // "Ljava/lang/String;" 228 229// Returns whether the given string is a valid field or method name, 230// additionally allowing names that begin with '<' and end with '>'. 231bool IsValidMemberName(const char* s); 232 233// Returns the JNI native function name for the non-overloaded method 'm'. 234std::string JniShortName(const Method* m); 235// Returns the JNI native function name for the overloaded method 'm'. 236std::string JniLongName(const Method* m); 237 238bool ReadFileToString(const std::string& file_name, std::string* result); 239 240// Returns the current date in ISO yyyy-mm-dd hh:mm:ss format. 241std::string GetIsoDate(); 242 243// Returns the current time in milliseconds (using the POSIX CLOCK_MONOTONIC). 244uint64_t MilliTime(); 245 246// Returns the current time in microseconds (using the POSIX CLOCK_MONOTONIC). 247uint64_t MicroTime(); 248 249// Returns the current time in nanoseconds (using the POSIX CLOCK_MONOTONIC). 250uint64_t NanoTime(); 251 252// Returns the current time in microseconds (using the POSIX CLOCK_THREAD_CPUTIME_ID). 253uint64_t ThreadCpuMicroTime(); 254 255// Converts the given number of nanoseconds to milliseconds. 256static inline uint64_t NsToMs(uint64_t ns) { 257 return ns / 1000 / 1000; 258} 259 260// Converts the given number of milliseconds to nanoseconds 261static inline uint64_t MsToNs(uint64_t ns) { 262 return ns * 1000 * 1000; 263} 264 265// Splits a string using the given separator character into a vector of 266// strings. Empty strings will be omitted. 267void Split(const std::string& s, char separator, std::vector<std::string>& result); 268 269// Joins a vector of strings into a single string, using the given separator. 270template <typename StringT> std::string Join(std::vector<StringT>& strings, char separator); 271 272// Returns the calling thread's tid. (The C libraries don't expose this.) 273pid_t GetTid(); 274 275// Reads data from "/proc/self/task/${tid}/stat". 276void GetTaskStats(pid_t tid, int& utime, int& stime, int& task_cpu); 277 278// Sets the name of the current thread. The name may be truncated to an 279// implementation-defined limit. 280void SetThreadName(const char* name); 281 282// Find $ANDROID_ROOT, /system, or abort 283const char* GetAndroidRoot(); 284 285// Find $ANDROID_DATA, /data, or abort 286const char* GetAndroidData(); 287 288// Returns the art-cache location, or dies trying. 289std::string GetArtCacheOrDie(); 290 291// Returns the art-cache location for a DexFile or OatFile, or dies trying. 292std::string GetArtCacheFilenameOrDie(const std::string& location); 293 294// Check whether the given filename has a valid zip or dex extension 295bool IsValidZipFilename(const std::string& filename); 296bool IsValidDexFilename(const std::string& filename); 297 298} // namespace art 299 300#endif // ART_SRC_UTILS_H_ 301