diff --git a/Android.mk b/Android.mk
index 38da8c7..1d36312 100644
--- a/Android.mk
+++ b/Android.mk
@@ -114,3 +114,15 @@
 LOCAL_CONLYFLAGS := $(vold_conlyflags)
 
 include $(BUILD_EXECUTABLE)
+
+include $(CLEAR_VARS)
+
+LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk
+LOCAL_CLANG := true
+LOCAL_SRC_FILES:= secdiscard.cpp
+LOCAL_MODULE:= secdiscard
+LOCAL_SHARED_LIBRARIES := libcutils
+LOCAL_CFLAGS := $(vold_cflags)
+LOCAL_CONLYFLAGS := $(vold_conlyflags)
+
+include $(BUILD_EXECUTABLE)
diff --git a/CryptCommandListener.cpp b/CryptCommandListener.cpp
index 2e46919..173be63 100644
--- a/CryptCommandListener.cpp
+++ b/CryptCommandListener.cpp
@@ -42,6 +42,7 @@
 #include "Process.h"
 #include "ResponseCode.h"
 #include "cryptfs.h"
+#include "Ext4Crypt.h"
 
 #define DUMP_ARGS 0
 
@@ -288,6 +289,35 @@
         dumpArgs(argc, argv, -1);
         cryptfs_clear_password();
         rc = 0;
+    } else if (!strcmp(argv[1], "setusercryptopolicies")) {
+        if (argc != 3) {
+            cli->sendMsg(ResponseCode::CommandSyntaxError,
+                "Usage: cryptfs setusercryptopolicies <path>", false);
+            return 0;
+        }
+        SLOGD("cryptfs setusercryptopolicies");
+        dumpArgs(argc, argv, -1);
+        rc = e4crypt_set_user_crypto_policies(argv[2]);
+    } else if (!strcmp(argv[1], "createnewuserdir")) {
+        if (argc != 4) {
+            cli->sendMsg(ResponseCode::CommandSyntaxError,
+                "Usage: cryptfs createnewuserdir <userHandle> <path>", false);
+            return 0;
+        }
+        // ext4enc:TODO: send a CommandSyntaxError if argv[2] not an integer
+        SLOGD("cryptfs createnewuserdir");
+        dumpArgs(argc, argv, -1);
+        rc = e4crypt_create_new_user_dir(argv[2], argv[3]);
+    } else if (!strcmp(argv[1], "deleteuserkey")) {
+        if (argc != 3) {
+            cli->sendMsg(ResponseCode::CommandSyntaxError,
+                "Usage: cryptfs deleteuserkey <userHandle>", false);
+            return 0;
+        }
+        // ext4enc:TODO: send a CommandSyntaxError if argv[2] not an integer
+        SLOGD("cryptfs deleteuserkey");
+        dumpArgs(argc, argv, -1);
+        rc = e4crypt_delete_user_key(argv[2]);
     } else {
         dumpArgs(argc, argv, -1);
         cli->sendMsg(ResponseCode::CommandSyntaxError, "Unknown cryptfs cmd", false);
diff --git a/Ext4Crypt.cpp b/Ext4Crypt.cpp
index d200ca6..95cbfb7 100644
--- a/Ext4Crypt.cpp
+++ b/Ext4Crypt.cpp
@@ -7,17 +7,24 @@
 #include <sstream>
 
 #include <errno.h>
+#include <dirent.h>
 #include <sys/mount.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
 #include <cutils/properties.h>
 #include <openssl/sha.h>
 
 #include "unencrypted_properties.h"
 #include "key_control.h"
 #include "cryptfs.h"
+#include "ext4_crypt_init_extensions.h"
 
 #define LOG_TAG "Ext4Crypt"
 #include "cutils/log.h"
 #include <cutils/klog.h>
+#include <base/file.h>
+#include <base/stringprintf.h>
 
 namespace {
     // Key length in bits
@@ -69,6 +76,8 @@
     }
 }
 
+static std::string e4crypt_install_key(const std::string &key);
+
 static int put_crypt_ftr_and_key(const crypt_mnt_ftr& crypt_ftr,
                                  UnencryptedProperties& props)
 {
@@ -240,10 +249,10 @@
         return -1;
     }
 
