auto import //branches/master/...@140412
diff --git a/pdk/docs/source_setup_guide.jd b/pdk/docs/source_setup_guide.jd
new file mode 100755
index 0000000..af63edb
--- /dev/null
+++ b/pdk/docs/source_setup_guide.jd
@@ -0,0 +1,97 @@
+page.title=Android - Source Setup Guide
+pdk.version=.4
+
+@jd:body
+
+<p>This section provides instructions on how to configure your host system to build Android for mobile devices. While Android is designed as host-environment agnostic, it has been tested and is known to work on the following Linux operating system; Ubuntu 6.06 (Dapper), 7.10 (Gutsy), and 8.04. Cygwin is not recommended.</p>
+
+<a name="androidSourceSetupBuildSystemSetupPackages"></a>
+<h2>Installing Packages</h2>
+<h4>Required Packages</h4>
+
+<p>Android requires the following system packages:</p> 
+<p><ul> 
+<li>flex: This lexical analyzer generator is used to read a given input file for a description of a scanner to generate.</li> 
+<li>bison: This is a general-purpose parser generator.</li> 
+<li>gperf: This is a perfect hash function generator.</li> 
+<li>libesd0-dev: This enlightened sound daemon (dev files) is used to mix digitized audio streams for playback by a single device.</li> 
+<li>libwxgtk2.6-dev: This package provides GUI components and other facilities for many different platforms.</li> 
+<li>build-essential: This package contains a list of packages considered fundamental to building Debian packages.</li> 
+</ul></p> 
+
+<h4>Ubuntu 6.06 (Dapper)</h4> 
+ 
+<p>On a clean Dapper system, type the following:</p> 
+<pre class="prettyprint"> 
+% sudo apt-get install flex bison gperf libesd0-dev libwxgtk2.6-dev zlib1g-dev 
+   build-essential
+</pre> 
+<p>This snippet includes an artificial line break to maintain a print-friendly document.</p> 
+
+<h4>Ubuntu 7.10</h4> 
+ 
+<ol><li>The libwxgtk2.6-dev package will only work if the following code is included in your  /etc/apt/source file.
+<p><pre class="prettyprint"> 
+## N.B. software from this repository is ENTIRELY UNSUPPORTED by the Ubuntu
+## team, and may not be under a free license. Please satisfy yourself as to
+## your rights to use the software. Also, please note that software in
+## universe WILL NOT receive any review or updates from the Ubuntu security
+## team.
+# Line commented out by installer because it failed to verify:
+deb http://us.archive.ubuntu.com/ubuntu/ gutsy universe
+# Line commented out by installer because it failed to verify:
+deb-src http://us.archive.ubuntu.com/ubuntu/ gutsy universe
+# Line commented out by installer because it failed to verify:
+deb http://us.archive.ubuntu.com/ubuntu/ gutsy-updates universe
+# Line commented out by installer because it failed to verify:
+deb-src http://us.archive.ubuntu.com/ubuntu/ gutsy-updates universe
+</pre></p></li> 
+<li>Install required packages with the following command:
+<p><pre class="prettyprint"> 
+% sudo apt-get install flex bison gperf libesd0-dev libwxgtk2.6-dev zlib1g-dev
+   build-essential
+</pre></p> 
+This snippet includes an artificial line break to maintain a print-friendly document.
+</li> 
+<li> 
+<p>Install the X11 development environment with the following commands:</p> 
+<p><pre class="prettyprint"> 
+% sudo apt-get install x-dev
+% sudo apt-get install libx11-dev
+% sudo apt-get install libncurses5-dev
+</pre></p> 
+</li> 
+</ol> 
+
+
+<h4>Ubuntu 8.04</h4> 
+ 
+<p>On a clean system, type the following:</p> 
+<pre class="prettify"> 
+% sudo apt-get install flex bison gperf libesd0-dev libwxgtk2.6-dev
+zlib1g-dev build-essential
+% sudo apt-get install x-dev
+% sudo apt-get install libx11-dev
+% sudo apt-get install libncurses5-dev
+% sudo apt-get install sun-java5-jdk
+</pre> 
+
+<a name="androidSourceSetupBuildSystemSetupJavaIntro"></a><h2>Installing Java</h2> 
+ 
+<p>Android source code includes a hard dependency on the Java Developer Kit (JDK) 5.0 Update 12 or greater. The specific file name of the Update 12 package is <code>jdk-1_5_0_12-linux-i586.bin</code>. To download this version of the Java JDK:</p> 
+<p><ol> 
+<li>Navigate to: <a href="http://java.sun.com/products/archive/">http://java.sun.com/products/archive/</a>.</li> 
+<li>Select '5.0 Update 12' from the 'Java 2 Platform Standard Edition (J2SE)' -> 'JDK/JRE - 5.0' field and click 'Go.'</li> 
+<li>Click 'Download JDK.'</li> 
+<li>In the 'Linux Platform' section, click 'Linux self-extracting file' associated with the jdk-1_5_0_12-linux-i586.bin package.</li> 
+<li>Follow the installation instructions.</li> 
+</ol> 
+</p> 
+ 
+<p>Once you have cleanly installed the JDK, modify your PATH environment variable to include <code>&lt;jdk-install-dir&gt;/jdk1.5.0_12/bin</code> at its beginning so that Dapper will use the correct installation. </p> 
+<p><b>Ubuntu 7.10</b></p> 
+<p>An alternative method to quickly install Java is to enable multiverse repo in <code>/etc/apt/sources.list</code> and then execute:</p> 
+<pre class="prettyprint"> 
+% sudo apt-get install sun-java5-jdk
+</pre>
+
diff --git a/simulator/wrapsim/Android.mk b/simulator/wrapsim/Android.mk
index ca9a592..0b7890d 100644
--- a/simulator/wrapsim/Android.mk
+++ b/simulator/wrapsim/Android.mk
@@ -22,7 +22,8 @@
 	Init.c \
 	Intercept.c \
 	Log.c \
