Implement Method.Bytecodes.

Change-Id: Ib24c1244818c1d5aa10606a4998c0e52fa2b70bd
diff --git a/src/jdwp/jdwp_handler.cc b/src/jdwp/jdwp_handler.cc
index 23a3130..14dd2a5 100644
--- a/src/jdwp/jdwp_handler.cc
+++ b/src/jdwp/jdwp_handler.cc
@@ -383,7 +383,7 @@
     SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
   expandBufAdd1(reply, false);   // canWatchFieldModification
   expandBufAdd1(reply, false);   // canWatchFieldAccess
-  expandBufAdd1(reply, false);   // canGetBytecodes
+  expandBufAdd1(reply, true);    // canGetBytecodes
   expandBufAdd1(reply, true);    // canGetSyntheticAttribute
   expandBufAdd1(reply, true);    // canGetOwnedMonitorInfo
   expandBufAdd1(reply, true);    // canGetCurrentContendedMonitor
@@ -828,6 +828,25 @@
   return M_VariableTable(state, buf, dataLen, pReply, true);
 }
 
+static JdwpError M_Bytecodes(JdwpState*, const uint8_t* buf, int, ExpandBuf* reply)
+    SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
+  RefTypeId class_id = ReadRefTypeId(&buf);
+  MethodId method_id = ReadMethodId(&buf);
+
+  std::vector<uint8_t> bytecodes;
+  JdwpError rc = Dbg::GetBytecodes(class_id, method_id, bytecodes);
+  if (rc != ERR_NONE) {
+    return rc;
+  }
+
+  expandBufAdd4BE(reply, bytecodes.size());
+  for (size_t i = 0; i < bytecodes.size(); ++i) {
+    expandBufAdd1(reply, bytecodes[i]);
+  }
+
+  return ERR_NONE;
+}
+
 /*
  * Given an object reference, return the runtime type of the object
  * (class or array).
@@ -1680,7 +1699,7 @@
   /* Method command set (6) */
   { 6,    1,  M_LineTable,                "Method.LineTable" },
   { 6,    2,  M_VariableTable,            "Method.VariableTable" },
-  { 6,    3,  NULL,                       "Method.Bytecodes" },
+  { 6,    3,  M_Bytecodes,                "Method.Bytecodes" },
   { 6,    4,  NULL,                       "Method.IsObsolete" },
   { 6,    5,  M_VariableTableWithGeneric, "Method.VariableTableWithGeneric" },