-    const unsigned char* master_key
+    const unsigned char* master_key_bytes
         = reinterpret_cast<const unsigned char*>(&mki->second.master_key[0]);
 
-    if (cryptfs_set_password(&ftr, password, master_key)) {
+    if (cryptfs_set_password(&ftr, password, master_key_bytes)) {
         SLOGE("Failed to set password");
         return -1;
     }
@@ -276,6 +285,7 @@
     return 0;
 }
 
+// Get raw keyref - used to make keyname and to pass to ioctl
 static std::string generate_key_ref(const char* key, int length)
 {
     SHA512_CTX c;
@@ -305,8 +315,8 @@
         return -1;
     }
 
-    unsigned char master_key[key_length / 8];
-    if (cryptfs_get_master_key (&ftr, password, master_key)){
+    unsigned char master_key_bytes[key_length / 8];
+    if (cryptfs_get_master_key (&ftr, password, master_key_bytes)){
         SLOGI("Incorrect password");
         ftr.failed_decrypt_count++;
         if (put_crypt_ftr_and_key(ftr, key_props)) {
@@ -321,15 +331,29 @@
             SLOGW("Failed to reset failed_decrypt_count");
         }
     }
+    std::string master_key(reinterpret_cast<char*>(master_key_bytes),
+                           sizeof(master_key_bytes));
 
     struct timespec now;
     clock_gettime(CLOCK_BOOTTIME, &now);
-    s_key_store[path] = keys{std::string(reinterpret_cast<char*>(master_key),
-                                         sizeof(master_key)),
-                             password,
+    s_key_store[path] = keys{master_key, password,
                              now.tv_sec + password_max_age_seconds};
+    auto raw_ref = e4crypt_install_key(master_key);
+    if (raw_ref.empty()) {
+        return -1;
+    }
 
-    // Install password into global keyring
+    // Save reference to key so we can set policy later
+    if (!props.Set(properties::ref, raw_ref)) {
+        SLOGE("Cannot save key reference");
+        return -1;
+    }
+
+    return 0;
+}
+
+static ext4_encryption_key fill_key(const std::string &key)
+{
     // ext4enc:TODO Currently raw key is required to be of length
     // sizeof(ext4_key.raw) == EXT4_MAX_KEY_SIZE, so zero pad to
     // this length. Change when kernel bug is fixed.
@@ -339,47 +363,56 @@
     memset(ext4_key.raw, 0, sizeof(ext4_key.raw));
     static_assert(key_length / 8 <= sizeof(ext4_key.raw),
                   "Key too long!");
-    memcpy(ext4_key.raw, master_key, key_length / 8);
+    memcpy(ext4_key.raw, &key[0], key.size());
+    return ext4_key;
+}
 
-    // Get raw keyref - used to make keyname and to pass to ioctl
-    auto raw_ref = generate_key_ref(ext4_key.raw, ext4_key.size);
-
-    // Generate keyname
+static std::string keyname(const std::string &raw_ref)
+{
     std::ostringstream o;
+    o << "ext4:";
     for (auto i = raw_ref.begin(); i != raw_ref.end(); ++i) {
         o << std::hex << std::setw(2) << std::setfill('0') << (int)*i;
     }
-    auto ref = std::string("ext4:") + o.str();
+    return o.str();
+}
 
-    // Find existing keyring
-    key_serial_t device_keyring = keyctl_search(KEY_SPEC_SESSION_KEYRING,
-                                                "keyring", "e4crypt", 0);
+// Get the keyring we store all keys in
+static key_serial_t e4crypt_keyring()
+{
+    return keyctl_search(KEY_SPEC_SESSION_KEYRING, "keyring", "e4crypt", 0);
+}
 
+static int e4crypt_install_key(const ext4_encryption_key &ext4_key, const std::string &ref)
+{
+    key_serial_t device_keyring = e4crypt_keyring();
     SLOGI("Found device_keyring - id is %d", device_keyring);
-
-    // Add key ...
     key_serial_t key_id = add_key("logon", ref.c_str(),
                                   (void*)&ext4_key, sizeof(ext4_key),
                                   device_keyring);
-
     if (key_id == -1) {
         SLOGE("Failed to insert key into keyring with error %s",
               strerror(errno));
         return -1;
     }
-
     SLOGI("Added key %d (%s) to keyring %d in process %d",
           key_id, ref.c_str(), device_keyring, getpid());
-
-    // Save reference to key so we can set policy later
-    if (!props.Set(properties::ref, raw_ref)) {
-        SLOGE("Cannot save key reference");
-        return -1;
-    }
-
     return 0;
 }
 
+// Install password into global keyring
+// Return raw key reference for use in policy
+static std::string e4crypt_install_key(const std::string &key)
+{
+    auto ext4_key = fill_key(key);
+    auto raw_ref = generate_key_ref(ext4_key.raw, ext4_key.size);
+    auto ref = keyname(raw_ref);
+    if (e4crypt_install_key(ext4_key, ref) == -1) {
+        return "";
+    }
+    return raw_ref;
+}
+
 int e4crypt_restart(const char* path)
 {
     SLOGI("e4crypt_restart");
@@ -473,3 +506,161 @@
     return GetPropsOrAltProps(path).GetChild(properties::props)
         .Set(fieldname, std::string(value)) ? 0 : -1;
 }
+
+static std::string get_key_path(
+    const char *mount_path,
+    const char *user_handle)
+{
+    // ext4enc:TODO get the path properly
+    auto key_dir = android::base::StringPrintf("%s/misc/vold/user_keys",
+        mount_path);
+    if (mkdir(key_dir.c_str(), 0700) < 0 && errno != EEXIST) {
+        SLOGE("Unable to create %s (%s)", key_dir.c_str(), strerror(errno));
+        return "";
+    }
+    return key_dir + "/" + user_handle;
+}
+
+// ext4enc:TODO this can't be the only place keys are read from /dev/urandom
+// we should unite those places.
+static std::string e4crypt_get_key(
+    const std::string &key_path,
+    bool create_if_absent)
+{
+    std::string content;
+    if (android::base::ReadFileToString(key_path, &content)) {
+        if (content.size() != key_length/8) {
+            SLOGE("Wrong size key %zu in  %s", content.size(), key_path.c_str());
+            return "";
+        }
+        return content;
+    }
+    if (!create_if_absent) {
+        SLOGE("No key found in %s", key_path.c_str());
+        return "";
+    }
+    std::ifstream urandom("/dev/urandom");
+    if (!urandom) {
+        SLOGE("Unable to open /dev/urandom (%s)", strerror(errno));
+        return "";
+    }
+    char key_bytes[key_length / 8];
+    errno = 0;
+    urandom.read(key_bytes, sizeof(key_bytes));
+    if (!urandom) {
+        SLOGE("Unable to read key from /dev/urandom (%s)", strerror(errno));
+        return "";
+    }
+    std::string key(key_bytes, sizeof(key_bytes));
+    if (!android::base::WriteStringToFile(key, key_path)) {
+        SLOGE("Unable to write key to %s (%s)",
+                key_path.c_str(), strerror(errno));
+        return "";
+    }
+    return key;
+}
+
+static int e4crypt_set_user_policy(const char *mount_path, const char *user_handle,
+                            const char *path, bool create_if_absent)
+{
+    SLOGD("e4crypt_set_user_policy for %s", user_handle);
+    auto user_key = e4crypt_get_key(
+        get_key_path(mount_path, user_handle),
+        create_if_absent);
+    if (user_key.empty()) {
+        return -1;
+    }
+    auto raw_ref = e4crypt_install_key(user_key);
+    if (raw_ref.empty()) {
+        return -1;
+    }
+    return do_policy_set(path, raw_ref.c_str(), raw_ref.size());
+}
+
+int e4crypt_create_new_user_dir(const char *user_handle, const char *path) {
+    SLOGD("e4crypt_create_new_user_dir(\"%s\", \"%s\")", user_handle, path);
+    if (mkdir(path, S_IRWXU | S_IRWXG | S_IXOTH) < 0) {
+        return -1;
+    }
+    if (chmod(path, S_IRWXU | S_IRWXG | S_IXOTH) < 0) {
+        return -1;
+    }
+    if (e4crypt_crypto_complete(DATA_MNT_POINT) == 0) {
+        // ext4enc:TODO handle errors from this.
+        e4crypt_set_user_policy(DATA_MNT_POINT, user_handle, path, true);
+    }
+    return 0;
+}
+
+static bool is_numeric(const char *name) {
+    for (const char *p = name; *p != '\0'; p++) {
+        if (!isdigit(*p))
+            return false;
+    }
+    return true;
+}
+
+int e4crypt_set_user_crypto_policies(const char *dir)
+{
+    if (e4crypt_crypto_complete(DATA_MNT_POINT) != 0) {
+        return 0;
+    }
+    SLOGD("e4crypt_set_user_crypto_policies");
+    std::unique_ptr<DIR, int(*)(DIR*)> dirp(opendir(dir), closedir);
+    if (!dirp) {
+        SLOGE("Unable to read directory %s, error %s\n",
+            dir, strerror(errno));
+        return -1;
+    }
+    for (;;) {
+        struct dirent *result = readdir(dirp.get());
+        if (!result) {
+            // ext4enc:TODO check errno
+            break;
+        }
+        if (result->d_type != DT_DIR || !is_numeric(result->d_name)) {
+            continue; // skips user 0, which is a symlink
+        }
+        auto user_dir = std::string() + dir + "/" + result->d_name;
+        // ext4enc:TODO don't hardcode /data
+        if (e4crypt_set_user_policy("/data", result->d_name,
+                user_dir.c_str(), false)) {
+            // ext4enc:TODO If this function fails, stop the boot: we must
+            // deliver on promised encryption.
+            SLOGE("Unable to set policy on %s\n", user_dir.c_str());
+        }
+    }
+    return 0;
+}
+
+int e4crypt_delete_user_key(const char *user_handle) {
+    SLOGD("e4crypt_delete_user_key(\"%s\")", user_handle);
+    auto key_path = get_key_path(DATA_MNT_POINT, user_handle);
+    auto key = e4crypt_get_key(key_path, false);
+    auto ext4_key = fill_key(key);
+    auto ref = keyname(generate_key_ref(ext4_key.raw, ext4_key.size));
+    auto key_serial = keyctl_search(e4crypt_keyring(), "logon", ref.c_str(), 0);
+    if (keyctl_revoke(key_serial) == 0) {
+        SLOGD("Revoked key with serial %ld ref %s\n", key_serial, ref.c_str());
+    } else {
+        SLOGE("Failed to revoke key with serial %ld ref %s: %s\n",
+            key_serial, ref.c_str(), strerror(errno));
+    }
+    int pid = fork();
+    if (pid < 0) {
+        SLOGE("Unable to fork: %s", strerror(errno));
+        return -1;
+    }
+    if (pid == 0) {
+        SLOGD("Forked for secdiscard");
+        execl("/system/bin/secdiscard",
+            "/system/bin/secdiscard",
+            key_path.c_str(),
+            NULL);
+        SLOGE("Unable to launch secdiscard on %s: %s\n", key_path.c_str(),
+            strerror(errno));
+        exit(-1);
+    }
+    // ext4enc:TODO reap the zombie
+    return 0;
+}
diff --git a/Ext4Crypt.h b/Ext4Crypt.h
index 53a26a0..f5c2871 100644
--- a/Ext4Crypt.h
+++ b/Ext4Crypt.h
@@ -18,5 +18,8 @@
                       char* value, size_t len);
 int e4crypt_set_field(const char* path, const char* fieldname,
                       const char* value);