-	SimMgr.c
+	SimMgr.c \
+	SysPower.c
 
 LOCAL_C_INCLUDES += prebuilt/common/esd
 
diff --git a/simulator/wrapsim/FakeDev.c b/simulator/wrapsim/FakeDev.c
index 3e223d3..7d2494e 100644
--- a/simulator/wrapsim/FakeDev.c
+++ b/simulator/wrapsim/FakeDev.c
@@ -67,6 +67,9 @@
     { "/dev/input/*",           NULL },
     { "/dev/log/*",             wsOpenDevLog },
     { "/sys/class/power_supply/*", wsOpenDevPower },
+    { "/sys/power/state",       wsOpenSysPower },
+    { "/sys/power/wake_lock",   wsOpenSysPower },
+    { "/sys/power/wake_unlock", wsOpenSysPower },
     { "/sys/devices/platform/android-vibrator/enable",  wsOpenDevVibrator },
     { "/sys/qemu_trace/*",      NULL },
     { NULL,                     NULL }
diff --git a/simulator/wrapsim/FakeDev.h b/simulator/wrapsim/FakeDev.h
index eacbbf5..4781cfc 100644
--- a/simulator/wrapsim/FakeDev.h
+++ b/simulator/wrapsim/FakeDev.h
@@ -108,6 +108,7 @@
 FakeDev* wsOpenDevFb(const char* pathName, int flags);
 FakeDev* wsOpenDevLog(const char* pathName, int flags);
 FakeDev* wsOpenDevPower(const char* pathName, int flags);
