diff --git a/mountd/ASEC.c b/mountd/ASEC.c
new file mode 100644
index 0000000..a6aab9c
--- /dev/null
+++ b/mountd/ASEC.c
@@ -0,0 +1,774 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+/*
+** Android Secure External Cache 
+*/
+
+#include "mountd.h"
+
+#include <stdio.h>
+#include <unistd.h>
+#include <string.h>
+#include <fcntl.h>
+#include <dirent.h>
+#include <ctype.h>
+#include <pwd.h>
+#include <stdlib.h>
+#include <poll.h>
+#include <errno.h>
+
+#include <sys/ioctl.h>
+#include <sys/mount.h>
+#include <sys/stat.h>
+
+#include <linux/dm-ioctl.h>
+#include <linux/loop.h>
+
+#include <cutils/properties.h>
+#include <cutils/misc.h>
+
+#include "ASEC.h"
+
+//#define MODULE_FAILURE_IS_FATAL
+
+extern int init_module(void *, unsigned long, const char *);
+extern int delete_module(const char *, unsigned int);
+
+struct asec_context
+{
+    char *name;           // Device mapper volume name
+    char *srcPath;        // Path to the source (original) mount
+    char *backingFile;    // Name of the image file
+    unsigned int sectors; // Number of sectors
+    char *dstPath;        // Destination mount point
+    char *crypt;          // Crypt options
+
+    boolean needs_format;
+    boolean started;
+    int cacheFd;
+    int lo_num;
+    int dm_num;
+    unsigned char key[16];
+};
+
+static const char *MODULES[] = { "dm_mod", "crypto", "crypto_algapi", "crypto_blkcipher", 
+                                 "cryptomgr", "dm_crypt", "jbd",  
+                                 "twofish_common", "twofish", "cbc",
+                                 "mbcache", "ext3",
+                                 NULL };
+static const char KEY_PATH[] = "/data/system/asec.key";
+static const char MODULE_PATH[] = "/system/lib/modules";
+static const char MKE2FS_PATH[] = "/system/bin/mke2fs";
+static const char E2FSCK_PATH[] = "/system/bin/e2fsck";
+
+boolean AsecIsStarted(void *Handle)
+{
+    struct asec_context *ctx = (struct asec_context *) Handle;
+
+    return ctx->started;
+}
+
+const char *AsecMountPoint(void *Handle)
+{
+    struct asec_context *ctx = (struct asec_context *) Handle;
+
+    return ctx->dstPath;
+}
+
+static boolean AsecIsEnabled()
+{
+    char value[PROPERTY_VALUE_MAX];
+    int  enabled;
+
+    property_get(ASEC_ENABLED, value, "0");
+
+    if (atoi(value) == 1)
+        return true;
+    return false;
+}
+
+void *AsecInit(const char *Name, const char *SrcPath, const char *BackingFile,
+               const char *Size, const char *DstPath, const char *Crypt)
+{
+    struct asec_context *ctx;
+
+    if (!AsecIsEnabled())
+        return NULL;
+
+    LOG_ASEC("AsecInit(%s, %s, %s, %s, %s, %s):\n",
+             Name, SrcPath, BackingFile, Size, DstPath, Crypt);
+
+    if (!Name || !SrcPath || !BackingFile || !Size || !DstPath || !Crypt) {
+        LOG_ERROR("AsecInit(): Invalid arguments\n");
+        return NULL;
+    }
+
+    if (!(ctx = malloc(sizeof(struct asec_context)))) {
+        LOG_ERROR("AsecInit(): Out of memory\n");
+        return NULL;
+    }
+
+    memset(ctx, 0, sizeof(struct asec_context));
+    ctx->name = strdup(Name);
+    ctx->srcPath = strdup(SrcPath);
+    ctx->backingFile = strdup(BackingFile);
+    ctx->sectors = atoi(Size);
+    ctx->dstPath = strdup(DstPath);
+    ctx->crypt = strdup(Crypt);
+    return ctx;
+}
+
+void AsecDeinit(void *Handle)
+{
+    struct asec_context *ctx = (struct asec_context *) Handle;
+
+    free(ctx->name);
+    free(ctx->srcPath);
+    free(ctx->backingFile);
+    free(ctx->dstPath);
+    free(ctx->crypt);
+
+    free(ctx);
+}
+
+static int AsecLoadModules()
+{
+    int i;
+
+    for (i = 0; MODULES[i] != NULL; i++) {
+	const char *moduleName = MODULES[i];
+        char moduleFile[255];
+        int rc = 0;
+        void *module;
+        unsigned int size;
+
+        sprintf(moduleFile, "%s/%s.ko", MODULE_PATH, moduleName);
+        module = load_file(moduleFile, &size);
+        if (!module) {
+            LOG_ERROR("Failed to load module %s (%d)\n", moduleFile, errno);
+            return -1;
+        }
+
+        rc = init_module(module, size, "");
+        free(module);
+        if (rc && errno != EEXIST) {
+            LOG_ERROR("Failed to init module %s (%d)\n", moduleFile, errno);
+            return -errno;
+        }
+    }
+    return 0;
+}
+
+static int AsecUnloadModules()
+{
+    int i, j, rc;
+
+    for (i = 0; MODULES[i] != NULL; i++);
+
+    for (j = (i - 1); j >= 0; j--) {
+	const char *moduleName = MODULES[j];
+        int maxretry = 10;
+        while(maxretry-- > 0) {
+            rc = delete_module(moduleName, O_NONBLOCK | O_EXCL);
+            if (rc < 0 && errno == EAGAIN)
+                usleep(500000);
+            else
+                break;
+        }
+        if (rc != 0) {
+            LOG_ERROR("Failed to unload module %s\n", moduleName);
+            return -errno;
+        }
+    }
+    return 0;
+}
+
+static int AsecGenerateKey(struct asec_context *ctx)
+{
+    LOG_ASEC("AsecGenerateKey():\n");
+
+    memset((void *) ctx->key, 0x69, sizeof(ctx->key));
+    return 0;
+}
+
+static int AsecLoadGenerateKey(struct asec_context *ctx)
+{
+    int fd;
+    int rc = 0;
+
+    if ((fd = open(KEY_PATH, O_RDWR | O_CREAT, 0600)) < 0) {
+        LOG_ERROR("Error opening / creating keyfile (%d)\n", errno);
+        return -errno;
+    }
+
+    if (read(fd, ctx->key, sizeof(ctx->key)) != sizeof(ctx->key)) {
+        LOG_ASEC("Generating key\n");
+        if ((rc = AsecGenerateKey(ctx)) < 0) {
+            LOG_ERROR("Error generating key (%d)\n", rc);
+            goto out;
+        }
+        if (write(fd, ctx->key, sizeof(ctx->key)) != sizeof(ctx->key)) {
+            LOG_ERROR("Error writing keyfile (%d)\n", errno);
+            rc = -1;
+            goto out;
+        }
+    }
+    
+ out:
+    close (fd);
+    return rc;
+}
+
+static int AsecFormatFilesystem(struct asec_context *ctx)
+{
+    char cmdline[255];
+    int rc;
+
+    sprintf(cmdline,
+            "%s -b 4096 -m 1 -j -L \"%s\" /dev/block/dm-%d",
+            MKE2FS_PATH, ctx->name, ctx->dm_num);
+
+    LOG_ASEC("Formatting filesystem (%s)\n", cmdline);
+    // XXX: PROTECT FROM VIKING KILLER
+    if ((rc = system(cmdline)) < 0) {
+        LOG_ERROR("Error executing format command (%d)\n", errno);
+        return -errno;
+    }
+
+    rc = WEXITSTATUS(rc);
+
+    if (!rc) {
+        LOG_ASEC("Format completed\n");
+    } else {
+        LOG_ASEC("Format failed (%d)\n", rc);
+    }
+
+    return rc;
+}
+
+static int AsecCheckFilesystem(struct asec_context *ctx)
+{
+    char cmdline[255];
+    int rc;
+
+    sprintf(cmdline, "%s -p /dev/block/dm-%d", E2FSCK_PATH, ctx->dm_num);
+
+    LOG_ASEC("Checking filesystem (%s)\n", cmdline);
+    // XXX: PROTECT FROM VIKING KILLER
+    if ((rc = system(cmdline)) < 0) {
+        LOG_ERROR("Error executing check command (%d)\n", errno);
+        return -errno;
+    }
+
+    rc = WEXITSTATUS(rc);
+
+    if (rc == 0) {
+        LOG_ASEC("ASEC volume '%s' had no errors\n", ctx->name);
+    } else if (rc == 1) {
+        LOG_ASEC("ASEC volume '%s' had corrected errors\n", ctx->name);
+        rc = 0;
+    } else if (rc == 2) {
+        LOG_ERROR("ASEC volume '%s' had corrected errors (system should be rebooted)\n", ctx->name);
+    } else if (rc == 4) {
+        LOG_ERROR("ASEC volume '%s' had uncorrectable errors\n", ctx->name);
+    } else if (rc == 8) {
+        LOG_ERROR("Operational error while checking volume '%s'\n", ctx->name);
+    } else {
+        LOG_ERROR("Unknown e2fsck exit code (%d)\n", rc);
+    }
+    return rc;
+}
+
+static int AsecOpenCreateCache(struct asec_context *ctx)
+{
+    char filepath[255];
+
+    sprintf(filepath, "%s/%s", ctx->srcPath, ctx->backingFile);
+
+    if ((ctx->cacheFd = open(filepath, O_RDWR)) < 0) {
+        if (errno == ENOENT) {
+            int rc = 0;
+
+            LOG_ASEC("Creating cache file (%u sectors)\n", ctx->sectors);
+            if ((ctx->cacheFd = creat(filepath, 0600)) < 0) {
+                LOG_ERROR("Error creating cache (%d)\n", errno);
+                return -errno;
+            }
+            if (ftruncate(ctx->cacheFd, ctx->sectors * 512) < 0) {
+                LOG_ERROR("Error truncating cache (%d)\n", errno);
+                close(ctx->cacheFd);
+                unlink(filepath);
+                return -errno;
+            }
+            LOG_ASEC("Cache created (%u sectors) \n", ctx->sectors);
+            close(ctx->cacheFd); // creat() is WRONLY
+           
+            if ((ctx->cacheFd = open(filepath, O_RDWR)) < 0) {
+               LOG_ERROR("Error opening cache file (%d)\n", errno);
+                close(ctx->cacheFd);
+                unlink(filepath);
+                return -errno;
+            }
+
+            ctx->needs_format = 1;
+        } else
+            return -errno;
+    } else {
+        struct stat stat_buf;
+
+        if (fstat(ctx->cacheFd, &stat_buf) < 0) {
+            LOG_ERROR("Failed to fstat cache (%d)\n", errno);
+            close(ctx->cacheFd);
+            return -errno;
+        }
+        if (stat_buf.st_size != ctx->sectors * 512) {
+            LOG_ERROR("Cache size %lld != configured size %u\n",
+                      stat_buf.st_size, ctx->sectors * 512);
+        }
+
+        // XXX: Verify volume label matches ctx->name
+    }
+
+    return 0;
+}
+
+static void AsecCloseCache(struct asec_context *ctx)
+{
+    close(ctx->cacheFd);
+}
+
+static void *_align(void *ptr, unsigned int a)
+{
+        register unsigned long agn = --a;
+
+        return (void *) (((unsigned long) ptr + agn) & ~agn);
+}
+
+static struct dm_ioctl *_dm_ioctl_setup(struct asec_context *ctx, int flags)
+{
+    void *buffer;
+    void *p;
+    const size_t min_size = 16 * 1024;
+    size_t len = sizeof(struct dm_ioctl);
+    struct dm_ioctl *io;
+    struct dm_target_spec *tgt;
+    int i;
+    char params[1024];
+    char key[80];
+
+    key[0] = '\0';
+
+    for (i = 0; i < (int) sizeof(ctx->key); i++) {
+        char tmp[8];
+
+        sprintf(tmp, "%02x", ctx->key[i]);
+        strcat(key, tmp);
+    }
+
+    // XXX: Handle ctx->crypt 
+    sprintf(params, "twofish %s 0 /dev/block/loop%d 0", key, ctx->lo_num);
+ 
+    if (len < min_size)
+        len = min_size;
+
+    if (!(buffer = malloc(len))) {
+        LOG_ERROR("Unable to allocate memory\n");
+        return NULL;
+    }
+
+    memset(buffer, 0, len);
+    io = buffer;
+    tgt = (struct dm_target_spec *) &buffer[sizeof(struct dm_ioctl)];
+    
+    io->version[0] = 4;
+    io->version[1] = 0;
+    io->version[2] = 0;
+
+    io->data_size = len;
+    io->data_start = sizeof(struct dm_ioctl);
+
+    io->flags = flags;
+    io->dev = 0; 
+
+    io->target_count = 1;
+    io->event_nr = 1;
+    strncpy(io->name, ctx->name, sizeof(io->name));
+
+    tgt->status = 0;
+    tgt->sector_start = 0;
+    tgt->length = ctx->sectors;
+    strncpy(tgt->target_type, "crypt", sizeof(tgt->target_type));
+
+    p = buffer + sizeof(struct dm_ioctl) + sizeof(struct dm_target_spec);
+    strcpy((char *) p, params);
+    p+= strlen(params) + 1;
+
+    p = _align(p, 8);
+    tgt->next = p - buffer;
+
+    return io;
+}
+
+static int FindNextAvailableDm()
+{
+    int i;
+
+    for (i = 0; i < 8; i++) {
+        char path[255];
+        sprintf(path, "/dev/block/dm-%d", i);
+        if ((access(path, F_OK) < 0) && (errno == ENOENT))
+            return i;
+    }
+
+    LOG_ERROR("Out of device mapper numbers\n");
+    return -1;
+}
+
+static int AsecCreateDeviceMapping(struct asec_context *ctx)
+{
+    struct dm_ioctl       *io;
+    int                   dmFd;
+    int                   rc = 0;
+
+    ctx->dm_num = FindNextAvailableDm();
+
+    if ((dmFd = open("/dev/device-mapper", O_RDWR)) < 0) {
+        LOG_ERROR("Error opening device mapper (%d)\n", errno);
+        return -errno;
+    }
+
+    if (!(io = _dm_ioctl_setup(ctx, 0))) {
+        LOG_ERROR("Unable to setup ioctl (out of memory)\n");
+        close(dmFd);
+        return -ENOMEM;
+    }
+
+    if ((rc = ioctl(dmFd, DM_DEV_CREATE, io)) < 0) {
+        LOG_ERROR("device-mapper create ioctl failed (%d)\n", errno);
+        rc = -errno;
+        goto out_free;
+    } 
+
+    free(io);
+
+    if (!(io = _dm_ioctl_setup(ctx, DM_STATUS_TABLE_FLAG))) {
+        LOG_ERROR("Unable to setup ioctl (out of memory)\n");
+        rc = -ENOMEM;
+        goto out_nofree;
+    }
+ 
+    if ((rc = ioctl(dmFd, DM_TABLE_LOAD, io)) < 0) {
+        LOG_ERROR("device-mapper load ioctl failed (%d)\n", errno);
+        rc = -errno;
+        goto out_free;
+    }
+
+    free(io);
+ 
+    if (!(io = _dm_ioctl_setup(ctx, 0))) {
+        LOG_ERROR("Unable to setup ioctl (out of memory)\n");
+        rc = -ENOMEM;
+        goto out_nofree;
+    }
+
+    if ((rc = ioctl(dmFd, DM_DEV_SUSPEND, io)) < 0) {
+        LOG_ERROR("device-mapper resume ioctl failed (%d)\n", errno);
+        rc = -errno;
+        goto out_free;
+    }
+
+out_free:
+    free (io);
+out_nofree:
+    close (dmFd);
+    return rc;
+}
+
+static int AsecDestroyDeviceMapping(struct asec_context *ctx)
+{
+    struct dm_ioctl       *io;
+    int                   dmFd;
+    int                   rc = 0;
+
+    if ((dmFd = open("/dev/device-mapper", O_RDWR)) < 0) {
+        LOG_ERROR("Error opening device mapper (%d)\n", errno);
+        return -errno;
+    }
+
+    if (!(io = _dm_ioctl_setup(ctx, DM_PERSISTENT_DEV_FLAG))) {
+        LOG_ERROR("Unable to setup ioctl (out of memory)\n");
+        rc = -ENOMEM;
+        goto out_nofree;
+    }
+
+    if ((rc = ioctl(dmFd, DM_DEV_REMOVE, io)) < 0) {
+        LOG_ERROR("device-mapper remove ioctl failed (%d)\n", errno);
+        rc = -errno;
+        goto out_free;
+    } 
+
+out_free:
+    free (io);
+out_nofree:
+    close (dmFd);
+    return rc;
+}
+
+static int AsecMountCache(struct asec_context *ctx)
+{
+    int flags = MS_NODEV | MS_NOEXEC | MS_NOSUID | MS_NOATIME | MS_NODIRATIME;
+    char devname[255];
+
+    if (access(ctx->dstPath, R_OK)) {
+        LOG_ERROR("Destination mount point '%s' unavailable (%d)\n", ctx->dstPath, errno);
+        return -errno;
+    }
+
+    sprintf(devname, "/dev/block/dm-%d", ctx->dm_num);
+
+    if (mount(devname, ctx->dstPath, "ext3", flags, NULL)) {
+        LOG_ERROR("ASEC mount failed (%d)\n", errno);
+        return -errno;
+    }
+    
+    return 0;
+}
+
+static int AsecUnmountCache(struct asec_context *ctx)
+{
+    if (umount(ctx->dstPath)) {
+        if (errno == EBUSY) {
+            LOG_ASEC("ASEC volume '%s' still busy\n", ctx->name);
+        } else {
+            LOG_ERROR("ASEC umount failed (%d)\n", errno);
+        }
+        return -errno;
+    }
+    LOG_ASEC("ASEC volume '%s' unmounted\n", ctx->name);
+    return 0;
+}
+
+static int FindNextAvailableLoop()
+{
+    int i;
+
+    for (i = 0; i < MAX_LOOP; i++) {
+        struct loop_info info;
+        char devname[255];
+        int fd;
+
+        sprintf(devname, "/dev/block/loop%d", i);
+
+        if ((fd = open(devname, O_RDONLY)) < 0) {
+            LOG_ERROR("Unable to open %s (%d)\n", devname, errno);
+            return -errno;
+        }
+
+        if (ioctl(fd, LOOP_GET_STATUS, &info) < 0) {
+            close(fd);
+
+            if (errno == ENXIO)
+                return i;
+
+            LOG_ERROR("Unable to get loop status for %s (%d)\n", devname, errno);
+            return -errno;
+        }
+        close(fd);
+    }
+    return -ENXIO;
+}
+
+static int AsecCreateLoop(struct asec_context *ctx)
+{
+    char devname[255];
+    int device_fd;
+    int rc = 0;
+
+    ctx->lo_num = FindNextAvailableLoop();
+    if (ctx->lo_num < 0) {
+        LOG_ERROR("No loop devices available\n");
+        return -ENXIO;
+    }
+
+    sprintf(devname, "/dev/block/loop%d", ctx->lo_num);
+    device_fd = open(devname, O_RDWR);
+    if (device_fd < 0) {
+        LOG_ERROR("failed to open loop device (%d)\n", errno);
+        return -errno;
+    }
+
+    if (ioctl(device_fd, LOOP_SET_FD, ctx->cacheFd) < 0) {
+        LOG_ERROR("loop_set_fd ioctl failed (%d)\n", errno);
+        rc = -errno;
+    }
+    close(device_fd);
+    return rc;
+}
+
+static int AsecDestroyLoop(struct asec_context *ctx)
+{
+    char devname[255];
+    int device_fd;
+    int rc = 0;
+
+    sprintf(devname, "/dev/block/loop%d", ctx->lo_num);
+    device_fd = open(devname, O_RDONLY);
+    if (device_fd < 0) {
+        LOG_ERROR("Failed to open loop (%d)\n", errno);
+        return -errno;
+    }
+
+    if (ioctl(device_fd, LOOP_CLR_FD, 0) < 0) {
+        LOG_ERROR("Failed to destroy loop (%d)\n", errno);
+        rc = -errno;
+    }
+
+    close(device_fd);
+    return rc;
+}
+
+int AsecStart(void *Handle)
+{
+    struct asec_context *ctx = (struct asec_context *) Handle;
+    char value[PROPERTY_VALUE_MAX];
+    int rc = 0;
+
+    if (!ctx)
+        return -EINVAL;
+
+    if (ctx->started)
+        return -EBUSY;
+
+    LOG_ASEC("AsecStart(%s):\n", ctx->name);
+
+    NotifyAsecState(ASEC_BUSY, ctx->dstPath);
+
+    if ((rc = AsecLoadModules()) < 0) {
+        LOG_ERROR("AsecStart: Failed to load kernel modules\n");
+#ifdef MODULE_FAILURE_IS_FATAL
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	return rc;
+#endif
+    }
+
+    if ((rc = AsecLoadGenerateKey(ctx))) {
+        LOG_ERROR("AsecStart: Failed to load / generate key\n");
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	return rc;
+    }
+    
+    if ((rc = AsecOpenCreateCache(ctx)) < 0) {
+        LOG_ERROR("AsecStart: Failed to open / create cache\n");
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	return rc;
+    }
+
+    if ((rc = AsecCreateLoop(ctx)) < 0) {
+        LOG_ERROR("AsecStart: Failed to create loop\n");
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	goto fail_closecache;
+    }
+
+    if ((rc = AsecCreateDeviceMapping(ctx)) < 0) {
+        LOG_ERROR("AsecStart: Failed to create devmapping (%d)\n", rc);
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+        goto fail_destroyloop;
+    }
+    
+    if (ctx->needs_format) {
+        if ((rc = AsecFormatFilesystem(ctx))) {
+            LOG_ERROR("AsecStart: Failed to format cache (%d)\n", rc);
+            NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+            goto fail_destroydm;
+        }
+        ctx->needs_format = 0;
+    } else {
+        if ((rc = AsecCheckFilesystem(ctx))) {
+            LOG_ERROR("AsecStart: Failed to check filesystem (%d)\n", rc);
+            NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+            goto fail_destroydm;
+        }
+    }
+
+    if ((rc = AsecMountCache(ctx)) < 0) {
+        LOG_ERROR("AsecStart: Failed to mount cache (%d)\n", rc);
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+        goto fail_destroydm;
+    }
+    
+    NotifyAsecState(ASEC_AVAILABLE, ctx->dstPath);
+    ctx->started = true;
+
+    return rc;
+
+ fail_destroydm:
+    AsecDestroyDeviceMapping(ctx);
+ fail_destroyloop:
+    AsecDestroyLoop(ctx);
+ fail_closecache:
+    AsecCloseCache(ctx);
+    return rc;
+}
+
+int AsecStop(void *Handle)
+{
+    struct asec_context *ctx = (struct asec_context *) Handle;
+    int rc = 0;
+
+    if (!ctx->started)
+        return -EINVAL;
+
+    LOG_ASEC("AsecStop(%s):\n", ctx->name);
+
+    NotifyAsecState(ASEC_BUSY, ctx->dstPath);
+
+    if ((rc = AsecUnmountCache(ctx)) < 0) {
+        LOG_ERROR("AsecStop: Failed to unmount cache (%d)\n", rc);
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	return rc;
+    }
+
+    if ((rc = AsecDestroyDeviceMapping(ctx)) < 0) {
+        LOG_ERROR("AsecStop: Failed to destroy devmapping (%d)\n", rc);
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	return rc;
+    }
+
+    if ((rc = AsecDestroyLoop(ctx)) < 0) {
+        LOG_ERROR("AsecStop: Failed to destroy loop device (%d)\n", rc);
+        NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	return rc;
+    }
+
+    AsecCloseCache(ctx);
+ 
+    if ((rc = AsecUnloadModules()) < 0) {
+        if (rc == -EAGAIN) {
+            LOG_ASEC("AsecStop: Kernel modules still in use\n");
+        } else {
+            LOG_ERROR("AsecStop: Failed to unload kernel modules (%d)\n", rc);
+#ifdef MODULE_FAILURE_IS_FATAL
+            NotifyAsecState(ASEC_FAILED_INTERR, ctx->dstPath);
+	    return rc;
+#endif
+        }
+    }
+
+    ctx->started = false;
+    NotifyAsecState(ASEC_DISABLED, ctx->dstPath);
+    return rc;
+}
diff --git a/mountd/ASEC.h b/mountd/ASEC.h
new file mode 100644
index 0000000..c87b288
--- /dev/null
+++ b/mountd/ASEC.h
@@ -0,0 +1,66 @@
+#ifndef _ASEC_H
+#define _ASEC_H
+
+#define ASEC_STORES_MAX 4
+#define MAX_LOOP 8
+
+typedef enum AsecState {
+    // Feature disabled
+    ASEC_DISABLED,
+
+    // Feature enabled and operational
+    ASEC_AVAILABLE,
+
+    // Busy
+    ASEC_BUSY,
+
+    // Internal Error
+    ASEC_FAILED_INTERR,
+
+    // No media available
+    ASEC_FAILED_NOMEDIA,
+
+    // Media is corrupt
+    ASEC_FAILED_BADMEDIA,
+
+    // Key mismatch
+    ASEC_FAILED_BADKEY,
+} AsecState;
+
+/*
+ * ASEC commands
+ */
+#define ASEC_CMD_SEND_STATUS		"asec_send_status"
+#define ASEC_CMD_ENABLE			"asec_enable"
+#define ASEC_CMD_DISABLE		"asec_disable"
+
+/*
+ * ASEC events
+ */
+
+// These events correspond to the states in the AsecState enum.
+// A path to the ASEC mount point follows the colon
+#define ASEC_EVENT_DISABLED		"asec_disabled:"
+#define ASEC_EVENT_AVAILABLE		"asec_available:"
+#define ASEC_EVENT_BUSY			"asec_busy:"
+#define ASEC_EVENT_FAILED_INTERR	"asec_failed_interror:"
+#define ASEC_EVENT_FAILED_NOMEDIA	"asec_failed_nomedia"
+#define ASEC_EVENT_FAILED_BADMEDIA	"asec_failed_badmedia:"
+#define ASEC_EVENT_FAILED_BADKEY	"asec_failed_badkey:"
+
+/*
+ * System Properties
+ */
+
+#define ASEC_ENABLED			"asec.enabled"
+
+#define ASEC_STATUS			"ro.asec.status"
+#define ASEC_STATUS_DISABLED		"disabled"
+#define ASEC_STATUS_AVAILABLE		"available"
+#define ASEC_STATUS_BUSY			"busy"
+#define ASEC_STATUS_FAILED_INTERR	"internal_error"
+#define ASEC_STATUS_FAILED_NOMEDIA	"no_media"
+#define ASEC_STATUS_FAILED_BADMEDIA	"bad_media"
+#define ASEC_STATUS_FAILED_BADKEY	"bad_key"
+
+#endif
diff --git a/mountd/Android.mk b/mountd/Android.mk
new file mode 100644
index 0000000..16532fa
--- /dev/null
+++ b/mountd/Android.mk
@@ -0,0 +1,22 @@
+LOCAL_PATH:= $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_SRC_FILES:=        \
+    AutoMount.c          \
+    ProcessKiller.c      \
+    Server.c             \
+    mountd.c		 \
+    ASEC.c		 \
+    logwrapper.c
+
+LOCAL_MODULE:= mountd
+
+LOCAL_C_INCLUDES := $(KERNEL_HEADERS)
+
+LOCAL_CFLAGS := -DCREATE_MOUNT_POINTS=0
+
+LOCAL_SHARED_LIBRARIES := libcutils
+
+# disabled - we are using vold now instead
+# include $(BUILD_EXECUTABLE)
diff --git a/mountd/AutoMount.c b/mountd/AutoMount.c
new file mode 100644
index 0000000..12ad572
--- /dev/null
+++ b/mountd/AutoMount.c
@@ -0,0 +1,1062 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+/*
+** mountd automount support
+*/
+
+#include "mountd.h"
+
+#include <pthread.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <string.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <ctype.h>
+#include <pwd.h>
+#include <stdlib.h>
+#include <poll.h>
+
+#include <sys/mount.h>
+#include <sys/stat.h>
+#include <linux/loop.h>
+#include <sys/inotify.h>
+#include <sys/socket.h>
+#include <sys/un.h>
+#include <linux/netlink.h>
+
+#define DEVPATH    "/dev/block/"
+#define DEVPATHLENGTH 11    // strlen(DEVPATH)
+
+// FIXME - only one loop mount is supported at a time
+#define LOOP_DEVICE "/dev/block/loop0"
+
+// timeout value for poll() when retries are pending
+#define POLL_TIMEOUT    1000
+
+#define MAX_MOUNT_RETRIES   3
+#define MAX_UNMOUNT_RETRIES   5
+
+typedef enum {
+    // device is unmounted
+    kUnmounted,
+    
+    // attempting to mount device
+    kMounting,
+    
+    // device is unmounted
+    kMounted,
+    
+    // attempting to unmount device
+    // so the media can be removed
+    kUnmountingForEject,
+    
+    // attempting to mount device
+    // so it can be shared via USB mass storage
+    kUnmountingForUms,
+} MountState;
+
+typedef struct MountPoint {
+    // block device to mount
+    const char* device;
+    
+    // mount point for device
+    const char* mountPoint;
+
+    // path to the UMS driver file for specifying the block device path
+    const char* driverStorePath;
+    
+    // true if device can be shared via
+    // USB mass storage
+    boolean enableUms;
+ 
+    // Array of ASEC handles
+    void *asecHandles[ASEC_STORES_MAX];
+
+    // true if the device is being shared via USB mass storage
+    boolean umsActive;
+    
+    // current state of the mount point
+    MountState state;
+    
+    // number of mount or unmount retries so far, 
+    // when attempting to mount or unmount the device
+    int retryCount; 
+ 
+    // next in sMountPointList linked list
+    struct MountPoint* next;   
+} MountPoint;
+
+// list of our mount points (does not change after initialization)
+static MountPoint* sMountPointList = NULL;
+boolean gMassStorageEnabled = false;
+boolean gMassStorageConnected = false;
+
+static pthread_t sAutoMountThread = 0;
+static pid_t gExcludedPids[2] = {-1, -1};
+
+static const char FSCK_MSDOS_PATH[] = "/system/bin/dosfsck";
+
+// number of mount points that have timeouts pending
+static int sRetriesPending = 0;
+
+// for synchronization between sAutoMountThread and the server thread
+static pthread_mutex_t sMutex = PTHREAD_MUTEX_INITIALIZER;
+
+// requests the USB mass_storage driver to begin or end sharing a block device
+// via USB mass storage.
+static void SetBackingStore(MountPoint* mp, boolean enable) 
+{
+    int fd;
+
+    if (!mp->driverStorePath) {
+        LOG_ERROR("no driver_store_path specified in config file for %s", mp->device);
+        return;
+    }
+
+    LOG_MOUNT("SetBackingStore enable: %s\n", (enable ? "true" : "false"));
+    fd = open(mp->driverStorePath, O_WRONLY);
+    if (fd < 0)
+    {
+        LOG_ERROR("could not open driver_store_path %s\n", mp->driverStorePath);
+    }
+    else
+    {
+        if (enable)
+        {
+            write(fd, mp->device, strlen(mp->device));
+            mp->umsActive = true;
+        }
+        else
+        {
+            char ch = 0;
+            write(fd, &ch, 1);
+            mp->umsActive = false;
+        }
+        close(fd);
+    }
+}
+
+static boolean ReadMassStorageState()
+{
+    FILE* file = fopen("/sys/class/switch/usb_mass_storage/state", "r");
+    if (file)
+    {
+        char    buffer[20];
+        fgets(buffer, sizeof(buffer), file);
+        fclose(file);
+        return (strncmp(buffer, "online", strlen("online")) == 0);
+    }
+    else
+    {
+        LOG_ERROR("could not read initial mass storage state\n");
+        return false;
+    }
+}
+
+static boolean IsLoopMounted(const char* path)
+{
+    FILE* f;
+    int count;
+    char device[256];
+    char mount_path[256];
+    char rest[256];
+    int result = 0;
+    int path_length = strlen(path);
+       
+    f = fopen("/proc/mounts", "r");
+    if (!f) {
+        LOG_ERROR("could not open /proc/mounts\n");
+        return -1;
+    }
+
+    do {
+        count = fscanf(f, "%255s %255s %255s\n", device, mount_path, rest);
+        if (count == 3) {
+            if (strcmp(LOOP_DEVICE, device) == 0 && strcmp(path, mount_path) == 0)
+            {
+                result = 1;
+                break;
+            }
+        }
+    } while (count == 3);
+
+    fclose(f);
+    LOG_MOUNT("IsLoopMounted: %s returning %d\n", path, result);
+    return result;
+}
+
+static int CheckFilesystem(const char *device)
+{
+    char cmdline[255];
+    int rc;
+
+    // XXX: SAN: Check for FAT signature
+    
+    int result = access(FSCK_MSDOS_PATH, X_OK);
+    if (result != 0) {
+        LOG_MOUNT("CheckFilesystem(%s): %s not found (skipping checks)\n", FSCK_MSDOS_PATH, device);
+        return 0;
+    }
+ 
+    char *args[7];
+    args[0] = FSCK_MSDOS_PATH;
+    args[1] = "-v";
+    args[2] = "-V";
+    args[3] = "-w";
+    args[4] = "-p";
+    args[5] = device;
+    args[6] = NULL;
+
+    LOG_MOUNT("Checking filesystem on %s\n", device);
+    rc = logwrap(6, args);
+  
+    // XXX: We need to be able to distinguish between a FS with an error
+    // and a block device which does not have a FAT fs at all on it
+    if (rc == 0) {
+        LOG_MOUNT("Filesystem check completed OK\n");
+        return 0;
+    } else if (rc == 1) {
+        LOG_MOUNT("Filesystem check failed (general failure)\n");
+        return -EINVAL;
+    } else if (rc == 2) {
+        LOG_MOUNT("Filesystem check failed (invalid usage)\n");
+        return -EIO;
+    } else {
+        LOG_MOUNT("Filesystem check failed (unknown exit code %d)\n", rc);
+        return -EIO;
+    }
+}
+
+static int DoMountDevice(const char* device, const char* mountPoint)
+{
+    LOG_MOUNT("Attempting mount of %s on %s\n", device, mountPoint);
+
+#if CREATE_MOUNT_POINTS
+    // make sure mount point exists
+    mkdir(mountPoint, 0000);
+#endif
+
+    int flags = 0;
+    
+    if (device && strncmp(device, "/dev/", 5))
+    {
+        // mount with the loop driver if device does not start with "/dev/"
+        int file_fd, device_fd;
+        
+        // FIXME - only one loop mount supported at a time
+        file_fd = open(device, O_RDWR);
+        if (file_fd < -1) {
+            LOG_ERROR("open backing file %s failed\n", device);
+            return 1;
+        }
+        device_fd = open(LOOP_DEVICE, O_RDWR);
+        if (device_fd < -1) {
+            LOG_ERROR("open %s failed", LOOP_DEVICE);
+            close(file_fd);
+            return 1;
+        }
+        if (ioctl(device_fd, LOOP_SET_FD, file_fd) < 0)
+        {
+            LOG_ERROR("ioctl LOOP_SET_FD failed\n");
+            close(file_fd);
+            close(device_fd);
+            return 1;
+        }
+
+        close(file_fd);
+        close(device_fd);
+        device = "/dev/block/loop0";
+    }
+
+    int result = access(device, R_OK);
+    if (result) {
+	LOG_ERROR("Unable to access '%s' (%d)\n", device, errno);
+   	return -errno;
+    }
+
+#if 0
+    if ((result = CheckFilesystem(device))) {
+        LOG_ERROR("Not mounting filesystem due to check failure (%d)\n", result);
+        // XXX:  Notify framework - need a new SDCARD state for the following:
+        //       - SD cards which are not present
+        //       - SD cards with no partition table
+        //       - SD cards with no filesystem
+        //       - SD cards with bad filesystem
+        return result;
+    }
+#endif
+
+    // Extra safety measures:
+    flags |= MS_NODEV | MS_NOEXEC | MS_NOSUID | MS_DIRSYNC;
+    // Also, set fmask = 711 so that files cannot be marked executable,
+    // and cannot by opened by uid 1000 (system). Similar, dmask = 700
+    // so that directories cannot be accessed by uid 1000.
+    result = mount(device, mountPoint, "vfat", flags, 
+                       "utf8,uid=1000,gid=1000,fmask=711,dmask=700");
+    if (result && errno == EROFS) {
+        LOG_ERROR("mount failed EROFS, try again read-only\n");
+        flags |= MS_RDONLY;
+        result = mount(device, mountPoint, "vfat", flags,
+                       "utf8,uid=1000,gid=1000,fmask=711,dmask=700");
+    }
+
+    if (result == 0) {
+        LOG_MOUNT("Partition %s mounted on %s\n", device, mountPoint);
+        NotifyMediaState(mountPoint, MEDIA_MOUNTED, (flags & MS_RDONLY) != 0);
+
+        MountPoint* mp = sMountPointList;
+        while (mp) {
+            if (!strcmp(mountPoint, mp->mountPoint)) {
+                int i;
+             
+                for (i = 0; i < ASEC_STORES_MAX; i++) {
+                    if (mp->asecHandles[i] != NULL) {
+                        int a_result;
+                        if ((a_result = AsecStart(mp->asecHandles[i])) < 0) {
+                            LOG_ERROR("ASEC start failure (%d)\n", a_result);
+                        }
+                    }
+                }
+                break;
+            }
+            mp = mp -> next;
+        }
+    } else if (errno == EBUSY) {
+        LOG_MOUNT("Mount failed (already mounted)\n");
+        result = 0;
+    } else {
+#if CREATE_MOUNT_POINTS
+        rmdir(mountPoint);
+#endif
+        LOG_MOUNT("Unable to mount %s on %s\n", device, mountPoint);
+    }
+
+    return result;
+}
+
+static int DoUnmountDevice(MountPoint *mp)
+{
+    boolean loop = IsLoopMounted(mp->mountPoint);
+    int i;
+
+    for (i = 0; i < ASEC_STORES_MAX; i++) {
+        if (mp->asecHandles[i] && AsecIsStarted(mp->asecHandles[i]))
+            AsecStop(mp->asecHandles[i]);
+    }
+
+    int result = umount(mp->mountPoint);
+    LOG_MOUNT("umount returned %d errno: %d\n", result, errno);
+
+    if (result == 0)
+    {
+#if CREATE_MOUNT_POINTS
+        rmdir(mountPoint);
+#endif
+        NotifyMediaState(mp->mountPoint, MEDIA_UNMOUNTED, false);
+    }
+
+    if (loop)
+    {
+        // free the loop device
+        int loop_fd = open(LOOP_DEVICE, O_RDONLY);
+        if (loop_fd < -1) {
+            LOG_ERROR("open loop device failed\n");
+        }
+        if (ioctl(loop_fd, LOOP_CLR_FD, 0) < 0) {
+            LOG_ERROR("ioctl LOOP_CLR_FD failed\n");
+        }
+
+        close(loop_fd);
+    }
+
+    // ignore EINVAL and ENOENT, since it usually means the device is already unmounted
+    if (result && (errno == EINVAL || errno == ENOENT))
+        result = 0;
+
+    return result;
+}
+
+static int MountPartition(const char* device, const char* mountPoint)
+{
+    char    buf[100];
+    int i;
+    
+    // attempt to mount subpartitions of the device
+    for (i = 1; i < 10; i++)
+    {
+        int rc;
+        snprintf(buf, sizeof(buf), "%sp%d", device, i);
+        rc = DoMountDevice(buf, mountPoint);
+        LOG_MOUNT("DoMountDevice(%s, %s) = %d\n", buf, mountPoint, rc);
+        if (rc == 0)
+            return 0;
+    }
+
+    return -1;
+}
+
+/*****************************************************
+ * 
+ * AUTO-MOUNTER STATE ENGINE IMPLEMENTATION
+ * 
+ *****************************************************/
+
+static void SetState(MountPoint* mp, MountState state)
+{
+    mp->state = state;
+}
+
+// Enter a state that requires retries and timeouts.
+static void SetRetries(MountPoint* mp, MountState state)
+{
+    SetState(mp, state);
+    mp->retryCount = 0;
+
+    sRetriesPending++;
+    // wake up the automounter thread if we are being called 
+    // from somewhere else with no retries pending
+    if (sRetriesPending == 1 && sAutoMountThread != 0 && 
+            pthread_self() != sAutoMountThread)
+        pthread_kill(sAutoMountThread, SIGUSR1);
+}
+
+// Exit a state that requires retries and timeouts.
+static void ClearRetries(MountPoint* mp, MountState state)
+{
+    SetState(mp, state);
+    sRetriesPending--;
+}
+
+// attempt to mount the specified mount point.
+// set up retry/timeout if it does not succeed at first.
+static void RequestMount(MountPoint* mp)
+{
+    LOG_MOUNT("RequestMount %s\n", mp->mountPoint);
+
+    if (mp->state != kMounted && mp->state != kMounting &&
+            access(mp->device, R_OK) == 0) {
+        // try raw device first
+        if (DoMountDevice(mp->device, mp->mountPoint) == 0 ||
+            MountPartition(mp->device, mp->mountPoint) == 0)
+        {
+            SetState(mp, kMounted);
+        }
+        else 
+        {
+            SetState(mp, kMounting);
+            mp->retryCount = 0;
+            SetRetries(mp, kMounting);
+        }
+    }
+}
+
+// Force the kernel to drop all caches.
+static void DropSystemCaches(void)
+{
+    int fd;
+
+    LOG_MOUNT("Dropping system caches\n");
+    fd = open("/proc/sys/vm/drop_caches", O_WRONLY);
+
+    if (fd > 0) {
+        char ch = 3;
+        int rc;
+
+        rc = write(fd, &ch, 1);
+        if (rc <= 0)
+            LOG_MOUNT("Error dropping caches (%d)\n", rc);
+        close(fd);
+    }
+}
+
+// attempt to unmount the specified mount point.
+// set up retry/timeout if it does not succeed at first.
+static void RequestUnmount(MountPoint* mp, MountState retryState)
+{
+    int result;
+
+    LOG_MOUNT("RequestUnmount %s retryState: %d\n", mp->mountPoint, retryState);
+    
+    if (mp->state == kMounted)
+    {
+        SendUnmountRequest(mp->mountPoint);
+
+        // do this in case the user pulls the SD card before we can successfully unmount
+        sync();
+        DropSystemCaches();
+
+        if (DoUnmountDevice(mp) == 0) 
+        {
+            SetState(mp, kUnmounted);
+            if (retryState == kUnmountingForUms) 
+            {
+                SetBackingStore(mp, true);
+                NotifyMediaState(mp->mountPoint, MEDIA_SHARED, false);
+            }
+        }
+        else 
+        {
+            LOG_MOUNT("unmount failed, set retry\n");
+            SetRetries(mp, retryState);
+        }
+    } 
+    else if (mp->state == kMounting)
+    {
+        SetState(mp, kUnmounted);
+    }
+}
+
+// returns true if the mount point should be shared via USB mass storage
+static boolean MassStorageEnabledForMountPoint(const MountPoint* mp)
+{
+    return (gMassStorageEnabled && gMassStorageConnected && mp->enableUms);
+}
+
+// handles changes in gMassStorageEnabled and gMassStorageConnected
+static void MassStorageStateChanged()
+{
+    MountPoint* mp = sMountPointList;
+
+    boolean enable = (gMassStorageEnabled && gMassStorageConnected);
+    LOG_MOUNT("MassStorageStateChanged enable: %s\n", (enable ? "true" : "false"));
+    
+    while (mp)
+    {
+        if (mp->enableUms)
+        {
+            if (enable)
+            {
+                if (mp->state == kMounting)
+                    SetState(mp, kUnmounted);
+                if (mp->state == kUnmounted) 
+                {
+                    SetBackingStore(mp, true);
+                    NotifyMediaState(mp->mountPoint, MEDIA_SHARED, false);
+                }
+                else
+                {
+                    LOG_MOUNT("MassStorageStateChanged requesting unmount\n");
+                    // need to successfully unmount first
+                    RequestUnmount(mp, kUnmountingForUms);
+                }
+            } else if (mp->umsActive) {
+                SetBackingStore(mp, false);
+                if (mp->state == kUnmountingForUms)
+                {
+                    ClearRetries(mp, kMounted);
+                    NotifyMediaState(mp->mountPoint, MEDIA_MOUNTED, false);
+                }
+                else if (mp->state == kUnmounted)
+                {
+                    NotifyMediaState(mp->mountPoint, MEDIA_UNMOUNTED, false);
+                    RequestMount(mp);
+                }
+            }
+        }
+
+        mp = mp->next;
+    }
+}
+
+// called when USB mass storage connected state changes
+static void HandleMassStorageOnline(boolean connected)
+{
+    if (connected != gMassStorageConnected)
+    {
+        gMassStorageConnected = connected;
+        SendMassStorageConnected(connected);
+        
+        // we automatically reset to mass storage off after USB is connected
+        if (!connected)
+            gMassStorageEnabled = false;
+    
+        MassStorageStateChanged();
+    }
+}
+
+// called when a new block device has been created
+static void HandleMediaInserted(const char* device)
+{
+    MountPoint* mp = sMountPointList;
+    
+    LOG_MOUNT("HandleMediaInserted(%s):\n", device);
+
+    while (mp)
+    {
+        // see if the device matches mount point's block device
+        if (mp->state == kUnmounted &&
+                strncmp(device, mp->device + DEVPATHLENGTH, strlen(mp->device) - DEVPATHLENGTH) == 0) 
+        {
+            if (MassStorageEnabledForMountPoint(mp))
+            {
+                SetBackingStore(mp, true);
+                NotifyMediaState(mp->mountPoint, MEDIA_SHARED, false);
+            }
+            else
+                RequestMount(mp);
+        }  
+        mp = mp->next;
+    }
+}
+
+// called when a new block device has been deleted
+static void HandleMediaRemoved(const char* device)
+{    
+    MountPoint* mp = sMountPointList;
+    while (mp)
+    {
+        if (strncmp(device, mp->device + DEVPATHLENGTH, strlen(mp->device) - DEVPATHLENGTH) == 0)
+        {
+            if (mp->enableUms)
+                SetBackingStore(mp, false);
+
+             if (mp->state == kMounted) 
+            {
+                RequestUnmount(mp, kUnmountingForEject);
+                NotifyMediaState(mp->mountPoint, MEDIA_BAD_REMOVAL, false);
+            }
+            
+            NotifyMediaState(mp->mountPoint, MEDIA_REMOVED, false);
+            break;
+        }  
+        mp = mp->next;
+    }
+}
+
+// Handle retrying to mount or unmount devices, 
+// and handle timeout condition if we have tried too many times
+static void HandleRetries()
+{
+    MountPoint* mp = sMountPointList;
+    
+    while (mp)
+    {
+       if (mp->state == kMounting) 
+       {
+            if (MountPartition(mp->device, mp->mountPoint) == 0)
+            {
+                // mount succeeded - clear the retry for this mount point
+                ClearRetries(mp, kMounted);
+            } 
+            else 
+            {
+                mp->retryCount++;
+                if (mp->retryCount == MAX_MOUNT_RETRIES)
+                {
+                    // we failed to mount the device too many times
+                    ClearRetries(mp, kUnmounted);
+                    // notify that we failed to mount
+                    NotifyMediaState(mp->mountPoint, MEDIA_UNMOUNTABLE, false);
+                }
+            }
+       } 
+       else if (mp->state == kUnmountingForEject || mp->state == kUnmountingForUms)
+       {
+            if (DoUnmountDevice(mp) == 0)
+            {
+                // unmounting succeeded
+                // start mass storage, if state is kUnmountingForUms
+                if (mp->state == kUnmountingForUms)
+                {
+                    SetBackingStore(mp, true);
+                     NotifyMediaState(mp->mountPoint, MEDIA_SHARED, false);
+                }
+                // clear the retry for this mount point
+                ClearRetries(mp, kUnmounted);
+            } 
+            else 
+            {
+                mp->retryCount++;
+                if (mp->retryCount >= MAX_UNMOUNT_RETRIES)
+                {
+                    // kill any processes that are preventing the device from unmounting
+                    // send SIGKILL instead of SIGTERM if the first attempt did not succeed
+                    boolean sigkill = (mp->retryCount > MAX_UNMOUNT_RETRIES);
+                    
+                    int i;
+
+                    for (i = 0; i < ASEC_STORES_MAX; i++) {
+                        if (mp->asecHandles[i] && AsecIsStarted(mp->asecHandles[i])) {
+                            LOG_MOUNT("Killing processes for ASEC path '%s'\n",
+                                      AsecMountPoint(mp->asecHandles[i]));
+                            KillProcessesWithOpenFiles(AsecMountPoint(mp->asecHandles[i]),
+                                                       sigkill,
+                                                       gExcludedPids, sizeof(gExcludedPids) / sizeof(pid_t));
+
+                            // Now that we've killed the processes, try to stop the volume again
+                            AsecStop(mp->asecHandles[i]);
+                        }
+                    }
+
+                    // unmounting the device is failing, so start killing processes
+                    KillProcessesWithOpenFiles(mp->mountPoint, sigkill, gExcludedPids, 
+                                               sizeof(gExcludedPids) / sizeof(pid_t));
+
+                }
+            }
+       } 
+        
+        mp = mp->next;
+    }
+}
+
+/*****************************************************
+ * 
+ * AUTO-MOUNTER THREAD
+ * 
+ *****************************************************/
+
+static void sigusr1_handler(int signo)
+{
+    // don't need to do anything here
+}
+
+// create a socket for listening to inotify events
+int CreateINotifySocket()
+{
+    // initialize inotify
+    int fd = inotify_init();
+
+    if (fd < 0) {
+        LOG_ERROR("inotify_init failed, %s\n", strerror(errno));
+        return -1;
+    }
+
+    fcntl(fd, F_SETFL, O_NONBLOCK | fcntl(fd, F_GETFL));
+
+    return fd;
+}
+
+
+// create a socket for listening to uevents
+int CreateUEventSocket()
+{
+    struct sockaddr_nl addr;
+    int sz = 64*1024;
+    int fd;
+
+    memset(&addr, 0, sizeof(addr));
+    addr.nl_family = AF_NETLINK;
+    addr.nl_pid = getpid();
+    addr.nl_groups = 0xffffffff;
+
+   fd = socket(PF_NETLINK, SOCK_DGRAM, NETLINK_KOBJECT_UEVENT);
+    if(fd < 0)
+    {
+        LOG_ERROR("could not create NETLINK_KOBJECT_UEVENT socket\n");
+        return -1;
+    }
+
+    setsockopt(fd, SOL_SOCKET, SO_RCVBUFFORCE, &sz, sizeof(sz));
+
+    if(bind(fd, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
+        LOG_ERROR("could not bind NETLINK_KOBJECT_UEVENT socket\n");
+        close(fd);
+        return -1;
+    }
+
+    return fd;
+}
+
+/*
+ * Automounter main event thread.
+ * This thread listens for block devices being created and deleted via inotify,
+ * and listens for changes in the USB mass storage connected/disconnected via uevents from the 
+ * power supply driver.
+ * This thread also handles retries and timeouts for requests to mount or unmount a device.
+ */
+static void* AutoMountThread(void* arg)
+{
+    int inotify_fd;
+    int uevent_fd;
+    int id;
+    struct sigaction    actions;
+
+    gExcludedPids[1] = getpid();
+
+    memset(&actions, 0, sizeof(actions));
+    sigemptyset(&actions.sa_mask);
+    actions.sa_flags = 0;
+    actions.sa_handler = sigusr1_handler;
+    sigaction(SIGUSR1, &actions, NULL);
+    
+    // initialize inotify
+    inotify_fd = CreateINotifySocket();
+    // watch for files created and deleted in "/dev"
+    inotify_add_watch(inotify_fd, DEVPATH, IN_CREATE|IN_DELETE);
+
+    // initialize uevent watcher
+    uevent_fd = CreateUEventSocket();
+    if (uevent_fd < 0) 
+    {
+        LOG_ERROR("CreateUEventSocket failed, %s\n", strerror(errno));
+        return NULL;
+    }
+    
+    while (1)
+    {
+        struct pollfd fds[2];
+        int timeout, result;
+
+#define INOTIFY_IDX 0
+#define UEVENT_IDX  1
+    
+        fds[INOTIFY_IDX].fd = inotify_fd;
+        fds[INOTIFY_IDX].events = POLLIN;
+        fds[INOTIFY_IDX].revents = 0;
+        fds[UEVENT_IDX].fd = uevent_fd;
+        fds[UEVENT_IDX].events = POLLIN;
+        fds[UEVENT_IDX].revents = 0;
+        
+        // wait for an event or a timeout to occur.
+        // poll() can also return in response to a SIGUSR1 signal
+        timeout = (sRetriesPending ? POLL_TIMEOUT : -1);
+        result = poll(fds, 2, timeout);
+
+        // lock the mutex while we are handling events
+        pthread_mutex_lock(&sMutex);
+
+        // handle inotify notifications for block device creation and deletion
+        if (fds[INOTIFY_IDX].revents == POLLIN)
+        {
+            struct inotify_event    event;
+            char    buffer[512];
+            int length = read(inotify_fd, buffer, sizeof(buffer));
+            int offset = 0;
+ 
+            while (length >= (int)sizeof(struct inotify_event))
+            {
+               struct inotify_event* event = (struct inotify_event *)&buffer[offset];
+               
+               if (event->mask == IN_CREATE)
+               {
+                   LOG_MOUNT("/dev/block/%s created\n", event->name);
+                   HandleMediaInserted(event->name);
+               }
+               else if (event->mask == IN_DELETE)
+               {
+                   LOG_MOUNT("/dev/block/%s deleted\n", event->name);
+                   HandleMediaRemoved(event->name);
+               }
+               
+               int size = sizeof(struct inotify_event) + event->len;
+               length -= size;
+               offset += size;
+            }
+        }
+
+        // handle uevent notifications for USB state changes
+        if (fds[UEVENT_IDX].revents == POLLIN)
+        {
+            char buffer[64*1024];
+            int count;
+            
+            count = recv(uevent_fd, buffer, sizeof(buffer), 0);
+            if (count > 0) {
+                char* s = buffer;
+                char* end = s + count;
+                char* type = NULL;
+                char* online = NULL;
+                char* switchName = NULL;
+                char* switchState = NULL;
+                                
+                while (s < end) {
+                    if (!strncmp("POWER_SUPPLY_TYPE=", s, strlen("POWER_SUPPLY_TYPE=")))
+                        type = s + strlen("POWER_SUPPLY_TYPE=");
+                    else if (!strncmp("POWER_SUPPLY_ONLINE=", s, strlen("POWER_SUPPLY_ONLINE=")))
+                        online = s + strlen("POWER_SUPPLY_ONLINE=");                    
+                    else if (!strncmp("SWITCH_NAME=", s, strlen("SWITCH_NAME=")))
+                        switchName = s + strlen("SWITCH_NAME=");                    
+                    else if (!strncmp("SWITCH_STATE=", s, strlen("SWITCH_STATE=")))
+                        switchState = s + strlen("SWITCH_STATE=");                    
+                    s += (strlen(s) + 1);
+                }
+
+                // we use the usb_mass_storage switch state to tell us when USB is online
+                if (switchName && switchState && 
+                        !strcmp(switchName, "usb_mass_storage") && !strcmp(switchState, "online"))
+                {
+                    LOG_MOUNT("USB online\n");
+                    HandleMassStorageOnline(true);
+                }
+                
+                // and we use the power supply state to tell us when USB is offline
+                // we can't rely on the switch for offline detection because we get false positives
+                // when USB is reenumerated by the host.
+                if (type && online && !strcmp(type, "USB") && !strcmp(online, "0"))
+                {
+                    LOG_MOUNT("USB offline\n");
+                    HandleMassStorageOnline(false);
+                }
+            }
+        }
+
+       // handle retries
+       if (sRetriesPending)
+            HandleRetries();
+
+        // done handling events, so unlock the mutex
+        pthread_mutex_unlock(&sMutex);
+    }
+
+    inotify_rm_watch(inotify_fd, id);
+    close(inotify_fd);
+    close(uevent_fd);
+
+    return NULL;
+}
+
+/*****************************************************
+ * 
+ * THESE FUNCTIONS ARE CALLED FROM THE SERVER THREAD
+ * 
+ *****************************************************/
+
+// Called to enable or disable USB mass storage support
+void EnableMassStorage(boolean enable)
+{
+    pthread_mutex_lock(&sMutex);
+
+    LOG_MOUNT("EnableMassStorage %s\n", (enable ? "true" : "false"));
+    gMassStorageEnabled = enable;
+    MassStorageStateChanged();
+    pthread_mutex_unlock(&sMutex);
+ }
+
+// Called to request that the specified mount point be mounted
+void MountMedia(const char* mountPoint)
+{
+    MountPoint* mp = sMountPointList;
+ 
+    LOG_MOUNT("MountMedia(%s)\n", mountPoint);
+   
+    pthread_mutex_lock(&sMutex);
+    while (mp)
+    {
+        if (strcmp(mp->mountPoint, mountPoint) == 0)
+        {
+            if (mp->state == kUnmountingForEject)
+            {
+                // handle the case where we try to remount before we actually unmounted
+                ClearRetries(mp, kMounted);
+            }
+            
+            // don't attempt to mount if mass storage is active
+            if (!MassStorageEnabledForMountPoint(mp))
+                RequestMount(mp);
+        }
+        
+        mp = mp->next;
+    }
+    pthread_mutex_unlock(&sMutex);
+ }
+
+// Called to request that the specified mount point be unmounted
+void UnmountMedia(const char* mountPoint)
+{
+    MountPoint* mp = sMountPointList;
+    
+    pthread_mutex_lock(&sMutex);
+    while (mp)
+    {
+        if (strcmp(mp->mountPoint, mountPoint) == 0)
+            RequestUnmount(mp, kUnmountingForEject);
+        
+        mp = mp->next;
+    }
+    pthread_mutex_unlock(&sMutex);
+}
+
+boolean IsMassStorageEnabled()
+{
+    return gMassStorageEnabled;
+}
+
+boolean IsMassStorageConnected()
+{
+    return gMassStorageConnected;
+}
+
+/***********************************************
+ * 
+ * THESE FUNCTIONS ARE CALLED ONLY AT STARTUP
+ * 
+ ***********************************************/
+ 
+void *AddMountPoint(const char* device, const char* mountPoint, const char * driverStorePath, boolean enableUms)
+{
+    MountPoint* newMountPoint;
+    
+    LOG_MOUNT("AddMountPoint device: %s, mountPoint: %s driverStorePath: %s\n", device, mountPoint, driverStorePath);
+    // add a new MountPoint to the head of our linked list
+    newMountPoint = (MountPoint *)malloc(sizeof(MountPoint));
+    newMountPoint->device = device;
+    newMountPoint->mountPoint = mountPoint;
+    newMountPoint->driverStorePath = driverStorePath;
+    newMountPoint->enableUms = enableUms;
+    newMountPoint->umsActive = false;
+    newMountPoint->state = kUnmounted;
+    newMountPoint->retryCount = 0;
+
+    // add to linked list
+    newMountPoint->next = sMountPointList;
+    sMountPointList = newMountPoint;
+    return newMountPoint;
+}
+
+int AddAsecToMountPoint(void *Mp, const char *name, const char *backing_file, const char *size,
+                        const char *mount_point, const char *crypt)
+{
+    MountPoint *mp = (MountPoint *) Mp;
+    int i;
+
+    for (i = 0; i < ASEC_STORES_MAX; i++) {
+        if (!mp->asecHandles[i])
+            break;   
+    }
+
+    if (i == ASEC_STORES_MAX) {
+        LOG_ERROR("Maximum # of ASEC stores exceeded\n");
+        return -EINVAL;
+    }
+
+    if (!(mp->asecHandles[i] = AsecInit(name, mp->mountPoint, backing_file, size, mount_point, crypt)))
+        return -1;
+
+    return 0;
+}
+static void MountDevices()
+{
+    MountPoint* mp = sMountPointList;
+    while (mp)
+    {
+        RequestMount(mp);
+        mp = mp->next;
+    }
+}
+
+void StartAutoMounter()
+{
+    gExcludedPids[0] = getpid();
+
+    gMassStorageConnected = ReadMassStorageState();
+    LOG_MOUNT(gMassStorageConnected ? "USB online\n" : "USB offline\n");
+
+    MountDevices();
+    pthread_create(&sAutoMountThread, NULL, AutoMountThread, NULL);
+}
diff --git a/mountd/MODULE_LICENSE_APACHE2 b/mountd/MODULE_LICENSE_APACHE2
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/mountd/MODULE_LICENSE_APACHE2
diff --git a/mountd/NOTICE b/mountd/NOTICE
new file mode 100644
index 0000000..c5b1efa
--- /dev/null
+++ b/mountd/NOTICE
@@ -0,0 +1,190 @@
+
+   Copyright (c) 2005-2008, 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.
+
+   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.
+
+
+                                 Apache License
+                           Version 2.0, January 2004
+                        http://www.apache.org/licenses/
+
+   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+   1. Definitions.
+
+      "License" shall mean the terms and conditions for use, reproduction,
+      and distribution as defined by Sections 1 through 9 of this document.
+
+      "Licensor" shall mean the copyright owner or entity authorized by
+      the copyright owner that is granting the License.
+
+      "Legal Entity" shall mean the union of the acting entity and all
+      other entities that control, are controlled by, or are under common
+      control with that entity. For the purposes of this definition,
+      "control" means (i) the power, direct or indirect, to cause the
+      direction or management of such entity, whether by contract or
+      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+      outstanding shares, or (iii) beneficial ownership of such entity.
+
+      "You" (or "Your") shall mean an individual or Legal Entity
+      exercising permissions granted by this License.
+
+      "Source" form shall mean the preferred form for making modifications,
+      including but not limited to software source code, documentation
+      source, and configuration files.
+
+      "Object" form shall mean any form resulting from mechanical
+      transformation or translation of a Source form, including but
+      not limited to compiled object code, generated documentation,
+      and conversions to other media types.
+
+      "Work" shall mean the work of authorship, whether in Source or
+      Object form, made available under the License, as indicated by a
+      copyright notice that is included in or attached to the work
+      (an example is provided in the Appendix below).
+
+      "Derivative Works" shall mean any work, whether in Source or Object
+      form, that is based on (or derived from) the Work and for which the
+      editorial revisions, annotations, elaborations, or other modifications
+      represent, as a whole, an original work of authorship. For the purposes
+      of this License, Derivative Works shall not include works that remain
+      separable from, or merely link (or bind by name) to the interfaces of,
+      the Work and Derivative Works thereof.
+
+      "Contribution" shall mean any work of authorship, including
+      the original version of the Work and any modifications or additions
+      to that Work or Derivative Works thereof, that is intentionally
+      submitted to Licensor for inclusion in the Work by the copyright owner
+      or by an individual or Legal Entity authorized to submit on behalf of
+      the copyright owner. For the purposes of this definition, "submitted"
+      means any form of electronic, verbal, or written communication sent
+      to the Licensor or its representatives, including but not limited to
+      communication on electronic mailing lists, source code control systems,
+      and issue tracking systems that are managed by, or on behalf of, the
+      Licensor for the purpose of discussing and improving the Work, but
+      excluding communication that is conspicuously marked or otherwise
+      designated in writing by the copyright owner as "Not a Contribution."
+
+      "Contributor" shall mean Licensor and any individual or Legal Entity
+      on behalf of whom a Contribution has been received by Licensor and
+      subsequently incorporated within the Work.
+
+   2. Grant of Copyright License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      copyright license to reproduce, prepare Derivative Works of,
+      publicly display, publicly perform, sublicense, and distribute the
+      Work and such Derivative Works in Source or Object form.
+
+   3. Grant of Patent License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      (except as stated in this section) patent license to make, have made,
+      use, offer to sell, sell, import, and otherwise transfer the Work,
+      where such license applies only to those patent claims licensable
+      by such Contributor that are necessarily infringed by their
+      Contribution(s) alone or by combination of their Contribution(s)
+      with the Work to which such Contribution(s) was submitted. If You
+      institute patent litigation against any entity (including a
+      cross-claim or counterclaim in a lawsuit) alleging that the Work
+      or a Contribution incorporated within the Work constitutes direct
+      or contributory patent infringement, then any patent licenses
+      granted to You under this License for that Work shall terminate
+      as of the date such litigation is filed.
+
+   4. Redistribution. You may reproduce and distribute copies of the
+      Work or Derivative Works thereof in any medium, with or without
+      modifications, and in Source or Object form, provided that You
+      meet the following conditions:
+
+      (a) You must give any other recipients of the Work or
+          Derivative Works a copy of this License; and
+
+      (b) You must cause any modified files to carry prominent notices
+          stating that You changed the files; and
+
+      (c) You must retain, in the Source form of any Derivative Works
+          that You distribute, all copyright, patent, trademark, and
+          attribution notices from the Source form of the Work,
+          excluding those notices that do not pertain to any part of
+          the Derivative Works; and
+
+      (d) If the Work includes a "NOTICE" text file as part of its
+          distribution, then any Derivative Works that You distribute must
+          include a readable copy of the attribution notices contained
+          within such NOTICE file, excluding those notices that do not
+          pertain to any part of the Derivative Works, in at least one
+          of the following places: within a NOTICE text file distributed
+          as part of the Derivative Works; within the Source form or
+          documentation, if provided along with the Derivative Works; or,
+          within a display generated by the Derivative Works, if and
+          wherever such third-party notices normally appear. The contents
+          of the NOTICE file are for informational purposes only and
+          do not modify the License. You may add Your own attribution
+          notices within Derivative Works that You distribute, alongside
+          or as an addendum to the NOTICE text from the Work, provided
+          that such additional attribution notices cannot be construed
+          as modifying the License.
+
+      You may add Your own copyright statement to Your modifications and
+      may provide additional or different license terms and conditions
+      for use, reproduction, or distribution of Your modifications, or
+      for any such Derivative Works as a whole, provided Your use,
+      reproduction, and distribution of the Work otherwise complies with
+      the conditions stated in this License.
+
+   5. Submission of Contributions. Unless You explicitly state otherwise,
+      any Contribution intentionally submitted for inclusion in the Work
+      by You to the Licensor shall be under the terms and conditions of
+      this License, without any additional terms or conditions.
+      Notwithstanding the above, nothing herein shall supersede or modify
+      the terms of any separate license agreement you may have executed
+      with Licensor regarding such Contributions.
+
+   6. Trademarks. This License does not grant permission to use the trade
+      names, trademarks, service marks, or product names of the Licensor,
+      except as required for reasonable and customary use in describing the
+      origin of the Work and reproducing the content of the NOTICE file.
+
+   7. Disclaimer of Warranty. Unless required by applicable law or
+      agreed to in writing, Licensor provides the Work (and each
+      Contributor provides its Contributions) on an "AS IS" BASIS,
+      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+      implied, including, without limitation, any warranties or conditions
+      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+      PARTICULAR PURPOSE. You are solely responsible for determining the
+      appropriateness of using or redistributing the Work and assume any
+      risks associated with Your exercise of permissions under this License.
+
+   8. Limitation of Liability. In no event and under no legal theory,
+      whether in tort (including negligence), contract, or otherwise,
+      unless required by applicable law (such as deliberate and grossly
+      negligent acts) or agreed to in writing, shall any Contributor be
+      liable to You for damages, including any direct, indirect, special,
+      incidental, or consequential damages of any character arising as a
+      result of this License or out of the use or inability to use the
+      Work (including but not limited to damages for loss of goodwill,
+      work stoppage, computer failure or malfunction, or any and all
+      other commercial damages or losses), even if such Contributor
+      has been advised of the possibility of such damages.
+
+   9. Accepting Warranty or Additional Liability. While redistributing
+      the Work or Derivative Works thereof, You may choose to offer,
+      and charge a fee for, acceptance of support, warranty, indemnity,
+      or other liability obligations and/or rights consistent with this
+      License. However, in accepting such obligations, You may act only
+      on Your own behalf and on Your sole responsibility, not on behalf
+      of any other Contributor, and only if You agree to indemnify,
+      defend, and hold each Contributor harmless for any liability
+      incurred by, or claims asserted against, such Contributor by reason
+      of your accepting any such warranty or additional liability.
+
+   END OF TERMS AND CONDITIONS
+
diff --git a/mountd/ProcessKiller.c b/mountd/ProcessKiller.c
new file mode 100644
index 0000000..e377774
--- /dev/null
+++ b/mountd/ProcessKiller.c
@@ -0,0 +1,222 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+/*
+** mountd process killer
+*/
+
+#include "mountd.h"
+
+#include <stdio.h>
+#include <unistd.h>
+#include <string.h>
+#include <fcntl.h>
+#include <dirent.h>
+#include <ctype.h>
+#include <pwd.h>
+#include <stdlib.h>
+#include <poll.h>
+#include <sys/stat.h>
+
+
+static boolean ReadSymLink(const char* path, char* link)
+{
+    struct stat s;
+    int length;
+
+    if (lstat(path, &s) < 0)
+        return false;
+    if ((s.st_mode & S_IFMT) != S_IFLNK)
+        return false;
+   
+    // we have a symlink    
+    length = readlink(path, link, PATH_MAX - 1);
+    if (length <= 0) 
+        return false;
+    link[length] = 0;
+    return true;
+}
+
+static boolean PathMatchesMountPoint(const char* path, const char* mountPoint)
+{
+    int length = strlen(mountPoint);
+    if (length > 1 && strncmp(path, mountPoint, length) == 0)
+    {
+        // we need to do extra checking if mountPoint does not end in a '/'
+        if (mountPoint[length - 1] == '/')
+            return true;
+        // if mountPoint does not have a trailing slash, we need to make sure
+        // there is one in the path to avoid partial matches.
+        return (path[length] == 0 || path[length] == '/');
+    }
+    
+    return false;
+}
+
+static void GetProcessName(int pid, char buffer[PATH_MAX])
+{
+    int fd;
+    sprintf(buffer, "/proc/%d/cmdline", pid);
+    fd = open(buffer, O_RDONLY);
+    if (fd < 0) {
+        strcpy(buffer, "???");
+    } else {
+        int length = read(fd, buffer, PATH_MAX - 1);
+        buffer[length] = 0;
+        close(fd);
+    }
+}
+
+static boolean CheckFileDescriptorSymLinks(int pid, const char* mountPoint)
+{
+    DIR*    dir;
+    struct dirent* de;
+    boolean fileOpen = false;
+    char    path[PATH_MAX];
+    char    link[PATH_MAX];
+    int     parent_length;
+
+    // compute path to process's directory of open files
+    sprintf(path, "/proc/%d/fd", pid);
+    dir = opendir(path);
+    if (!dir)
+        return false;
+
+    // remember length of the path
+    parent_length = strlen(path);
+    // append a trailing '/'
+    path[parent_length++] = '/';
+    
+    while ((de = readdir(dir)) != 0 && !fileOpen) {
+        if (!strcmp(de->d_name, ".") || !strcmp(de->d_name, ".."))
+            continue;
+        
+        // append the file name, after truncating to parent directory
+        path[parent_length] = 0;
+        strcat(path, de->d_name);
+
+        if (ReadSymLink(path, link) && PathMatchesMountPoint(link, mountPoint))
+        {
+            char    name[PATH_MAX];
+            GetProcessName(pid, name);
+            LOG_ERROR("process %s (%d) has open file %s\n", name, pid, link);
+            fileOpen = true;
+        }
+    }
+
+    closedir(dir);
+    return fileOpen;
+}
+
+static boolean CheckFileMaps(int pid, const char* mountPoint)
+{
+    FILE*   file;
+    char    buffer[PATH_MAX + 100];
+    boolean mapOpen = false;
+
+    sprintf(buffer, "/proc/%d/maps", pid);
+    file = fopen(buffer, "r");
+    if (!file)
+        return false;
+    
+    while (!mapOpen && fgets(buffer, sizeof(buffer), file))
+    {
+        // skip to the path
+        const char* path = strchr(buffer, '/');
+        if (path && PathMatchesMountPoint(path, mountPoint))
+        {
+            char    name[PATH_MAX];
+            GetProcessName(pid, name);
+            LOG_ERROR("process %s (%d) has open file map for %s\n", name, pid, path);
+            mapOpen = true;
+        }
+    }
+    
+    fclose(file);
+    return mapOpen;
+}
+
+static boolean CheckSymLink(int pid, const char* mountPoint, const char* name, const char* message)
+{
+    char    path[PATH_MAX];
+    char    link[PATH_MAX];
+
+    sprintf(path, "/proc/%d/%s", pid, name);
+    if (ReadSymLink(path, link) && PathMatchesMountPoint(link, mountPoint)) 
+    {
+        char    name[PATH_MAX];
+        GetProcessName(pid, name);
+        LOG_ERROR("process %s (%d) has %s in %s\n", name, pid, message, mountPoint);
+        return true;
+    }
+    else
+        return false;
+}
+
+static int get_pid(const char* s)
+{
+    int result = 0;
+    while (*s) {
+        if (!isdigit(*s)) return -1;
+        result = 10 * result + (*s++ - '0');
+    }
+    return result;
+}
+
+// hunt down and kill processes that have files open on the given mount point
+void KillProcessesWithOpenFiles(const char* mountPoint, boolean sigkill, int *excluded, int num_excluded)
+{
+    DIR*    dir;
+    struct dirent* de;
+
+    LOG_ERROR("KillProcessesWithOpenFiles %s\n", mountPoint);
+    dir = opendir("/proc");
+    if (!dir) return;
+
+    while ((de = readdir(dir)) != 0)
+    {
+        boolean killed = false;
+        // does the name look like a process ID?
+        int pid = get_pid(de->d_name);
+        if (pid == -1) continue;
+
+        if (CheckFileDescriptorSymLinks(pid, mountPoint)    // check for open files
+                || CheckFileMaps(pid, mountPoint)           // check for mmap()
+                || CheckSymLink(pid, mountPoint, "cwd", "working directory")    // check working directory
+                || CheckSymLink(pid, mountPoint, "root", "chroot")              // check for chroot()
+                || CheckSymLink(pid, mountPoint, "exe", "executable path")      // check executable path
+            ) 
+        {
+            int i;
+            boolean hit = false;
+
+            for (i = 0; i < num_excluded; i++) {
+                if (pid == excluded[i]) {
+                    LOG_ERROR("I just need a little more TIME captain!\n");
+                    hit = true;
+                    break;
+                }
+            }
+
+            if (!hit) {
+                LOG_ERROR("Killing process %d\n", pid);
+                kill(pid, (sigkill ? SIGKILL : SIGTERM));
+            }
+        }
+    }
+
+    closedir(dir);
+}        
diff --git a/mountd/Server.c b/mountd/Server.c
new file mode 100644
index 0000000..64459bd
--- /dev/null
+++ b/mountd/Server.c
@@ -0,0 +1,313 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+/*
+**	mountd server support
+*/
+
+#include "mountd.h"
+#include "ASEC.h"
+
+#include <cutils/properties.h>
+#include <cutils/sockets.h>
+
+#include <pthread.h>
+#include <errno.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <sys/socket.h>
+
+#include <private/android_filesystem_config.h>
+
+
+// current client file descriptor
+static int sFD = -1;
+
+// to synchronize writing to client
+static pthread_mutex_t sWriteMutex = PTHREAD_MUTEX_INITIALIZER;
+
+// path for media that failed to mount before the runtime is connected
+static char* sDeferredUnmountableMediaPath = NULL;
+
+// last asec msg before the runtime was connected
+static char* sAsecDeferredMessage = NULL;
+static char* sAsecDeferredArgument = NULL;
+
+static int Write(const char* message)
+{
+    int result = -1;
+
+    pthread_mutex_lock(&sWriteMutex);
+    
+    LOG_SERVER("Write: %s\n", message);
+    if (sFD >= 0)
+        result = write(sFD, message, strlen(message) + 1);
+
+    pthread_mutex_unlock(&sWriteMutex); 
+    
+    return result;
+}
+
+static int Write2(const char* message, const char* data)
+{
+    int result = -1;
+
+    char* buffer = (char *)alloca(strlen(message) + strlen(data) + 1);
+    if (!buffer)
+    {
+        LOG_ERROR("alloca failed in Write2\n");
+        return -1;
+    }
+
+    strcpy(buffer, message);
+    strcat(buffer, data);
+    return Write(buffer);
+}
+
+static void SendStatus()
+{
+    Write(IsMassStorageConnected() ? MOUNTD_UMS_CONNECTED : MOUNTD_UMS_DISCONNECTED);
+    Write(IsMassStorageEnabled() ? MOUNTD_UMS_ENABLED : MOUNTD_UMS_DISABLED);
+}
+
+static void DoCommand(const char* command)
+{
+    LOG_SERVER("DoCommand %s\n", command);
+    
+    if (strcmp(command, MOUNTD_ENABLE_UMS) == 0)
+    {
+        EnableMassStorage(true);
+        Write(MOUNTD_UMS_ENABLED);
+     }
+    else if (strcmp(command, MOUNTD_DISABLE_UMS) == 0) 
+    {
+        EnableMassStorage(false);
+        Write(MOUNTD_UMS_DISABLED);
+    }
+    else if (strcmp(command, MOUNTD_SEND_STATUS) == 0)
+    {
+        SendStatus();
+    }
+    else if (strncmp(command, MOUNTD_MOUNT_MEDIA, strlen(MOUNTD_MOUNT_MEDIA)) == 0)
+    {
+        const char* path = command + strlen(MOUNTD_MOUNT_MEDIA);
+        MountMedia(path);
+    }
+    else if (strncmp(command, MOUNTD_EJECT_MEDIA, strlen(MOUNTD_EJECT_MEDIA)) == 0)
+    {
+        const char* path = command + strlen(MOUNTD_EJECT_MEDIA);
+        UnmountMedia(path);
+    } 
+    else if (strncmp(command, ASEC_CMD_ENABLE, strlen(ASEC_CMD_ENABLE)) == 0) {
+        LOG_ASEC("Got ASEC_CMD_ENABLE\n");
+	// XXX: SAN: Impliment
+    }
+    else if (strncmp(command, ASEC_CMD_DISABLE, strlen(ASEC_CMD_DISABLE)) == 0) {
+        LOG_ASEC("Got ASEC_CMD_DISABLE\n");
+	// XXX: SAN: Impliment
+    }
+    else if (strncmp(command, ASEC_CMD_SEND_STATUS, strlen(ASEC_CMD_SEND_STATUS)) == 0) {
+        LOG_ASEC("Got ASEC_CMD_SEND_STATUS\n");
+	// XXX: SAN: Impliment
+    }
+    else
+        LOGE("unknown command %s\n", command);
+}
+
+int RunServer()
+{
+    int socket = android_get_control_socket(MOUNTD_SOCKET);
+    if (socket < 0) {
+        LOGE("Obtaining file descriptor for socket '%s' failed: %s",
+             MOUNTD_SOCKET, strerror(errno));
+        return -1;
+    }
+
+    if (listen(socket, 4) < 0) {
+        LOGE("Unable to listen on file descriptor '%d' for socket '%s': %s",
+             socket, MOUNTD_SOCKET, strerror(errno));
+        return -1;
+    }
+
+    while (1)
+    {
+        struct sockaddr addr;
+        socklen_t alen;
+        struct ucred cred;
+        socklen_t size;
+        
+        alen = sizeof(addr);
+        sFD = accept(socket, &addr, &alen);
+        if (sFD < 0)
+            continue;
+            
+        if (sDeferredUnmountableMediaPath) {
+            NotifyMediaState(sDeferredUnmountableMediaPath, MEDIA_UNMOUNTABLE, false);
+            free(sDeferredUnmountableMediaPath);
+            sDeferredUnmountableMediaPath = NULL;
+        }
+
+        if (sAsecDeferredMessage) {
+    
+            if (Write2(sAsecDeferredMessage, sAsecDeferredArgument) < 0)
+                LOG_ERROR("Failed to deliver deferred ASEC msg to framework\n");
+            free(sAsecDeferredMessage);
+            free(sAsecDeferredArgument);
+            sAsecDeferredMessage = sAsecDeferredArgument = NULL;
+        }
+
+        while (1)
+        {    
+            char    buffer[101];
+            int result = read(sFD, buffer, sizeof(buffer) - 1);
+            if (result > 0)
+            {
+                int start = 0;
+                int i;
+                // command should be zero terminated, but just in case
+                buffer[result] = 0;
+                for (i = 0; i < result; i++) 
+                {
+                    if (buffer[i] == 0) 
+                    {
+                        DoCommand(buffer + start);
+                        start = i + 1;
+                    }                   
+                }
+            }
+            else
+            {
+                close(sFD);
+                sFD = -1;
+                break;
+            }
+        }
+    }  
+
+    // should never get here
+    return 0;
+}
+
+void SendMassStorageConnected(boolean connected)
+{
+    Write(connected ? MOUNTD_UMS_CONNECTED : MOUNTD_UMS_DISCONNECTED);
+}
+
+void SendUnmountRequest(const char* path)
+{
+    Write2(MOUNTD_REQUEST_EJECT, path);
+}
+
+void NotifyAsecState(AsecState state, const char *argument)
+{
+    const char *event = NULL;
+    const char *status = NULL;
+    boolean deferr = true;;
+
+    switch (state) {
+        case ASEC_DISABLED:
+            event = ASEC_EVENT_DISABLED;
+            status = ASEC_STATUS_DISABLED;
+            break;
+        case ASEC_AVAILABLE:
+            event = ASEC_EVENT_AVAILABLE;
+            status = ASEC_STATUS_AVAILABLE;
+            break;
+        case ASEC_BUSY:
+            event = ASEC_EVENT_BUSY;
+            status = ASEC_STATUS_BUSY;
+            deferr = false;
+            break;
+        case ASEC_FAILED_INTERR:
+            event = ASEC_EVENT_FAILED_INTERR;
+            status = ASEC_STATUS_FAILED_INTERR;
+            break;
+        case ASEC_FAILED_NOMEDIA:
+            event = ASEC_EVENT_FAILED_NOMEDIA;
+            status = ASEC_STATUS_FAILED_NOMEDIA;
+            break;
+        case ASEC_FAILED_BADMEDIA:
+            event = ASEC_EVENT_FAILED_BADMEDIA;
+            status = ASEC_STATUS_FAILED_BADMEDIA;
+            break;
+        case ASEC_FAILED_BADKEY:
+            event = ASEC_EVENT_FAILED_BADKEY;
+            status = ASEC_STATUS_FAILED_BADKEY;
+            break;
+        default:
+            LOG_ERROR("unknown AsecState %d in NotifyAsecState\n", state);
+            return;
+    }
+
+    property_set(ASEC_STATUS, status);
+
+    int result = Write2(event, argument);
+    if ((result < 0) && deferr) {
+        if (sAsecDeferredMessage) 
+            free(sAsecDeferredMessage);
+        sAsecDeferredMessage = strdup(event);
+        if (sAsecDeferredArgument)
+            free(sAsecDeferredArgument);
+        sAsecDeferredArgument = strdup(argument);
+        LOG_ASEC("Deferring event '%s' arg '%s' until framework connects\n", event, argument);
+    }
+}
+
+void NotifyMediaState(const char* path, MediaState state, boolean readOnly)
+{
+    const char* event = NULL;
+    const char* propertyValue = NULL;
+    
+    switch (state) {
+        case MEDIA_REMOVED:
+            event = MOUNTD_MEDIA_REMOVED;
+            propertyValue = EXTERNAL_STORAGE_REMOVED;
+            break;
+        case MEDIA_UNMOUNTED:
+            event = MOUNTD_MEDIA_UNMOUNTED;
+            propertyValue = EXTERNAL_STORAGE_UNMOUNTED;
+            break;
+        case MEDIA_MOUNTED:
+            event = (readOnly ? MOUNTD_MEDIA_MOUNTED_READ_ONLY : MOUNTD_MEDIA_MOUNTED);
+             propertyValue = (readOnly ? EXTERNAL_STORAGE_MOUNTED_READ_ONLY : EXTERNAL_STORAGE_MOUNTED);
+           break;
+        case MEDIA_SHARED:
+            event = MOUNTD_MEDIA_SHARED;
+            propertyValue = EXTERNAL_STORAGE_SHARED;
+            break;
+        case MEDIA_BAD_REMOVAL:
+            event = MOUNTD_MEDIA_BAD_REMOVAL;
+            propertyValue = EXTERNAL_STORAGE_BAD_REMOVAL;
+            break;
+        case MEDIA_UNMOUNTABLE:
+            event = MOUNTD_MEDIA_UNMOUNTABLE;
+            propertyValue = EXTERNAL_STORAGE_UNMOUNTABLE;
+            break;
+        default:
+            LOG_ERROR("unknown MediaState %d in NotifyMediaState\n", state);
+            return;
+    }
+    
+    property_set(EXTERNAL_STORAGE_STATE, propertyValue);
+    int result = Write2(event, path);
+    if (result < 0 && state == MEDIA_UNMOUNTABLE) {
+    
+        // if we cannot communicate with the runtime, defer this message until the runtime is available
+        sDeferredUnmountableMediaPath = strdup(path);
+    }
+}
diff --git a/mountd/logwrapper.c b/mountd/logwrapper.c
new file mode 100644
index 0000000..69606ab
--- /dev/null
+++ b/mountd/logwrapper.c
@@ -0,0 +1,154 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+#include <string.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <errno.h>
+#include <fcntl.h>
+
+#include "private/android_filesystem_config.h"
+#include "cutils/log.h"
+
+int parent(const char *tag, int parent_read) {
+    int status;
+    char buffer[4096];
+
+    int a = 0;  // start index of unprocessed data
+    int b = 0;  // end index of unprocessed data
+    int sz;
+    while ((sz = read(parent_read, &buffer[b], sizeof(buffer) - 1 - b)) > 0) {
+
+        sz += b;
+        // Log one line at a time
+        for (b = 0; b < sz; b++) {
+            if (buffer[b] == '\r') {
+                buffer[b] = '\0';
+            } else if (buffer[b] == '\n') {
+                buffer[b] = '\0';
+                LOG(LOG_INFO, tag, &buffer[a]);
+                a = b + 1;
+            }
+        }
+
+        if (a == 0 && b == sizeof(buffer) - 1) {
+            // buffer is full, flush
+            buffer[b] = '\0';
+            LOG(LOG_INFO, tag, &buffer[a]);
+            b = 0;
+        } else if (a != b) {
+            // Keep left-overs
+            b -= a;
+            memmove(buffer, &buffer[a], b);
+            a = 0;
+        } else {
+            a = 0;
+            b = 0;
+        }
+
+    }
+    // Flush remaining data
+    if (a != b) {
+        buffer[b] = '\0';
+        LOG(LOG_INFO, tag, &buffer[a]);
+    }
+    status = 0xAAAA;
+    if (wait(&status) != -1) {  // Wait for child
+        if (WIFEXITED(status)) {
+            LOG(LOG_INFO, "logwrapper", "%s terminated by exit(%d)", tag,
+                    WEXITSTATUS(status));
+            return WEXITSTATUS(status);
+        } else if (WIFSIGNALED(status))
+            LOG(LOG_INFO, "logwrapper", "%s terminated by signal %d", tag,
+                    WTERMSIG(status));
+        else if (WIFSTOPPED(status))
+            LOG(LOG_INFO, "logwrapper", "%s stopped by signal %d", tag,
+                    WSTOPSIG(status));
+    } else
+        LOG(LOG_INFO, "logwrapper", "%s wait() failed: %s (%d)", tag,
+                strerror(errno), errno);
+    return -EAGAIN;
+}
+
+void child(int argc, char* argv[]) {
+    // create null terminated argv_child array
+    char* argv_child[argc + 1];
+    memcpy(argv_child, argv, argc * sizeof(char *));
+    argv_child[argc] = NULL;
+
+    // XXX: PROTECT FROM VIKING KILLER
+    if (execvp(argv_child[0], argv_child)) {
+        LOG(LOG_ERROR, "logwrapper",
+            "executing %s failed: %s\n", argv_child[0], strerror(errno));
+        exit(-1);
+    }
+}
+
+int logwrap(int argc, char* argv[])
+{
+    pid_t pid;
+
+    int parent_ptty;
+    int child_ptty;
+    char *child_devname = NULL;
+
+    /* Use ptty instead of socketpair so that STDOUT is not buffered */
+    parent_ptty = open("/dev/ptmx", O_RDWR);
+    if (parent_ptty < 0) {
+	LOG(LOG_ERROR, "logwrapper", "Cannot create parent ptty\n");
+	return -errno;
+    }
+
+    if (grantpt(parent_ptty) || unlockpt(parent_ptty) ||
+            ((child_devname = (char*)ptsname(parent_ptty)) == 0)) {
+	LOG(LOG_ERROR, "logwrapper", "Problem with /dev/ptmx\n");
+	return -1;
+    }
+
+    pid = fork();
+    if (pid < 0) {
+	LOG(LOG_ERROR, "logwrapper", "Failed to fork\n");
+        return -errno;
+    } else if (pid == 0) {
+        child_ptty = open(child_devname, O_RDWR);
+        if (child_ptty < 0) {
+	    LOG(LOG_ERROR, "logwrapper", "Problem with child ptty\n");
+            return -errno;
+        }
+
+        // redirect stdout and stderr
+        close(parent_ptty);
+        dup2(child_ptty, 1);
+        dup2(child_ptty, 2);
+        close(child_ptty);
+
+        child(argc, argv);
+    } else {
+        // switch user and group to "log"
+        // this may fail if we are not root, 
+        // but in that case switching user/group is unnecessary 
+        
+      //  setgid(AID_LOG);
+      //  setuid(AID_LOG);
+
+        return parent(argv[0], parent_ptty);
+    }
+
+    return 0;
+}
diff --git a/mountd/mountd.c b/mountd/mountd.c
new file mode 100644
index 0000000..27ec8de
--- /dev/null
+++ b/mountd/mountd.c
@@ -0,0 +1,174 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+/*
+**    mountd main program
+*/
+
+#include "mountd.h"
+
+#include <cutils/config_utils.h>
+#include <cutils/cpu_info.h>
+#include <cutils/properties.h>
+
+#include <sys/mount.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <linux/capability.h>
+#include <linux/prctl.h>
+
+#include <private/android_filesystem_config.h>
+
+#ifdef MOUNTD_LOG
+FILE*    logFile;
+#endif
+
+struct asec_cfg {
+    const char *name;
+    const char *backing_file;
+    const char *size;
+    const char *mount_point;
+    const char *crypt;
+};
+
+static int ProcessAsecData(cnode *node, struct asec_cfg *stores, int idx)
+{
+    cnode *child = node->first_child;
+    const char *name = NULL;
+    const char *file = NULL;
+    const char *size = NULL;
+    const char *mp = NULL;
+    const char *crypt = NULL;
+
+    LOG_ASEC("ProcessAsecData(%s, %p, %d)\n", node->name, stores, idx);
+
+    while (child) {
+        if (!strcmp(child->name, "name"))
+            name = child->value;
+        else if (!strcmp(child->name, "backing_file"))
+            file = child->value;
+        else if (!strcmp(child->name, "size"))
+            size = child->value;
+        else if (!strcmp(child->name, "mount_point"))
+            mp = child->value;
+        else if (!strcmp(child->name, "crypt"))
+            crypt = child->value;
+        child = child->next;
+    }
+
+    if (!name || !file || !size || !mp || !crypt) {
+        LOG_ERROR("Missing required token from config. Skipping ASEC volume\n");
+        return -1;
+    } else if (idx == ASEC_STORES_MAX) {
+        LOG_ERROR("Maximum # of ASEC stores already defined\n");
+        return -1;
+    }
+
+    stores[idx].name = name;
+    stores[idx].backing_file = file;
+    stores[idx].size = size;
+    stores[idx].mount_point = mp;
+    stores[idx].crypt = crypt;
+    return ++idx;
+}
+
+static void ReadConfigFile(const char* path)
+{
+    cnode* root = config_node("", "");
+    cnode* node;
+
+    config_load_file(root, path);
+    node = root->first_child;
+
+    while (node)
+    {
+        if (strcmp(node->name, "mount") == 0)
+        {
+            const char* block_device = NULL;
+            const char* mount_point = NULL;
+            const char* driver_store_path = NULL;
+            boolean enable_ums = false;
+            cnode* child = node->first_child;
+            struct asec_cfg asec_stores[ASEC_STORES_MAX];
+            int    asec_idx = 0;
+
+            memset(asec_stores, 0, sizeof(asec_stores));
+
+            while (child)
+            {
+                const char* name = child->name;
+                const char* value = child->value;
+
+                if (!strncmp(name, "asec_", 5)) {
+                     int rc = ProcessAsecData(child, asec_stores, asec_idx);
+                     if (rc < 0) {
+                         LOG_ERROR("Error processing ASEC cfg data\n");
+                     } else
+                         asec_idx = rc;
+                } else if (strcmp(name, "block_device") == 0)
+                    block_device = value;
+                else if (strcmp(name, "mount_point") == 0)
+                    mount_point = value;
+                else if (strcmp(name, "driver_store_path") == 0)
+                    driver_store_path = value;
+                else if (strcmp(name, "enable_ums") == 0 &&
+                        strcmp(value, "true") == 0)
+                    enable_ums = true;
+                
+                child = child->next;
+            }
+
+            // mount point and removable fields are optional
+            if (block_device && mount_point)
+            {
+                void *mp = AddMountPoint(block_device, mount_point, driver_store_path, enable_ums);
+                int i;
+
+                for (i = 0; i < asec_idx; i++) {
+                    AddAsecToMountPoint(mp, asec_stores[i].name, asec_stores[i].backing_file,
+                                        asec_stores[i].size, asec_stores[i].mount_point,
+                                        asec_stores[i].crypt);
+                }
+            }
+        }
+            
+        node = node->next;
+    }
+}
+
+int main(int argc, char* argv[])
+{
+    const char*     configPath = "/system/etc/mountd.conf";
+    int             i;    
+
+    for (i = 1; i < argc; i++)
+    {
+        const char* arg = argv[i];
+        
+        if (strcmp(arg, "-f") == 0)
+        {
+            if (i < argc - 1)
+                configPath = argv[++i];
+        }
+    }
+        
+    ReadConfigFile(configPath);
+    StartAutoMounter();
+    return RunServer();
+}
diff --git a/mountd/mountd.h b/mountd/mountd.h
new file mode 100644
index 0000000..c4bc91d
--- /dev/null
+++ b/mountd/mountd.h
@@ -0,0 +1,190 @@
+/*
+ * Copyright (C) 2008 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.
+ */
+
+#ifndef MOUNTD_H__
+#define MOUNTD_H__
+
+#define LOG_TAG "mountd"
+#include "cutils/log.h"
+
+#include "ASEC.h"
+
+typedef int boolean;
+enum {
+    false = 0,
+    true = 1
+};
+
+#define WEXITSTATUS(status) (((status) & 0xff00) >> 8)
+
+// Set this for logging error messages
+#define ENABLE_LOG_ERROR
+
+// set this to log automounter events
+#define ENABLE_LOG_MOUNT
+
+// set this to log server events
+//#define ENABLE_LOG_SERVER
+
+// set this to log ASEC events
+#define ENABLE_LOG_ASEC
+
+#ifdef ENABLE_LOG_ERROR
+#define LOG_ERROR(fmt, args...) \
+    { LOGE(fmt , ## args); }
+#else
+#define LOG_ERROR(fmt, args...) \
+    do { } while (0)
+#endif /* ENABLE_LOG_ERROR */
+
+#ifdef ENABLE_LOG_MOUNT
+#define LOG_MOUNT(fmt, args...) \
+    { LOGD(fmt , ## args); }
+#else
+#define LOG_MOUNT(fmt, args...) \
+    do { } while (0)
+#endif /* ENABLE_LOG_MOUNT */
+
+#ifdef ENABLE_LOG_SERVER
+#define LOG_SERVER(fmt, args...) \
+    { LOGD(fmt , ## args); }
+#else
+#define LOG_SERVER(fmt, args...) \
+    do { } while (0)
+#endif /* ENABLE_LOG_SERVER */
+
+#ifdef ENABLE_LOG_ASEC
+#define LOG_ASEC(fmt, args...) \
+    { LOGD(fmt , ## args); }
+#else
+#define LOG_ASEC(fmt, args...) \
+    do { } while (0)
+#endif /* ENABLE_LOG_ASEC */
+
+
+typedef enum MediaState {
+    // no media in SD card slot
+    MEDIA_REMOVED,
+    
+    // media in SD card slot, but not mounted
+    MEDIA_UNMOUNTED,
+    
+    // media in SD card slot and mounted at its mount point
+    MEDIA_MOUNTED,
+    
+    // media in SD card slot, unmounted, and shared as a mass storage device
+    MEDIA_SHARED,
+    
+    // media was removed from SD card slot, but mount point was not unmounted
+    // this state is cleared after the mount point is unmounted
+    MEDIA_BAD_REMOVAL,
+
+    // media in SD card slot could not be mounted (corrupt file system?)
+    MEDIA_UNMOUNTABLE,
+} MediaState;
+
+// socket name for connecting to mountd
+#define MOUNTD_SOCKET         "mountd"
+
+// mountd commands
+// these must match the corresponding strings in //device/java/android/android/os/UsbListener.java
+#define MOUNTD_ENABLE_UMS     "enable_ums"
+#define MOUNTD_DISABLE_UMS    "disable_ums"
+#define MOUNTD_SEND_STATUS    "send_status"
+
+// these commands should contain a mount point following the colon
+#define MOUNTD_MOUNT_MEDIA  "mount_media:"
+#define MOUNTD_EJECT_MEDIA  "eject_media:"
+
+// mountd events
+// these must match the corresponding strings in //device/java/android/android/os/UsbListener.java
+#define MOUNTD_UMS_ENABLED              "ums_enabled"
+#define MOUNTD_UMS_DISABLED             "ums_disabled"
+#define MOUNTD_UMS_CONNECTED            "ums_connected"
+#define MOUNTD_UMS_DISCONNECTED         "ums_disconnected"
+
+// these events correspond to the states in the MediaState enum.
+// a path to the mount point follows the colon.
+#define MOUNTD_MEDIA_REMOVED            "media_removed:"
+#define MOUNTD_MEDIA_UNMOUNTED        	"media_unmounted:"
+#define MOUNTD_MEDIA_MOUNTED          	"media_mounted:"
+#define MOUNTD_MEDIA_MOUNTED_READ_ONLY  "media_mounted_ro:"
+#define MOUNTD_MEDIA_SHARED             "media_shared:"
+#define MOUNTD_MEDIA_BAD_REMOVAL        "media_bad_removal:"
+#define MOUNTD_MEDIA_UNMOUNTABLE        "media_unmountable:"
+
+// this event sent to request unmount for media mount point
+#define MOUNTD_REQUEST_EJECT            "request_eject:"
+
+// system properties
+// these must match the corresponding strings in //device/java/android/android/os/Environment.java
+#define EXTERNAL_STORAGE_STATE          "EXTERNAL_STORAGE_STATE"
+#define EXTERNAL_STORAGE_REMOVED        "removed"
+#define EXTERNAL_STORAGE_UNMOUNTED      "unmounted"
+#define EXTERNAL_STORAGE_MOUNTED        "mounted"
+#define EXTERNAL_STORAGE_MOUNTED_READ_ONLY        "mounted_ro"
+#define EXTERNAL_STORAGE_SHARED         "shared"
+#define EXTERNAL_STORAGE_BAD_REMOVAL    "bad_removal"
+#define EXTERNAL_STORAGE_UNMOUNTABLE    "unmountable"
+
+// AutoMount.c
+
+boolean IsMassStorageEnabled();
+boolean IsMassStorageConnected();
+
+void MountMedia(const char* mountPoint);
+void UnmountMedia(const char* mountPoint);
+void EnableMassStorage(boolean enable);
+
+// call this before StartAutoMounter() to add a mount point to monitor
+void *AddMountPoint(const char* device, const char* mountPoint, const char* driverStorePath,
+                    boolean enableUms);
+
+int AddAsecToMountPoint(void *Mp, const char *name, const char *backing_file,
+                        const char *size, const char *mount_point, const char *crypt);
+
+// start automounter thread
+void StartAutoMounter();
+
+// check /proc/mounts for mounted file systems, and notify mount or unmount for any that are in our automount list
+void NotifyExistingMounts();
+
+
+// ASEC.c
+
+void *AsecInit(const char *Name, const char *SrcPath, const char *BackingFile,
+               const char *Size, const char *DstPath, const char *Crypt);
+int AsecStart(void *Handle);
+int AsecStop(void *Handle);
+void AsecDeinit(void *Handle);
+boolean AsecIsStarted(void *Handle);
+const char *AsecMountPoint(void *Handle);
+
+// ProcessKiller.c
+
+void KillProcessesWithOpenFiles(const char* mountPoint, boolean sigkill, pid_t *excluded, int num_excluded);
+
+// logwrapper.c
+int logwrap(int argc, char* argv[]);
+
+// Server.c
+
+int RunServer();
+void SendMassStorageConnected(boolean connected); 
+void SendUnmountRequest(const char* path);
+void NotifyMediaState(const char* path, MediaState state, boolean readOnly);
+void NotifyAsecState(AsecState state, const char *argument);
+#endif // MOUNTD_H__
