PageRenderTime 46ms CodeModel.GetById 18ms RepoModel.GetById 1ms app.codeStats 0ms

/tools/preload2/src/com/android/preload/classdataretrieval/hprof/Hprof.java

http://github.com/android/platform_frameworks_base
Java | 220 lines | 170 code | 28 blank | 22 comment | 21 complexity | fd33c20611292e060da4b5cdfa0f8091 MD5 | raw file
Possible License(s): BitTorrent-1.0, LGPL-2.1, MPL-2.0-no-copyleft-exception, CC0-1.0
  1. /*
  2. * Copyright (C) 2015 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.preload.classdataretrieval.hprof;
  17. import com.android.ddmlib.Client;
  18. import com.android.ddmlib.ClientData;
  19. import com.android.ddmlib.ClientData.IHprofDumpHandler;
  20. import com.android.preload.classdataretrieval.ClassDataRetriever;
  21. import com.android.preload.ui.NullProgressMonitor;
  22. import com.android.tools.perflib.captures.MemoryMappedFileBuffer;
  23. import com.android.tools.perflib.heap.ClassObj;
  24. import com.android.tools.perflib.heap.Queries;
  25. import com.android.tools.perflib.heap.Snapshot;
  26. import java.io.BufferedOutputStream;
  27. import java.io.File;
  28. import java.io.FileOutputStream;
  29. import java.util.HashMap;
  30. import java.util.Map;
  31. import java.util.Set;
  32. public class Hprof implements ClassDataRetriever {
  33. private static GeneralHprofDumpHandler hprofHandler;
  34. public static void init() {
  35. synchronized(Hprof.class) {
  36. if (hprofHandler == null) {
  37. ClientData.setHprofDumpHandler(hprofHandler = new GeneralHprofDumpHandler());
  38. }
  39. }
  40. }
  41. public static File doHprof(Client client, int timeout) {
  42. GetHprof gh = new GetHprof(client, timeout);
  43. return gh.get();
  44. }
  45. /**
  46. * Return a map of class names to class-loader names derived from the hprof dump.
  47. *
  48. * @param hprofLocalFile
  49. */
  50. public static Map<String, String> analyzeHprof(File hprofLocalFile) throws Exception {
  51. Snapshot snapshot = Snapshot.createSnapshot(new MemoryMappedFileBuffer(hprofLocalFile));
  52. Map<String, Set<ClassObj>> classes = Queries.classes(snapshot, null);
  53. Map<String, String> retValue = new HashMap<String, String>();
  54. for (Map.Entry<String, Set<ClassObj>> e : classes.entrySet()) {
  55. for (ClassObj c : e.getValue()) {
  56. String cl = c.getClassLoader() == null ? null : c.getClassLoader().toString();
  57. String cName = c.getClassName();
  58. int aDepth = 0;
  59. while (cName.endsWith("[]")) {
  60. cName = cName.substring(0, cName.length()-2);
  61. aDepth++;
  62. }
  63. String newName = transformPrimitiveClass(cName);
  64. if (aDepth > 0) {
  65. // Need to use kind-a descriptor syntax. If it was transformed, it is primitive.
  66. if (newName.equals(cName)) {
  67. newName = "L" + newName + ";";
  68. }
  69. for (int i = 0; i < aDepth; i++) {
  70. newName = "[" + newName;
  71. }
  72. }
  73. retValue.put(newName, cl);
  74. }
  75. }
  76. // Free up memory.
  77. snapshot.dispose();
  78. return retValue;
  79. }
  80. private static Map<String, String> primitiveMapping;
  81. static {
  82. primitiveMapping = new HashMap<>();
  83. primitiveMapping.put("boolean", "Z");
  84. primitiveMapping.put("byte", "B");
  85. primitiveMapping.put("char", "C");
  86. primitiveMapping.put("double", "D");
  87. primitiveMapping.put("float", "F");
  88. primitiveMapping.put("int", "I");
  89. primitiveMapping.put("long", "J");
  90. primitiveMapping.put("short", "S");
  91. primitiveMapping.put("void", "V");
  92. }
  93. private static String transformPrimitiveClass(String name) {
  94. String rep = primitiveMapping.get(name);
  95. if (rep != null) {
  96. return rep;
  97. }
  98. return name;
  99. }
  100. private static class GetHprof implements IHprofDumpHandler {
  101. private File target;
  102. private long timeout;
  103. private Client client;
  104. public GetHprof(Client client, long timeout) {
  105. this.client = client;
  106. this.timeout = timeout;
  107. }
  108. public File get() {
  109. synchronized (this) {
  110. hprofHandler.addHandler(this);
  111. client.dumpHprof();
  112. if (target == null) {
  113. try {
  114. wait(timeout);
  115. } catch (Exception e) {
  116. System.out.println(e);
  117. }
  118. }
  119. }
  120. hprofHandler.removeHandler(this);
  121. return target;
  122. }
  123. private void wakeUp() {
  124. synchronized (this) {
  125. notifyAll();
  126. }
  127. }
  128. @Override
  129. public void onEndFailure(Client arg0, String arg1) {
  130. System.out.println("GetHprof.onEndFailure");
  131. if (client == arg0) {
  132. wakeUp();
  133. }
  134. }
  135. private static File createTargetFile() {
  136. try {
  137. return File.createTempFile("ddms", ".hprof");
  138. } catch (Exception e) {
  139. throw new RuntimeException(e);
  140. }
  141. }
  142. @Override
  143. public void onSuccess(String arg0, Client arg1) {
  144. System.out.println("GetHprof.onSuccess");
  145. if (client == arg1) {
  146. try {
  147. target = createTargetFile();
  148. arg1.getDevice().getSyncService().pullFile(arg0,
  149. target.getAbsoluteFile().toString(), new NullProgressMonitor());
  150. } catch (Exception e) {
  151. e.printStackTrace();
  152. target = null;
  153. }
  154. wakeUp();
  155. }
  156. }
  157. @Override
  158. public void onSuccess(byte[] arg0, Client arg1) {
  159. System.out.println("GetHprof.onSuccess");
  160. if (client == arg1) {
  161. try {
  162. target = createTargetFile();
  163. BufferedOutputStream out =
  164. new BufferedOutputStream(new FileOutputStream(target));
  165. out.write(arg0);
  166. out.close();
  167. } catch (Exception e) {
  168. e.printStackTrace();
  169. target = null;
  170. }
  171. wakeUp();
  172. }
  173. }
  174. }
  175. private int timeout;
  176. public Hprof(int timeout) {
  177. this.timeout = timeout;
  178. }
  179. @Override
  180. public Map<String, String> getClassData(Client client) {
  181. File hprofLocalFile = Hprof.doHprof(client, timeout);
  182. if (hprofLocalFile == null) {
  183. throw new RuntimeException("Failed getting dump...");
  184. }
  185. System.out.println("Dump file is " + hprofLocalFile);
  186. try {
  187. return analyzeHprof(hprofLocalFile);
  188. } catch (Exception e) {
  189. throw new RuntimeException(e);
  190. }
  191. }
  192. }