+FakeDev* wsOpenSysPower(const char* pathName, int flags);
 FakeDev* wsOpenDevVibrator(const char* pathName, int flags);
 
 /*
diff --git a/simulator/wrapsim/SysPower.c b/simulator/wrapsim/SysPower.c
new file mode 100644
index 0000000..fa7ae0a
--- /dev/null
+++ b/simulator/wrapsim/SysPower.c
@@ -0,0 +1,140 @@
+/*
+ * Copyright 2009 The Android Open Source Project
+ *
+ * Magic entries in /sys/power/.
+ */
+#include "Common.h"
+
+#include <stdlib.h>
+#include <string.h>
+#include <ctype.h>
+
+/*
+ * Map filename to device index.
+ *
+ * [ not using DeviceIndex -- would be useful if we need to return something
+ * other than a static string ]
+ */
+static const struct {
+    const char*     name;
+    //DeviceIndex     idx;
+    const char*     data;
+} gDeviceMap[] = {
+    { "state",
+        "mem\n" },
+    { "wake_lock",
+        "\n" },
+    { "wake_unlock",
+        "KeyEvents PowerManagerService radio-interface\n" },
+};
+
+/*
+ * Power driver state.
+ *
+ * Right now we just ignore everything written.
+ */
+typedef struct PowerState {
+    int         which;
+} PowerState;
+
+
+/*
+ * Figure out who we are, based on "pathName".
+ */
+static void configureInitialState(const char* pathName, PowerState* powerState)
+{
+    const char* cp = pathName + strlen("/sys/power/");
+    int i;
+
+    powerState->which = -1;
+    for (i = 0; i < (int) (sizeof(gDeviceMap) / sizeof(gDeviceMap[0])); i++) {
+        if (strcmp(cp, gDeviceMap[i].name) == 0) {
+            powerState->which = i;
+            break;
+        }
+    }
+
+    if (powerState->which == -1) {
+        wsLog("Warning: access to unknown power device '%s'\n", pathName);
+        return;
+    }
+}
+
+/*
+ * Free up the state structure.
+ */
+static void freeState(PowerState* powerState)
+{
+    free(powerState);
+}
+
+/*
+ * Read data from the device.
+ *
+ * We don't try to keep track of how much was read -- existing clients just
+ * try to read into a large buffer.
+ */
+static ssize_t readPower(FakeDev* dev, int fd, void* buf, size_t count)
+{
+    PowerState* state = (PowerState*) dev->state;
+    int dataLen;
+
+    wsLog("%s: read %d\n", dev->debugName, count);
+
+    if (state->which < 0 ||
+        state->which >= (int) (sizeof(gDeviceMap)/sizeof(gDeviceMap[0])))
+    {
+        return 0;
+    }
+
+    const char* data = gDeviceMap[state->which].data;
+    size_t strLen = strlen(data);
+
+    while(strLen == 0)
+        sleep(10); // block forever
+
+    ssize_t copyCount = (strLen < count) ? strLen : count;
+    memcpy(buf, data, copyCount);
+    return copyCount;
+}
+
+/*
+ * Ignore the request.
+ */
+static ssize_t writePower(FakeDev* dev, int fd, const void* buf, size_t count)
+{
+    wsLog("%s: write %d bytes\n", dev->debugName, count);
+    return count;
+}
+
+/*
+ * Free up our state before closing down the fake descriptor.
+ */
+static int closePower(FakeDev* dev, int fd)
+{
+    freeState((PowerState*)dev->state);
+    dev->state = NULL;
+    return 0;
+}
+
+/*
+ * Open a power device.
+ */
+FakeDev* wsOpenSysPower(const char* pathName, int flags)
+{
+    FakeDev* newDev = wsCreateFakeDev(pathName);
+    if (newDev != NULL) {
+        newDev->read = readPower;
+        newDev->write = writePower;
+        newDev->ioctl = NULL;
+        newDev->close = closePower;
+
+        PowerState* powerState = calloc(1, sizeof(PowerState));
+
+        configureInitialState(pathName, powerState);
+        newDev->state = powerState;
+    }
+
+    return newDev;
+}
+
diff --git a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/AndroidDebugBridge.java b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/AndroidDebugBridge.java
index 795bf88..0957171 100644
--- a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/AndroidDebugBridge.java
+++ b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/AndroidDebugBridge.java
@@ -194,6 +194,7 @@
         HandleThread.register(monitorThread);
         HandleHeap.register(monitorThread);
         HandleWait.register(monitorThread);