+int e4crypt_set_user_crypto_policies(const char *path);
+int e4crypt_create_new_user_dir(const char *user_handle, const char *path);
+int e4crypt_delete_user_key(const char *user_handle);
 
 __END_DECLS
diff --git a/cryptfs.c b/cryptfs.c
index a905ff6..1a63a5b 100644
--- a/cryptfs.c
+++ b/cryptfs.c
@@ -3237,7 +3237,9 @@
 int cryptfs_changepw(int crypt_type, const char *newpw)
 {
     if (e4crypt_crypto_complete(DATA_MNT_POINT) == 0) {
-        return e4crypt_change_password(DATA_MNT_POINT, crypt_type, newpw);
+        return e4crypt_change_password(DATA_MNT_POINT, crypt_type,
+                    crypt_type == CRYPT_TYPE_DEFAULT ? DEFAULT_PASSWORD
+                                                     : newpw);
     }
 
     struct crypt_mnt_ftr crypt_ftr;
diff --git a/secdiscard.cpp b/secdiscard.cpp
new file mode 100644
index 0000000..3f4ab2e
--- /dev/null
+++ b/secdiscard.cpp
@@ -0,0 +1,236 @@
+/*
+ * Copyright (C) 2015 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>
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <linux/fs.h>
+#include <linux/fiemap.h>
+
+#define LOG_TAG "secdiscard"
+#include "cutils/log.h"
+
+// Deliberately limit ourselves to wiping small files.
+#define MAX_WIPE_LENGTH 4096
+#define INIT_BUFFER_SIZE 2048
+
+static void usage(char *progname);
+static void destroy_key(const std::string &path);
+static int file_device_range(const std::string &path, uint64_t range[2]);
+static int open_block_device_for_path(const std::string &path);
+static int read_file_as_string_atomically(const std::string &path, std::string &contents);
+static int find_block_device_for_path(
+    const std::string &mounts,
+    const std::string &path,
+    std::string &block_device);
+
+int main(int argc, char **argv) {
+    if (argc != 2 || argv[1][0] != '/') {
+        usage(argv[0]);
+        return -1;
+    }
+    SLOGD("Running: %s %s", argv[0], argv[1]);
+    std::string target(argv[1]);
+    destroy_key(target);
+    if (unlink(argv[1]) != 0 && errno != ENOENT) {
+        SLOGE("Unable to delete %s: %s",
+            argv[1], strerror(errno));
+        return -1;
+    }
+    return 0;
+}
+
+static void usage(char *progname) {
+    fprintf(stderr, "Usage: %s <absolute path>\n", progname);
+}
+
+// BLKSECDISCARD all content in "path", if it's small enough.
+static void destroy_key(const std::string &path) {
+    uint64_t range[2];
+    if (file_device_range(path, range) < 0) {
+        return;
+    }
+    int fs_fd = open_block_device_for_path(path);
+    if (fs_fd < 0) {
+        return;
+    }
+    if (ioctl(fs_fd, BLKSECDISCARD, range) != 0) {
+        SLOGE("Unable to BLKSECDISCARD %s: %s", path.c_str(), strerror(errno));
+        close(fs_fd);
+        return;
+    }
+    close(fs_fd);
+    SLOGD("Discarded %s", path.c_str());
+}
+
+// Find a short range that completely covers the file.
+// If there isn't one, return -1, otherwise 0.
+static int file_device_range(const std::string &path, uint64_t range[2])
+{
+    int fd = open(path.c_str(), O_RDONLY | O_CLOEXEC);
+    if (fd < 0) {
+        if (errno == ENOENT) {
+            SLOGD("Unable to open %s: %s", path.c_str(), strerror(errno));
+        } else {
+            SLOGE("Unable to open %s: %s", path.c_str(), strerror(errno));
+        }
+        return -1;
+    }
+    alignas(struct fiemap) char fiemap_buffer[offsetof(struct fiemap, fm_extents[1])];
+    memset(fiemap_buffer, 0, sizeof(fiemap_buffer));
+    struct fiemap *fiemap = (struct fiemap *)fiemap_buffer;
+    fiemap->fm_start = 0;
+    fiemap->fm_length = UINT64_MAX;
+    fiemap->fm_flags = 0;
+    fiemap->fm_extent_count = 1;
+    fiemap->fm_mapped_extents = 0;
+    if (ioctl(fd, FS_IOC_FIEMAP, fiemap) != 0) {
+        SLOGE("Unable to FIEMAP %s: %s", path.c_str(), strerror(errno));
+        close(fd);
+        return -1;
+    }
+    close(fd);
+    if (fiemap->fm_mapped_extents != 1) {
+        SLOGE("Expecting one extent, got %d in %s", fiemap->fm_mapped_extents, path.c_str());
+        return -1;
+    }
+    struct fiemap_extent *extent = &fiemap->fm_extents[0];
+    if (!(extent->fe_flags & FIEMAP_EXTENT_LAST)) {
+        SLOGE("First extent was not the last in %s", path.c_str());
+        return -1;
+    }
+    if (extent->fe_flags &
+            (FIEMAP_EXTENT_UNKNOWN | FIEMAP_EXTENT_DELALLOC | FIEMAP_EXTENT_NOT_ALIGNED)) {
+        SLOGE("Extent has unexpected flags %ulx: %s", extent->fe_flags, path.c_str());
+        return -1;
+    }
+    if (extent->fe_length > MAX_WIPE_LENGTH) {
+        SLOGE("Extent too big, %llu bytes in %s", extent->fe_length, path.c_str());
+        return -1;
+    }
+    range[0] = extent->fe_physical;
+    range[1] = extent->fe_length;
+    return 0;
+}
+
+// Given a file path, look for the corresponding
+// block device in /proc/mounts and open it.
+static int open_block_device_for_path(const std::string &path)
+{
+    std::string mountsfile("/proc/mounts");
+    std::string mounts;
+    if (read_file_as_string_atomically(mountsfile, mounts) < 0) {
+        return -1;
+    }
+    std::string block_device;
+    if (find_block_device_for_path(mounts, path, block_device) < 0) {
+        return -1;
+    }
+    SLOGD("For path %s block device is %s", path.c_str(), block_device.c_str());
+    int res = open(block_device.c_str(), O_RDWR | O_LARGEFILE | O_CLOEXEC);
+    if (res < 0) {
+        SLOGE("Failed to open device %s: %s", block_device.c_str(), strerror(errno));
+        return -1;
+    }
+    return res;
+}
+
+// Read a file into a buffer in a single gulp, for atomicity.
+// Null-terminate the buffer.
+// Retry until the buffer is big enough.
+static int read_file_as_string_atomically(const std::string &path, std::string &contents)
+{
+    ssize_t buffer_size = INIT_BUFFER_SIZE;
+    while (true) {
+        int fd = open(path.c_str(), O_RDONLY | O_CLOEXEC);
+        if (fd < 0) {
+            SLOGE("Failed to open %s: %s", path.c_str(), strerror(errno));
+            return -1;
+        }
+        contents.resize(buffer_size);
+        ssize_t read_size = read(fd, &contents[0], buffer_size);
+        if (read_size < 0) {
+            SLOGE("Failed to read from %s: %s", path.c_str(), strerror(errno));
+            close(fd);
+            return -1;
+        }
+        close(fd);
+        if (read_size < buffer_size) {
+            contents.resize(read_size);
+            return 0;
+        }
+        SLOGD("%s too big for buffer of size %zu", path.c_str(), buffer_size);
+        buffer_size <<= 1;
+    }
+}
+
+// Search a string representing the contents of /proc/mounts
+// for the mount point of a particular file by prefix matching
+// and return the corresponding block device.
+static int find_block_device_for_path(
+    const std::string &mounts,
+    const std::string &path,
+    std::string &block_device)
+{
+    auto line_begin = mounts.begin();
+    size_t best_prefix = 0;
+    std::string::const_iterator line_end;
+    while (line_begin != mounts.end()) {
+        line_end = std::find(line_begin, mounts.end(), '\n');
+        if (line_end == mounts.end()) {
+            break;
+        }
+        auto device_end = std::find(line_begin, line_end, ' ');
+        if (device_end == line_end) {
+            break;
+        }
+        auto mountpoint_begin = device_end + 1;
+        auto mountpoint_end = std::find(mountpoint_begin, line_end, ' ');
+        if (mountpoint_end == line_end) {
+            break;
+        }
+        if (std::find(line_begin, mountpoint_end, '\\') != mountpoint_end) {
+            // We don't correctly handle escape sequences, and we don't expect
+            // to encounter any, so fail if we do.
+            break;
+        }
+        size_t mountpoint_len = mountpoint_end - mountpoint_begin;
+        if (mountpoint_len > best_prefix &&
+                mountpoint_len < path.length() &&
+                path[mountpoint_len] == '/' &&
+                std::equal(mountpoint_begin, mountpoint_end, path.begin())) {
+            block_device = std::string(line_begin, device_end);
+            best_prefix = mountpoint_len;
+        }
+        line_begin = line_end + 1;
+    }
+    // All of the "break"s above are fatal parse errors.
+    if (line_begin != mounts.end()) {
+        auto bad_line = std::string(line_begin, line_end);
+        SLOGE("Unable to parse line in %s: %s", path.c_str(), bad_line.c_str());
+        return -1;
+    }
+    if (best_prefix == 0) {
+        SLOGE("No prefix found for path: %s", path.c_str());
+        return -1;
+    }
+    return 0;
+}