+        HandleProfiling.register(monitorThread);
     }
 
     /**
diff --git a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHeap.java b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHeap.java
index 5752b86..5111638 100644
--- a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHeap.java
+++ b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHeap.java
@@ -32,6 +32,7 @@
     public static final int CHUNK_HPEN = type("HPEN");
     public static final int CHUNK_HPSG = type("HPSG");
     public static final int CHUNK_HPGC = type("HPGC");
+    public static final int CHUNK_HPDU = type("HPDU");
     public static final int CHUNK_REAE = type("REAE");
     public static final int CHUNK_REAQ = type("REAQ");
     public static final int CHUNK_REAL = type("REAL");
@@ -98,6 +99,8 @@
             client.update(Client.CHANGE_HEAP_DATA);
         } else if (type == CHUNK_HPSG) {
             handleHPSG(client, data);
+        } else if (type == CHUNK_HPDU) {
+            handleHPDU(client, data);
         } else if (type == CHUNK_REAQ) {
             handleREAQ(client, data);
             client.update(Client.CHANGE_HEAP_ALLOCATION_STATUS);
@@ -221,6 +224,44 @@
     }
 
     /**
+     * Sends an HPDU request to the client.
+     *
+     * We will get an HPDU response when the heap dump has completed.  On
+     * failure we get a generic failure response.
+     *
+     * @param fileName name of output file (on device)
+     */
+    public static void sendHPDU(Client client, String fileName)
+        throws IOException {
+        ByteBuffer rawBuf = allocBuffer(4 + fileName.length() * 2);
+        JdwpPacket packet = new JdwpPacket(rawBuf);
+        ByteBuffer buf = getChunkDataBuf(rawBuf);
+
+        buf.putInt(fileName.length());
+        putString(buf, fileName);
+
+        finishChunkPacket(packet, CHUNK_HPDU, buf.position());
+        Log.d("ddm-heap", "Sending " + name(CHUNK_HPDU) + " '" + fileName +"'");
+        client.sendAndConsume(packet, mInst);
+    }
+
+    /*
+     * Handle notification of completion of a HeaP DUmp.
+     */
+    private void handleHPDU(Client client, ByteBuffer data) {
+        byte result;
+
+        result = data.get();
+
+        if (result == 0) {
+            Log.i("ddm-heap", "Heap dump request has finished");
+            // TODO: stuff
+        } else {
+            Log.w("ddm-heap", "Heap dump request failed (check device log)");
+        }
+    }
+
+    /**
      * Sends a REAE (REcent Allocation Enable) request to the client.
      */
     public static void sendREAE(Client client, boolean enable)
diff --git a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHello.java b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHello.java
index 5ba5aeb..fb9697c 100644
--- a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHello.java
+++ b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleHello.java
@@ -20,11 +20,12 @@
 import java.nio.ByteBuffer;
 
 /**
- * Handle the "hello" chunk (HELO).
+ * Handle the "hello" chunk (HELO) and feature discovery.
  */
 final class HandleHello extends ChunkHandler {
 
     public static final int CHUNK_HELO = ChunkHandler.type("HELO");
+    public static final int CHUNK_FEAT = ChunkHandler.type("FEAT");
 
     private static final HandleHello mInst = new HandleHello();
 
@@ -65,6 +66,8 @@
         if (type == CHUNK_HELO) {
             assert isReply;
             handleHELO(client, data);
+        } else if (type == CHUNK_FEAT) {
+            handleFEAT(client, data);
         } else {
             handleUnknownChunk(client, type, data, isReply, msgId);
         }
@@ -126,5 +129,37 @@
             + " ID=0x" + Integer.toHexString(packet.getId()));
         client.sendAndConsume(packet, mInst);
     }
+
+    /**
+     * Handle a reply to our FEAT request.
+     */
+    private static void handleFEAT(Client client, ByteBuffer data) {
+        int featureCount;
+        int i;
+
+        featureCount = data.getInt();
+        for (i = 0; i < featureCount; i++) {
+            int len = data.getInt();
+            String feature = getString(data, len);
+
+            Log.d("ddm-hello", "Feature: " + feature);
+        }
+    }
+
+    /**
+     * Send a FEAT request to the client.
+     */
+    public static void sendFEAT(Client client) throws IOException {
+        ByteBuffer rawBuf = allocBuffer(0);
+        JdwpPacket packet = new JdwpPacket(rawBuf);
+        ByteBuffer buf = getChunkDataBuf(rawBuf);
+
+        // no data
+
+        finishChunkPacket(packet, CHUNK_FEAT, buf.position());
+        Log.d("ddm-heap", "Sending " + name(CHUNK_FEAT));
+        client.sendAndConsume(packet, mInst);
+    }
+
 }
 
diff --git a/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleProfiling.java b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleProfiling.java
new file mode 100644
index 0000000..0789655
--- /dev/null
+++ b/tools/ddms/libs/ddmlib/src/com/android/ddmlib/HandleProfiling.java
@@ -0,0 +1,166 @@
+/*
+ * Copyright (C) 2009 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.ddmlib;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+
+/**
+ * Handle heap status updates.
+ */
+final class HandleProfiling extends ChunkHandler {
+
+    public static final int CHUNK_MPRS = type("MPRS");
+    public static final int CHUNK_MPRE = type("MPRE");
+    public static final int CHUNK_MPRQ = type("MPRQ");
+
+    private static final HandleProfiling mInst = new HandleProfiling();
+
+    private HandleProfiling() {}
+
+    /**
+     * Register for the packets we expect to get from the client.
+     */
+    public static void register(MonitorThread mt) {
+        mt.registerChunkHandler(CHUNK_MPRE, mInst);
+        mt.registerChunkHandler(CHUNK_MPRQ, mInst);
+    }
+
+    /**
+     * Client is ready.
+     */
+    @Override
+    public void clientReady(Client client) throws IOException {}
+
+    /**
+     * Client went away.
+     */
+    @Override
+    public void clientDisconnected(Client client) {}
+
+    /**
+     * Chunk handler entry point.
+     */
+    @Override
+    public void handleChunk(Client client, int type, ByteBuffer data,
+        boolean isReply, int msgId) {
+
+        Log.d("ddm-prof", "handling " + ChunkHandler.name(type));
+
+        if (type == CHUNK_MPRE) {
+            handleMPRE(client, data);
+        } else if (type == CHUNK_MPRQ) {
+            handleMPRQ(client, data);
+        } else {
+            handleUnknownChunk(client, type, data, isReply, msgId);
+        }
+    }
+
+    /**
+     * Send a MPRS (Method PRofiling Start) request to the client.
+     *
+     * The arguments to this method will eventually be passed to
+     * android.os.Debug.startMethodTracing() on the device.
+     *
+     * @param fileName is the name of the file to which profiling data
+     *          will be written (on the device); it will have ".trace"
+     *          appended if necessary
+     * @param bufferSize is the desired buffer size in bytes (8MB is good)
+     * @param flags see startMethodTracing() docs; use 0 for default behavior
+     */
+    public static void sendMPRS(Client client, String fileName, int bufferSize,
+        int flags) throws IOException {
+
+        ByteBuffer rawBuf = allocBuffer(3*4 + fileName.length() * 2);
+        JdwpPacket packet = new JdwpPacket(rawBuf);
+        ByteBuffer buf = getChunkDataBuf(rawBuf);
+
+        buf.putInt(bufferSize);
+        buf.putInt(flags);
+        buf.putInt(fileName.length());
+        putString(buf, fileName);
+
+        finishChunkPacket(packet, CHUNK_MPRS, buf.position());
+        Log.d("ddm-prof", "Sending " + name(CHUNK_MPRS) + " '" + fileName
+            + "', size=" + bufferSize + ", flags=" + flags);
+        client.sendAndConsume(packet, mInst);
+    }
+
+    /**
+     * Send a MPRE (Method PRofiling End) request to the client.
+     */
+    public static void sendMPRE(Client client) throws IOException {
+        ByteBuffer rawBuf = allocBuffer(0);
+        JdwpPacket packet = new JdwpPacket(rawBuf);
+        ByteBuffer buf = getChunkDataBuf(rawBuf);
+
+        // no data
+
+        finishChunkPacket(packet, CHUNK_MPRE, buf.position());
+        Log.d("ddm-prof", "Sending " + name(CHUNK_MPRE));
+        client.sendAndConsume(packet, mInst);
+    }
+
+    /**
+     * Handle notification that method profiling has finished writing
+     * data to disk.
+     */
+    private void handleMPRE(Client client, ByteBuffer data) {
+        byte result;
+
+        result = data.get();
+
+        if (result == 0) {
+            Log.i("ddm-prof", "Method profiling has finished");
+        } else {
+            Log.w("ddm-prof", "Method profiling has failed (check device log)");
+        }
+
+        // TODO: stuff
+    }
+
+    /**
+     * Send a MPRQ (Method PRofiling Query) request to the client.
+     */
+    public static void sendMPRQ(Client client) throws IOException {
+        ByteBuffer rawBuf = allocBuffer(0);
+        JdwpPacket packet = new JdwpPacket(rawBuf);
+        ByteBuffer buf = getChunkDataBuf(rawBuf);
+
+        // no data
+
+        finishChunkPacket(packet, CHUNK_MPRQ, buf.position());
+        Log.d("ddm-prof", "Sending " + name(CHUNK_MPRQ));
+        client.sendAndConsume(packet, mInst);
+    }
+
+    /**
+     * Receive response to query.
+     */
+    private void handleMPRQ(Client client, ByteBuffer data) {
+        byte result;
+
+        result = data.get();
+
+        if (result == 0) {
+            Log.i("ddm-prof", "Method profiling is not running");
+        } else {
+            Log.i("ddm-prof", "Method profiling is running");
+        }
+    }
+}
+