summaryrefslogtreecommitdiffstats
path: root/crypto
diff options
context:
space:
mode:
Diffstat (limited to 'crypto')
-rw-r--r--crypto/cryptfs/Android.mk54
-rw-r--r--crypto/cryptfs/cryptfs.c74
-rw-r--r--crypto/cryptsettings/Android.mk17
-rw-r--r--crypto/cryptsettings/cryptsettings.c55
-rw-r--r--crypto/crypttools/Android.mk15
-rw-r--r--crypto/crypttools/getfooter.c219
-rw-r--r--crypto/fs_mgr/Android.mk38
-rw-r--r--crypto/fs_mgr/fs_mgr.c948
-rw-r--r--crypto/fs_mgr/fs_mgr_main.c114
-rw-r--r--crypto/fs_mgr/fs_mgr_priv.h85
-rw-r--r--crypto/fs_mgr/fs_mgr_priv_verity.h17
-rw-r--r--crypto/fs_mgr/fs_mgr_verity.c410
-rw-r--r--crypto/fs_mgr/include/fs_mgr.h72
-rw-r--r--crypto/ics/Android.mk25
-rw-r--r--crypto/ics/cryptfs.c729
-rw-r--r--crypto/ics/cryptfs.h86
-rw-r--r--crypto/jb/Android.mk17
-rw-r--r--crypto/jb/cryptfs.c1735
-rw-r--r--crypto/jb/cryptfs.h157
-rw-r--r--crypto/libcrypt_samsung/Android.mk11
-rw-r--r--crypto/libcrypt_samsung/include/libcrypt_samsung.h144
-rw-r--r--crypto/libcrypt_samsung/libcrypt_samsung.c65
-rw-r--r--crypto/logwrapper/Android.mk34
-rw-r--r--crypto/logwrapper/NOTICE190
-rw-r--r--crypto/logwrapper/include/logwrap/logwrap.h87
-rw-r--r--crypto/logwrapper/logwrap.c569
-rw-r--r--crypto/logwrapper/logwrapper.c96
-rw-r--r--crypto/lollipop/Android.mk26
-rw-r--r--crypto/lollipop/cryptfs.c2215
-rw-r--r--crypto/lollipop/cryptfs.h17
-rw-r--r--crypto/scrypt/Android.mk3
-rw-r--r--crypto/scrypt/Scrypt-config.mk4
-rw-r--r--crypto/scrypt/tests/Android.mk4
-rw-r--r--crypto/scrypt/tests/scrypt_test.cpp2
34 files changed, 53 insertions, 8281 deletions
diff --git a/crypto/cryptfs/Android.mk b/crypto/cryptfs/Android.mk
deleted file mode 100644
index f0388c228..000000000
--- a/crypto/cryptfs/Android.mk
+++ /dev/null
@@ -1,54 +0,0 @@
-LOCAL_PATH:= $(call my-dir)
-include $(CLEAR_VARS)
-ifeq ($(TW_INCLUDE_CRYPTO), true)
-LOCAL_SRC_FILES:= \
- cryptfs.c
-
-LOCAL_CFLAGS:= -g -c -W -I../fs_mgr/include
-LOCAL_CFLAGS += -DTW_INCLUDE_CRYPTO
-LOCAL_CFLAGS += -DCRYPTO_FS_TYPE=\"$(TW_CRYPTO_FS_TYPE)\"
-LOCAL_CFLAGS += -DCRYPTO_REAL_BLKDEV=\"$(TW_CRYPTO_REAL_BLKDEV)\"
-LOCAL_CFLAGS += -DCRYPTO_MNT_POINT=\"$(TW_CRYPTO_MNT_POINT)\"
-LOCAL_CFLAGS += -DCRYPTO_FS_OPTIONS=\"$(TW_CRYPTO_FS_OPTIONS)\"
-LOCAL_CFLAGS += -DCRYPTO_FS_FLAGS=\"$(TW_CRYPTO_FS_FLAGS)\"
-LOCAL_CFLAGS += -DCRYPTO_KEY_LOC=\"$(TW_CRYPTO_KEY_LOC)\"
-ifdef TW_CRYPTO_SD_REAL_BLKDEV
- LOCAL_CFLAGS += -DCRYPTO_SD_REAL_BLKDEV=\"$(TW_CRYPTO_SD_REAL_BLKDEV)\"
- LOCAL_CFLAGS += -DCRYPTO_SD_FS_TYPE=\"$(TW_CRYPTO_SD_FS_TYPE)\"
-endif
-ifneq ($(TW_INTERNAL_STORAGE_PATH),)
- LOCAL_CFLAGS += -DTW_INTERNAL_STORAGE_PATH=$(TW_INTERNAL_STORAGE_PATH)
-endif
-ifneq ($(TW_INTERNAL_STORAGE_MOUNT_POINT),)
- LOCAL_CFLAGS += -DTW_INTERNAL_STORAGE_MOUNT_POINT=$(TW_INTERNAL_STORAGE_MOUNT_POINT)
-endif
-ifneq ($(TW_EXTERNAL_STORAGE_PATH),)
- LOCAL_CFLAGS += -DTW_EXTERNAL_STORAGE_PATH=$(TW_EXTERNAL_STORAGE_PATH)
-endif
-ifneq ($(TW_EXTERNAL_STORAGE_MOUNT_POINT),)
- LOCAL_CFLAGS += -DTW_EXTERNAL_STORAGE_MOUNT_POINT=$(TW_EXTERNAL_STORAGE_MOUNT_POINT)
-endif
-
-LOCAL_C_INCLUDES += system/extras/ext4_utils external/openssl/include
-LOCAL_MODULE:=cryptfs
-LOCAL_MODULE_TAGS:= eng
-LOCAL_SHARED_LIBRARIES += libc libcutils
-LOCAL_SHARED_LIBRARIES += libcrypto
-
-
-#LOCAL_LDFLAGS += -L$(TARGET_OUT_SHARED_LIBRARIES) -lsec_km -lsec_ecryptfs -ldl
-LOCAL_LDFLAGS += -ldl
-
-LOCAL_STATIC_LIBRARIES += libmtdutils
-LOCAL_STATIC_LIBRARIES += libminzip libunz
-LOCAL_STATIC_LIBRARIES += libpixelflinger_static libpng libmincrypttwrp
-LOCAL_SHARED_LIBRARIES += libz libc libstlport libcutils libstdc++ libext4_utils
-LOCAL_STATIC_LIBRARIES += libcrypt_samsung
-
-
-LOCAL_STATIC_LIBRARIES += $(TARGET_RECOVERY_UI_LIB)
-#LOCAL_STATIC_LIBRARIES += libfs_mgrtwrp
-LOCAL_MODULE_CLASS := UTILITY_EXECUTABLES
-LOCAL_MODULE_PATH := $(PRODUCT_OUT)/utilities
-include $(BUILD_EXECUTABLE)
-endif
diff --git a/crypto/cryptfs/cryptfs.c b/crypto/cryptfs/cryptfs.c
deleted file mode 100644
index 59e7added..000000000
--- a/crypto/cryptfs/cryptfs.c
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright (c) 2013 a3955269 all rights reversed, no rights reserved.
- */
-
-#define TW_INCLUDE_CRYPTO_SAMSUNG
-#include "../ics/cryptfs.c"
-
-int dm_remove_device(const char *name)
-{
- int r;
- r = delete_crypto_blk_dev(name);
- if(!r)
- printf("crypto block device '%s' deleted.\n", name);
- else
- printf("deleting crypto block device '%s' failed. [%d - %s]\n", name, r, strerror(errno));
- return r;
-}
-
-int ecryptfs_test(const char *pw)
-{
- char pwbuf[256];
- int r;
-
- strcpy(pwbuf, pw);
- // 0: building options without file encryption filtering.
- // 1: building options with media files filtering.
- // 2: building options with all new files filtering.
- r = mount_ecryptfs_drive(pwbuf, "/emmc", "/emmc", 0);
- printf("mount_ecryptfs_drive: %d\n", r);
- r = mount("/dev/block/mmcblk1", "/emmc", "vfat", MS_RDONLY, "");
- printf("mount: %d\n", r);
-
- r = umount("/emmc");///dev/block/mmcblk1");
- printf("umount: %d\n", r);
-
- //r = unmount_ecryptfs_drive("/emmc");
- //printf("unmount_ecryptfs_drive: %d\n", r);
-
- return r;
-}
-
-int main(int argc, char* argv[])
-{
- if(argc < 2)
- {
- printf("no args!\n");
- return 1;
- }
-
- property_set("ro.crypto.state", "encrypted");
-
- property_set("ro.crypto.fs_type", CRYPTO_FS_TYPE);
- property_set("ro.crypto.fs_real_blkdev", CRYPTO_REAL_BLKDEV);
- property_set("ro.crypto.fs_mnt_point", CRYPTO_MNT_POINT);
- property_set("ro.crypto.fs_options", CRYPTO_FS_OPTIONS);
- property_set("ro.crypto.fs_flags", CRYPTO_FS_FLAGS);
- property_set("ro.crypto.keyfile.userdata", CRYPTO_KEY_LOC);
-
-#ifdef CRYPTO_SD_FS_TYPE
- property_set("ro.crypto.sd_fs_type", CRYPTO_SD_FS_TYPE);
- property_set("ro.crypto.sd_fs_real_blkdev", CRYPTO_SD_REAL_BLKDEV);
- property_set("ro.crypto.sd_fs_mnt_point", EXPAND(TW_INTERNAL_STORAGE_PATH));
-#endif
-
- property_set("rw.km_fips_status", "ready");
-
- delete_crypto_blk_dev("userdata");
- delete_crypto_blk_dev("sdcard");
- delete_crypto_blk_dev("emmc");
-
- cryptfs_check_passwd(argv[1]);
-
- return 0;
-};
diff --git a/crypto/cryptsettings/Android.mk b/crypto/cryptsettings/Android.mk
deleted file mode 100644
index 3a5704891..000000000
--- a/crypto/cryptsettings/Android.mk
+++ /dev/null
@@ -1,17 +0,0 @@
-LOCAL_PATH:= $(call my-dir)
-include $(CLEAR_VARS)
-ifeq ($(TW_INCLUDE_CRYPTO), true)
-LOCAL_SRC_FILES:= \
- cryptsettings.c
-LOCAL_CFLAGS:= -g -c -W
-LOCAL_MODULE:=cryptsettings
-LOCAL_MODULE_TAGS:= eng
-LOCAL_SHARED_LIBRARIES += libc libcutils
-ifeq ($(TW_INCLUDE_JB_CRYPTO), true)
-LOCAL_CFLAGS += -DTW_INCLUDE_JB_CRYPTO
-LOCAL_STATIC_LIBRARIES += libfs_mgrtwrp
-endif
-LOCAL_MODULE_CLASS := UTILITY_EXECUTABLES
-LOCAL_MODULE_PATH := $(PRODUCT_OUT)/utilities
-include $(BUILD_EXECUTABLE)
-endif
diff --git a/crypto/cryptsettings/cryptsettings.c b/crypto/cryptsettings/cryptsettings.c
deleted file mode 100644
index 4fa2b9354..000000000
--- a/crypto/cryptsettings/cryptsettings.c
+++ /dev/null
@@ -1,55 +0,0 @@
-#include <sys/types.h>
-#include <unistd.h>
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-#ifdef TW_INCLUDE_JB_CRYPTO
-#include "../crypto/fs_mgr/include/fs_mgr.h"
-#endif
-
-#include "cutils/properties.h"
-
-#ifndef PROPERTY_VALUE_MAX
-#define PROPERTY_VALUE_MAX 255
-#endif
-#ifndef FSTAB_PREFIX
-#define FSTAB_PREFIX "/fstab."
-#endif
-
-int main(void)
-{
- char prop[PROPERTY_VALUE_MAX];
- char key_loc[PROPERTY_VALUE_MAX];
- char blk_dev[PROPERTY_VALUE_MAX];
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
-
- printf("This tool will gather the build flags needed for decryption support for TWRP.\n");
- printf("This tool comes with no warranties whatsoever.\n");
- printf("http://teamw.in\n\n");
- property_get("ro.crypto.state", prop, "encrypted");
- if (strcmp(prop, "encrypted") != 0)
- printf("Your device is not encrypted, continuing anyway.\n\nTW_INCLUDE_CRYPTO := true\n");
- property_get("ro.crypto.fs_type", prop, "ERROR");
- printf("TW_CRYPTO_FS_TYPE := \"%s\"\n", prop);
- property_get("ro.crypto.fs_real_blkdev", prop, "ERROR");
- printf("TW_CRYPTO_REAL_BLKDEV := \"%s\"\n", prop);
- property_get("ro.crypto.fs_mnt_point", prop, "ERROR");
- printf("TW_CRYPTO_MNT_POINT := \"%s\"\n", prop);
- property_get("ro.crypto.fs_options", prop, "ERROR");
- printf("TW_CRYPTO_FS_OPTIONS := \"%s\"\n", prop);
- property_get("ro.crypto.fs_flags", prop, "ERROR");
- printf("TW_CRYPTO_FS_FLAGS := \"%s\"\n", prop);
- property_get("ro.crypto.keyfile.userdata", prop, "footer");
- printf("TW_CRYPTO_KEY_LOC := \"%s\"\n", prop);
-#ifdef TW_INCLUDE_JB_CRYPTO
- printf("\n*** NEW FOR JELLY BEAN:\n");
- strcpy(fstab_filename, FSTAB_PREFIX);
- property_get("ro.hardware", fstab_filename + sizeof(FSTAB_PREFIX) - 1, "");
- fs_mgr_get_crypt_info(fstab_filename, key_loc, blk_dev, sizeof(key_loc));
- printf("fstab file location: '%s'\n\nTW_INCLUDE_JB_CRYPTO := true\n", fstab_filename);
-#endif
-
- return 0;
-}
diff --git a/crypto/crypttools/Android.mk b/crypto/crypttools/Android.mk
deleted file mode 100644
index fc62583c4..000000000
--- a/crypto/crypttools/Android.mk
+++ /dev/null
@@ -1,15 +0,0 @@
-LOCAL_PATH:= $(call my-dir)
-include $(CLEAR_VARS)
-ifeq ($(TW_INCLUDE_JB_CRYPTO), true)
-LOCAL_SRC_FILES:= \
- getfooter.c
-LOCAL_CFLAGS:= -g -c -W
-LOCAL_MODULE:=getfooter
-LOCAL_MODULE_TAGS:= eng
-LOCAL_STATIC_LIBRARIES += libfs_mgrtwrp libc libcutils
-LOCAL_MODULE_CLASS := UTILITY_EXECUTABLES
-LOCAL_MODULE_PATH := $(PRODUCT_OUT)/utilities
-LOCAL_FORCE_STATIC_EXECUTABLE := true
-LOCAL_C_INCLUDES := $(commands_recovery_local_path)/crypto/jb/
-include $(BUILD_EXECUTABLE)
-endif \ No newline at end of file
diff --git a/crypto/crypttools/getfooter.c b/crypto/crypttools/getfooter.c
deleted file mode 100644
index aa7f88e84..000000000
--- a/crypto/crypttools/getfooter.c
+++ /dev/null
@@ -1,219 +0,0 @@
-#include <sys/types.h>
-#include <unistd.h>
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-#include <sys/ioctl.h>
-#include <linux/dm-ioctl.h>
-#include <sys/mount.h>
-#include "../fs_mgr/include/fs_mgr.h"
-#include "cryptfs.h"
-
-#include "cutils/properties.h"
-
-#ifndef PROPERTY_VALUE_MAX
-#define PROPERTY_VALUE_MAX 255
-#endif
-#ifndef FSTAB_PREFIX
-#define FSTAB_PREFIX "/fstab."
-#endif
-#ifndef KEY_IN_FOOTER
-#define KEY_IN_FOOTER "footer"
-#endif
-
-struct fstab *fstab;
-
-static unsigned int get_blkdev_size(int fd)
-{
- unsigned int nr_sec;
-
- if ( (ioctl(fd, BLKGETSIZE, &nr_sec)) == -1) {
- nr_sec = 0;
- }
-
- return nr_sec;
-}
-
-int get_crypt_ftr_info(char **metadata_fname, off64_t *off)
-{
- static int cached_data = 0;
- static off64_t cached_off = 0;
- static char cached_metadata_fname[PROPERTY_VALUE_MAX] = "";
- int fd;
- char key_loc[PROPERTY_VALUE_MAX];
- char real_blkdev[PROPERTY_VALUE_MAX];
- unsigned int nr_sec;
- int rc = -1;
-
- fs_mgr_get_crypt_info(fstab, key_loc, real_blkdev, sizeof(key_loc));
-
- if (!strcmp(key_loc, KEY_IN_FOOTER)) {
- if ( (fd = open(real_blkdev, O_RDWR)) < 0) {
- printf("Cannot open real block device %s\n", real_blkdev);
- return -1;
- }
-
- if ((nr_sec = get_blkdev_size(fd))) {
- /* If it's an encrypted Android partition, the last 16 Kbytes contain the
- * encryption info footer and key, and plenty of bytes to spare for future
- * growth.
- */
- strlcpy(cached_metadata_fname, real_blkdev, sizeof(cached_metadata_fname));
- cached_off = ((off64_t)nr_sec * 512) - CRYPT_FOOTER_OFFSET;
- cached_data = 1;
- } else {
- printf("Cannot get size of block device %s\n", real_blkdev);
- }
- close(fd);
- } else {
- strlcpy(cached_metadata_fname, key_loc, sizeof(cached_metadata_fname));
- cached_off = 0;
- cached_data = 1;
- }
-
- if (cached_data) {
- if (metadata_fname) {
- *metadata_fname = cached_metadata_fname;
- }
- if (off) {
- *off = cached_off;
- }
- rc = 0;
- }
-
- return rc;
-}
-
-int get_crypt_ftr_and_key(struct crypt_mnt_ftr *crypt_ftr)
-{
- int fd;
- unsigned int nr_sec, cnt;
- off64_t starting_off;
- int rc = -1;
- char *fname = NULL;
- struct stat statbuf;
-
- if (get_crypt_ftr_info(&fname, &starting_off)) {
- printf("Unable to get crypt_ftr_info\n");
- return -1;
- }
- if (fname[0] != '/') {
- printf("Unexpected value for crypto key location '%s'\n", fname);
- //return -1;
- }
- if ( (fd = open(fname, O_RDWR)) < 0) {
- printf("Cannot open footer file %s for get\n", fname);
- return -1;
- }
-
- /* Make sure it's 16 Kbytes in length */
- fstat(fd, &statbuf);
- if (S_ISREG(statbuf.st_mode) && (statbuf.st_size != 0x4000)) {
- printf("footer file %s is not the expected size!\n", fname);
- close(fd);
- return -1;
- }
-
- /* Seek to the start of the crypt footer */
- if (lseek64(fd, starting_off, SEEK_SET) == -1) {
- printf("Cannot seek to real block device footer\n");
- close(fd);
- return -1;
- }
-
- if ( (cnt = read(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr))) != sizeof(struct crypt_mnt_ftr)) {
- printf("Cannot read real block device footer\n");
- close(fd);
- return -1;
- }
- close(fd);
- return 0;
-}
-
-int main(void)
-{
- char key_loc[PROPERTY_VALUE_MAX];
- char blk_dev[PROPERTY_VALUE_MAX];
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
- struct stat st;
- struct crypt_mnt_ftr crypt_ftr;
- int fdout;
-
- printf("This tool comes with no warranties whatsoever.\n");
- printf("http://teamw.in\n\n");
- strcpy(fstab_filename, FSTAB_PREFIX);
- property_get("ro.hardware", fstab_filename + sizeof(FSTAB_PREFIX) - 1, "");
-
- if (stat(fstab_filename, &st) != 0) {
- printf("Cannot locate fstab file '%s'\n", fstab_filename);
- return -1;
- }
-
- fstab = fs_mgr_read_fstab(fstab_filename);
- if (!fstab) {
- printf("failed to open %s\n", fstab_filename);
- return -1;
- }
-
- fs_mgr_get_crypt_info(fstab, key_loc, blk_dev, sizeof(blk_dev));
-
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Error getting crypt footer and key\n");
- return -1;
- }
-
- if ( (fdout = open("/footerfile", O_WRONLY | O_CREAT, 0644)) < 0) {
- printf("Cannot open output file /footerfile\n");
- return -1;
- }
- if (write(fdout, (void*) &crypt_ftr, sizeof(struct crypt_mnt_ftr)) != sizeof(struct crypt_mnt_ftr)) {
- printf("Failed to write footer.\n");
- }
- close(fdout);
-
- if (!strcmp(key_loc, KEY_IN_FOOTER)) {
- unsigned int nr_sec, cnt;
- off64_t off = 0;
- char buffer[CRYPT_FOOTER_OFFSET];
- int fd;
-
- printf("\n\nDumping footer from '%s'...\n", blk_dev);
- if ( (fd = open(blk_dev, O_RDONLY)) < 0) {
- printf("Cannot open real block device %s\n", blk_dev);
- return -1;
- }
-
- if ((nr_sec = get_blkdev_size(fd))) {
- off = ((off64_t)nr_sec * 512) - CRYPT_FOOTER_OFFSET;
- } else {
- printf("Cannot get size of block device %s\n", blk_dev);
- close(fd);
- return -1;
- }
- printf("Size is %llu, offset is %llu\n", ((off64_t)nr_sec * 512), off);
- if (lseek64(fd, off, SEEK_SET) == -1) {
- printf("Cannot seek to real block device footer\n");
- close(fd);
- return -1;
- }
-
- if ( (cnt = read(fd, buffer, sizeof(buffer))) != sizeof(buffer)) {
- printf("Cannot read real block device footer\n");
- close(fd);
- return -1;
- }
- close(fd);
- if ( (fdout = open("/footerdump", O_WRONLY | O_CREAT, 0644)) < 0) {
- printf("Cannot open output file /footerdump\n");
- return -1;
- }
- if (write(fdout, buffer, sizeof(buffer)) != sizeof(buffer)) {
- printf("Failed to write footer.\n");
- }
- close(fdout);
- }
-
- return 0;
-}
diff --git a/crypto/fs_mgr/Android.mk b/crypto/fs_mgr/Android.mk
deleted file mode 100644
index 8dd9d4ca2..000000000
--- a/crypto/fs_mgr/Android.mk
+++ /dev/null
@@ -1,38 +0,0 @@
-# Copyright 2011 The Android Open Source Project
-ifeq ($(TW_INCLUDE_JB_CRYPTO), true)
-LOCAL_PATH:= $(call my-dir)
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES:= fs_mgr.c fs_mgr_verity.c
-
-LOCAL_C_INCLUDES := $(LOCAL_PATH)/include
-
-LOCAL_MODULE:= libfs_mgrtwrp
-LOCAL_SHARED_LIBRARIES := libext4_utils
-LOCAL_STATIC_LIBRARIES := liblogwraptwrp libmincrypttwrp
-LOCAL_C_INCLUDES += \
- system/extras/ext4_utils \
- $(commands_recovery_local_path)/libmincrypt/includes
-LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/include
-
-include $(BUILD_STATIC_LIBRARY)
-
-
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES:= fs_mgr_main.c
-
-LOCAL_C_INCLUDES := $(LOCAL_PATH)/include
-
-LOCAL_MODULE:= fs_mgrtwrp
-
-LOCAL_MODULE_TAGS := optional
-LOCAL_FORCE_STATIC_EXECUTABLE := true
-LOCAL_MODULE_PATH := $(TARGET_ROOT_OUT)/sbin
-LOCAL_UNSTRIPPED_PATH := $(TARGET_ROOT_OUT_UNSTRIPPED)
-
-LOCAL_STATIC_LIBRARIES := libfs_mgrtwrp liblogwraptwrp libcutils liblog libc libmincrypttwrp libext4_utils_static
-
-include $(BUILD_EXECUTABLE)
-
-endif
diff --git a/crypto/fs_mgr/fs_mgr.c b/crypto/fs_mgr/fs_mgr.c
deleted file mode 100644
index 3aa9e6039..000000000
--- a/crypto/fs_mgr/fs_mgr.c
+++ /dev/null
@@ -1,948 +0,0 @@
-/*
- * Copyright (C) 2012 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 <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <ctype.h>
-#include <sys/mount.h>
-#include <sys/stat.h>
-#include <errno.h>
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <libgen.h>
-#include <time.h>
-//#include <sys/swap.h>
-/* XXX These need to be obtained from kernel headers. See b/9336527 */
-#define SWAP_FLAG_PREFER 0x8000
-#define SWAP_FLAG_PRIO_MASK 0x7fff
-#define SWAP_FLAG_PRIO_SHIFT 0
-#define SWAP_FLAG_DISCARD 0x10000
-
-#include <linux/loop.h>
-#include <private/android_filesystem_config.h>
-#include <cutils/partition_utils.h>
-#include <cutils/properties.h>
-#include <logwrap/logwrap.h>
-
-#include "mincrypt/rsa.h"
-#include "mincrypt/sha.h"
-#include "mincrypt/sha256.h"
-
-#include "fs_mgr_priv.h"
-#include "fs_mgr_priv_verity.h"
-
-#define KEY_LOC_PROP "ro.crypto.keyfile.userdata"
-#define KEY_IN_FOOTER "footer"
-
-#define E2FSCK_BIN "/system/bin/e2fsck"
-#define MKSWAP_BIN "/system/bin/mkswap"
-
-#define FSCK_LOG_FILE "/dev/fscklogs/log"
-
-#define ZRAM_CONF_DEV "/sys/block/zram0/disksize"
-
-#define ARRAY_SIZE(a) (sizeof(a) / sizeof(*(a)))
-
-struct flag_list {
- const char *name;
- unsigned flag;
-};
-
-static struct flag_list mount_flags[] = {
- { "noatime", MS_NOATIME },
- { "noexec", MS_NOEXEC },
- { "nosuid", MS_NOSUID },
- { "nodev", MS_NODEV },
- { "nodiratime", MS_NODIRATIME },
- { "ro", MS_RDONLY },
- { "rw", 0 },
- { "remount", MS_REMOUNT },
- { "bind", MS_BIND },
- { "rec", MS_REC },
- { "unbindable", MS_UNBINDABLE },
- { "private", MS_PRIVATE },
- { "slave", MS_SLAVE },
- { "shared", MS_SHARED },
- { "defaults", 0 },
- { 0, 0 },
-};
-
-static struct flag_list fs_mgr_flags[] = {
- { "wait", MF_WAIT },
- { "check", MF_CHECK },
- { "encryptable=",MF_CRYPT },
- { "nonremovable",MF_NONREMOVABLE },
- { "voldmanaged=",MF_VOLDMANAGED},
- { "length=", MF_LENGTH },
- { "recoveryonly",MF_RECOVERYONLY },
- { "swapprio=", MF_SWAPPRIO },
- { "zramsize=", MF_ZRAMSIZE },
- { "verify", MF_VERIFY },
- { "noemulatedsd", MF_NOEMULATEDSD },
- { "defaults", 0 },
- { 0, 0 },
-};
-
-struct fs_mgr_flag_values {
- char *key_loc;
- long long part_length;
- char *label;
- int partnum;
- int swap_prio;
- unsigned int zram_size;
-};
-
-/*
- * gettime() - returns the time in seconds of the system's monotonic clock or
- * zero on error.
- */
-static time_t gettime(void)
-{
- struct timespec ts;
- int ret;
-
- ret = clock_gettime(CLOCK_MONOTONIC, &ts);
- if (ret < 0) {
- ERROR("clock_gettime(CLOCK_MONOTONIC) failed: %s\n", strerror(errno));
- return 0;
- }
-
- return ts.tv_sec;
-}
-
-static int wait_for_file(const char *filename, int timeout)
-{
- struct stat info;
- time_t timeout_time = gettime() + timeout;
- int ret = -1;
-
- while (gettime() < timeout_time && ((ret = stat(filename, &info)) < 0))
- usleep(10000);
-
- return ret;
-}
-
-static int parse_flags(char *flags, struct flag_list *fl,
- struct fs_mgr_flag_values *flag_vals,
- char *fs_options, int fs_options_len)
-{
- int f = 0;
- int i;
- char *p;
- char *savep;
-
- /* initialize flag values. If we find a relevant flag, we'll
- * update the value */
- if (flag_vals) {
- memset(flag_vals, 0, sizeof(*flag_vals));
- flag_vals->partnum = -1;
- flag_vals->swap_prio = -1; /* negative means it wasn't specified. */
- }
-
- /* initialize fs_options to the null string */
- if (fs_options && (fs_options_len > 0)) {
- fs_options[0] = '\0';
- }
-
- p = strtok_r(flags, ",", &savep);
- while (p) {
- /* Look for the flag "p" in the flag list "fl"
- * If not found, the loop exits with fl[i].name being null.
- */
- for (i = 0; fl[i].name; i++) {
- if (!strncmp(p, fl[i].name, strlen(fl[i].name))) {
- f |= fl[i].flag;
- if ((fl[i].flag == MF_CRYPT) && flag_vals) {
- /* The encryptable flag is followed by an = and the
- * location of the keys. Get it and return it.
- */
- flag_vals->key_loc = strdup(strchr(p, '=') + 1);
- } else if ((fl[i].flag == MF_LENGTH) && flag_vals) {
- /* The length flag is followed by an = and the
- * size of the partition. Get it and return it.
- */
- flag_vals->part_length = strtoll(strchr(p, '=') + 1, NULL, 0);
- } else if ((fl[i].flag == MF_VOLDMANAGED) && flag_vals) {
- /* The voldmanaged flag is followed by an = and the
- * label, a colon and the partition number or the
- * word "auto", e.g.
- * voldmanaged=sdcard:3
- * Get and return them.
- */
- char *label_start;
- char *label_end;
- char *part_start;
-
- label_start = strchr(p, '=') + 1;
- label_end = strchr(p, ':');
- if (label_end) {
- flag_vals->label = strndup(label_start,
- (int) (label_end - label_start));
- part_start = strchr(p, ':') + 1;
- if (!strcmp(part_start, "auto")) {
- flag_vals->partnum = -1;
- } else {
- flag_vals->partnum = strtol(part_start, NULL, 0);
- }
- } else {
- ERROR("Warning: voldmanaged= flag malformed\n");
- }
- } else if ((fl[i].flag == MF_SWAPPRIO) && flag_vals) {
- flag_vals->swap_prio = strtoll(strchr(p, '=') + 1, NULL, 0);
- } else if ((fl[i].flag == MF_ZRAMSIZE) && flag_vals) {
- flag_vals->zram_size = strtoll(strchr(p, '=') + 1, NULL, 0);
- }
- break;
- }
- }
-
- if (!fl[i].name) {
- if (fs_options) {
- /* It's not a known flag, so it must be a filesystem specific
- * option. Add it to fs_options if it was passed in.
- */
- strlcat(fs_options, p, fs_options_len);
- strlcat(fs_options, ",", fs_options_len);
- } else {
- /* fs_options was not passed in, so if the flag is unknown
- * it's an error.
- */
- ERROR("Warning: unknown flag %s\n", p);
- }
- }
- p = strtok_r(NULL, ",", &savep);
- }
-
-out:
- if (fs_options && fs_options[0]) {
- /* remove the last trailing comma from the list of options */
- fs_options[strlen(fs_options) - 1] = '\0';
- }
-
- return f;
-}
-
-/* Read a line of text till the next newline character.
- * If no newline is found before the buffer is full, continue reading till a new line is seen,
- * then return an empty buffer. This effectively ignores lines that are too long.
- * On EOF, return null.
- */
-static char *fs_getline(char *buf, int size, FILE *file)
-{
- int cnt = 0;
- int eof = 0;
- int eol = 0;
- int c;
-
- if (size < 1) {
- return NULL;
- }
-
- while (cnt < (size - 1)) {
- c = getc(file);
- if (c == EOF) {
- eof = 1;
- break;
- }
-
- *(buf + cnt) = c;
- cnt++;
-
- if (c == '\n') {
- eol = 1;
- break;
- }
- }
-
- /* Null terminate what we've read */
- *(buf + cnt) = '\0';
-
- if (eof) {
- if (cnt) {
- return buf;
- } else {
- return NULL;
- }
- } else if (eol) {
- return buf;
- } else {
- /* The line is too long. Read till a newline or EOF.
- * If EOF, return null, if newline, return an empty buffer.
- */
- while(1) {
- c = getc(file);
- if (c == EOF) {
- return NULL;
- } else if (c == '\n') {
- *buf = '\0';
- return buf;
- }
- }
- }
-}
-
-struct fstab *fs_mgr_read_fstab(const char *fstab_path)
-{
- FILE *fstab_file;
- int cnt, entries;
- int len;
- char line[256];
- const char *delim = " \t";
- char *save_ptr, *p;
- struct fstab *fstab;
- struct fstab_rec *recs;
- struct fs_mgr_flag_values flag_vals;
-#define FS_OPTIONS_LEN 1024
- char tmp_fs_options[FS_OPTIONS_LEN];
-
- fstab_file = fopen(fstab_path, "r");
- if (!fstab_file) {
- ERROR("Cannot open file %s\n", fstab_path);
- return 0;
- }
-
- entries = 0;
- while (fs_getline(line, sizeof(line), fstab_file)) {
- /* if the last character is a newline, shorten the string by 1 byte */
- len = strlen(line);
- if (line[len - 1] == '\n') {
- line[len - 1] = '\0';
- }
- /* Skip any leading whitespace */
- p = line;
- while (isspace(*p)) {
- p++;
- }
- /* ignore comments or empty lines */
- if (*p == '#' || *p == '\0')
- continue;
- entries++;
- }
-
- if (!entries) {
- ERROR("No entries found in fstab\n");
- return 0;
- }
-
- /* Allocate and init the fstab structure */
- fstab = calloc(1, sizeof(struct fstab));
- fstab->num_entries = entries;
- fstab->fstab_filename = strdup(fstab_path);
- fstab->recs = calloc(fstab->num_entries, sizeof(struct fstab_rec));
-
- fseek(fstab_file, 0, SEEK_SET);
-
- cnt = 0;
- while (fs_getline(line, sizeof(line), fstab_file)) {
- /* if the last character is a newline, shorten the string by 1 byte */
- len = strlen(line);
- if (line[len - 1] == '\n') {
- line[len - 1] = '\0';
- }
-
- /* Skip any leading whitespace */
- p = line;
- while (isspace(*p)) {
- p++;
- }
- /* ignore comments or empty lines */
- if (*p == '#' || *p == '\0')
- continue;
-
- /* If a non-comment entry is greater than the size we allocated, give an
- * error and quit. This can happen in the unlikely case the file changes
- * between the two reads.
- */
- if (cnt >= entries) {
- ERROR("Tried to process more entries than counted\n");
- break;
- }
-
- if (!(p = strtok_r(line, delim, &save_ptr))) {
- ERROR("Error parsing mount source\n");
- return 0;
- }
- fstab->recs[cnt].blk_device = strdup(p);
-
- if (!(p = strtok_r(NULL, delim, &save_ptr))) {
- ERROR("Error parsing mount_point\n");
- return 0;
- }
- fstab->recs[cnt].mount_point = strdup(p);
-
- if (!(p = strtok_r(NULL, delim, &save_ptr))) {
- ERROR("Error parsing fs_type\n");
- return 0;
- }
- fstab->recs[cnt].fs_type = strdup(p);
-
- if (!(p = strtok_r(NULL, delim, &save_ptr))) {
- ERROR("Error parsing mount_flags\n");
- return 0;
- }
- tmp_fs_options[0] = '\0';
- fstab->recs[cnt].flags = parse_flags(p, mount_flags, NULL,
- tmp_fs_options, FS_OPTIONS_LEN);
-
- /* fs_options are optional */
- if (tmp_fs_options[0]) {
- fstab->recs[cnt].fs_options = strdup(tmp_fs_options);
- } else {
- fstab->recs[cnt].fs_options = NULL;
- }
-
- if (!(p = strtok_r(NULL, delim, &save_ptr))) {
- ERROR("Error parsing fs_mgr_options\n");
- return 0;
- }
- fstab->recs[cnt].fs_mgr_flags = parse_flags(p, fs_mgr_flags,
- &flag_vals, NULL, 0);
- fstab->recs[cnt].key_loc = flag_vals.key_loc;
- fstab->recs[cnt].length = flag_vals.part_length;
- fstab->recs[cnt].label = flag_vals.label;
- fstab->recs[cnt].partnum = flag_vals.partnum;
- fstab->recs[cnt].swap_prio = flag_vals.swap_prio;
- fstab->recs[cnt].zram_size = flag_vals.zram_size;
- cnt++;
- }
- fclose(fstab_file);
-
- return fstab;
-}
-
-void fs_mgr_free_fstab(struct fstab *fstab)
-{
- int i;
-
- if (!fstab) {
- return;
- }
-
- for (i = 0; i < fstab->num_entries; i++) {
- /* Free the pointers return by strdup(3) */
- free(fstab->recs[i].blk_device);
- free(fstab->recs[i].mount_point);
- free(fstab->recs[i].fs_type);
- free(fstab->recs[i].fs_options);
- free(fstab->recs[i].key_loc);
- free(fstab->recs[i].label);
- i++;
- }
-
- /* Free the fstab_recs array created by calloc(3) */
- free(fstab->recs);
-
- /* Free the fstab filename */
- free(fstab->fstab_filename);
-
- /* Free fstab */
- free(fstab);
-}
-
-static void check_fs(char *blk_device, char *fs_type, char *target)
-{
- int status;
- int ret;
- long tmpmnt_flags = MS_NOATIME | MS_NOEXEC | MS_NOSUID;
- char *tmpmnt_opts = "nomblk_io_submit,errors=remount-ro";
- char *e2fsck_argv[] = {
- E2FSCK_BIN,
- "-y",
- blk_device
- };
-
- /* Check for the types of filesystems we know how to check */
- if (!strcmp(fs_type, "ext2") || !strcmp(fs_type, "ext3") || !strcmp(fs_type, "ext4")) {
- /*
- * First try to mount and unmount the filesystem. We do this because
- * the kernel is more efficient than e2fsck in running the journal and
- * processing orphaned inodes, and on at least one device with a
- * performance issue in the emmc firmware, it can take e2fsck 2.5 minutes
- * to do what the kernel does in about a second.
- *
- * After mounting and unmounting the filesystem, run e2fsck, and if an
- * error is recorded in the filesystem superblock, e2fsck will do a full
- * check. Otherwise, it does nothing. If the kernel cannot mount the
- * filesytsem due to an error, e2fsck is still run to do a full check
- * fix the filesystem.
- */
- ret = mount(blk_device, target, fs_type, tmpmnt_flags, tmpmnt_opts);
- if (!ret) {
- umount(target);
- }
-
- INFO("Running %s on %s\n", E2FSCK_BIN, blk_device);
-
- ret = android_fork_execvp_ext(ARRAY_SIZE(e2fsck_argv), e2fsck_argv,
- &status, true, LOG_KLOG | LOG_FILE,
- true, FSCK_LOG_FILE);
-
- if (ret < 0) {
- /* No need to check for error in fork, we can't really handle it now */
- ERROR("Failed trying to run %s\n", E2FSCK_BIN);
- }
- }
-
- return;
-}
-
-static void remove_trailing_slashes(char *n)
-{
- int len;
-
- len = strlen(n) - 1;
- while ((*(n + len) == '/') && len) {
- *(n + len) = '\0';
- len--;
- }
-}
-
-/*
- * Mark the given block device as read-only, using the BLKROSET ioctl.
- * Return 0 on success, and -1 on error.
- */
-static void fs_set_blk_ro(const char *blockdev)
-{
- int fd;
- int ON = 1;
-
- fd = open(blockdev, O_RDONLY);
- if (fd < 0) {
- // should never happen
- return;
- }
-
- ioctl(fd, BLKROSET, &ON);
- close(fd);
-}
-
-/*
- * __mount(): wrapper around the mount() system call which also
- * sets the underlying block device to read-only if the mount is read-only.
- * See "man 2 mount" for return values.
- */
-static int __mount(const char *source, const char *target,
- const char *filesystemtype, unsigned long mountflags,
- const void *data)
-{
- int ret = mount(source, target, filesystemtype, mountflags, data);
-
- if ((ret == 0) && (mountflags & MS_RDONLY) != 0) {
- fs_set_blk_ro(source);
- }
-
- return ret;
-}
-
-static int fs_match(char *in1, char *in2)
-{
- char *n1;
- char *n2;
- int ret;
-
- n1 = strdup(in1);
- n2 = strdup(in2);
-
- remove_trailing_slashes(n1);
- remove_trailing_slashes(n2);
-
- ret = !strcmp(n1, n2);
-
- free(n1);
- free(n2);
-
- return ret;
-}
-
-int fs_mgr_mount_all(struct fstab *fstab)
-{
- int i = 0;
- int encrypted = 0;
- int ret = -1;
- int mret;
-
- if (!fstab) {
- return ret;
- }
-
- for (i = 0; i < fstab->num_entries; i++) {
- /* Don't mount entries that are managed by vold */
- if (fstab->recs[i].fs_mgr_flags & (MF_VOLDMANAGED | MF_RECOVERYONLY)) {
- continue;
- }
-
- /* Skip swap and raw partition entries such as boot, recovery, etc */
- if (!strcmp(fstab->recs[i].fs_type, "swap") ||
- !strcmp(fstab->recs[i].fs_type, "emmc") ||
- !strcmp(fstab->recs[i].fs_type, "mtd")) {
- continue;
- }
-
- if (fstab->recs[i].fs_mgr_flags & MF_WAIT) {
- wait_for_file(fstab->recs[i].blk_device, WAIT_TIMEOUT);
- }
-
- if (fstab->recs[i].fs_mgr_flags & MF_CHECK) {
- check_fs(fstab->recs[i].blk_device, fstab->recs[i].fs_type,
- fstab->recs[i].mount_point);
- }
-
- if (fstab->recs[i].fs_mgr_flags & MF_VERIFY) {
- if (fs_mgr_setup_verity(&fstab->recs[i]) < 0) {
- ERROR("Could not set up verified partition, skipping!");
- continue;
- }
- }
-
- mret = __mount(fstab->recs[i].blk_device, fstab->recs[i].mount_point,
- fstab->recs[i].fs_type, fstab->recs[i].flags,
- fstab->recs[i].fs_options);
-
- if (!mret) {
- /* Success! Go get the next one */
- continue;
- }
-
- /* mount(2) returned an error, check if it's encrypted and deal with it */
- if ((fstab->recs[i].fs_mgr_flags & MF_CRYPT) &&
- !partition_wiped(fstab->recs[i].blk_device)) {
- /* Need to mount a tmpfs at this mountpoint for now, and set
- * properties that vold will query later for decrypting
- */
- if (mount("tmpfs", fstab->recs[i].mount_point, "tmpfs",
- MS_NOATIME | MS_NOSUID | MS_NODEV, CRYPTO_TMPFS_OPTIONS) < 0) {
- ERROR("Cannot mount tmpfs filesystem for encrypted fs at %s\n",
- fstab->recs[i].mount_point);
- goto out;
- }
- encrypted = 1;
- } else {
- ERROR("Cannot mount filesystem on %s at %s\n",
- fstab->recs[i].blk_device, fstab->recs[i].mount_point);
- goto out;
- }
- }
-
- if (encrypted) {
- ret = 1;
- } else {
- ret = 0;
- }
-
-out:
- return ret;
-}
-
-/* If tmp_mount_point is non-null, mount the filesystem there. This is for the
- * tmp mount we do to check the user password
- */
-int fs_mgr_do_mount(struct fstab *fstab, char *n_name, char *n_blk_device,
- char *tmp_mount_point)
-{
- int i = 0;
- int ret = -1;
- char *m;
-
- if (!fstab) {
- return ret;
- }
-
- for (i = 0; i < fstab->num_entries; i++) {
- if (!fs_match(fstab->recs[i].mount_point, n_name)) {
- continue;
- }
-
- /* We found our match */
- /* If this swap or a raw partition, report an error */
- if (!strcmp(fstab->recs[i].fs_type, "swap") ||
- !strcmp(fstab->recs[i].fs_type, "emmc") ||
- !strcmp(fstab->recs[i].fs_type, "mtd")) {
- ERROR("Cannot mount filesystem of type %s on %s\n",
- fstab->recs[i].fs_type, n_blk_device);
- goto out;
- }
-
- /* First check the filesystem if requested */
- if (fstab->recs[i].fs_mgr_flags & MF_WAIT) {
- wait_for_file(n_blk_device, WAIT_TIMEOUT);
- }
-
- if (fstab->recs[i].fs_mgr_flags & MF_CHECK) {
- check_fs(n_blk_device, fstab->recs[i].fs_type,
- fstab->recs[i].mount_point);
- }
-
- if (fstab->recs[i].fs_mgr_flags & MF_VERIFY) {
- if (fs_mgr_setup_verity(&fstab->recs[i]) < 0) {
- ERROR("Could not set up verified partition, skipping!");
- continue;
- }
- }
-
- /* Now mount it where requested */
- if (tmp_mount_point) {
- m = tmp_mount_point;
- } else {
- m = fstab->recs[i].mount_point;
- }
- if (__mount(n_blk_device, m, fstab->recs[i].fs_type,
- fstab->recs[i].flags, fstab->recs[i].fs_options)) {
- ERROR("Cannot mount filesystem on %s at %s\n",
- n_blk_device, m);
- goto out;
- } else {
- ret = 0;
- goto out;
- }
- }
-
- /* We didn't find a match, say so and return an error */
- ERROR("Cannot find mount point %s in fstab\n", fstab->recs[i].mount_point);
-
-out:
- return ret;
-}
-
-/*
- * mount a tmpfs filesystem at the given point.
- * return 0 on success, non-zero on failure.
- */
-int fs_mgr_do_tmpfs_mount(char *n_name)
-{
- int ret;
-
- ret = mount("tmpfs", n_name, "tmpfs",
- MS_NOATIME | MS_NOSUID | MS_NODEV, CRYPTO_TMPFS_OPTIONS);
- if (ret < 0) {
- ERROR("Cannot mount tmpfs filesystem at %s\n", n_name);
- return -1;
- }
-
- /* Success */
- return 0;
-}
-
-int fs_mgr_unmount_all(struct fstab *fstab)
-{
- int i = 0;
- int ret = 0;
-
- if (!fstab) {
- return -1;
- }
-
- while (fstab->recs[i].blk_device) {
- if (umount(fstab->recs[i].mount_point)) {
- ERROR("Cannot unmount filesystem at %s\n", fstab->recs[i].mount_point);
- ret = -1;
- }
- i++;
- }
-
- return ret;
-}
-
-/* This must be called after mount_all, because the mkswap command needs to be
- * available.
- */
-int fs_mgr_swapon_all(struct fstab *fstab)
-{
- int i = 0;
- int flags = 0;
- int err = 0;
- int ret = 0;
- int status;
- char *mkswap_argv[2] = {
- MKSWAP_BIN,
- NULL
- };
-
- if (!fstab) {
- return -1;
- }
-
- for (i = 0; i < fstab->num_entries; i++) {
- /* Skip non-swap entries */
- if (strcmp(fstab->recs[i].fs_type, "swap")) {
- continue;
- }
-
- if (fstab->recs[i].zram_size > 0) {
- /* A zram_size was specified, so we need to configure the
- * device. There is no point in having multiple zram devices
- * on a system (all the memory comes from the same pool) so
- * we can assume the device number is 0.
- */
- FILE *zram_fp;
-
- zram_fp = fopen(ZRAM_CONF_DEV, "r+");
- if (zram_fp == NULL) {
- ERROR("Unable to open zram conf device " ZRAM_CONF_DEV);
- ret = -1;
- continue;
- }
- fprintf(zram_fp, "%d\n", fstab->recs[i].zram_size);
- fclose(zram_fp);
- }
-
- if (fstab->recs[i].fs_mgr_flags & MF_WAIT) {
- wait_for_file(fstab->recs[i].blk_device, WAIT_TIMEOUT);
- }
-
- /* Initialize the swap area */
- mkswap_argv[1] = fstab->recs[i].blk_device;
- err = android_fork_execvp_ext(ARRAY_SIZE(mkswap_argv), mkswap_argv,
- &status, true, LOG_KLOG, false, NULL);
- if (err) {
- ERROR("mkswap failed for %s\n", fstab->recs[i].blk_device);
- ret = -1;
- continue;
- }
-
- /* If -1, then no priority was specified in fstab, so don't set
- * SWAP_FLAG_PREFER or encode the priority */
- if (fstab->recs[i].swap_prio >= 0) {
- flags = (fstab->recs[i].swap_prio << SWAP_FLAG_PRIO_SHIFT) &
- SWAP_FLAG_PRIO_MASK;
- flags |= SWAP_FLAG_PREFER;
- } else {
- flags = 0;
- }
- // requires sys/swap.h which is not available in older trees
- // this entire function does not appear to be used for decrypt
- err = -1; //swapon(fstab->recs[i].blk_device, flags);
- if (err) {
- ERROR("swapon failed for %s\n", fstab->recs[i].blk_device);
- ret = -1;
- }
- }
-
- return ret;
-}
-
-/*
- * key_loc must be at least PROPERTY_VALUE_MAX bytes long
- *
- * real_blk_device must be at least PROPERTY_VALUE_MAX bytes long
- */
-int fs_mgr_get_crypt_info(struct fstab *fstab, char *key_loc, char *real_blk_device, int size)
-{
- int i = 0;
-
- if (!fstab) {
- return -1;
- }
- /* Initialize return values to null strings */
- if (key_loc) {
- *key_loc = '\0';
- }
- if (real_blk_device) {
- *real_blk_device = '\0';
- }
-
- /* Look for the encryptable partition to find the data */
- for (i = 0; i < fstab->num_entries; i++) {
- /* Don't deal with vold managed enryptable partitions here */
- if (fstab->recs[i].fs_mgr_flags & MF_VOLDMANAGED) {
- continue;
- }
- if (!(fstab->recs[i].fs_mgr_flags & MF_CRYPT)) {
- continue;
- }
-
- /* We found a match */
- if (key_loc) {
- strlcpy(key_loc, fstab->recs[i].key_loc, size);
- }
- if (real_blk_device) {
- strlcpy(real_blk_device, fstab->recs[i].blk_device, size);
- }
- break;
- }
-
- return 0;
-}
-
-/* Add an entry to the fstab, and return 0 on success or -1 on error */
-int fs_mgr_add_entry(struct fstab *fstab,
- const char *mount_point, const char *fs_type,
- const char *blk_device, long long length)
-{
- struct fstab_rec *new_fstab_recs;
- int n = fstab->num_entries;
-
- new_fstab_recs = (struct fstab_rec *)
- realloc(fstab->recs, sizeof(struct fstab_rec) * (n + 1));
-
- if (!new_fstab_recs) {
- return -1;
- }
-
- /* A new entry was added, so initialize it */
- memset(&new_fstab_recs[n], 0, sizeof(struct fstab_rec));
- new_fstab_recs[n].mount_point = strdup(mount_point);
- new_fstab_recs[n].fs_type = strdup(fs_type);
- new_fstab_recs[n].blk_device = strdup(blk_device);
- new_fstab_recs[n].length = 0;
-
- /* Update the fstab struct */
- fstab->recs = new_fstab_recs;
- fstab->num_entries++;
-
- return 0;
-}
-
-struct fstab_rec *fs_mgr_get_entry_for_mount_point(struct fstab *fstab, const char *path)
-{
- int i;
-
- if (!fstab) {
- return NULL;
- }
-
- for (i = 0; i < fstab->num_entries; i++) {
- int len = strlen(fstab->recs[i].mount_point);
- if (strncmp(path, fstab->recs[i].mount_point, len) == 0 &&
- (path[len] == '\0' || path[len] == '/')) {
- return &fstab->recs[i];
- }
- }
-
- return NULL;
-}
-
-int fs_mgr_is_voldmanaged(struct fstab_rec *fstab)
-{
- return fstab->fs_mgr_flags & MF_VOLDMANAGED;
-}
-
-int fs_mgr_is_nonremovable(struct fstab_rec *fstab)
-{
- return fstab->fs_mgr_flags & MF_NONREMOVABLE;
-}
-
-int fs_mgr_is_encryptable(struct fstab_rec *fstab)
-{
- return fstab->fs_mgr_flags & MF_CRYPT;
-}
-
-int fs_mgr_is_noemulatedsd(struct fstab_rec *fstab)
-{
- return fstab->fs_mgr_flags & MF_NOEMULATEDSD;
-}
diff --git a/crypto/fs_mgr/fs_mgr_main.c b/crypto/fs_mgr/fs_mgr_main.c
deleted file mode 100644
index 4bde4a1da..000000000
--- a/crypto/fs_mgr/fs_mgr_main.c
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright (C) 2012 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 <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-#include <libgen.h>
-#include "fs_mgr_priv.h"
-
-char *me = "";
-
-static void usage(void)
-{
- ERROR("%s: usage: %s <-a | -n mnt_point blk_dev | -u> <fstab_file>\n", me, me);
- exit(1);
-}
-
-/* Parse the command line. If an error is encountered, print an error message
- * and exit the program, do not return to the caller.
- * Return the number of argv[] entries consumed.
- */
-static void parse_options(int argc, char *argv[], int *a_flag, int *u_flag, int *n_flag,
- char **n_name, char **n_blk_dev)
-{
- me = basename(strdup(argv[0]));
-
- if (argc <= 1) {
- usage();
- }
-
- if (!strcmp(argv[1], "-a")) {
- if (argc != 3) {
- usage();
- }
- *a_flag = 1;
- }
- if (!strcmp(argv[1], "-n")) {
- if (argc != 5) {
- usage();
- }
- *n_flag = 1;
- *n_name = argv[2];
- *n_blk_dev = argv[3];
- }
- if (!strcmp(argv[1], "-u")) {
- if (argc != 3) {
- usage();
- }
- *u_flag = 1;
- }
-
- /* If no flag is specified, it's an error */
- if (!(*a_flag | *n_flag | *u_flag)) {
- usage();
- }
-
- /* If more than one flag is specified, it's an error */
- if ((*a_flag + *n_flag + *u_flag) > 1) {
- usage();
- }
-
- return;
-}
-
-int main(int argc, char *argv[])
-{
- int a_flag=0;
- int u_flag=0;
- int n_flag=0;
- char *n_name;
- char *n_blk_dev;
- char *fstab_file;
- struct fstab *fstab;
-
- klog_init();
- klog_set_level(6);
-
- parse_options(argc, argv, &a_flag, &u_flag, &n_flag, &n_name, &n_blk_dev);
-
- /* The name of the fstab file is last, after the option */
- fstab_file = argv[argc - 1];
-
- fstab = fs_mgr_read_fstab(fstab_file);
-
- if (a_flag) {
- return fs_mgr_mount_all(fstab);
- } else if (n_flag) {
- return fs_mgr_do_mount(fstab, n_name, n_blk_dev, 0);
- } else if (u_flag) {
- return fs_mgr_unmount_all(fstab);
- } else {
- ERROR("%s: Internal error, unknown option\n", me);
- exit(1);
- }
-
- fs_mgr_free_fstab(fstab);
-
- /* Should not get here */
- exit(1);
-}
-
diff --git a/crypto/fs_mgr/fs_mgr_priv.h b/crypto/fs_mgr/fs_mgr_priv.h
deleted file mode 100644
index 59ffd785c..000000000
--- a/crypto/fs_mgr/fs_mgr_priv.h
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright (C) 2012 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 __CORE_FS_MGR_PRIV_H
-#define __CORE_FS_MGR_PRIV_H
-
-#include <cutils/klog.h>
-#include <fs_mgr.h>
-
-#define INFO(x...) KLOG_INFO("fs_mgr", x)
-#define ERROR(x...) KLOG_ERROR("fs_mgr", x)
-
-#define CRYPTO_TMPFS_OPTIONS "size=128m,mode=0771,uid=1000,gid=1000"
-
-#define WAIT_TIMEOUT 20
-
-/* fstab has the following format:
- *
- * Any line starting with a # is a comment and ignored
- *
- * Any blank line is ignored
- *
- * All other lines must be in this format:
- * <source> <mount_point> <fs_type> <mount_flags> <fs_options> <fs_mgr_options>
- *
- * <mount_flags> is a comma separated list of flags that can be passed to the
- * mount command. The list includes noatime, nosuid, nodev, nodiratime,
- * ro, rw, remount, defaults.
- *
- * <fs_options> is a comma separated list of options accepted by the filesystem being
- * mounted. It is passed directly to mount without being parsed
- *
- * <fs_mgr_options> is a comma separated list of flags that control the operation of
- * the fs_mgr program. The list includes "wait", which will wait till
- * the <source> file exists, and "check", which requests that the fs_mgr
- * run an fscheck program on the <source> before mounting the filesystem.
- * If check is specifed on a read-only filesystem, it is ignored.
- * Also, "encryptable" means that filesystem can be encrypted.
- * The "encryptable" flag _MUST_ be followed by a = and a string which
- * is the location of the encryption keys. It can either be a path
- * to a file or partition which contains the keys, or the word "footer"
- * which means the keys are in the last 16 Kbytes of the partition
- * containing the filesystem.
- *
- * When the fs_mgr is requested to mount all filesystems, it will first mount all the
- * filesystems that do _NOT_ specify check (including filesystems that are read-only and
- * specify check, because check is ignored in that case) and then it will check and mount
- * filesystem marked with check.
- *
- */
-
-#define MF_WAIT 0x1
-#define MF_CHECK 0x2
-#define MF_CRYPT 0x4
-#define MF_NONREMOVABLE 0x8
-#define MF_VOLDMANAGED 0x10
-#define MF_LENGTH 0x20
-#define MF_RECOVERYONLY 0x40
-#define MF_SWAPPRIO 0x80
-#define MF_ZRAMSIZE 0x100
-#define MF_VERIFY 0x200
-/*
- * There is no emulated sdcard daemon running on /data/media on this device,
- * so treat the physical SD card as the only external storage device,
- * a la the Nexus One.
- */
-#define MF_NOEMULATEDSD 0x400
-
-#define DM_BUF_SIZE 4096
-
-#endif /* __CORE_FS_MGR_PRIV_H */
-
diff --git a/crypto/fs_mgr/fs_mgr_priv_verity.h b/crypto/fs_mgr/fs_mgr_priv_verity.h
deleted file mode 100644
index 61937849a..000000000
--- a/crypto/fs_mgr/fs_mgr_priv_verity.h
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright (C) 2013 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.
- */
-
-int fs_mgr_setup_verity(struct fstab_rec *fstab); \ No newline at end of file
diff --git a/crypto/fs_mgr/fs_mgr_verity.c b/crypto/fs_mgr/fs_mgr_verity.c
deleted file mode 100644
index 969eab2a0..000000000
--- a/crypto/fs_mgr/fs_mgr_verity.c
+++ /dev/null
@@ -1,410 +0,0 @@
-/*
- * Copyright (C) 2013 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 <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <ctype.h>
-#include <sys/mount.h>
-#include <sys/stat.h>
-#include <errno.h>
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <libgen.h>
-#include <time.h>
-
-#include <private/android_filesystem_config.h>
-#include <logwrap/logwrap.h>
-
-#include "mincrypt/rsa.h"
-#include "mincrypt/sha.h"
-#include "mincrypt/sha256.h"
-
-#include "ext4_utils.h"
-#include "ext4.h"
-
-#include "fs_mgr_priv.h"
-#include "fs_mgr_priv_verity.h"
-
-#define VERITY_METADATA_SIZE 32768
-#define VERITY_METADATA_MAGIC_NUMBER 0xb001b001
-#define VERITY_TABLE_RSA_KEY "/verity_key"
-
-extern struct fs_info info;
-
-static RSAPublicKey *load_key(char *path)
-{
- FILE *f;
- RSAPublicKey *key;
-
- key = malloc(sizeof(RSAPublicKey));
- if (!key) {
- ERROR("Can't malloc key\n");
- return NULL;
- }
-
- f = fopen(path, "r");
- if (!f) {
- ERROR("Can't open '%s'\n", path);
- free(key);
- return NULL;
- }
-
- if (!fread(key, sizeof(*key), 1, f)) {
- ERROR("Could not read key!");
- fclose(f);
- free(key);
- return NULL;
- }
-
- if (key->len != RSANUMWORDS) {
- ERROR("Invalid key length %d\n", key->len);
- fclose(f);
- free(key);
- return NULL;
- }
-
- fclose(f);
- return key;
-}
-
-static int verify_table(char *signature, char *table, int table_length)
-{
- int fd;
- RSAPublicKey *key;
- uint8_t hash_buf[SHA_DIGEST_SIZE];
- int retval = -1;
-
- // Hash the table
- SHA_hash((uint8_t*)table, table_length, hash_buf);
-
- // Now get the public key from the keyfile
- key = load_key(VERITY_TABLE_RSA_KEY);
- if (!key) {
- ERROR("Couldn't load verity keys");
- goto out;
- }
-
- // verify the result
- if (!RSA_verify(key,
- (uint8_t*) signature,
- RSANUMBYTES,
- (uint8_t*) hash_buf,
- SHA_DIGEST_SIZE)) {
- ERROR("Couldn't verify table.");
- goto out;
- }
-
- retval = 0;
-
-out:
- free(key);
- return retval;
-}
-
-static int get_target_device_size(char *blk_device, uint64_t *device_size)
-{
- int data_device;
- struct ext4_super_block sb;
-
- data_device = open(blk_device, O_RDONLY);
- if (data_device < 0) {
- ERROR("Error opening block device (%s)", strerror(errno));
- return -1;
- }
-
- if (lseek64(data_device, 1024, SEEK_SET) < 0) {
- ERROR("Error seeking to superblock");
- close(data_device);
- return -1;
- }
-
- if (read(data_device, &sb, sizeof(sb)) != sizeof(sb)) {
- ERROR("Error reading superblock");
- close(data_device);
- return -1;
- }
-
- ext4_parse_sb(&sb);
- *device_size = info.len;
-
- close(data_device);
- return 0;
-}
-
-static int read_verity_metadata(char *block_device, char **signature, char **table)
-{
- unsigned magic_number;
- unsigned table_length;
- uint64_t device_length;
- int protocol_version;
- FILE *device;
- int retval = -1;
-
- device = fopen(block_device, "r");
- if (!device) {
- ERROR("Could not open block device %s (%s).\n", block_device, strerror(errno));
- goto out;
- }
-
- // find the start of the verity metadata
- if (get_target_device_size(block_device, &device_length) < 0) {
- ERROR("Could not get target device size.\n");
- goto out;
- }
- if (fseek(device, device_length, SEEK_SET) < 0) {
- ERROR("Could not seek to start of verity metadata block.\n");
- goto out;
- }
-
- // check the magic number
- if (!fread(&magic_number, sizeof(int), 1, device)) {
- ERROR("Couldn't read magic number!\n");
- goto out;
- }
- if (magic_number != VERITY_METADATA_MAGIC_NUMBER) {
- ERROR("Couldn't find verity metadata at offset %llu!\n", device_length);
- goto out;
- }
-
- // check the protocol version
- if (!fread(&protocol_version, sizeof(int), 1, device)) {
- ERROR("Couldn't read verity metadata protocol version!\n");
- goto out;
- }
- if (protocol_version != 0) {
- ERROR("Got unknown verity metadata protocol version %d!\n", protocol_version);
- goto out;
- }
-
- // get the signature
- *signature = (char*) malloc(RSANUMBYTES * sizeof(char));
- if (!*signature) {
- ERROR("Couldn't allocate memory for signature!\n");
- goto out;
- }
- if (!fread(*signature, RSANUMBYTES, 1, device)) {
- ERROR("Couldn't read signature from verity metadata!\n");
- free(*signature);
- goto out;
- }
-
- // get the size of the table
- if (!fread(&table_length, sizeof(int), 1, device)) {
- ERROR("Couldn't get the size of the verity table from metadata!\n");
- free(*signature);
- goto out;
- }
-
- // get the table + null terminator
- table_length += 1;
- *table = malloc(table_length);
- if(!*table) {
- ERROR("Couldn't allocate memory for verity table!\n");
- goto out;
- }
- if (!fgets(*table, table_length, device)) {
- ERROR("Couldn't read the verity table from metadata!\n");
- free(*table);
- free(*signature);
- goto out;
- }
-
- retval = 0;
-
-out:
- if (device)
- fclose(device);
- return retval;
-}
-
-static void verity_ioctl_init(struct dm_ioctl *io, char *name, unsigned flags)
-{
- memset(io, 0, DM_BUF_SIZE);
- io->data_size = DM_BUF_SIZE;
- io->data_start = sizeof(struct dm_ioctl);
- io->version[0] = 4;
- io->version[1] = 0;
- io->version[2] = 0;
- io->flags = flags | DM_READONLY_FLAG;
- if (name) {
- strlcpy(io->name, name, sizeof(io->name));
- }
-}
-
-static int create_verity_device(struct dm_ioctl *io, char *name, int fd)
-{
- verity_ioctl_init(io, name, 1);
- if (ioctl(fd, DM_DEV_CREATE, io)) {
- ERROR("Error creating device mapping (%s)", strerror(errno));
- return -1;
- }
- return 0;
-}
-
-static int get_verity_device_name(struct dm_ioctl *io, char *name, int fd, char **dev_name)
-{
- verity_ioctl_init(io, name, 0);
- if (ioctl(fd, DM_DEV_STATUS, io)) {
- ERROR("Error fetching verity device number (%s)", strerror(errno));
- return -1;
- }
- int dev_num = (io->dev & 0xff) | ((io->dev >> 12) & 0xfff00);
- if (asprintf(dev_name, "/dev/block/dm-%u", dev_num) < 0) {
- ERROR("Error getting verity block device name (%s)", strerror(errno));
- return -1;
- }
- return 0;
-}
-
-static int load_verity_table(struct dm_ioctl *io, char *name, char *blockdev, int fd, char *table)
-{
- char *verity_params;
- char *buffer = (char*) io;
- uint64_t device_size = 0;
-
- if (get_target_device_size(blockdev, &device_size) < 0) {
- return -1;
- }
-
- verity_ioctl_init(io, name, DM_STATUS_TABLE_FLAG);
-
- struct dm_target_spec *tgt = (struct dm_target_spec *) &buffer[sizeof(struct dm_ioctl)];
-
- // set tgt arguments here
- io->target_count = 1;
- tgt->status=0;
- tgt->sector_start=0;
- tgt->length=device_size/512;
- strcpy(tgt->target_type, "verity");
-
- // build the verity params here
- verity_params = buffer + sizeof(struct dm_ioctl) + sizeof(struct dm_target_spec);
- if (sprintf(verity_params, "%s", table) < 0) {
- return -1;
- }
-
- // set next target boundary
- verity_params += strlen(verity_params) + 1;
- verity_params = (char*) (((unsigned long)verity_params + 7) & ~8);
- tgt->next = verity_params - buffer;
-
- // send the ioctl to load the verity table
- if (ioctl(fd, DM_TABLE_LOAD, io)) {
- ERROR("Error loading verity table (%s)", strerror(errno));
- return -1;
- }
-
- return 0;
-}
-
-static int resume_verity_table(struct dm_ioctl *io, char *name, int fd)
-{
- verity_ioctl_init(io, name, 0);
- if (ioctl(fd, DM_DEV_SUSPEND, io)) {
- ERROR("Error activating verity device (%s)", strerror(errno));
- return -1;
- }
- return 0;
-}
-
-static int test_access(char *device) {
- int tries = 25;
- while (tries--) {
- if (!access(device, F_OK) || errno != ENOENT) {
- return 0;
- }
- usleep(40 * 1000);
- }
- return -1;
-}
-
-int fs_mgr_setup_verity(struct fstab_rec *fstab) {
-
- int retval = -1;
-
- char *verity_blk_name;
- char *verity_table;
- char *verity_table_signature;
-
- char buffer[DM_BUF_SIZE];
- struct dm_ioctl *io = (struct dm_ioctl *) buffer;
- char *mount_point = basename(fstab->mount_point);
-
- // set the dm_ioctl flags
- io->flags |= 1;
- io->target_count = 1;
-
- // get the device mapper fd
- int fd;
- if ((fd = open("/dev/device-mapper", O_RDWR)) < 0) {
- ERROR("Error opening device mapper (%s)", strerror(errno));
- return retval;
- }
-
- // create the device
- if (create_verity_device(io, mount_point, fd) < 0) {
- ERROR("Couldn't create verity device!");
- goto out;
- }
-
- // get the name of the device file
- if (get_verity_device_name(io, mount_point, fd, &verity_blk_name) < 0) {
- ERROR("Couldn't get verity device number!");
- goto out;
- }
-
- // read the verity block at the end of the block device
- if (read_verity_metadata(fstab->blk_device,
- &verity_table_signature,
- &verity_table) < 0) {
- goto out;
- }
-
- // verify the signature on the table
- if (verify_table(verity_table_signature,
- verity_table,
- strlen(verity_table)) < 0) {
- goto out;
- }
-
- // load the verity mapping table
- if (load_verity_table(io, mount_point, fstab->blk_device, fd, verity_table) < 0) {
- goto out;
- }
-
- // activate the device
- if (resume_verity_table(io, mount_point, fd) < 0) {
- goto out;
- }
-
- // assign the new verity block device as the block device
- free(fstab->blk_device);
- fstab->blk_device = verity_blk_name;
-
- // make sure we've set everything up properly
- if (test_access(fstab->blk_device) < 0) {
- goto out;
- }
-
- retval = 0;
-
-out:
- close(fd);
- return retval;
-}
diff --git a/crypto/fs_mgr/include/fs_mgr.h b/crypto/fs_mgr/include/fs_mgr.h
deleted file mode 100644
index 0f90c32f1..000000000
--- a/crypto/fs_mgr/include/fs_mgr.h
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright (C) 2012 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 __CORE_FS_MGR_H
-#define __CORE_FS_MGR_H
-
-#include <stdint.h>
-#include <linux/dm-ioctl.h>
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-struct fstab {
- int num_entries;
- struct fstab_rec *recs;
- char *fstab_filename;
-};
-
-struct fstab_rec {
- char *blk_device;
- char *mount_point;
- char *fs_type;
- unsigned long flags;
- char *fs_options;
- int fs_mgr_flags;
- char *key_loc;
- char *verity_loc;
- long long length;
- char *label;
- int partnum;
- int swap_prio;
- unsigned int zram_size;
-};
-
-struct fstab *fs_mgr_read_fstab(const char *fstab_path);
-void fs_mgr_free_fstab(struct fstab *fstab);
-int fs_mgr_mount_all(struct fstab *fstab);
-int fs_mgr_do_mount(struct fstab *fstab, char *n_name, char *n_blk_device,
- char *tmp_mount_point);
-int fs_mgr_do_tmpfs_mount(char *n_name);
-int fs_mgr_unmount_all(struct fstab *fstab);
-int fs_mgr_get_crypt_info(struct fstab *fstab, char *key_loc,
- char *real_blk_device, int size);
-int fs_mgr_add_entry(struct fstab *fstab,
- const char *mount_point, const char *fs_type,
- const char *blk_device, long long length);
-struct fstab_rec *fs_mgr_get_entry_for_mount_point(struct fstab *fstab, const char *path);
-int fs_mgr_is_voldmanaged(struct fstab_rec *fstab);
-int fs_mgr_is_nonremovable(struct fstab_rec *fstab);
-int fs_mgr_is_encryptable(struct fstab_rec *fstab);
-int fs_mgr_is_noemulatedsd(struct fstab_rec *fstab);
-int fs_mgr_swapon_all(struct fstab *fstab);
-#ifdef __cplusplus
-}
-#endif
-
-#endif /* __CORE_FS_MGR_H */
-
diff --git a/crypto/ics/Android.mk b/crypto/ics/Android.mk
deleted file mode 100644
index 5616c195a..000000000
--- a/crypto/ics/Android.mk
+++ /dev/null
@@ -1,25 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-ifeq ($(TW_INCLUDE_CRYPTO), true)
-include $(CLEAR_VARS)
-
-LOCAL_MODULE := libcryptfsics
-LOCAL_MODULE_TAGS := eng optional
-LOCAL_CFLAGS :=
-LOCAL_CFLAGS += -DCRYPTO_FS_TYPE=\"$(TW_CRYPTO_FS_TYPE)\"
-ifeq ($(TW_INCLUDE_CRYPTO_SAMSUNG), true)
- LOCAL_CFLAGS += -DTW_INCLUDE_CRYPTO_SAMSUNG=\"$(TW_INCLUDE_CRYPTO_SAMSUNG)\"
- LOCAL_LDFLAGS += -ldl
- LOCAL_STATIC_LIBRARIES += libcrypt_samsung
-endif
-ifneq ($(TW_INTERNAL_STORAGE_PATH),)
- LOCAL_CFLAGS += -DTW_INTERNAL_STORAGE_PATH=$(TW_INTERNAL_STORAGE_PATH)
-endif
-ifneq ($(TW_EXTERNAL_STORAGE_PATH),)
- LOCAL_CFLAGS += -DTW_EXTERNAL_STORAGE_PATH=$(TW_EXTERNAL_STORAGE_PATH)
-endif
-LOCAL_SRC_FILES = cryptfs.c
-LOCAL_C_INCLUDES += system/extras/ext4_utils external/openssl/include
-LOCAL_SHARED_LIBRARIES += libc liblog libcutils libcrypto
-
-include $(BUILD_SHARED_LIBRARY)
-endif
diff --git a/crypto/ics/cryptfs.c b/crypto/ics/cryptfs.c
deleted file mode 100644
index 4f3d5d01a..000000000
--- a/crypto/ics/cryptfs.c
+++ /dev/null
@@ -1,729 +0,0 @@
-/*
- * Copyright (C) 2010 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.
- */
-
-/* TO DO:
- * 1. Perhaps keep several copies of the encrypted key, in case something
- * goes horribly wrong?
- *
- */
-
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-#include <unistd.h>
-#include <stdio.h>
-#include <sys/ioctl.h>
-#include <linux/dm-ioctl.h>
-#include <libgen.h>
-#include <stdlib.h>
-#include <sys/param.h>
-#include <string.h>
-#include <sys/mount.h>
-#include <openssl/evp.h>
-#include <openssl/sha.h>
-#include <errno.h>
-#include <cutils/android_reboot.h>
-#include <ext4.h>
-#include <linux/kdev_t.h>
-#include "cryptfs.h"
-#define LOG_TAG "Cryptfs"
-#include "cutils/log.h"
-#include "cutils/properties.h"
-#include "hardware_legacy/power.h"
-//#include "VolumeManager.h"
-
-#define DM_CRYPT_BUF_SIZE 4096
-#define DATA_MNT_POINT "/data"
-
-#define HASH_COUNT 2000
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
-#define KEY_LEN_BYTES_SAMSUNG (sizeof(edk_t))
-#endif
-#define KEY_LEN_BYTES 16
-#define IV_LEN_BYTES 16
-
-#define KEY_LOC_PROP "ro.crypto.keyfile.userdata"
-#define KEY_IN_FOOTER "footer"
-
-#define EXT4_FS 1
-#define FAT_FS 2
-
-#ifndef EXPAND
-#define STRINGIFY(x) #x
-#define EXPAND(x) STRINGIFY(x)
-#endif
-
-char *me = "cryptfs";
-
-static char *saved_data_blkdev;
-static char *saved_mount_point;
-static int master_key_saved = 0;
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
-static int using_samsung_encryption = 0;
-//static edk_t saved_master_key;
-static unsigned char saved_master_key[KEY_LEN_BYTES_SAMSUNG];
-edk_payload_t edk_payload;
-#else
-static unsigned char saved_master_key[KEY_LEN_BYTES];
-#endif
-
-int cryptfs_setup_volume(const char *label, const char *real_blkdev, char *crypto_blkdev);
-
-
-static void ioctl_init(struct dm_ioctl *io, size_t dataSize, const char *name, unsigned flags)
-{
- memset(io, 0, dataSize);
- io->data_size = dataSize;
- io->data_start = sizeof(struct dm_ioctl);
- io->version[0] = 4;
- io->version[1] = 0;
- io->version[2] = 0;
- io->flags = flags;
- if (name) {
- strncpy(io->name, name, sizeof(io->name));
- }
-}
-
-static unsigned int get_blkdev_size(int fd)
-{
- unsigned int nr_sec;
-
- if ( (ioctl(fd, BLKGETSIZE, &nr_sec)) == -1) {
- nr_sec = 0;
- }
-
- return nr_sec;
-}
-
-/* key or salt can be NULL, in which case just skip writing that value. Useful to
- * update the failed mount count but not change the key.
- */
-static int put_crypt_ftr_and_key(char *real_blk_name, struct crypt_mnt_ftr *crypt_ftr,
- unsigned char *key, unsigned char *salt)
-{
- // we don't need to update it...
- return 0;
-}
-
-static int get_crypt_ftr_and_key(char *real_blk_name, struct crypt_mnt_ftr *crypt_ftr,
- unsigned char *key, unsigned char *salt)
-{
- int fd;
- unsigned int nr_sec, cnt;
- off64_t off;
- int rc = -1;
- char key_loc[PROPERTY_VALUE_MAX];
- char *fname;
- struct stat statbuf;
-
- property_get(KEY_LOC_PROP, key_loc, KEY_IN_FOOTER);
-
- if (!strcmp(key_loc, KEY_IN_FOOTER)) {
- fname = real_blk_name;
- if ( (fd = open(fname, O_RDONLY)) < 0) {
- printf("Cannot open real block device %s\n", fname);
- return -1;
- }
-
- if ( (nr_sec = get_blkdev_size(fd)) == 0) {
- SLOGE("Cannot get size of block device %s\n", fname);
- goto errout;
- }
-
- /* If it's an encrypted Android partition, the last 16 Kbytes contain the
- * encryption info footer and key, and plenty of bytes to spare for future
- * growth.
- */
- off = ((off64_t)nr_sec * 512) - CRYPT_FOOTER_OFFSET;
-
- if (lseek64(fd, off, SEEK_SET) == -1) {
- printf("Cannot seek to real block device footer\n");
- goto errout;
- }
- } else if (key_loc[0] == '/') {
- fname = key_loc;
- if ( (fd = open(fname, O_RDONLY)) < 0) {
- printf("Cannot open footer file %s\n", fname);
- return -1;
- }
-
- /* Make sure it's 16 Kbytes in length */
- fstat(fd, &statbuf);
- if (S_ISREG(statbuf.st_mode) && (statbuf.st_size != 0x4000
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
- && statbuf.st_size != 0x8000
-#endif
- )) {
- printf("footer file %s is not the expected size!\n", fname);
- goto errout;
- }
- } else {
- printf("Unexpected value for" KEY_LOC_PROP "\n");
- return -1;;
- }
-
- if ( (cnt = read(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr))) != sizeof(struct crypt_mnt_ftr)) {
- printf("Cannot read real block device footer\n");
- goto errout;
- }
-
- if (crypt_ftr->magic != CRYPT_MNT_MAGIC) {
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
- if (crypt_ftr->magic != CRYPT_MNT_MAGIC_SAMSUNG) {
- printf("Bad magic for real block device %s\n", fname);
- goto errout;
- } else {
- printf("Using Samsung encryption.\n");
- using_samsung_encryption = 1;
- if ( (cnt = read(fd, &edk_payload, sizeof(edk_payload_t))) != sizeof(edk_payload_t)) {
- printf("Cannot read EDK payload from real block device footer\n");
- goto errout;
- }
- if (lseek64(fd, sizeof(__le32), SEEK_CUR) == -1) {
- printf("Cannot seek past unknown data from real block device footer\n");
- goto errout;
- }
- memcpy(key, &edk_payload, sizeof(edk_payload_t));
- }
-#else
- printf("Bad magic for real block device %s\n", fname);
- goto errout;
-#endif
- }
-
- if (crypt_ftr->major_version != 1) {
- printf("Cannot understand major version %d real block device footer\n",
- crypt_ftr->major_version);
- goto errout;
- }
-
- if (crypt_ftr->minor_version != 0) {
- printf("Warning: crypto footer minor version %d, expected 0, continuing...\n",
- crypt_ftr->minor_version);
- }
-
- if (crypt_ftr->ftr_size > sizeof(struct crypt_mnt_ftr)) {
- /* the footer size is bigger than we expected.
- * Skip to it's stated end so we can read the key.
- */
- if (lseek64(fd, crypt_ftr->ftr_size - sizeof(struct crypt_mnt_ftr), SEEK_CUR) == -1) {
- printf("Cannot seek to start of key\n");
- goto errout;
- }
- }
-
- if (crypt_ftr->keysize > sizeof(saved_master_key)) {
- printf("Keysize of %d bits not supported for real block device %s\n",
- crypt_ftr->keysize * 8, fname);
- goto errout;
- }
-
- if ( (cnt = read(fd, key, crypt_ftr->keysize)) != crypt_ftr->keysize) {
- printf("Cannot read key for real block device %s\n", fname);
- goto errout;
- }
-
- if (lseek64(fd, KEY_TO_SALT_PADDING, SEEK_CUR) == -1) {
- printf("Cannot seek to real block device salt\n");
- goto errout;
- }
-
- if ( (cnt = read(fd, salt, SALT_LEN)) != SALT_LEN) {
- printf("Cannot read salt for real block device %s\n", fname);
- goto errout;
- }
-
- /* Success! */
- rc = 0;
-
-errout:
- close(fd);
- return rc;
-}
-
-/* Convert a binary key of specified length into an ascii hex string equivalent,
- * without the leading 0x and with null termination
- */
-void convert_key_to_hex_ascii(unsigned char *master_key, unsigned int keysize,
- char *master_key_ascii)
-{
- unsigned int i, a;
- unsigned char nibble;
-
- for (i=0, a=0; i<keysize; i++, a+=2) {
- /* For each byte, write out two ascii hex digits */
- nibble = (master_key[i] >> 4) & 0xf;
- master_key_ascii[a] = nibble + (nibble > 9 ? 0x37 : 0x30);
-
- nibble = master_key[i] & 0xf;
- master_key_ascii[a+1] = nibble + (nibble > 9 ? 0x37 : 0x30);
- }
-
- /* Add the null termination */
- master_key_ascii[a] = '\0';
-
-}
-
-static int create_crypto_blk_dev(struct crypt_mnt_ftr *crypt_ftr, unsigned char *master_key,
- const char *real_blk_name, char *crypto_blk_name, const char *name)
-{
- char buffer[DM_CRYPT_BUF_SIZE];
- char master_key_ascii[129]; /* Large enough to hold 512 bit key and null */
- char *crypt_params;
- struct dm_ioctl *io;
- struct dm_target_spec *tgt;
- unsigned int minor;
- int fd;
- int retval = -1;
-
- if ((fd = open("/dev/device-mapper", O_RDWR)) < 0 ) {
- printf("Cannot open device-mapper\n");
- goto errout;
- }
-
- io = (struct dm_ioctl *) buffer;
-
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- if (ioctl(fd, DM_DEV_CREATE, io)) {
- printf("Cannot create dm-crypt device\n");
- goto errout;
- }
-
- /* Get the device status, in particular, the name of it's device file */
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- if (ioctl(fd, DM_DEV_STATUS, io)) {
- printf("Cannot retrieve dm-crypt device status\n");
- goto errout;
- }
- minor = (io->dev & 0xff) | ((io->dev >> 12) & 0xfff00);
- snprintf(crypto_blk_name, MAXPATHLEN, "/dev/block/dm-%u", minor);
-
- /* Load the mapping table for this device */
- tgt = (struct dm_target_spec *) &buffer[sizeof(struct dm_ioctl)];
-
- ioctl_init(io, 4096, name, 0);
- io->target_count = 1;
- tgt->status = 0;
- tgt->sector_start = 0;
- tgt->length = crypt_ftr->fs_size;
- strcpy(tgt->target_type, "crypt");
-
- crypt_params = buffer + sizeof(struct dm_ioctl) + sizeof(struct dm_target_spec);
- convert_key_to_hex_ascii(master_key, crypt_ftr->keysize, master_key_ascii);
- sprintf(crypt_params, "%s %s 0 %s 0", crypt_ftr->crypto_type_name,
- master_key_ascii, real_blk_name);
- //printf("cryptsetup params: '%s'\n", crypt_params);
- crypt_params += strlen(crypt_params) + 1;
- crypt_params = (char *) (((unsigned long)crypt_params + 7) & ~8); /* Align to an 8 byte boundary */
- tgt->next = crypt_params - buffer;
-
- if (ioctl(fd, DM_TABLE_LOAD, io)) {
- printf("Cannot load dm-crypt mapping table.\n");
- goto errout;
- }
-
- /* Resume this device to activate it */
- ioctl_init(io, 4096, name, 0);
-
- if (ioctl(fd, DM_DEV_SUSPEND, io)) {
- printf("Cannot resume the dm-crypt device\n");
- goto errout;
- }
-
- /* We made it here with no errors. Woot! */
- retval = 0;
-
-errout:
- close(fd); /* If fd is <0 from a failed open call, it's safe to just ignore the close error */
-
- return retval;
-}
-
-static int delete_crypto_blk_dev(const char *name)
-{
- int fd;
- char buffer[DM_CRYPT_BUF_SIZE];
- struct dm_ioctl *io;
- int retval = -1;
-
- if ((fd = open("/dev/device-mapper", O_RDWR)) < 0 ) {
- printf("Cannot open device-mapper\n");
- goto errout;
- }
-
- io = (struct dm_ioctl *) buffer;
-
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- if (ioctl(fd, DM_DEV_REMOVE, io)) {
- printf("Cannot remove dm-crypt device\n");
- goto errout;
- }
-
- /* We made it here with no errors. Woot! */
- retval = 0;
-
-errout:
- close(fd); /* If fd is <0 from a failed open call, it's safe to just ignore the close error */
-
- return retval;
-
-}
-
-static void pbkdf2(char *passwd, unsigned char *salt, unsigned char *ikey)
-{
- /* Turn the password into a key and IV that can decrypt the master key */
- PKCS5_PBKDF2_HMAC_SHA1(passwd, strlen(passwd), salt, SALT_LEN,
- HASH_COUNT, KEY_LEN_BYTES+IV_LEN_BYTES, ikey);
-}
-
-static int decrypt_master_key(char *passwd, unsigned char *salt,
- unsigned char *encrypted_master_key,
- unsigned char *decrypted_master_key)
-{
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
- if (using_samsung_encryption) {
- property_set("rw.km_fips_status", "ready");
- return decrypt_EDK((dek_t*)decrypted_master_key, (edk_payload_t*)encrypted_master_key, passwd);
- }
-#endif
-
- unsigned char ikey[32+32] = { 0 }; /* Big enough to hold a 256 bit key and 256 bit IV */
- EVP_CIPHER_CTX d_ctx;
- int decrypted_len, final_len;
-
- /* Turn the password into a key and IV that can decrypt the master key */
- pbkdf2(passwd, salt, ikey);
-
- /* Initialize the decryption engine */
- if (! EVP_DecryptInit(&d_ctx, EVP_aes_128_cbc(), ikey, ikey+KEY_LEN_BYTES)) {
- return -1;
- }
- EVP_CIPHER_CTX_set_padding(&d_ctx, 0); /* Turn off padding as our data is block aligned */
- /* Decrypt the master key */
- if (! EVP_DecryptUpdate(&d_ctx, decrypted_master_key, &decrypted_len,
- encrypted_master_key, KEY_LEN_BYTES)) {
- return -1;
- }
- if (! EVP_DecryptFinal(&d_ctx, decrypted_master_key + decrypted_len, &final_len)) {
- return -1;
- }
-
- if (decrypted_len + final_len != KEY_LEN_BYTES) {
- return -1;
- } else {
- return 0;
- }
-}
-
-static int get_orig_mount_parms(
- const char *mount_point, char *fs_type, char *real_blkdev,
- unsigned long *mnt_flags, char *fs_options)
-{
- char mount_point2[PROPERTY_VALUE_MAX];
- char fs_flags[PROPERTY_VALUE_MAX];
-
- property_get("ro.crypto.fs_type", fs_type, "");
- property_get("ro.crypto.fs_real_blkdev", real_blkdev, "");
- property_get("ro.crypto.fs_mnt_point", mount_point2, "");
- property_get("ro.crypto.fs_options", fs_options, "");
- property_get("ro.crypto.fs_flags", fs_flags, "");
- *mnt_flags = strtol(fs_flags, 0, 0);
-
- if (strcmp(mount_point, mount_point2)) {
- /* Consistency check. These should match. If not, something odd happened. */
- return -1;
- }
-
- return 0;
-}
-
-static int get_orig_mount_parms_sd(
- const char *mount_point, char *fs_type, char *real_blkdev)
-{
- char mount_point2[PROPERTY_VALUE_MAX];
-
- property_get("ro.crypto.sd_fs_type", fs_type, "");
- property_get("ro.crypto.sd_fs_real_blkdev", real_blkdev, "");
- property_get("ro.crypto.sd_fs_mnt_point", mount_point2, "");
-
- if (strcmp(mount_point, mount_point2)) {
- /* Consistency check. These should match. If not, something odd happened. */
- return -1;
- }
-
- return 0;
-}
-
-static int test_mount_encrypted_fs(
- char *passwd, char *mount_point, char *label, char *crypto_blkdev)
-{
- struct crypt_mnt_ftr crypt_ftr;
- /* Allocate enough space for a 256 bit key, but we may use less */
- unsigned char encrypted_master_key[256], decrypted_master_key[32];
- unsigned char salt[SALT_LEN];
- char real_blkdev[MAXPATHLEN];
- char fs_type[PROPERTY_VALUE_MAX];
- char fs_options[PROPERTY_VALUE_MAX];
- char tmp_mount_point[MAXPATHLEN];
- unsigned long mnt_flags;
- unsigned int orig_failed_decrypt_count;
- char encrypted_state[PROPERTY_VALUE_MAX];
- int rc;
-
- property_get("ro.crypto.state", encrypted_state, "");
- if ( master_key_saved || strcmp(encrypted_state, "encrypted") ) {
- printf("encrypted fs already validated or not running with encryption, aborting %s\n", encrypted_state);
- return -1;
- }
-
- if (get_orig_mount_parms(mount_point, fs_type, real_blkdev, &mnt_flags, fs_options)) {
- printf("Error reading original mount parms for mount point %s\n", mount_point);
- return -1;
- }
-
- if (get_crypt_ftr_and_key(real_blkdev, &crypt_ftr, encrypted_master_key, salt)) {
- printf("Error getting crypt footer and key\n");
- return -1;
- }
-
- //printf("crypt_ftr->fs_size = %lld\n", crypt_ftr.fs_size);
- orig_failed_decrypt_count = crypt_ftr.failed_decrypt_count;
-
- if (! (crypt_ftr.flags & CRYPT_MNT_KEY_UNENCRYPTED) ) {
- decrypt_master_key(passwd, salt, encrypted_master_key, decrypted_master_key);
- }
-
- if (create_crypto_blk_dev(&crypt_ftr, decrypted_master_key, real_blkdev,
- crypto_blkdev, label)) {
- printf("Error creating decrypted block device\n");
- return -1;
- }
-
- /* If init detects an encrypted filesystme, it writes a file for each such
- * encrypted fs into the tmpfs /data filesystem, and then the framework finds those
- * files and passes that data to me */
- /* Create a tmp mount point to try mounting the decryptd fs
- * Since we're here, the mount_point should be a tmpfs filesystem, so make
- * a directory in it to test mount the decrypted filesystem.
- */
- sprintf(tmp_mount_point, "%s/tmp_mnt", mount_point);
- mkdir(tmp_mount_point, 0755);
- if ( mount(crypto_blkdev, tmp_mount_point, fs_type, MS_RDONLY, "") ) {
- printf("Error temp mounting decrypted block device\n");
- delete_crypto_blk_dev(label);
- crypt_ftr.failed_decrypt_count++;
- } else {
- /* Success, so just umount and we'll mount it properly when we restart
- * the framework.
- */
- umount(tmp_mount_point);
- crypt_ftr.failed_decrypt_count = 0;
- }
-
- rmdir(tmp_mount_point);
-
- if (crypt_ftr.failed_decrypt_count) {
- /* We failed to mount the device, so return an error */
- rc = crypt_ftr.failed_decrypt_count;
-
- } else {
- /* Woot! Success! Save the name of the crypto block device
- * so we can mount it when restarting the framework.
- */
- property_set("ro.crypto.fs_crypto_blkdev", crypto_blkdev);
-
- /* Also save a the master key so we can reencrypted the key
- * the key when we want to change the password on it.
- */
- memcpy(saved_master_key, decrypted_master_key, sizeof(saved_master_key));
- saved_data_blkdev = strdup(real_blkdev);
- saved_mount_point = strdup(mount_point);
- master_key_saved = 1;
- rc = 0;
- }
-
- return rc;
-}
-
-static int test_mount_encrypted_fs_sd(
- const char *passwd, const char *mount_point, const char *label)
-{
- char real_blkdev[MAXPATHLEN];
- char crypto_blkdev[MAXPATHLEN];
- char tmp_mount_point[MAXPATHLEN];
- char encrypted_state[PROPERTY_VALUE_MAX];
- char fs_type[PROPERTY_VALUE_MAX];
- int rc;
-
- property_get("ro.crypto.state", encrypted_state, "");
- if ( !master_key_saved || strcmp(encrypted_state, "encrypted") ) {
- printf("encrypted fs not yet validated or not running with encryption, aborting\n");
- return -1;
- }
-
- if (get_orig_mount_parms_sd(mount_point, fs_type, real_blkdev)) {
- printf("Error reading original mount parms for mount point %s\n", mount_point);
- return -1;
- }
-
- rc = cryptfs_setup_volume(label, real_blkdev, crypto_blkdev);
- if(rc){
- printf("Error setting up cryptfs volume %s\n", real_blkdev);
- return -1;
- }
-
- sprintf(tmp_mount_point, "%s/tmp_mnt", mount_point);
- mkdir(tmp_mount_point, 0755);
- if ( mount(crypto_blkdev, tmp_mount_point, fs_type, MS_RDONLY, "") ) {
- printf("Error temp mounting decrypted block device\n");
- delete_crypto_blk_dev(label);
- } else {
- /* Success, so just umount and we'll mount it properly when we restart
- * the framework.
- */
- umount(tmp_mount_point);
-
- property_set("ro.crypto.sd_fs_crypto_blkdev", crypto_blkdev);
- }
-
- rmdir(tmp_mount_point);
-
- return rc;
-}
-
-/*
- * Called by vold when it's asked to mount an encrypted, nonremovable volume.
- * Setup a dm-crypt mapping, use the saved master key from
- * setting up the /data mapping, and return the new device path.
- */
-int cryptfs_setup_volume(const char *label, const char *real_blkdev, char *crypto_blkdev)
-{
- struct crypt_mnt_ftr sd_crypt_ftr;
- unsigned char key[256], salt[32];
- struct stat statbuf;
- int nr_sec, fd, rc;
-
- /* Just want the footer, but gotta get it all */
- get_crypt_ftr_and_key(saved_data_blkdev, &sd_crypt_ftr, key, salt);
-
- /* Update the fs_size field to be the size of the volume */
- fd = open(real_blkdev, O_RDONLY);
- nr_sec = get_blkdev_size(fd);
- close(fd);
- if (nr_sec == 0) {
- SLOGE("Cannot get size of volume %s\n", real_blkdev);
- return -1;
- }
-
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
- if(using_samsung_encryption) {
- if(!access("/efs/essiv", R_OK)){
- strcpy(sd_crypt_ftr.crypto_type_name, "aes-cbc-plain:sha1");
- }
- else if(!access("/efs/cryptprop_essiv", R_OK)){
- strcpy(sd_crypt_ftr.crypto_type_name, "aes-cbc-essiv:sha256");
- }
- }
-#endif
-
- sd_crypt_ftr.fs_size = nr_sec;
- rc = create_crypto_blk_dev(
- &sd_crypt_ftr, saved_master_key, real_blkdev, crypto_blkdev, label);
-
- stat(crypto_blkdev, &statbuf);
-
- return rc;
-}
-
-int cryptfs_crypto_complete(void)
-{
- return -1;
-}
-
-int cryptfs_check_footer(void)
-{
- int rc = -1;
- char fs_type[PROPERTY_VALUE_MAX];
- char real_blkdev[MAXPATHLEN];
- char fs_options[PROPERTY_VALUE_MAX];
- unsigned long mnt_flags;
- struct crypt_mnt_ftr crypt_ftr;
- /* Allocate enough space for a 256 bit key, but we may use less */
- unsigned char encrypted_master_key[256];
- unsigned char salt[SALT_LEN];
-
- if (get_orig_mount_parms(DATA_MNT_POINT, fs_type, real_blkdev, &mnt_flags, fs_options)) {
- printf("Error reading original mount parms for mount point %s\n", DATA_MNT_POINT);
- return rc;
- }
-
- rc = get_crypt_ftr_and_key(real_blkdev, &crypt_ftr, encrypted_master_key, salt);
-
- return rc;
-}
-
-int cryptfs_check_passwd(const char *passwd)
-{
- char pwbuf[256];
- char crypto_blkdev_data[MAXPATHLEN];
- int rc = -1;
-
- strcpy(pwbuf, passwd);
- rc = test_mount_encrypted_fs(pwbuf, DATA_MNT_POINT, "userdata", crypto_blkdev_data);
-
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
- if(using_samsung_encryption) {
-
- int rc2 = 1;
-#ifndef RECOVERY_SDCARD_ON_DATA
-#ifdef TW_INTERNAL_STORAGE_PATH
- // internal storage for non data/media devices
- if(!rc) {
- strcpy(pwbuf, passwd);
- rc2 = test_mount_encrypted_fs_sd(
- pwbuf, EXPAND(TW_INTERNAL_STORAGE_PATH),
- EXPAND(TW_INTERNAL_STORAGE_MOUNT_POINT));
- }
-#endif
-#endif
-#ifdef TW_EXTERNAL_STORAGE_PATH
- printf("Temp mounting /data\n");
- // mount data so mount_ecryptfs_drive can access edk in /data/system/
- rc2 = mount(crypto_blkdev_data, DATA_MNT_POINT, CRYPTO_FS_TYPE, MS_RDONLY, "");
- // external sd
- char decrypt_external[256], external_blkdev[256];
- property_get("ro.crypto.external_encrypted", decrypt_external, "0");
- // Mount the external storage as ecryptfs so that ecryptfs can act as a pass-through
- if (!rc2 && strcmp(decrypt_external, "1") == 0) {
- printf("Mounting external with ecryptfs...\n");
- strcpy(pwbuf, passwd);
- rc2 = mount_ecryptfs_drive(
- pwbuf, EXPAND(TW_EXTERNAL_STORAGE_PATH),
- EXPAND(TW_EXTERNAL_STORAGE_PATH), 0);
- if (rc2 == 0)
- property_set("ro.crypto.external_use_ecryptfs", "1");
- else
- property_set("ro.crypto.external_use_ecryptfs", "0");
- } else {
- printf("Unable to mount external storage with ecryptfs.\n");
- umount(EXPAND(TW_EXTERNAL_STORAGE_PATH));
- }
- umount(DATA_MNT_POINT);
- }
-#endif // #ifdef TW_EXTERNAL_STORAGE_PATH
-#endif // #ifdef TW_INCLUDE_CRYPTO_SAMSUNG
- return rc;
-}
diff --git a/crypto/ics/cryptfs.h b/crypto/ics/cryptfs.h
deleted file mode 100644
index 8c8037659..000000000
--- a/crypto/ics/cryptfs.h
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright (C) 2010 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.
- */
-
-/* This structure starts 16,384 bytes before the end of a hardware
- * partition that is encrypted.
- * Immediately following this structure is the encrypted key.
- * The keysize field tells how long the key is, in bytes.
- * Then there is 32 bytes of padding,
- * Finally there is the salt used with the user password.
- * The salt is fixed at 16 bytes long.
- * Obviously, the filesystem does not include the last 16 kbytes
- * of the partition.
- */
-
-#ifndef __CRYPTFS_H__
-#define __CRYPTFS_H__
-
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
-#include "../libcrypt_samsung/include/libcrypt_samsung.h"
-#endif
-
-#define CRYPT_FOOTER_OFFSET 0x4000
-
-#define MAX_CRYPTO_TYPE_NAME_LEN 64
-
-#define SALT_LEN 16
-#define KEY_TO_SALT_PADDING 32
-
-/* definitions of flags in the structure below */
-#define CRYPT_MNT_KEY_UNENCRYPTED 0x1 /* The key for the partition is not encrypted. */
-#define CRYPT_ENCRYPTION_IN_PROGRESS 0x2 /* Set when starting encryption,
- * clear when done before rebooting */
-
-#ifdef TW_INCLUDE_CRYPTO_SAMSUNG
-#define CRYPT_MNT_MAGIC_SAMSUNG 0xD0B5B1C5
-#endif
-#define CRYPT_MNT_MAGIC 0xD0B5B1C4
-
-#define __le32 unsigned int
-#define __le16 unsigned short int
-
-#pragma pack(1)
-
-struct crypt_mnt_ftr {
- __le32 magic; /* See above */
- __le16 major_version;
- __le16 minor_version;
- __le32 ftr_size; /* in bytes, not including key following */
- __le32 flags; /* See above */
- __le32 keysize; /* in bytes */
- __le32 spare1; /* ignored */
- __le64 fs_size; /* Size of the encrypted fs, in 512 byte sectors */
- __le32 failed_decrypt_count; /* count of # of failed attempts to decrypt and
- mount, set to 0 on successful mount */
- char crypto_type_name[MAX_CRYPTO_TYPE_NAME_LEN]; /* The type of encryption
- needed to decrypt this
- partition, null terminated */
-};
-
-#pragma pack()
-
-
-#ifdef __cplusplus
-extern "C" {
-#endif
- int cryptfs_check_footer(void);
- int cryptfs_check_passwd(const char *pw);
-#ifdef __cplusplus
-}
-#endif
-
-#endif // __CRYPTFS_H__
-
diff --git a/crypto/jb/Android.mk b/crypto/jb/Android.mk
deleted file mode 100644
index 90321d67e..000000000
--- a/crypto/jb/Android.mk
+++ /dev/null
@@ -1,17 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-ifeq ($(TW_INCLUDE_JB_CRYPTO), true)
-include $(CLEAR_VARS)
-
-LOCAL_MODULE := libcryptfsjb
-LOCAL_MODULE_TAGS := eng optional
-LOCAL_CFLAGS :=
-LOCAL_SRC_FILES = cryptfs.c
-LOCAL_C_INCLUDES += \
- system/extras/ext4_utils \
- external/openssl/include \
- $(commands_recovery_local_path)/crypto/scrypt/lib/crypto
-LOCAL_SHARED_LIBRARIES += libc liblog libcutils libcrypto libext4_utils
-LOCAL_STATIC_LIBRARIES += libfs_mgrtwrp libscrypttwrp_static liblogwraptwrp libmincrypttwrp
-
-include $(BUILD_SHARED_LIBRARY)
-endif
diff --git a/crypto/jb/cryptfs.c b/crypto/jb/cryptfs.c
deleted file mode 100644
index f9c0d7489..000000000
--- a/crypto/jb/cryptfs.c
+++ /dev/null
@@ -1,1735 +0,0 @@
-/*
- * Copyright (C) 2010 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.
- */
-
-/* TO DO:
- * 1. Perhaps keep several copies of the encrypted key, in case something
- * goes horribly wrong?
- *
- */
-
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-#include <unistd.h>
-#include <stdio.h>
-#include <sys/ioctl.h>
-#include <linux/dm-ioctl.h>
-#include <libgen.h>
-#include <stdlib.h>
-#include <sys/param.h>
-#include <string.h>
-#include <sys/mount.h>
-#include <openssl/evp.h>
-#include <openssl/sha.h>
-#include <errno.h>
-#include <ext4.h>
-#include <linux/kdev_t.h>
-#include <fs_mgr.h>
-#include "cryptfs.h"
-#define LOG_TAG "Cryptfs"
-#include "cutils/log.h"
-#include "cutils/properties.h"
-#include "cutils/android_reboot.h"
-#include "hardware_legacy/power.h"
-/*#include <logwrap/logwrap.h>
-#include "VolumeManager.h"
-#include "VoldUtil.h"*/
-#include "crypto_scrypt.h"
-
-#define DM_CRYPT_BUF_SIZE 4096
-#define DATA_MNT_POINT "/data"
-
-#define HASH_COUNT 2000
-#define KEY_LEN_BYTES 16
-#define IV_LEN_BYTES 16
-
-#define KEY_IN_FOOTER "footer"
-
-#define EXT4_FS 1
-#define FAT_FS 2
-
-#define TABLE_LOAD_RETRIES 10
-
-char *me = "cryptfs";
-
-static unsigned char saved_master_key[KEY_LEN_BYTES];
-static char *saved_mount_point;
-static int master_key_saved = 0;
-static struct crypt_persist_data *persist_data = NULL;
-
-struct fstab *fstab;
-
-static void cryptfs_reboot(int recovery)
-{
- /*if (recovery) {
- property_set(ANDROID_RB_PROPERTY, "reboot,recovery");
- } else {
- property_set(ANDROID_RB_PROPERTY, "reboot");
- }
- sleep(20);*/
-
- /* Shouldn't get here, reboot should happen before sleep times out */
- return;
-}
-
-static void ioctl_init(struct dm_ioctl *io, size_t dataSize, const char *name, unsigned flags)
-{
- memset(io, 0, dataSize);
- io->data_size = dataSize;
- io->data_start = sizeof(struct dm_ioctl);
- io->version[0] = 4;
- io->version[1] = 0;
- io->version[2] = 0;
- io->flags = flags;
- if (name) {
- strncpy(io->name, name, sizeof(io->name));
- }
-}
-
-/**
- * Gets the default device scrypt parameters for key derivation time tuning.
- * The parameters should lead to about one second derivation time for the
- * given device.
- */
-static void get_device_scrypt_params(struct crypt_mnt_ftr *ftr) {
- const int default_params[] = SCRYPT_DEFAULTS;
- int params[] = SCRYPT_DEFAULTS;
- char paramstr[PROPERTY_VALUE_MAX];
- char *token;
- char *saveptr;
- int i;
-
- property_get(SCRYPT_PROP, paramstr, "");
- if (paramstr[0] != '\0') {
- /*
- * The token we're looking for should be three integers separated by
- * colons (e.g., "12:8:1"). Scan the property to make sure it matches.
- */
- for (i = 0, token = strtok_r(paramstr, ":", &saveptr);
- token != NULL && i < 3;
- i++, token = strtok_r(NULL, ":", &saveptr)) {
- char *endptr;
- params[i] = strtol(token, &endptr, 10);
-
- /*
- * Check that there was a valid number and it's 8-bit. If not,
- * break out and the end check will take the default values.
- */
- if ((*token == '\0') || (*endptr != '\0') || params[i] < 0 || params[i] > 255) {
- break;
- }
- }
-
- /*
- * If there were not enough tokens or a token was malformed (not an
- * integer), it will end up here and the default parameters can be
- * taken.
- */
- if ((i != 3) || (token != NULL)) {
- printf("bad scrypt parameters '%s' should be like '12:8:1'; using defaults", paramstr);
- memcpy(params, default_params, sizeof(params));
- }
- }
-
- ftr->N_factor = params[0];
- ftr->r_factor = params[1];
- ftr->p_factor = params[2];
-}
-
-static unsigned int get_fs_size(char *dev)
-{
- int fd, block_size;
- struct ext4_super_block sb;
- off64_t len;
-
- if ((fd = open(dev, O_RDONLY)) < 0) {
- printf("Cannot open device to get filesystem size ");
- return 0;
- }
-
- if (lseek64(fd, 1024, SEEK_SET) < 0) {
- printf("Cannot seek to superblock");
- return 0;
- }
-
- if (read(fd, &sb, sizeof(sb)) != sizeof(sb)) {
- printf("Cannot read superblock");
- return 0;
- }
-
- close(fd);
-
- block_size = 1024 << sb.s_log_block_size;
- /* compute length in bytes */
- len = ( ((off64_t)sb.s_blocks_count_hi << 32) + sb.s_blocks_count_lo) * block_size;
-
- /* return length in sectors */
- return (unsigned int) (len / 512);
-}
-
-static unsigned int get_blkdev_size(int fd)
-{
- unsigned int nr_sec;
-
- if ( (ioctl(fd, BLKGETSIZE, &nr_sec)) == -1) {
- nr_sec = 0;
- }
-
- return nr_sec;
-}
-
-static int get_crypt_ftr_info(char **metadata_fname, off64_t *off)
-{
- static int cached_data = 0;
- static off64_t cached_off = 0;
- static char cached_metadata_fname[PROPERTY_VALUE_MAX] = "";
- int fd;
- char key_loc[PROPERTY_VALUE_MAX];
- char real_blkdev[PROPERTY_VALUE_MAX];
- unsigned int nr_sec;
- int rc = -1;
-
- if (!cached_data) {
- fs_mgr_get_crypt_info(fstab, key_loc, real_blkdev, sizeof(key_loc));
-
- if (!strcmp(key_loc, KEY_IN_FOOTER)) {
- if ( (fd = open(real_blkdev, O_RDWR)) < 0) {
- printf("Cannot open real block device %s\n", real_blkdev);
- return -1;
- }
-
- if ((nr_sec = get_blkdev_size(fd))) {
- /* If it's an encrypted Android partition, the last 16 Kbytes contain the
- * encryption info footer and key, and plenty of bytes to spare for future
- * growth.
- */
- strlcpy(cached_metadata_fname, real_blkdev, sizeof(cached_metadata_fname));
- cached_off = ((off64_t)nr_sec * 512) - CRYPT_FOOTER_OFFSET;
- cached_data = 1;
- } else {
- printf("Cannot get size of block device %s\n", real_blkdev);
- }
- close(fd);
- } else {
- strlcpy(cached_metadata_fname, key_loc, sizeof(cached_metadata_fname));
- cached_off = 0;
- cached_data = 1;
- }
- }
-
- if (cached_data) {
- if (metadata_fname) {
- *metadata_fname = cached_metadata_fname;
- }
- if (off) {
- *off = cached_off;
- }
- rc = 0;
- }
-
- return rc;
-}
-
-/* key or salt can be NULL, in which case just skip writing that value. Useful to
- * update the failed mount count but not change the key.
- */
-static int put_crypt_ftr_and_key(struct crypt_mnt_ftr *crypt_ftr)
-{
- int fd;
- unsigned int nr_sec, cnt;
- /* starting_off is set to the SEEK_SET offset
- * where the crypto structure starts
- */
- off64_t starting_off;
- int rc = -1;
- char *fname = NULL;
- struct stat statbuf;
-
- if (get_crypt_ftr_info(&fname, &starting_off)) {
- printf("Unable to get crypt_ftr_info\n");
- return -1;
- }
- if (fname[0] != '/') {
- printf("Unexpected value for crypto key location\n");
- return -1;
- }
- if ( (fd = open(fname, O_RDWR | O_CREAT, 0600)) < 0) {
- printf("Cannot open footer file %s for put\n", fname);
- return -1;
- }
-
- /* Seek to the start of the crypt footer */
- if (lseek64(fd, starting_off, SEEK_SET) == -1) {
- printf("Cannot seek to real block device footer\n");
- goto errout;
- }
-
- if ((cnt = write(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr))) != sizeof(struct crypt_mnt_ftr)) {
- printf("Cannot write real block device footer\n");
- goto errout;
- }
-
- fstat(fd, &statbuf);
- /* If the keys are kept on a raw block device, do not try to truncate it. */
- if (S_ISREG(statbuf.st_mode)) {
- if (ftruncate(fd, 0x4000)) {
- printf("Cannot set footer file size\n", fname);
- goto errout;
- }
- }
-
- /* Success! */
- rc = 0;
-
-errout:
- close(fd);
- return rc;
-
-}
-
-static inline int unix_read(int fd, void* buff, int len)
-{
- return TEMP_FAILURE_RETRY(read(fd, buff, len));
-}
-
-static inline int unix_write(int fd, const void* buff, int len)
-{
- return TEMP_FAILURE_RETRY(write(fd, buff, len));
-}
-
-static void init_empty_persist_data(struct crypt_persist_data *pdata, int len)
-{
- memset(pdata, 0, len);
- pdata->persist_magic = PERSIST_DATA_MAGIC;
- pdata->persist_valid_entries = 0;
-}
-
-/* A routine to update the passed in crypt_ftr to the lastest version.
- * fd is open read/write on the device that holds the crypto footer and persistent
- * data, crypt_ftr is a pointer to the struct to be updated, and offset is the
- * absolute offset to the start of the crypt_mnt_ftr on the passed in fd.
- */
-static void upgrade_crypt_ftr(int fd, struct crypt_mnt_ftr *crypt_ftr, off64_t offset)
-{
- int orig_major = crypt_ftr->major_version;
- int orig_minor = crypt_ftr->minor_version;
- return; // in recovery we don't want to upgrade
- if ((crypt_ftr->major_version == 1) && (crypt_ftr->minor_version == 0)) {
- struct crypt_persist_data *pdata;
- off64_t pdata_offset = offset + CRYPT_FOOTER_TO_PERSIST_OFFSET;
-
- printf("upgrading crypto footer to 1.1");
-
- pdata = malloc(CRYPT_PERSIST_DATA_SIZE);
- if (pdata == NULL) {
- printf("Cannot allocate persisent data\n");
- return;
- }
- memset(pdata, 0, CRYPT_PERSIST_DATA_SIZE);
-
- /* Need to initialize the persistent data area */
- if (lseek64(fd, pdata_offset, SEEK_SET) == -1) {
- printf("Cannot seek to persisent data offset\n");
- return;
- }
- /* Write all zeros to the first copy, making it invalid */
- unix_write(fd, pdata, CRYPT_PERSIST_DATA_SIZE);
-
- /* Write a valid but empty structure to the second copy */
- init_empty_persist_data(pdata, CRYPT_PERSIST_DATA_SIZE);
- unix_write(fd, pdata, CRYPT_PERSIST_DATA_SIZE);
-
- /* Update the footer */
- crypt_ftr->persist_data_size = CRYPT_PERSIST_DATA_SIZE;
- crypt_ftr->persist_data_offset[0] = pdata_offset;
- crypt_ftr->persist_data_offset[1] = pdata_offset + CRYPT_PERSIST_DATA_SIZE;
- crypt_ftr->minor_version = 1;
- }
-
- if ((crypt_ftr->major_version == 1) && (crypt_ftr->minor_version)) {
- printf("upgrading crypto footer to 1.2");
- crypt_ftr->kdf_type = KDF_PBKDF2;
- get_device_scrypt_params(crypt_ftr);
- crypt_ftr->minor_version = 2;
- }
-
- if ((orig_major != crypt_ftr->major_version) || (orig_minor != crypt_ftr->minor_version)) {
- if (lseek64(fd, offset, SEEK_SET) == -1) {
- printf("Cannot seek to crypt footer\n");
- return;
- }
- unix_write(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr));
- }
-}
-
-
-static int get_crypt_ftr_and_key(struct crypt_mnt_ftr *crypt_ftr)
-{
- int fd;
- unsigned int nr_sec, cnt;
- off64_t starting_off;
- int rc = -1;
- char *fname = NULL;
- struct stat statbuf;
-
- if (get_crypt_ftr_info(&fname, &starting_off)) {
- printf("Unable to get crypt_ftr_info\n");
- return -1;
- }
- if (fname[0] != '/') {
- printf("Unexpected value for crypto key location\n");
- return -1;
- }
- if ( (fd = open(fname, O_RDWR)) < 0) {
- printf("Cannot open footer file %s for get\n", fname);
- return -1;
- }
-
- /* Make sure it's 16 Kbytes in length */
- fstat(fd, &statbuf);
- if (S_ISREG(statbuf.st_mode) && (statbuf.st_size != 0x4000)) {
- printf("footer file %s is not the expected size!\n", fname);
- goto errout;
- }
-
- /* Seek to the start of the crypt footer */
- if (lseek64(fd, starting_off, SEEK_SET) == -1) {
- printf("Cannot seek to real block device footer\n");
- goto errout;
- }
-
- if ( (cnt = read(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr))) != sizeof(struct crypt_mnt_ftr)) {
- printf("Cannot read real block device footer\n");
- goto errout;
- }
-
- if (crypt_ftr->magic != CRYPT_MNT_MAGIC) {
- printf("Bad magic for real block device %s\n", fname);
- goto errout;
- }
-
- if (crypt_ftr->major_version != CURRENT_MAJOR_VERSION) {
- printf("Cannot understand major version %d real block device footer; expected %d\n",
- crypt_ftr->major_version, CURRENT_MAJOR_VERSION);
- goto errout;
- }
-
- if (crypt_ftr->minor_version > CURRENT_MINOR_VERSION) {
- printf("Warning: crypto footer minor version %d, expected <= %d, continuing...\n",
- crypt_ftr->minor_version, CURRENT_MINOR_VERSION);
- }
-
- /* If this is a verion 1.0 crypt_ftr, make it a 1.1 crypt footer, and update the
- * copy on disk before returning.
- */
- /*if (crypt_ftr->minor_version < CURRENT_MINOR_VERSION) {
- upgrade_crypt_ftr(fd, crypt_ftr, starting_off);
- }*/
-
- /* Success! */
- rc = 0;
-
-errout:
- close(fd);
- return rc;
-}
-
-static int validate_persistent_data_storage(struct crypt_mnt_ftr *crypt_ftr)
-{
- if (crypt_ftr->persist_data_offset[0] + crypt_ftr->persist_data_size >
- crypt_ftr->persist_data_offset[1]) {
- printf("Crypt_ftr persist data regions overlap");
- return -1;
- }
-
- if (crypt_ftr->persist_data_offset[0] >= crypt_ftr->persist_data_offset[1]) {
- printf("Crypt_ftr persist data region 0 starts after region 1");
- return -1;
- }
-
- if (((crypt_ftr->persist_data_offset[1] + crypt_ftr->persist_data_size) -
- (crypt_ftr->persist_data_offset[0] - CRYPT_FOOTER_TO_PERSIST_OFFSET)) >
- CRYPT_FOOTER_OFFSET) {
- printf("Persistent data extends past crypto footer");
- return -1;
- }
-
- return 0;
-}
-
-static int load_persistent_data(void)
-{
- struct crypt_mnt_ftr crypt_ftr;
- struct crypt_persist_data *pdata = NULL;
- char encrypted_state[PROPERTY_VALUE_MAX];
- char *fname;
- int found = 0;
- int fd;
- int ret;
- int i;
-
- if (persist_data) {
- /* Nothing to do, we've already loaded or initialized it */
- return 0;
- }
-
-
- /* If not encrypted, just allocate an empty table and initialize it */
- property_get("ro.crypto.state", encrypted_state, "");
- if (strcmp(encrypted_state, "encrypted") ) {
- pdata = malloc(CRYPT_PERSIST_DATA_SIZE);
- if (pdata) {
- init_empty_persist_data(pdata, CRYPT_PERSIST_DATA_SIZE);
- persist_data = pdata;
- return 0;
- }
- return -1;
- }
-
- if(get_crypt_ftr_and_key(&crypt_ftr)) {
- return -1;
- }
-
- if ((crypt_ftr.major_version != 1) || (crypt_ftr.minor_version != 1)) {
- printf("Crypt_ftr version doesn't support persistent data");
- return -1;
- }
-
- if (get_crypt_ftr_info(&fname, NULL)) {
- return -1;
- }
-
- ret = validate_persistent_data_storage(&crypt_ftr);
- if (ret) {
- return -1;
- }
-
- fd = open(fname, O_RDONLY);
- if (fd < 0) {
- printf("Cannot open %s metadata file", fname);
- return -1;
- }
-
- if (persist_data == NULL) {
- pdata = malloc(crypt_ftr.persist_data_size);
- if (pdata == NULL) {
- printf("Cannot allocate memory for persistent data");
- goto err;
- }
- }
-
- for (i = 0; i < 2; i++) {
- if (lseek64(fd, crypt_ftr.persist_data_offset[i], SEEK_SET) < 0) {
- printf("Cannot seek to read persistent data on %s", fname);
- goto err2;
- }
- if (unix_read(fd, pdata, crypt_ftr.persist_data_size) < 0){
- printf("Error reading persistent data on iteration %d", i);
- goto err2;
- }
- if (pdata->persist_magic == PERSIST_DATA_MAGIC) {
- found = 1;
- break;
- }
- }
-
- if (!found) {
- printf("Could not find valid persistent data, creating");
- init_empty_persist_data(pdata, crypt_ftr.persist_data_size);
- }
-
- /* Success */
- persist_data = pdata;
- close(fd);
- return 0;
-
-err2:
- free(pdata);
-
-err:
- close(fd);
- return -1;
-}
-
-static int save_persistent_data(void)
-{
- struct crypt_mnt_ftr crypt_ftr;
- struct crypt_persist_data *pdata;
- char *fname;
- off64_t write_offset;
- off64_t erase_offset;
- int found = 0;
- int fd;
- int ret;
-
- if (persist_data == NULL) {
- printf("No persistent data to save");
- return -1;
- }
-
- if(get_crypt_ftr_and_key(&crypt_ftr)) {
- return -1;
- }
-
- if ((crypt_ftr.major_version != 1) || (crypt_ftr.minor_version != 1)) {
- printf("Crypt_ftr version doesn't support persistent data");
- return -1;
- }
-
- ret = validate_persistent_data_storage(&crypt_ftr);
- if (ret) {
- return -1;
- }
-
- if (get_crypt_ftr_info(&fname, NULL)) {
- return -1;
- }
-
- fd = open(fname, O_RDWR);
- if (fd < 0) {
- printf("Cannot open %s metadata file", fname);
- return -1;
- }
-
- pdata = malloc(crypt_ftr.persist_data_size);
- if (pdata == NULL) {
- printf("Cannot allocate persistant data");
- goto err;
- }
-
- if (lseek64(fd, crypt_ftr.persist_data_offset[0], SEEK_SET) < 0) {
- printf("Cannot seek to read persistent data on %s", fname);
- goto err2;
- }
-
- if (unix_read(fd, pdata, crypt_ftr.persist_data_size) < 0) {
- printf("Error reading persistent data before save");
- goto err2;
- }
-
- if (pdata->persist_magic == PERSIST_DATA_MAGIC) {
- /* The first copy is the curent valid copy, so write to
- * the second copy and erase this one */
- write_offset = crypt_ftr.persist_data_offset[1];
- erase_offset = crypt_ftr.persist_data_offset[0];
- } else {
- /* The second copy must be the valid copy, so write to
- * the first copy, and erase the second */
- write_offset = crypt_ftr.persist_data_offset[0];
- erase_offset = crypt_ftr.persist_data_offset[1];
- }
-
- /* Write the new copy first, if successful, then erase the old copy */
- if (lseek(fd, write_offset, SEEK_SET) < 0) {
- printf("Cannot seek to write persistent data");
- goto err2;
- }
- if (unix_write(fd, persist_data, crypt_ftr.persist_data_size) ==
- (int) crypt_ftr.persist_data_size) {
- if (lseek(fd, erase_offset, SEEK_SET) < 0) {
- printf("Cannot seek to erase previous persistent data");
- goto err2;
- }
- fsync(fd);
- memset(pdata, 0, crypt_ftr.persist_data_size);
- if (unix_write(fd, pdata, crypt_ftr.persist_data_size) !=
- (int) crypt_ftr.persist_data_size) {
- printf("Cannot write to erase previous persistent data");
- goto err2;
- }
- fsync(fd);
- } else {
- printf("Cannot write to save persistent data");
- goto err2;
- }
-
- /* Success */
- free(pdata);
- close(fd);
- return 0;
-
-err2:
- free(pdata);
-err:
- close(fd);
- return -1;
-}
-
-/* Convert a binary key of specified length into an ascii hex string equivalent,
- * without the leading 0x and with null termination
- */
-void convert_key_to_hex_ascii(unsigned char *master_key, unsigned int keysize,
- char *master_key_ascii)
-{
- unsigned int i, a;
- unsigned char nibble;
-
- for (i=0, a=0; i<keysize; i++, a+=2) {
- /* For each byte, write out two ascii hex digits */
- nibble = (master_key[i] >> 4) & 0xf;
- master_key_ascii[a] = nibble + (nibble > 9 ? 0x37 : 0x30);
-
- nibble = master_key[i] & 0xf;
- master_key_ascii[a+1] = nibble + (nibble > 9 ? 0x37 : 0x30);
- }
-
- /* Add the null termination */
- master_key_ascii[a] = '\0';
-
-}
-
-static int load_crypto_mapping_table(struct crypt_mnt_ftr *crypt_ftr, unsigned char *master_key,
- char *real_blk_name, const char *name, int fd,
- char *extra_params)
-{
- char buffer[DM_CRYPT_BUF_SIZE];
- struct dm_ioctl *io;
- struct dm_target_spec *tgt;
- char *crypt_params;
- char master_key_ascii[129]; /* Large enough to hold 512 bit key and null */
- int i;
-
- io = (struct dm_ioctl *) buffer;
-
- /* Load the mapping table for this device */
- tgt = (struct dm_target_spec *) &buffer[sizeof(struct dm_ioctl)];
-
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- io->target_count = 1;
- tgt->status = 0;
- tgt->sector_start = 0;
- tgt->length = crypt_ftr->fs_size;
- strcpy(tgt->target_type, "crypt");
-
- crypt_params = buffer + sizeof(struct dm_ioctl) + sizeof(struct dm_target_spec);
- convert_key_to_hex_ascii(master_key, crypt_ftr->keysize, master_key_ascii);
- sprintf(crypt_params, "%s %s 0 %s 0 %s", crypt_ftr->crypto_type_name,
- master_key_ascii, real_blk_name, extra_params);
- crypt_params += strlen(crypt_params) + 1;
- crypt_params = (char *) (((unsigned long)crypt_params + 7) & ~8); /* Align to an 8 byte boundary */
- tgt->next = crypt_params - buffer;
-
- for (i = 0; i < TABLE_LOAD_RETRIES; i++) {
- if (! ioctl(fd, DM_TABLE_LOAD, io)) {
- break;
- }
- usleep(500000);
- }
-
- if (i == TABLE_LOAD_RETRIES) {
- /* We failed to load the table, return an error */
- return -1;
- } else {
- return i + 1;
- }
-}
-
-
-static int get_dm_crypt_version(int fd, const char *name, int *version)
-{
- char buffer[DM_CRYPT_BUF_SIZE];
- struct dm_ioctl *io;
- struct dm_target_versions *v;
- int i;
-
- io = (struct dm_ioctl *) buffer;
-
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
-
- if (ioctl(fd, DM_LIST_VERSIONS, io)) {
- return -1;
- }
-
- /* Iterate over the returned versions, looking for name of "crypt".
- * When found, get and return the version.
- */
- v = (struct dm_target_versions *) &buffer[sizeof(struct dm_ioctl)];
- while (v->next) {
- if (! strcmp(v->name, "crypt")) {
- /* We found the crypt driver, return the version, and get out */
- version[0] = v->version[0];
- version[1] = v->version[1];
- version[2] = v->version[2];
- return 0;
- }
- v = (struct dm_target_versions *)(((char *)v) + v->next);
- }
-
- return -1;
-}
-
-static int create_crypto_blk_dev(struct crypt_mnt_ftr *crypt_ftr, unsigned char *master_key,
- char *real_blk_name, char *crypto_blk_name, const char *name)
-{
- char buffer[DM_CRYPT_BUF_SIZE];
- char master_key_ascii[129]; /* Large enough to hold 512 bit key and null */
- char *crypt_params;
- struct dm_ioctl *io;
- struct dm_target_spec *tgt;
- unsigned int minor;
- int fd;
- int i;
- int retval = -1;
- int version[3];
- char *extra_params;
- int load_count;
-
- if ((fd = open("/dev/device-mapper", O_RDWR)) < 0 ) {
- printf("Cannot open device-mapper\n");
- goto errout;
- }
-
- io = (struct dm_ioctl *) buffer;
-
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- if (ioctl(fd, DM_DEV_CREATE, io)) {
- printf("Cannot create dm-crypt device\n");
- goto errout;
- }
-
- /* Get the device status, in particular, the name of it's device file */
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- if (ioctl(fd, DM_DEV_STATUS, io)) {
- printf("Cannot retrieve dm-crypt device status\n");
- goto errout;
- }
- minor = (io->dev & 0xff) | ((io->dev >> 12) & 0xfff00);
- snprintf(crypto_blk_name, MAXPATHLEN, "/dev/block/dm-%u", minor);
-
- extra_params = "";
- if (! get_dm_crypt_version(fd, name, version)) {
- /* Support for allow_discards was added in version 1.11.0 */
- if ((version[0] >= 2) ||
- ((version[0] == 1) && (version[1] >= 11))) {
- extra_params = "1 allow_discards";
- printf("Enabling support for allow_discards in dmcrypt.\n");
- }
- }
-
- load_count = load_crypto_mapping_table(crypt_ftr, master_key, real_blk_name, name,
- fd, extra_params);
- if (load_count < 0) {
- printf("Cannot load dm-crypt mapping table.\n");
- goto errout;
- } else if (load_count > 1) {
- printf("Took %d tries to load dmcrypt table.\n", load_count);
- }
-
- /* Resume this device to activate it */
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
-
- if (ioctl(fd, DM_DEV_SUSPEND, io)) {
- printf("Cannot resume the dm-crypt device\n");
- goto errout;
- }
-
- /* We made it here with no errors. Woot! */
- retval = 0;
-
-errout:
- close(fd); /* If fd is <0 from a failed open call, it's safe to just ignore the close error */
-
- return retval;
-}
-
-static int delete_crypto_blk_dev(char *name)
-{
- int fd;
- char buffer[DM_CRYPT_BUF_SIZE];
- struct dm_ioctl *io;
- int retval = -1;
-
- if ((fd = open("/dev/device-mapper", O_RDWR)) < 0 ) {
- printf("Cannot open device-mapper\n");
- goto errout;
- }
-
- io = (struct dm_ioctl *) buffer;
-
- ioctl_init(io, DM_CRYPT_BUF_SIZE, name, 0);
- if (ioctl(fd, DM_DEV_REMOVE, io)) {
- printf("Cannot remove dm-crypt device\n");
- goto errout;
- }
-
- /* We made it here with no errors. Woot! */
- retval = 0;
-
-errout:
- close(fd); /* If fd is <0 from a failed open call, it's safe to just ignore the close error */
-
- return retval;
-
-}
-
-static void pbkdf2(char *passwd, unsigned char *salt, unsigned char *ikey, void *params) {
- /* Turn the password into a key and IV that can decrypt the master key */
- PKCS5_PBKDF2_HMAC_SHA1(passwd, strlen(passwd), salt, SALT_LEN,
- HASH_COUNT, KEY_LEN_BYTES+IV_LEN_BYTES, ikey);
-}
-
-static void scrypt(char *passwd, unsigned char *salt, unsigned char *ikey, void *params) {
- struct crypt_mnt_ftr *ftr = (struct crypt_mnt_ftr *) params;
-
- int N = 1 << ftr->N_factor;
- int r = 1 << ftr->r_factor;
- int p = 1 << ftr->p_factor;
-
- /* Turn the password into a key and IV that can decrypt the master key */
- crypto_scrypt((unsigned char *) passwd, strlen(passwd), salt, SALT_LEN, N, r, p, ikey,
- KEY_LEN_BYTES + IV_LEN_BYTES);
-}
-
-static int encrypt_master_key(char *passwd, unsigned char *salt,
- unsigned char *decrypted_master_key,
- unsigned char *encrypted_master_key,
- struct crypt_mnt_ftr *crypt_ftr)
-{
- unsigned char ikey[32+32] = { 0 }; /* Big enough to hold a 256 bit key and 256 bit IV */
- EVP_CIPHER_CTX e_ctx;
- int encrypted_len, final_len;
-
- /* Turn the password into a key and IV that can decrypt the master key */
- get_device_scrypt_params(crypt_ftr);
- scrypt(passwd, salt, ikey, crypt_ftr);
-
- /* Initialize the decryption engine */
- if (! EVP_EncryptInit(&e_ctx, EVP_aes_128_cbc(), ikey, ikey+KEY_LEN_BYTES)) {
- printf("EVP_EncryptInit failed\n");
- return -1;
- }
- EVP_CIPHER_CTX_set_padding(&e_ctx, 0); /* Turn off padding as our data is block aligned */
-
- /* Encrypt the master key */
- if (! EVP_EncryptUpdate(&e_ctx, encrypted_master_key, &encrypted_len,
- decrypted_master_key, KEY_LEN_BYTES)) {
- printf("EVP_EncryptUpdate failed\n");
- return -1;
- }
- if (! EVP_EncryptFinal(&e_ctx, encrypted_master_key + encrypted_len, &final_len)) {
- printf("EVP_EncryptFinal failed\n");
- return -1;
- }
-
- if (encrypted_len + final_len != KEY_LEN_BYTES) {
- printf("EVP_Encryption length check failed with %d, %d bytes\n", encrypted_len, final_len);
- return -1;
- } else {
- return 0;
- }
-}
-
-static int decrypt_master_key(char *passwd, unsigned char *salt,
- unsigned char *encrypted_master_key,
- unsigned char *decrypted_master_key,
- kdf_func kdf, void *kdf_params)
-{
- unsigned char ikey[32+32] = { 0 }; /* Big enough to hold a 256 bit key and 256 bit IV */
- EVP_CIPHER_CTX d_ctx;
- int decrypted_len, final_len;
-
- /* Turn the password into a key and IV that can decrypt the master key */
- kdf(passwd, salt, ikey, kdf_params);
-
- /* Initialize the decryption engine */
- if (! EVP_DecryptInit(&d_ctx, EVP_aes_128_cbc(), ikey, ikey+KEY_LEN_BYTES)) {
- return -1;
- }
- EVP_CIPHER_CTX_set_padding(&d_ctx, 0); /* Turn off padding as our data is block aligned */
- /* Decrypt the master key */
- if (! EVP_DecryptUpdate(&d_ctx, decrypted_master_key, &decrypted_len,
- encrypted_master_key, KEY_LEN_BYTES)) {
- return -1;
- }
- if (! EVP_DecryptFinal(&d_ctx, decrypted_master_key + decrypted_len, &final_len)) {
- return -1;
- }
-
- if (decrypted_len + final_len != KEY_LEN_BYTES) {
- return -1;
- } else {
- return 0;
- }
-}
-
-static void get_kdf_func(struct crypt_mnt_ftr *ftr, kdf_func *kdf, void** kdf_params)
-{
- if (ftr->kdf_type == KDF_SCRYPT) {
- *kdf = scrypt;
- *kdf_params = ftr;
- } else {
- *kdf = pbkdf2;
- *kdf_params = NULL;
- }
-}
-
-static int decrypt_master_key_and_upgrade(char *passwd, unsigned char *decrypted_master_key,
- struct crypt_mnt_ftr *crypt_ftr)
-{
- kdf_func kdf;
- void *kdf_params;
- int ret;
-
- get_kdf_func(crypt_ftr, &kdf, &kdf_params);
- ret = decrypt_master_key(passwd, crypt_ftr->salt, crypt_ftr->master_key, decrypted_master_key, kdf,
- kdf_params);
- if (ret != 0) {
- printf("failure decrypting master key");
- return ret;
- }
-
- /*
- * Upgrade if we're not using the latest KDF.
- */
- /*if (crypt_ftr->kdf_type != KDF_SCRYPT) {
- crypt_ftr->kdf_type = KDF_SCRYPT;
- encrypt_master_key(passwd, crypt_ftr->salt, decrypted_master_key, crypt_ftr->master_key,
- crypt_ftr);
- put_crypt_ftr_and_key(crypt_ftr);
- }*/
-
- return ret;
-}
-
-static int create_encrypted_random_key(char *passwd, unsigned char *master_key, unsigned char *salt,
- struct crypt_mnt_ftr *crypt_ftr) {
- int fd;
- unsigned char key_buf[KEY_LEN_BYTES];
- EVP_CIPHER_CTX e_ctx;
- int encrypted_len, final_len;
-
- /* Get some random bits for a key */
- fd = open("/dev/urandom", O_RDONLY);
- read(fd, key_buf, sizeof(key_buf));
- read(fd, salt, SALT_LEN);
- close(fd);
-
- /* Now encrypt it with the password */
- return encrypt_master_key(passwd, salt, key_buf, master_key, crypt_ftr);
-}
-
-static int wait_and_unmount(char *mountpoint)
-{
- int i, rc;
-#define WAIT_UNMOUNT_COUNT 20
-
- /* Now umount the tmpfs filesystem */
- for (i=0; i<WAIT_UNMOUNT_COUNT; i++) {
- if (umount(mountpoint)) {
- if (errno == EINVAL) {
- /* EINVAL is returned if the directory is not a mountpoint,
- * i.e. there is no filesystem mounted there. So just get out.
- */
- break;
- }
- sleep(1);
- i++;
- } else {
- break;
- }
- }
-
- if (i < WAIT_UNMOUNT_COUNT) {
- printf("unmounting %s succeeded\n", mountpoint);
- rc = 0;
- } else {
- printf("unmounting %s failed\n", mountpoint);
- rc = -1;
- }
-
- return rc;
-}
-
-#define DATA_PREP_TIMEOUT 200
-static int prep_data_fs(void)
-{
- int i;
-
- /* Do the prep of the /data filesystem */
- property_set("vold.post_fs_data_done", "0");
- property_set("vold.decrypt", "trigger_post_fs_data");
- printf("Just triggered post_fs_data\n");
-
- /* Wait a max of 50 seconds, hopefully it takes much less */
- for (i=0; i<DATA_PREP_TIMEOUT; i++) {
- char p[PROPERTY_VALUE_MAX];
-
- property_get("vold.post_fs_data_done", p, "0");
- if (*p == '1') {
- break;
- } else {
- usleep(250000);
- }
- }
- if (i == DATA_PREP_TIMEOUT) {
- /* Ugh, we failed to prep /data in time. Bail. */
- printf("post_fs_data timed out!\n");
- return -1;
- } else {
- printf("post_fs_data done\n");
- return 0;
- }
-}
-
-int cryptfs_restart(void)
-{
- char fs_type[32];
- char real_blkdev[MAXPATHLEN];
- char crypto_blkdev[MAXPATHLEN];
- char fs_options[256];
- unsigned long mnt_flags;
- struct stat statbuf;
- int rc = -1, i;
- static int restart_successful = 0;
-
- /* Validate that it's OK to call this routine */
- if (! master_key_saved) {
- printf("Encrypted filesystem not validated, aborting");
- return -1;
- }
-
- if (restart_successful) {
- printf("System already restarted with encrypted disk, aborting");
- return -1;
- }
-
- /* Here is where we shut down the framework. The init scripts
- * start all services in one of three classes: core, main or late_start.
- * On boot, we start core and main. Now, we stop main, but not core,
- * as core includes vold and a few other really important things that
- * we need to keep running. Once main has stopped, we should be able
- * to umount the tmpfs /data, then mount the encrypted /data.
- * We then restart the class main, and also the class late_start.
- * At the moment, I've only put a few things in late_start that I know
- * are not needed to bring up the framework, and that also cause problems
- * with unmounting the tmpfs /data, but I hope to add add more services
- * to the late_start class as we optimize this to decrease the delay
- * till the user is asked for the password to the filesystem.
- */
-
- /* The init files are setup to stop the class main when vold.decrypt is
- * set to trigger_reset_main.
- */
- property_set("vold.decrypt", "trigger_reset_main");
- printf("Just asked init to shut down class main\n");
-
- /* Ugh, shutting down the framework is not synchronous, so until it
- * can be fixed, this horrible hack will wait a moment for it all to
- * shut down before proceeding. Without it, some devices cannot
- * restart the graphics services.
- */
- sleep(2);
-
- /* Now that the framework is shutdown, we should be able to umount()
- * the tmpfs filesystem, and mount the real one.
- */
-
- property_get("ro.crypto.fs_crypto_blkdev", crypto_blkdev, "");
- if (strlen(crypto_blkdev) == 0) {
- printf("fs_crypto_blkdev not set\n");
- return -1;
- }
-
- if (! (rc = wait_and_unmount(DATA_MNT_POINT)) ) {
- /* If that succeeded, then mount the decrypted filesystem */
- fs_mgr_do_mount(fstab, DATA_MNT_POINT, crypto_blkdev, 0);
-
- property_set("vold.decrypt", "trigger_load_persist_props");
- /* Create necessary paths on /data */
- if (prep_data_fs()) {
- return -1;
- }
-
- /* startup service classes main and late_start */
- property_set("vold.decrypt", "trigger_restart_framework");
- printf("Just triggered restart_framework\n");
-
- /* Give it a few moments to get started */
- sleep(1);
- }
-
- if (rc == 0) {
- restart_successful = 1;
- }
-
- return rc;
-}
-
-static int do_crypto_complete(char *mount_point)
-{
- struct crypt_mnt_ftr crypt_ftr;
- char encrypted_state[PROPERTY_VALUE_MAX];
- char key_loc[PROPERTY_VALUE_MAX];
-
- property_get("ro.crypto.state", encrypted_state, "");
- if (strcmp(encrypted_state, "encrypted") ) {
- printf("not running with encryption, aborting");
- return 1;
- }
-
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- fs_mgr_get_crypt_info(fstab, key_loc, 0, sizeof(key_loc));
-
- /*
- * Only report this error if key_loc is a file and it exists.
- * If the device was never encrypted, and /data is not mountable for
- * some reason, returning 1 should prevent the UI from presenting the
- * a "enter password" screen, or worse, a "press button to wipe the
- * device" screen.
- */
- if ((key_loc[0] == '/') && (access("key_loc", F_OK) == -1)) {
- printf("master key file does not exist, aborting");
- return 1;
- } else {
- printf("Error getting crypt footer and key\n");
- return -1;
- }
- }
-
- if (crypt_ftr.flags & CRYPT_ENCRYPTION_IN_PROGRESS) {
- printf("Encryption process didn't finish successfully\n");
- return -2; /* -2 is the clue to the UI that there is no usable data on the disk,
- * and give the user an option to wipe the disk */
- }
-
- /* We passed the test! We shall diminish, and return to the west */
- return 0;
-}
-
-static int test_mount_encrypted_fs(char *passwd, char *mount_point, char *label)
-{
- struct crypt_mnt_ftr crypt_ftr;
- /* Allocate enough space for a 256 bit key, but we may use less */
- unsigned char decrypted_master_key[32];
- char crypto_blkdev[MAXPATHLEN];
- char real_blkdev[MAXPATHLEN];
- char tmp_mount_point[64];
- unsigned int orig_failed_decrypt_count;
- char encrypted_state[PROPERTY_VALUE_MAX];
- int rc;
- kdf_func kdf;
- void *kdf_params;
-
- property_get("ro.crypto.state", encrypted_state, "");
- if ( master_key_saved || strcmp(encrypted_state, "encrypted") ) {
- printf("encrypted fs already validated or not running with encryption, aborting");
- return -1;
- }
-
- fs_mgr_get_crypt_info(fstab, 0, real_blkdev, sizeof(real_blkdev));
-
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Error getting crypt footer and key\n");
- return -1;
- }
-
- printf("crypt_ftr->fs_size = %lld\n", crypt_ftr.fs_size);
- orig_failed_decrypt_count = crypt_ftr.failed_decrypt_count;
-
- if (! (crypt_ftr.flags & CRYPT_MNT_KEY_UNENCRYPTED) ) {
- decrypt_master_key_and_upgrade(passwd, decrypted_master_key, &crypt_ftr);
- }
-
- if (create_crypto_blk_dev(&crypt_ftr, decrypted_master_key,
- real_blkdev, crypto_blkdev, label)) {
- printf("Error creating decrypted block device\n");
- return -1;
- }
-
- /* If init detects an encrypted filesystem, it writes a file for each such
- * encrypted fs into the tmpfs /data filesystem, and then the framework finds those
- * files and passes that data to me */
- /* Create a tmp mount point to try mounting the decryptd fs
- * Since we're here, the mount_point should be a tmpfs filesystem, so make
- * a directory in it to test mount the decrypted filesystem.
- */
- sprintf(tmp_mount_point, "%s/tmp_mnt", mount_point);
- mkdir(tmp_mount_point, 0755);
- if (fs_mgr_do_mount(fstab, DATA_MNT_POINT, crypto_blkdev, tmp_mount_point)) {
- printf("Error temp mounting decrypted block device\n");
- delete_crypto_blk_dev(label);
- crypt_ftr.failed_decrypt_count++;
- } else {
- /* Success, so just umount and we'll mount it properly when we restart
- * the framework.
- */
- umount(tmp_mount_point);
- crypt_ftr.failed_decrypt_count = 0;
- }
-
- if (orig_failed_decrypt_count != crypt_ftr.failed_decrypt_count) {
- put_crypt_ftr_and_key(&crypt_ftr);
- }
-
- if (crypt_ftr.failed_decrypt_count) {
- /* We failed to mount the device, so return an error */
- rc = crypt_ftr.failed_decrypt_count;
-
- } else {
- /* Woot! Success! Save the name of the crypto block device
- * so we can mount it when restarting the framework.
- */
- property_set("ro.crypto.fs_crypto_blkdev", crypto_blkdev);
-
- /* Also save a the master key so we can reencrypted the key
- * the key when we want to change the password on it.
- */
- memcpy(saved_master_key, decrypted_master_key, KEY_LEN_BYTES);
- saved_mount_point = strdup(mount_point);
- master_key_saved = 1;
- rc = 0;
- }
-
- return rc;
-}
-
-/* Called by vold when it wants to undo the crypto mapping of a volume it
- * manages. This is usually in response to a factory reset, when we want
- * to undo the crypto mapping so the volume is formatted in the clear.
- */
-int cryptfs_revert_volume(const char *label)
-{
- return delete_crypto_blk_dev((char *)label);
-}
-
-/*
- * Called by vold when it's asked to mount an encrypted, nonremovable volume.
- * Setup a dm-crypt mapping, use the saved master key from
- * setting up the /data mapping, and return the new device path.
- */
-int cryptfs_setup_volume(const char *label, int major, int minor,
- char *crypto_sys_path, unsigned int max_path,
- int *new_major, int *new_minor)
-{
- char real_blkdev[MAXPATHLEN], crypto_blkdev[MAXPATHLEN];
- struct crypt_mnt_ftr sd_crypt_ftr;
- struct stat statbuf;
- int nr_sec, fd;
-
- sprintf(real_blkdev, "/dev/block/vold/%d:%d", major, minor);
-
- get_crypt_ftr_and_key(&sd_crypt_ftr);
-
- /* Update the fs_size field to be the size of the volume */
- fd = open(real_blkdev, O_RDONLY);
- nr_sec = get_blkdev_size(fd);
- close(fd);
- if (nr_sec == 0) {
- printf("Cannot get size of volume %s\n", real_blkdev);
- return -1;
- }
-
- sd_crypt_ftr.fs_size = nr_sec;
- create_crypto_blk_dev(&sd_crypt_ftr, saved_master_key, real_blkdev,
- crypto_blkdev, label);
-
- stat(crypto_blkdev, &statbuf);
- *new_major = MAJOR(statbuf.st_rdev);
- *new_minor = MINOR(statbuf.st_rdev);
-
- /* Create path to sys entry for this block device */
- snprintf(crypto_sys_path, max_path, "/devices/virtual/block/%s", strrchr(crypto_blkdev, '/')+1);
-
- return 0;
-}
-
-int cryptfs_crypto_complete(void)
-{
- return do_crypto_complete("/data");
-}
-
-#define FSTAB_PREFIX "/fstab."
-
-int cryptfs_check_footer(void)
-{
- int rc = -1;
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
- char propbuf[PROPERTY_VALUE_MAX];
- struct crypt_mnt_ftr crypt_ftr;
-
- property_get("ro.hardware", propbuf, "");
- snprintf(fstab_filename, sizeof(fstab_filename), FSTAB_PREFIX"%s", propbuf);
-
- fstab = fs_mgr_read_fstab(fstab_filename);
- if (!fstab) {
- printf("failed to open %s\n", fstab_filename);
- return -1;
- }
-
- rc = get_crypt_ftr_and_key(&crypt_ftr);
-
- return rc;
-}
-
-int cryptfs_check_passwd(char *passwd)
-{
- int rc = -1;
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
- char propbuf[PROPERTY_VALUE_MAX];
-
- property_get("ro.hardware", propbuf, "");
- snprintf(fstab_filename, sizeof(fstab_filename), FSTAB_PREFIX"%s", propbuf);
-
- fstab = fs_mgr_read_fstab(fstab_filename);
- if (!fstab) {
- printf("failed to open %s\n", fstab_filename);
- return -1;
- }
-
- rc = test_mount_encrypted_fs(passwd, DATA_MNT_POINT, "userdata");
-
- return rc;
-}
-
-int cryptfs_verify_passwd(char *passwd)
-{
- struct crypt_mnt_ftr crypt_ftr;
- /* Allocate enough space for a 256 bit key, but we may use less */
- unsigned char decrypted_master_key[32];
- char encrypted_state[PROPERTY_VALUE_MAX];
- int rc;
-
- property_get("ro.crypto.state", encrypted_state, "");
- if (strcmp(encrypted_state, "encrypted") ) {
- printf("device not encrypted, aborting");
- return -2;
- }
-
- if (!master_key_saved) {
- printf("encrypted fs not yet mounted, aborting");
- return -1;
- }
-
- if (!saved_mount_point) {
- printf("encrypted fs failed to save mount point, aborting");
- return -1;
- }
-
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Error getting crypt footer and key\n");
- return -1;
- }
-
- if (crypt_ftr.flags & CRYPT_MNT_KEY_UNENCRYPTED) {
- /* If the device has no password, then just say the password is valid */
- rc = 0;
- } else {
- decrypt_master_key_and_upgrade(passwd, decrypted_master_key, &crypt_ftr);
- if (!memcmp(decrypted_master_key, saved_master_key, crypt_ftr.keysize)) {
- /* They match, the password is correct */
- rc = 0;
- } else {
- /* If incorrect, sleep for a bit to prevent dictionary attacks */
- sleep(1);
- rc = 1;
- }
- }
-
- return rc;
-}
-
-/* Initialize a crypt_mnt_ftr structure. The keysize is
- * defaulted to 16 bytes, and the filesystem size to 0.
- * Presumably, at a minimum, the caller will update the
- * filesystem size and crypto_type_name after calling this function.
- */
-static void cryptfs_init_crypt_mnt_ftr(struct crypt_mnt_ftr *ftr)
-{
- off64_t off;
-
- memset(ftr, 0, sizeof(struct crypt_mnt_ftr));
- ftr->magic = CRYPT_MNT_MAGIC;
- ftr->major_version = CURRENT_MAJOR_VERSION;
- ftr->minor_version = CURRENT_MINOR_VERSION;
- ftr->ftr_size = sizeof(struct crypt_mnt_ftr);
- ftr->keysize = KEY_LEN_BYTES;
-
- ftr->kdf_type = KDF_SCRYPT;
- get_device_scrypt_params(ftr);
-
- ftr->persist_data_size = CRYPT_PERSIST_DATA_SIZE;
- if (get_crypt_ftr_info(NULL, &off) == 0) {
- ftr->persist_data_offset[0] = off + CRYPT_FOOTER_TO_PERSIST_OFFSET;
- ftr->persist_data_offset[1] = off + CRYPT_FOOTER_TO_PERSIST_OFFSET +
- ftr->persist_data_size;
- }
-}
-
-static int cryptfs_enable_wipe(char *crypto_blkdev, off64_t size, int type)
-{
- return -1;
-}
-
-#define CRYPT_INPLACE_BUFSIZE 4096
-#define CRYPT_SECTORS_PER_BUFSIZE (CRYPT_INPLACE_BUFSIZE / 512)
-static int cryptfs_enable_inplace(char *crypto_blkdev, char *real_blkdev, off64_t size,
- off64_t *size_already_done, off64_t tot_size)
-{
- int realfd, cryptofd;
- char *buf[CRYPT_INPLACE_BUFSIZE];
- int rc = -1;
- off64_t numblocks, i, remainder;
- off64_t one_pct, cur_pct, new_pct;
- off64_t blocks_already_done, tot_numblocks;
-
- if ( (realfd = open(real_blkdev, O_RDONLY)) < 0) {
- printf("Error opening real_blkdev %s for inplace encrypt\n", real_blkdev);
- return -1;
- }
-
- if ( (cryptofd = open(crypto_blkdev, O_WRONLY)) < 0) {
- printf("Error opening crypto_blkdev %s for inplace encrypt\n", crypto_blkdev);
- close(realfd);
- return -1;
- }
-
- /* This is pretty much a simple loop of reading 4K, and writing 4K.
- * The size passed in is the number of 512 byte sectors in the filesystem.
- * So compute the number of whole 4K blocks we should read/write,
- * and the remainder.
- */
- numblocks = size / CRYPT_SECTORS_PER_BUFSIZE;
- remainder = size % CRYPT_SECTORS_PER_BUFSIZE;
- tot_numblocks = tot_size / CRYPT_SECTORS_PER_BUFSIZE;
- blocks_already_done = *size_already_done / CRYPT_SECTORS_PER_BUFSIZE;
-
- printf("Encrypting filesystem in place...");
-
- one_pct = tot_numblocks / 100;
- cur_pct = 0;
- /* process the majority of the filesystem in blocks */
- for (i=0; i<numblocks; i++) {
- new_pct = (i + blocks_already_done) / one_pct;
- if (new_pct > cur_pct) {
- char buf[8];
-
- cur_pct = new_pct;
- snprintf(buf, sizeof(buf), "%lld", cur_pct);
- property_set("vold.encrypt_progress", buf);
- }
- if (unix_read(realfd, buf, CRYPT_INPLACE_BUFSIZE) <= 0) {
- printf("Error reading real_blkdev %s for inplace encrypt\n", crypto_blkdev);
- goto errout;
- }
- if (unix_write(cryptofd, buf, CRYPT_INPLACE_BUFSIZE) <= 0) {
- printf("Error writing crypto_blkdev %s for inplace encrypt\n", crypto_blkdev);
- goto errout;
- }
- }
-
- /* Do any remaining sectors */
- for (i=0; i<remainder; i++) {
- if (unix_read(realfd, buf, 512) <= 0) {
- printf("Error reading rival sectors from real_blkdev %s for inplace encrypt\n", crypto_blkdev);
- goto errout;
- }
- if (unix_write(cryptofd, buf, 512) <= 0) {
- printf("Error writing final sectors to crypto_blkdev %s for inplace encrypt\n", crypto_blkdev);
- goto errout;
- }
- }
-
- *size_already_done += size;
- rc = 0;
-
-errout:
- close(realfd);
- close(cryptofd);
-
- return rc;
-}
-
-#define CRYPTO_ENABLE_WIPE 1
-#define CRYPTO_ENABLE_INPLACE 2
-
-#define FRAMEWORK_BOOT_WAIT 60
-
-static inline int should_encrypt(struct volume_info *volume)
-{
- return (volume->flags & (VOL_ENCRYPTABLE | VOL_NONREMOVABLE)) ==
- (VOL_ENCRYPTABLE | VOL_NONREMOVABLE);
-}
-
-int cryptfs_enable(char *howarg, char *passwd)
-{
- return -1;
-}
-
-int cryptfs_changepw(char *newpw)
-{
- struct crypt_mnt_ftr crypt_ftr;
- unsigned char decrypted_master_key[KEY_LEN_BYTES];
-
- /* This is only allowed after we've successfully decrypted the master key */
- if (! master_key_saved) {
- printf("Key not saved, aborting");
- return -1;
- }
-
- /* get key */
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Error getting crypt footer and key");
- return -1;
- }
-
- encrypt_master_key(newpw, crypt_ftr.salt, saved_master_key, crypt_ftr.master_key, &crypt_ftr);
-
- /* save the key */
- put_crypt_ftr_and_key(&crypt_ftr);
-
- return 0;
-}
-
-static int persist_get_key(char *fieldname, char *value)
-{
- unsigned int i;
-
- if (persist_data == NULL) {
- return -1;
- }
- for (i = 0; i < persist_data->persist_valid_entries; i++) {
- if (!strncmp(persist_data->persist_entry[i].key, fieldname, PROPERTY_KEY_MAX)) {
- /* We found it! */
- strlcpy(value, persist_data->persist_entry[i].val, PROPERTY_VALUE_MAX);
- return 0;
- }
- }
-
- return -1;
-}
-
-static int persist_set_key(char *fieldname, char *value, int encrypted)
-{
- unsigned int i;
- unsigned int num;
- struct crypt_mnt_ftr crypt_ftr;
- unsigned int max_persistent_entries;
- unsigned int dsize;
-
- if (persist_data == NULL) {
- return -1;
- }
-
- /* If encrypted, use the values from the crypt_ftr, otherwise
- * use the values for the current spec.
- */
- if (encrypted) {
- if(get_crypt_ftr_and_key(&crypt_ftr)) {
- return -1;
- }
- dsize = crypt_ftr.persist_data_size;
- } else {
- dsize = CRYPT_PERSIST_DATA_SIZE;
- }
- max_persistent_entries = (dsize - sizeof(struct crypt_persist_data)) /
- sizeof(struct crypt_persist_entry);
-
- num = persist_data->persist_valid_entries;
-
- for (i = 0; i < num; i++) {
- if (!strncmp(persist_data->persist_entry[i].key, fieldname, PROPERTY_KEY_MAX)) {
- /* We found an existing entry, update it! */
- memset(persist_data->persist_entry[i].val, 0, PROPERTY_VALUE_MAX);
- strlcpy(persist_data->persist_entry[i].val, value, PROPERTY_VALUE_MAX);
- return 0;
- }
- }
-
- /* We didn't find it, add it to the end, if there is room */
- if (persist_data->persist_valid_entries < max_persistent_entries) {
- memset(&persist_data->persist_entry[num], 0, sizeof(struct crypt_persist_entry));
- strlcpy(persist_data->persist_entry[num].key, fieldname, PROPERTY_KEY_MAX);
- strlcpy(persist_data->persist_entry[num].val, value, PROPERTY_VALUE_MAX);
- persist_data->persist_valid_entries++;
- return 0;
- }
-
- return -1;
-}
-
-/* Return the value of the specified field. */
-int cryptfs_getfield(char *fieldname, char *value, int len)
-{
- char temp_value[PROPERTY_VALUE_MAX];
- char real_blkdev[MAXPATHLEN];
- /* 0 is success, 1 is not encrypted,
- * -1 is value not set, -2 is any other error
- */
- int rc = -2;
-
- if (persist_data == NULL) {
- load_persistent_data();
- if (persist_data == NULL) {
- printf("Getfield error, cannot load persistent data");
- goto out;
- }
- }
-
- if (!persist_get_key(fieldname, temp_value)) {
- /* We found it, copy it to the caller's buffer and return */
- strlcpy(value, temp_value, len);
- rc = 0;
- } else {
- /* Sadness, it's not there. Return the error */
- rc = -1;
- }
-
-out:
- return rc;
-}
-
-/* Set the value of the specified field. */
-int cryptfs_setfield(char *fieldname, char *value)
-{
- struct crypt_persist_data stored_pdata;
- struct crypt_persist_data *pdata_p;
- struct crypt_mnt_ftr crypt_ftr;
- char encrypted_state[PROPERTY_VALUE_MAX];
- /* 0 is success, -1 is an error */
- int rc = -1;
- int encrypted = 0;
-
- if (persist_data == NULL) {
- load_persistent_data();
- if (persist_data == NULL) {
- printf("Setfield error, cannot load persistent data");
- goto out;
- }
- }
-
- property_get("ro.crypto.state", encrypted_state, "");
- if (!strcmp(encrypted_state, "encrypted") ) {
- encrypted = 1;
- }
-
- if (persist_set_key(fieldname, value, encrypted)) {
- goto out;
- }
-
- /* If we are running encrypted, save the persistent data now */
- if (encrypted) {
- if (save_persistent_data()) {
- printf("Setfield error, cannot save persistent data");
- goto out;
- }
- }
-
- rc = 0;
-
-out:
- return rc;
-}
diff --git a/crypto/jb/cryptfs.h b/crypto/jb/cryptfs.h
deleted file mode 100644
index d815814d3..000000000
--- a/crypto/jb/cryptfs.h
+++ /dev/null
@@ -1,157 +0,0 @@
-/*
- * Copyright (C) 2010 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.
- */
-
-/* This structure starts 16,384 bytes before the end of a hardware
- * partition that is encrypted, or in a separate partition. It's location
- * is specified by a property set in init.<device>.rc.
- * The structure allocates 48 bytes for a key, but the real key size is
- * specified in the struct. Currently, the code is hardcoded to use 128
- * bit keys.
- * The fields after salt are only valid in rev 1.1 and later stuctures.
- * Obviously, the filesystem does not include the last 16 kbytes
- * of the partition if the crypt_mnt_ftr lives at the end of the
- * partition.
- */
-
-#include <cutils/properties.h>
-
-/* The current cryptfs version */
-#define CURRENT_MAJOR_VERSION 1
-#define CURRENT_MINOR_VERSION 2
-
-#define CRYPT_FOOTER_OFFSET 0x4000
-#define CRYPT_FOOTER_TO_PERSIST_OFFSET 0x1000
-#define CRYPT_PERSIST_DATA_SIZE 0x1000
-
-#define MAX_CRYPTO_TYPE_NAME_LEN 64
-
-#define MAX_KEY_LEN 48
-#define SALT_LEN 16
-
-/* definitions of flags in the structure below */
-#define CRYPT_MNT_KEY_UNENCRYPTED 0x1 /* The key for the partition is not encrypted. */
-#define CRYPT_ENCRYPTION_IN_PROGRESS 0x2 /* Set when starting encryption,
- * clear when done before rebooting */
-
-#define CRYPT_MNT_MAGIC 0xD0B5B1C4
-#define PERSIST_DATA_MAGIC 0xE950CD44
-
-#define SCRYPT_PROP "ro.crypto.scrypt_params"
-#define SCRYPT_DEFAULTS { 15, 3, 1 }
-
-/* Key Derivation Function algorithms */
-#define KDF_PBKDF2 1
-#define KDF_SCRYPT 2
-
-#define __le32 unsigned int
-#define __le16 unsigned short int
-#define __le8 unsigned char
-
-struct crypt_mnt_ftr {
- __le32 magic; /* See above */
- __le16 major_version;
- __le16 minor_version;
- __le32 ftr_size; /* in bytes, not including key following */
- __le32 flags; /* See above */
- __le32 keysize; /* in bytes */
- __le32 spare1; /* ignored */
- __le64 fs_size; /* Size of the encrypted fs, in 512 byte sectors */
- __le32 failed_decrypt_count; /* count of # of failed attempts to decrypt and
- mount, set to 0 on successful mount */
- unsigned char crypto_type_name[MAX_CRYPTO_TYPE_NAME_LEN]; /* The type of encryption
- needed to decrypt this
- partition, null terminated */
- __le32 spare2; /* ignored */
- unsigned char master_key[MAX_KEY_LEN]; /* The encrypted key for decrypting the filesystem */
- unsigned char salt[SALT_LEN]; /* The salt used for this encryption */
- __le64 persist_data_offset[2]; /* Absolute offset to both copies of crypt_persist_data
- * on device with that info, either the footer of the
- * real_blkdevice or the metadata partition. */
-
- __le32 persist_data_size; /* The number of bytes allocated to each copy of the
- * persistent data table*/
-
- __le8 kdf_type; /* The key derivation function used. */
-
- /* scrypt parameters. See www.tarsnap.com/scrypt/scrypt.pdf */
- __le8 N_factor; /* (1 << N) */
- __le8 r_factor; /* (1 << r) */
- __le8 p_factor; /* (1 << p) */
-};
-
-/* Persistant data that should be available before decryption.
- * Things like airplane mode, locale and timezone are kept
- * here and can be retrieved by the CryptKeeper UI to properly
- * configure the phone before asking for the password
- * This is only valid if the major and minor version above
- * is set to 1.1 or higher.
- *
- * This is a 4K structure. There are 2 copies, and the code alternates
- * writing one and then clearing the previous one. The reading
- * code reads the first valid copy it finds, based on the magic number.
- * The absolute offset to the first of the two copies is kept in rev 1.1
- * and higher crypt_mnt_ftr structures.
- */
-struct crypt_persist_entry {
- char key[PROPERTY_KEY_MAX];
- char val[PROPERTY_VALUE_MAX];
-};
-
-/* Should be exactly 4K in size */
-struct crypt_persist_data {
- __le32 persist_magic;
- __le32 persist_valid_entries;
- __le32 persist_spare[30];
- struct crypt_persist_entry persist_entry[0];
-};
-
-struct volume_info {
- unsigned int size;
- unsigned int flags;
- struct crypt_mnt_ftr crypt_ftr;
- char mnt_point[256];
- char blk_dev[256];
- char crypto_blkdev[256];
- char label[256];
-};
-#define VOL_NONREMOVABLE 0x1
-#define VOL_ENCRYPTABLE 0x2
-#define VOL_PRIMARY 0x4
-#define VOL_PROVIDES_ASEC 0x8
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
- typedef void (*kdf_func)(char *passwd, unsigned char *salt, unsigned char *ikey, void *params);
-
- int cryptfs_crypto_complete(void);
- int cryptfs_check_footer(void);
- int cryptfs_check_passwd(char *pw);
- int cryptfs_verify_passwd(char *newpw);
- int cryptfs_restart(void);
- int cryptfs_enable(char *flag, char *passwd);
- int cryptfs_changepw(char *newpw);
- int cryptfs_setup_volume(const char *label, int major, int minor,
- char *crypto_dev_path, unsigned int max_pathlen,
- int *new_major, int *new_minor);
- int cryptfs_revert_volume(const char *label);
- int cryptfs_getfield(char *fieldname, char *value, int len);
- int cryptfs_setfield(char *fieldname, char *value);
-#ifdef __cplusplus
-}
-#endif
-
diff --git a/crypto/libcrypt_samsung/Android.mk b/crypto/libcrypt_samsung/Android.mk
deleted file mode 100644
index 6e0e86903..000000000
--- a/crypto/libcrypt_samsung/Android.mk
+++ /dev/null
@@ -1,11 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-
-ifneq ($(TARGET_SIMULATOR),true)
-
-include $(CLEAR_VARS)
-LOCAL_MODULE := libcrypt_samsung
-LOCAL_SRC_FILES := $(LOCAL_MODULE).c
-LOCAL_MODULE_TAGS := eng
-include $(BUILD_STATIC_LIBRARY)
-
-endif
diff --git a/crypto/libcrypt_samsung/include/libcrypt_samsung.h b/crypto/libcrypt_samsung/include/libcrypt_samsung.h
deleted file mode 100644
index 2fb6f2c4f..000000000
--- a/crypto/libcrypt_samsung/include/libcrypt_samsung.h
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright (c) 2013 a3955269 all rights reversed, no rights reserved.
- */
-
-#ifndef __LIBCRYPT_SAMSUNG_H__
-#define __LIBCRYPT_SAMSUNG_H__
-
-//////////////////////////////////////////////////////////////////////////////
-// Name Address Ordinal
-// ---- ------- -------
-// SECKM_AES_set_encrypt_key 000010D8
-// SECKM_AES_set_decrypt_key 00001464
-// SECKM_AES_encrypt 00001600
-// SECKM_AES_decrypt 00001A10
-// SECKM_aes_selftest 00001D94
-// verify_EDK 00001F7C
-// encrypt_dek 00001FC8
-// decrypt_EDK 000020D4
-// change_EDK 0000218C
-// generate_dek_salt 000022A4
-// create_EDK 000023A0
-// free_DEK 000024DC
-// alloc_DEK 000024F4
-// SECKM_HMAC_SHA256 00002500
-// SECKM_HMAC_SHA256_selftest 00002690
-// pbkdf 000026FC
-// pbkdf_selftest 00002898
-// _SECKM_PRNG_get16 00002958
-// SECKM_PRNG_get16 00002C48
-// _SECKM_PRNG_init 00002C54
-// SECKM_PRNG_selftest 00002F38
-// SECKM_PRNG_set_seed 00002FF0
-// SECKM_PRNG_init 00002FF8
-// SECKM_SHA256_Transform 00003004
-// SECKM_SHA256_Final 000031D8
-// SECKM_SHA256_Update 00003330
-// SECKM_SHA256_Init 000033FC
-// SECKM_SHA2_selftest 00003430
-// integrity_check 00003488
-// update_system_property 00003580
-// setsec_km_fips_status 00003630
-// _all_checks 00003684
-// get_fips_status 000036D4
-
-
-// EDK Payload is defined as:
-// Encrypted DEK – EDK itself
-// HMAC of EDK (32 bytes ???)
-// Salt 16 bytes
-
-#define EDK_MAGIC 0x1001e4b1
-
-#pragma pack(1)
-
-typedef struct {
- unsigned int magic; // EDK_MAGIC
- unsigned int flags; // 2
- unsigned int zeros[6];
-} dek_t;
-
-typedef struct {
- unsigned char data[32];
-} edk_t;
-
-
-// size 0x70 -> 112
-typedef struct {
- dek_t dek;
- edk_t edk;
- unsigned char hmac[32];
- unsigned char salt[16];
-} edk_payload_t;
-
-#pragma pack()
-
-//////////////////////////////////////////////////////////////////////////////
-
-int decrypt_EDK(
- dek_t *dek, const edk_payload_t *edk, /*const*/ char *passwd);
-
-typedef int (*decrypt_EDK_t)(
- dek_t *dek, const edk_payload_t *edk, /*const*/ char *passwd);
-
-
-int verify_EDK(const edk_payload_t *edk, const char *passwd);
-//change_EDK()
-//create_EDK()
-
-// internally just mallocs 32 bytes
-dek_t *alloc_DEK();
-void free_DEK(dek_t *dek);
-//encrypt_dek()
-//generate_dek_salt()
-
-//pbkdf(_buf_, "passwordPASSWORDpassword", 0x18, "saltSALTsaltSALTsaltSALTsaltSALTsalt", 0x24, 0x1000, 0x140);
-int pbkdf(
- void *buf, void *pw, int pwlen, void *salt, int saltlen, int hashcnt,
- int keylen);
-
-// getprop("rw.km_fips_status")
-// "ready, undefined, error_selftest, error_integrity"
-int get_fips_status();
-
-//////////////////////////////////////////////////////////////////////////////
-//
-// libsec_ecryptfs.so (internally uses libkeyutils.so)
-//
-// Name Address Ordinal
-// ---- ------- -------
-// unmount_ecryptfs_drive 00000A78
-// mount_ecryptfs_drive 00000B48
-// fips_read_edk 00000E44
-// fips_save_edk 00000EA4
-// fips_create_edk 00000F20
-// fips_change_password 00001018
-// fips_delete_edk 00001124
-//
-
-// might depend on /data beeing mounted for reading /data/system/edk_p_sd
-//
-// filter
-// 0: building options without file encryption filtering.
-// 1: building options with media files filtering.
-// 2: building options with all new files filtering.
-
-int mount_ecryptfs_drive(
- const char *passwd, const char *source, const char *target, int filter);
-
-typedef int (*mount_ecryptfs_drive_t)(
- const char *passwd, const char *source, const char *target, int filter);
-
-// calls 2 times umount2(source, MNT_EXPIRE)
-int unmount_ecryptfs_drive(
- const char *source);
-
-typedef int (*unmount_ecryptfs_drive_t)(
- const char *source);
-
-//////////////////////////////////////////////////////////////////////////////
-
-#endif // #ifndef __LIBCRYPT_SAMSUNG_H__
-
-//////////////////////////////////////////////////////////////////////////////
-
diff --git a/crypto/libcrypt_samsung/libcrypt_samsung.c b/crypto/libcrypt_samsung/libcrypt_samsung.c
deleted file mode 100644
index cd3a17804..000000000
--- a/crypto/libcrypt_samsung/libcrypt_samsung.c
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright (c) 2013 a3955269 all rights reversed, no rights reserved.
- */
-
-//////////////////////////////////////////////////////////////////////////////
-
-#include <string.h>
-#include <stdio.h>
-#include <dlfcn.h>
-
-#include "include/libcrypt_samsung.h"
-
-//////////////////////////////////////////////////////////////////////////////
-
-int decrypt_EDK(
- dek_t *dek, const edk_payload_t *edk, /*const*/ char *passwd)
-{
- void *lib = dlopen("libsec_km.so", RTLD_LAZY);
-
- if(!lib)
- return -100;
-
- int r = -101;
- decrypt_EDK_t sym = (decrypt_EDK_t)dlsym(lib, "decrypt_EDK");
- if(sym)
- r = sym(dek, edk, passwd);
-
- dlclose(lib);
-
- return r;
-}
-
-int mount_ecryptfs_drive(
- const char *passwd, const char *source, const char *target, int filter)
-{
- void *lib = dlopen("libsec_ecryptfs.so", RTLD_LAZY);
- if(!lib)
- return -100;
-
- int r = -101;
- mount_ecryptfs_drive_t sym = (mount_ecryptfs_drive_t)dlsym(lib, "mount_ecryptfs_drive");
- if(sym)
- r = sym(passwd, source, target, filter);
-
- dlclose(lib);
-
- return r;
-}
-
-int unmount_ecryptfs_drive(
- const char *source)
-{
- void *lib = dlopen("libsec_ecryptfs.so", RTLD_LAZY);
- if(!lib)
- return -100;
-
- int r = -101;
- unmount_ecryptfs_drive_t sym = (unmount_ecryptfs_drive_t)dlsym(lib, "unmount_ecryptfs_drive");
- if(sym)
- r = sym(source);
-
- dlclose(lib);
-
- return r;
-} \ No newline at end of file
diff --git a/crypto/logwrapper/Android.mk b/crypto/logwrapper/Android.mk
deleted file mode 100644
index 01b61930d..000000000
--- a/crypto/logwrapper/Android.mk
+++ /dev/null
@@ -1,34 +0,0 @@
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-# ========================================================
-# Static library
-# ========================================================
-include $(CLEAR_VARS)
-LOCAL_MODULE := liblogwraptwrp
-LOCAL_SRC_FILES := logwrap.c
-LOCAL_SHARED_LIBRARIES := libcutils liblog
-LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/include
-LOCAL_C_INCLUDES := $(LOCAL_PATH)/include
-include $(BUILD_STATIC_LIBRARY)
-
-# ========================================================
-# Shared library
-# ========================================================
-#include $(CLEAR_VARS)
-#LOCAL_MODULE := liblogwrap
-#LOCAL_SHARED_LIBRARIES := libcutils liblog
-#LOCAL_WHOLE_STATIC_LIBRARIES := liblogwrap
-#LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/include
-#LOCAL_C_INCLUDES := $(LOCAL_PATH)/include
-#include $(BUILD_SHARED_LIBRARY)
-
-# ========================================================
-# Executable
-# ========================================================
-#include $(CLEAR_VARS)
-#LOCAL_SRC_FILES:= logwrapper.c
-#LOCAL_MODULE := logwrapper
-#LOCAL_STATIC_LIBRARIES := liblog liblogwrap libcutils
-#include $(BUILD_EXECUTABLE)
diff --git a/crypto/logwrapper/NOTICE b/crypto/logwrapper/NOTICE
deleted file mode 100644
index c5b1efa7a..000000000
--- a/crypto/logwrapper/NOTICE
+++ /dev/null
@@ -1,190 +0,0 @@
-
- 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/crypto/logwrapper/include/logwrap/logwrap.h b/crypto/logwrapper/include/logwrap/logwrap.h
deleted file mode 100644
index 4307a3055..000000000
--- a/crypto/logwrapper/include/logwrap/logwrap.h
+++ /dev/null
@@ -1,87 +0,0 @@
-/* system/core/include/logwrap/logwrap.h
- *
- * Copyright 2013, 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 __LIBS_LOGWRAP_H
-#define __LIBS_LOGWRAP_H
-
-#include <stdbool.h>
-
-__BEGIN_DECLS
-
-/*
- * Run a command while logging its stdout and stderr
- *
- * WARNING: while this function is running it will clear all SIGCHLD handlers
- * if you rely on SIGCHLD in the caller there is a chance zombies will be
- * created if you're not calling waitpid after calling this. This function will
- * log a warning when it clears SIGCHLD for processes other than the child it
- * created.
- *
- * Arguments:
- * argc: the number of elements in argv
- * argv: an array of strings containing the command to be executed and its
- * arguments as separate strings. argv does not need to be
- * NULL-terminated
- * status: the equivalent child status as populated by wait(status). This
- * value is only valid when logwrap successfully completes. If NULL
- * the return value of the child will be the function's return value.
- * ignore_int_quit: set to true if you want to completely ignore SIGINT and
- * SIGQUIT while logwrap is running. This may force the end-user to
- * send a signal twice to signal the caller (once for the child, and
- * once for the caller)
- * log_target: Specify where to log the output of the child, either LOG_NONE,
- * LOG_ALOG (for the Android system log), LOG_KLOG (for the kernel
- * log), or LOG_FILE (and you need to specify a pathname in the
- * file_path argument, otherwise pass NULL). These are bit fields,
- * and can be OR'ed together to log to multiple places.
- * abbreviated: If true, capture up to the first 100 lines and last 4K of
- * output from the child. The abbreviated output is not dumped to
- * the specified log until the child has exited.
- * file_path: if log_target has the LOG_FILE bit set, then this parameter
- * must be set to the pathname of the file to log to.
- *
- * Return value:
- * 0 when logwrap successfully run the child process and captured its status
- * -1 when an internal error occurred
- * -ECHILD if status is NULL and the child didn't exit properly
- * the return value of the child if it exited properly and status is NULL
- *
- */
-
-/* Values for the log_target parameter android_fork_execvp_ext() */
-#define LOG_NONE 0
-#define LOG_ALOG 1
-#define LOG_KLOG 2
-#define LOG_FILE 4
-
-int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int_quit,
- int log_target, bool abbreviated, char *file_path);
-
-/* Similar to above, except abbreviated logging is not available, and if logwrap
- * is true, logging is to the Android system log, and if false, there is no
- * logging.
- */
-static inline int android_fork_execvp(int argc, char* argv[], int *status,
- bool ignore_int_quit, bool logwrap)
-{
- return android_fork_execvp_ext(argc, argv, status, ignore_int_quit,
- (logwrap ? LOG_ALOG : LOG_NONE), false, NULL);
-}
-
-__END_DECLS
-
-#endif /* __LIBS_LOGWRAP_H */
diff --git a/crypto/logwrapper/logwrap.c b/crypto/logwrapper/logwrap.c
deleted file mode 100644
index 4ca1db4c8..000000000
--- a/crypto/logwrapper/logwrap.c
+++ /dev/null
@@ -1,569 +0,0 @@
-/*
- * 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/socket.h>
-#include <poll.h>
-#include <sys/wait.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <libgen.h>
-#include <stdbool.h>
-#include <pthread.h>
-
-#include <logwrap/logwrap.h>
-#include "private/android_filesystem_config.h"
-#include "cutils/log.h"
-#include <cutils/klog.h>
-
-#define ARRAY_SIZE(x) (sizeof(x) / sizeof(*(x)))
-#define MIN(a,b) (((a)<(b))?(a):(b))
-
-static pthread_mutex_t fd_mutex = PTHREAD_MUTEX_INITIALIZER;
-
-#define ERROR(fmt, args...) \
-do { \
- fprintf(stderr, fmt, ## args); \
- ALOG(LOG_ERROR, "logwrapper", fmt, ## args); \
-} while(0)
-
-#define FATAL_CHILD(fmt, args...) \
-do { \
- ERROR(fmt, ## args); \
- _exit(-1); \
-} while(0)
-
-#define MAX_KLOG_TAG 16
-
-/* This is a simple buffer that holds up to the first beginning_buf->buf_size
- * bytes of output from a command.
- */
-#define BEGINNING_BUF_SIZE 0x1000
-struct beginning_buf {
- char *buf;
- size_t alloc_len;
- /* buf_size is the usable space, which is one less than the allocated size */
- size_t buf_size;
- size_t used_len;
-};
-
-/* This is a circular buf that holds up to the last ending_buf->buf_size bytes
- * of output from a command after the first beginning_buf->buf_size bytes
- * (which are held in beginning_buf above).
- */
-#define ENDING_BUF_SIZE 0x1000
-struct ending_buf {
- char *buf;
- ssize_t alloc_len;
- /* buf_size is the usable space, which is one less than the allocated size */
- ssize_t buf_size;
- ssize_t used_len;
- /* read and write offsets into the circular buffer */
- int read;
- int write;
-};
-
- /* A structure to hold all the abbreviated buf data */
-struct abbr_buf {
- struct beginning_buf b_buf;
- struct ending_buf e_buf;
- int beginning_buf_full;
-};
-
-/* Collect all the various bits of info needed for logging in one place. */
-struct log_info {
- int log_target;
- char klog_fmt[MAX_KLOG_TAG * 2];
- char *btag;
- bool abbreviated;
- FILE *fp;
- struct abbr_buf a_buf;
-};
-
-/* Forware declaration */
-static void add_line_to_abbr_buf(struct abbr_buf *a_buf, char *linebuf, int linelen);
-
-/* Return 0 on success, and 1 when full */
-static int add_line_to_linear_buf(struct beginning_buf *b_buf,
- char *line, ssize_t line_len)
-{
- size_t new_len;
- char *new_buf;
- int full = 0;
-
- if ((line_len + b_buf->used_len) > b_buf->buf_size) {
- full = 1;
- } else {
- /* Add to the end of the buf */
- memcpy(b_buf->buf + b_buf->used_len, line, line_len);
- b_buf->used_len += line_len;
- }
-
- return full;
-}
-
-static void add_line_to_circular_buf(struct ending_buf *e_buf,
- char *line, ssize_t line_len)
-{
- ssize_t free_len;
- ssize_t needed_space;
- char *new_buf;
- int cnt;
-
- if (e_buf->buf == NULL) {
- return;
- }
-
- if (line_len > e_buf->buf_size) {
- return;
- }
-
- free_len = e_buf->buf_size - e_buf->used_len;
-
- if (line_len > free_len) {
- /* remove oldest entries at read, and move read to make
- * room for the new string */
- needed_space = line_len - free_len;
- e_buf->read = (e_buf->read + needed_space) % e_buf->buf_size;
- e_buf->used_len -= needed_space;
- }
-
- /* Copy the line into the circular buffer, dealing with possible
- * wraparound.
- */
- cnt = MIN(line_len, e_buf->buf_size - e_buf->write);
- memcpy(e_buf->buf + e_buf->write, line, cnt);
- if (cnt < line_len) {
- memcpy(e_buf->buf, line + cnt, line_len - cnt);
- }
- e_buf->used_len += line_len;
- e_buf->write = (e_buf->write + line_len) % e_buf->buf_size;
-}
-
-/* Log directly to the specified log */
-static void do_log_line(struct log_info *log_info, char *line) {
- if (log_info->log_target & LOG_KLOG) {
- klog_write(6, log_info->klog_fmt, line);
- }
- if (log_info->log_target & LOG_ALOG) {
- ALOG(LOG_INFO, log_info->btag, "%s", line);
- }
- if (log_info->log_target & LOG_FILE) {
- fprintf(log_info->fp, "%s\n", line);
- }
-}
-
-/* Log to either the abbreviated buf, or directly to the specified log
- * via do_log_line() above.
- */
-static void log_line(struct log_info *log_info, char *line, int len) {
- if (log_info->abbreviated) {
- add_line_to_abbr_buf(&log_info->a_buf, line, len);
- } else {
- do_log_line(log_info, line);
- }
-}
-
-/*
- * The kernel will take a maximum of 1024 bytes in any single write to
- * the kernel logging device file, so find and print each line one at
- * a time. The allocated size for buf should be at least 1 byte larger
- * than buf_size (the usable size of the buffer) to make sure there is
- * room to temporarily stuff a null byte to terminate a line for logging.
- */
-static void print_buf_lines(struct log_info *log_info, char *buf, int buf_size)
-{
- char *line_start;
- char c;
- int line_len;
- int i;
-
- line_start = buf;
- for (i = 0; i < buf_size; i++) {
- if (*(buf + i) == '\n') {
- /* Found a line ending, print the line and compute new line_start */
- /* Save the next char and replace with \0 */
- c = *(buf + i + 1);
- *(buf + i + 1) = '\0';
- do_log_line(log_info, line_start);
- /* Restore the saved char */
- *(buf + i + 1) = c;
- line_start = buf + i + 1;
- } else if (*(buf + i) == '\0') {
- /* The end of the buffer, print the last bit */
- do_log_line(log_info, line_start);
- break;
- }
- }
- /* If the buffer was completely full, and didn't end with a newline, just
- * ignore the partial last line.
- */
-}
-
-static void init_abbr_buf(struct abbr_buf *a_buf) {
- char *new_buf;
-
- memset(a_buf, 0, sizeof(struct abbr_buf));
- new_buf = malloc(BEGINNING_BUF_SIZE);
- if (new_buf) {
- a_buf->b_buf.buf = new_buf;
- a_buf->b_buf.alloc_len = BEGINNING_BUF_SIZE;
- a_buf->b_buf.buf_size = BEGINNING_BUF_SIZE - 1;
- }
- new_buf = malloc(ENDING_BUF_SIZE);
- if (new_buf) {
- a_buf->e_buf.buf = new_buf;
- a_buf->e_buf.alloc_len = ENDING_BUF_SIZE;
- a_buf->e_buf.buf_size = ENDING_BUF_SIZE - 1;
- }
-}
-
-static void free_abbr_buf(struct abbr_buf *a_buf) {
- free(a_buf->b_buf.buf);
- free(a_buf->e_buf.buf);
-}
-
-static void add_line_to_abbr_buf(struct abbr_buf *a_buf, char *linebuf, int linelen) {
- if (!a_buf->beginning_buf_full) {
- a_buf->beginning_buf_full =
- add_line_to_linear_buf(&a_buf->b_buf, linebuf, linelen);
- }
- if (a_buf->beginning_buf_full) {
- add_line_to_circular_buf(&a_buf->e_buf, linebuf, linelen);
- }
-}
-
-static void print_abbr_buf(struct log_info *log_info) {
- struct abbr_buf *a_buf = &log_info->a_buf;
-
- /* Add the abbreviated output to the kernel log */
- if (a_buf->b_buf.alloc_len) {
- print_buf_lines(log_info, a_buf->b_buf.buf, a_buf->b_buf.used_len);
- }
-
- /* Print an ellipsis to indicate that the buffer has wrapped or
- * is full, and some data was not logged.
- */
- if (a_buf->e_buf.used_len == a_buf->e_buf.buf_size) {
- do_log_line(log_info, "...\n");
- }
-
- if (a_buf->e_buf.used_len == 0) {
- return;
- }
-
- /* Simplest way to print the circular buffer is allocate a second buf
- * of the same size, and memcpy it so it's a simple linear buffer,
- * and then cal print_buf_lines on it */
- if (a_buf->e_buf.read < a_buf->e_buf.write) {
- /* no wrap around, just print it */
- print_buf_lines(log_info, a_buf->e_buf.buf + a_buf->e_buf.read,
- a_buf->e_buf.used_len);
- } else {
- /* The circular buffer will always have at least 1 byte unused,
- * so by allocating alloc_len here we will have at least
- * 1 byte of space available as required by print_buf_lines().
- */
- char * nbuf = malloc(a_buf->e_buf.alloc_len);
- if (!nbuf) {
- return;
- }
- int first_chunk_len = a_buf->e_buf.buf_size - a_buf->e_buf.read;
- memcpy(nbuf, a_buf->e_buf.buf + a_buf->e_buf.read, first_chunk_len);
- /* copy second chunk */
- memcpy(nbuf + first_chunk_len, a_buf->e_buf.buf, a_buf->e_buf.write);
- print_buf_lines(log_info, nbuf, first_chunk_len + a_buf->e_buf.write);
- free(nbuf);
- }
-}
-
-static int parent(const char *tag, int parent_read, pid_t pid,
- int *chld_sts, int log_target, bool abbreviated, char *file_path) {
- int status = 0;
- char buffer[4096];
- struct pollfd poll_fds[] = {
- [0] = {
- .fd = parent_read,
- .events = POLLIN,
- },
- };
- int rc = 0;
- int fd;
-
- struct log_info log_info;
-
- int a = 0; // start index of unprocessed data
- int b = 0; // end index of unprocessed data
- int sz;
- bool found_child = false;
- char tmpbuf[256];
-
- log_info.btag = basename(tag);
- if (!log_info.btag) {
- log_info.btag = (char*) tag;
- }
-
- if (abbreviated && (log_target == LOG_NONE)) {
- abbreviated = 0;
- }
- if (abbreviated) {
- init_abbr_buf(&log_info.a_buf);
- }
-
- if (log_target & LOG_KLOG) {
- snprintf(log_info.klog_fmt, sizeof(log_info.klog_fmt),
- "<6>%.*s: %%s", MAX_KLOG_TAG, log_info.btag);
- }
-
- if ((log_target & LOG_FILE) && !file_path) {
- /* No file_path specified, clear the LOG_FILE bit */
- log_target &= ~LOG_FILE;
- }
-
- if (log_target & LOG_FILE) {
- fd = open(file_path, O_WRONLY | O_CREAT, 0664);
- if (fd < 0) {
- ERROR("Cannot log to file %s\n", file_path);
- log_target &= ~LOG_FILE;
- } else {
- lseek(fd, 0, SEEK_END);
- log_info.fp = fdopen(fd, "a");
- }
- }
-
- log_info.log_target = log_target;
- log_info.abbreviated = abbreviated;
-
- while (!found_child) {
- if (TEMP_FAILURE_RETRY(poll(poll_fds, ARRAY_SIZE(poll_fds), -1)) < 0) {
- ERROR("poll failed\n");
- rc = -1;
- goto err_poll;
- }
-
- if (poll_fds[0].revents & POLLIN) {
- sz = read(parent_read, &buffer[b], sizeof(buffer) - 1 - b);
-
- sz += b;
- // Log one line at a time
- for (b = 0; b < sz; b++) {
- if (buffer[b] == '\r') {
- if (abbreviated) {
- /* The abbreviated logging code uses newline as
- * the line separator. Lucikly, the pty layer
- * helpfully cooks the output of the command
- * being run and inserts a CR before NL. So
- * I just change it to NL here when doing
- * abbreviated logging.
- */
- buffer[b] = '\n';
- } else {
- buffer[b] = '\0';
- }
- } else if (buffer[b] == '\n') {
- buffer[b] = '\0';
- log_line(&log_info, &buffer[a], b - a);
- a = b + 1;
- }
- }
-
- if (a == 0 && b == sizeof(buffer) - 1) {
- // buffer is full, flush
- buffer[b] = '\0';
- log_line(&log_info, &buffer[a], b - a);
- b = 0;
- } else if (a != b) {
- // Keep left-overs
- b -= a;
- memmove(buffer, &buffer[a], b);
- a = 0;
- } else {
- a = 0;
- b = 0;
- }
- }
-
- if (poll_fds[0].revents & POLLHUP) {
- int ret;
-
- ret = waitpid(pid, &status, WNOHANG);
- if (ret < 0) {
- rc = errno;
- ALOG(LOG_ERROR, "logwrap", "waitpid failed with %s\n", strerror(errno));
- goto err_waitpid;
- }
- if (ret > 0) {
- found_child = true;
- }
- }
- }
-
- if (chld_sts != NULL) {
- *chld_sts = status;
- } else {
- if (WIFEXITED(status))
- rc = WEXITSTATUS(status);
- else
- rc = -ECHILD;
- }
-
- // Flush remaining data
- if (a != b) {
- buffer[b] = '\0';
- log_line(&log_info, &buffer[a], b - a);
- }
-
- /* All the output has been processed, time to dump the abbreviated output */
- if (abbreviated) {
- print_abbr_buf(&log_info);
- }
-
- if (WIFEXITED(status)) {
- if (WEXITSTATUS(status)) {
- snprintf(tmpbuf, sizeof(tmpbuf),
- "%s terminated by exit(%d)\n", log_info.btag, WEXITSTATUS(status));
- do_log_line(&log_info, tmpbuf);
- }
- } else {
- if (WIFSIGNALED(status)) {
- snprintf(tmpbuf, sizeof(tmpbuf),
- "%s terminated by signal %d\n", log_info.btag, WTERMSIG(status));
- do_log_line(&log_info, tmpbuf);
- } else if (WIFSTOPPED(status)) {
- snprintf(tmpbuf, sizeof(tmpbuf),
- "%s stopped by signal %d\n", log_info.btag, WSTOPSIG(status));
- do_log_line(&log_info, tmpbuf);
- }
- }
-
-err_waitpid:
-err_poll:
- if (log_target & LOG_FILE) {
- fclose(log_info.fp); /* Also closes underlying fd */
- }
- if (abbreviated) {
- free_abbr_buf(&log_info.a_buf);
- }
- return rc;
-}
-
-static 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;
-
- if (execvp(argv_child[0], argv_child)) {
- FATAL_CHILD("executing %s failed: %s\n", argv_child[0],
- strerror(errno));
- }
-}
-
-int android_fork_execvp_ext(int argc, char* argv[], int *status, bool ignore_int_quit,
- int log_target, bool abbreviated, char *file_path) {
- pid_t pid;
- int parent_ptty;
- int child_ptty;
- char *child_devname = NULL;
- struct sigaction intact;
- struct sigaction quitact;
- sigset_t blockset;
- sigset_t oldset;
- int rc = 0;
-
- rc = pthread_mutex_lock(&fd_mutex);
- if (rc) {
- ERROR("failed to lock signal_fd mutex\n");
- goto err_lock;
- }
-
- /* Use ptty instead of socketpair so that STDOUT is not buffered */
- parent_ptty = open("/dev/ptmx", O_RDWR);
- if (parent_ptty < 0) {
- ERROR("Cannot create parent ptty\n");
- rc = -1;
- goto err_open;
- }
-
- if (grantpt(parent_ptty) || unlockpt(parent_ptty) ||
- ((child_devname = (char*)ptsname(parent_ptty)) == 0)) {
- ERROR("Problem with /dev/ptmx\n");
- rc = -1;
- goto err_ptty;
- }
-
- child_ptty = open(child_devname, O_RDWR);
- if (child_ptty < 0) {
- ERROR("Cannot open child_ptty\n");
- rc = -1;
- goto err_child_ptty;
- }
-
- sigemptyset(&blockset);
- sigaddset(&blockset, SIGINT);
- sigaddset(&blockset, SIGQUIT);
- pthread_sigmask(SIG_BLOCK, &blockset, &oldset);
-
- pid = fork();
- if (pid < 0) {
- close(child_ptty);
- ERROR("Failed to fork\n");
- rc = -1;
- goto err_fork;
- } else if (pid == 0) {
- pthread_mutex_unlock(&fd_mutex);
- pthread_sigmask(SIG_SETMASK, &oldset, NULL);
- close(parent_ptty);
-
- // redirect stdout and stderr
- dup2(child_ptty, 1);
- dup2(child_ptty, 2);
- close(child_ptty);
-
- child(argc, argv);
- } else {
- close(child_ptty);
- if (ignore_int_quit) {
- struct sigaction ignact;
-
- memset(&ignact, 0, sizeof(ignact));
- ignact.sa_handler = SIG_IGN;
- sigaction(SIGINT, &ignact, &intact);
- sigaction(SIGQUIT, &ignact, &quitact);
- }
-
- rc = parent(argv[0], parent_ptty, pid, status, log_target,
- abbreviated, file_path);
- }
-
- if (ignore_int_quit) {
- sigaction(SIGINT, &intact, NULL);
- sigaction(SIGQUIT, &quitact, NULL);
- }
-err_fork:
- pthread_sigmask(SIG_SETMASK, &oldset, NULL);
-err_child_ptty:
-err_ptty:
- close(parent_ptty);
-err_open:
- pthread_mutex_unlock(&fd_mutex);
-err_lock:
- return rc;
-}
diff --git a/crypto/logwrapper/logwrapper.c b/crypto/logwrapper/logwrapper.c
deleted file mode 100644
index d0d8d1471..000000000
--- a/crypto/logwrapper/logwrapper.c
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * 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 <stdio.h>
-#include <stdlib.h>
-#include <sys/wait.h>
-#include <unistd.h>
-
-#include <logwrap/logwrap.h>
-#include <cutils/klog.h>
-
-#include "cutils/log.h"
-
-void fatal(const char *msg) {
- fprintf(stderr, "%s", msg);
- ALOG(LOG_ERROR, "logwrapper", "%s", msg);
- exit(-1);
-}
-
-void usage() {
- fatal(
- "Usage: logwrapper [-a] [-d] [-k] BINARY [ARGS ...]\n"
- "\n"
- "Forks and executes BINARY ARGS, redirecting stdout and stderr to\n"
- "the Android logging system. Tag is set to BINARY, priority is\n"
- "always LOG_INFO.\n"
- "\n"
- "-a: Causes logwrapper to do abbreviated logging.\n"
- " This logs up to the first 4K and last 4K of the command\n"
- " being run, and logs the output when the command exits\n"
- "-d: Causes logwrapper to SIGSEGV when BINARY terminates\n"
- " fault address is set to the status of wait()\n"
- "-k: Causes logwrapper to log to the kernel log instead of\n"
- " the Android system log\n");
-}
-
-int main(int argc, char* argv[]) {
- int seg_fault_on_exit = 0;
- int log_target = LOG_ALOG;
- bool abbreviated = false;
- int ch;
- int status = 0xAAAA;
- int rc;
-
- while ((ch = getopt(argc, argv, "adk")) != -1) {
- switch (ch) {
- case 'a':
- abbreviated = true;
- break;
- case 'd':
- seg_fault_on_exit = 1;
- break;
- case 'k':
- log_target = LOG_KLOG;
- klog_set_level(6);
- break;
- case '?':
- default:
- usage();
- }
- }
- argc -= optind;
- argv += optind;
-
- if (argc < 1) {
- usage();
- }
-
- rc = android_fork_execvp_ext(argc, &argv[0], &status, true,
- log_target, abbreviated, NULL);
- if (!rc) {
- if (WIFEXITED(status))
- rc = WEXITSTATUS(status);
- else
- rc = -ECHILD;
- }
-
- if (seg_fault_on_exit) {
- *(int *)status = 0; // causes SIGSEGV with fault_address = status
- }
-
- return rc;
-}
diff --git a/crypto/lollipop/Android.mk b/crypto/lollipop/Android.mk
index 40b4d5f95..da25eac30 100644
--- a/crypto/lollipop/Android.mk
+++ b/crypto/lollipop/Android.mk
@@ -21,16 +21,17 @@ common_shared_libraries := \
libcutils \
liblog \
libdiskconfig \
- libhardware_legacy \
liblogwrap \
libext4_utils \
libf2fs_sparseblock \
libcrypto \
libselinux \
libutils \
- libhardware \
+ libminhardware \
libsoftkeymaster
+common_shared_libraries := libcrypto libselinux libhardware libsoftkeymaster libcutils
+
LOCAL_MODULE := libcryptfslollipop
LOCAL_MODULE_TAGS := eng optional
LOCAL_CFLAGS :=
@@ -44,9 +45,26 @@ LOCAL_SRC_FILES = cryptfs.c
# hardware/libhardware/include/hardware \
# system/security/softkeymaster/include/keymaster
#LOCAL_SHARED_LIBRARIES += libc liblog libcutils libcrypto libext4_utils
-LOCAL_SHARED_LIBRARIES := $(common_shared_libraries) libmincrypttwrp liblogwrap
+LOCAL_SHARED_LIBRARIES := $(common_shared_libraries) libmincrypttwrp
LOCAL_C_INCLUDES := external/openssl/include $(common_c_includes)
-LOCAL_WHOLE_STATIC_LIBRARIES += libfs_mgr libscrypt_static
+LOCAL_WHOLE_STATIC_LIBRARIES += libscrypttwrp_static
+
+include $(BUILD_SHARED_LIBRARY)
+
+include $(CLEAR_VARS)
+
+LOCAL_SHARED_LIBRARIES := libcutils liblog
+
+LOCAL_INCLUDES += $(LOCAL_PATH) $(LOCAL_PATH)\libminhardware
+
+LOCAL_CFLAGS += -DQEMU_HARDWARE
+QEMU_HARDWARE := true
+
+LOCAL_SHARED_LIBRARIES += libdl
+
+LOCAL_SRC_FILES += libminhardware/hardware.c
+
+LOCAL_MODULE:= libminhardware
include $(BUILD_SHARED_LIBRARY)
endif
diff --git a/crypto/lollipop/cryptfs.c b/crypto/lollipop/cryptfs.c
index 0277c78ef..90f1523d3 100644
--- a/crypto/lollipop/cryptfs.c
+++ b/crypto/lollipop/cryptfs.c
@@ -37,27 +37,17 @@
#include <sys/mount.h>
#include <openssl/evp.h>
#include <errno.h>
-#include <ext4.h>
#include <linux/kdev_t.h>
-#include <fs_mgr.h>
#include <time.h>
#include "cryptfs.h"
-#define LOG_TAG "Cryptfs"
-#include "cutils/log.h"
#include "cutils/properties.h"
-#include "cutils/android_reboot.h"
-#include "hardware_legacy/power.h"
-#include <logwrap/logwrap.h>
-//#include "VolumeManager.h"
-//#include "VoldUtil.h"
#include "crypto_scrypt.h"
-#include "ext4_utils.h"
-#include "f2fs_sparseblock.h"
-//#include "CheckBattery.h"
-//#include "Process.h"
-
#include <hardware/keymaster.h>
+#ifndef min /* already defined by windows.h */
+#define min(a, b) ((a) < (b) ? (a) : (b))
+#endif
+
#define UNUSED __attribute__((unused))
#define UNUSED __attribute__((unused))
@@ -91,6 +81,16 @@ static unsigned char saved_master_key[KEY_LEN_BYTES];
static char *saved_mount_point;
static int master_key_saved = 0;
static struct crypt_persist_data *persist_data = NULL;
+static char key_fname[PROPERTY_VALUE_MAX] = "";
+static char real_blkdev[PROPERTY_VALUE_MAX] = "";
+static char file_system[PROPERTY_VALUE_MAX] = "";
+
+void set_partition_data(const char* block_device, const char* key_location, const char* fs)
+{
+ strcpy(key_fname, key_location);
+ strcpy(real_blkdev, block_device);
+ strcpy(file_system, fs);
+}
static int keymaster_init(keymaster_device_t **keymaster_dev)
{
@@ -291,31 +291,6 @@ static char* password = 0;
static int password_expiry_time = 0;
static const int password_max_age_seconds = 60;
-struct fstab *fstab;
-
-enum RebootType {reboot, recovery, shutdown};
-static void cryptfs_reboot(enum RebootType rt)
-{
- switch(rt) {
- case reboot:
- property_set(ANDROID_RB_PROPERTY, "reboot");
- break;
-
- case recovery:
- property_set(ANDROID_RB_PROPERTY, "reboot,recovery");
- break;
-
- case shutdown:
- property_set(ANDROID_RB_PROPERTY, "shutdown");
- break;
- }
-
- sleep(20);
-
- /* Shouldn't get here, reboot should happen before sleep times out */
- return;
-}
-
static void ioctl_init(struct dm_ioctl *io, size_t dataSize, const char *name, unsigned flags)
{
memset(io, 0, dataSize);
@@ -380,41 +355,6 @@ static void get_device_scrypt_params(struct crypt_mnt_ftr *ftr) {
ftr->p_factor = params[2];
}
-static unsigned int get_fs_size(char *dev)
-{
- int fd, block_size;
- struct ext4_super_block sb;
- off64_t len;
-
- if ((fd = open(dev, O_RDONLY)) < 0) {
- printf("Cannot open device to get filesystem size ");
- return 0;
- }
-
- if (lseek64(fd, 1024, SEEK_SET) < 0) {
- printf("Cannot seek to superblock");
- return 0;
- }
-
- if (read(fd, &sb, sizeof(sb)) != sizeof(sb)) {
- printf("Cannot read superblock");
- return 0;
- }
-
- close(fd);
-
- if (le32_to_cpu(sb.s_magic) != EXT4_SUPER_MAGIC) {
- printf("Not a valid ext4 superblock");
- return 0;
- }
- block_size = 1024 << sb.s_log_block_size;
- /* compute length in bytes */
- len = ( ((off64_t)sb.s_blocks_count_hi << 32) + sb.s_blocks_count_lo) * block_size;
-
- /* return length in sectors */
- return (unsigned int) (len / 512);
-}
-
static unsigned int get_blkdev_size(int fd)
{
unsigned int nr_sec;
@@ -432,15 +372,12 @@ static int get_crypt_ftr_info(char **metadata_fname, off64_t *off)
static off64_t cached_off = 0;
static char cached_metadata_fname[PROPERTY_VALUE_MAX] = "";
int fd;
- char key_loc[PROPERTY_VALUE_MAX];
- char real_blkdev[PROPERTY_VALUE_MAX];
unsigned int nr_sec;
int rc = -1;
if (!cached_data) {
- fs_mgr_get_crypt_info(fstab, key_loc, real_blkdev, sizeof(key_loc));
- printf("get_crypt_ftr_info crypto key location: '%s'\n", key_loc);
- if (!strcmp(key_loc, KEY_IN_FOOTER)) {
+ printf("get_crypt_ftr_info crypto key location: '%s'\n", key_fname);
+ if (!strcmp(key_fname, KEY_IN_FOOTER)) {
if ( (fd = open(real_blkdev, O_RDWR)) < 0) {
printf("Cannot open real block device %s\n", real_blkdev);
return -1;
@@ -459,7 +396,7 @@ static int get_crypt_ftr_info(char **metadata_fname, off64_t *off)
}
close(fd);
} else {
- strlcpy(cached_metadata_fname, key_loc, sizeof(cached_metadata_fname));
+ strlcpy(cached_metadata_fname, key_fname, sizeof(cached_metadata_fname));
cached_off = 0;
cached_data = 1;
}
@@ -478,65 +415,6 @@ static int get_crypt_ftr_info(char **metadata_fname, off64_t *off)
return rc;
}
-/* key or salt can be NULL, in which case just skip writing that value. Useful to
- * update the failed mount count but not change the key.
- */
-static int put_crypt_ftr_and_key(struct crypt_mnt_ftr *crypt_ftr)
-{
- printf("TWRP NOT putting crypt footer and key\n");
- return 0;
- int fd;
- unsigned int nr_sec, cnt;
- /* starting_off is set to the SEEK_SET offset
- * where the crypto structure starts
- */
- off64_t starting_off;
- int rc = -1;
- char *fname = NULL;
- struct stat statbuf;
-
- if (get_crypt_ftr_info(&fname, &starting_off)) {
- printf("Unable to get crypt_ftr_info\n");
- return -1;
- }
- if (fname[0] != '/') {
- printf("Unexpected value for crypto key location\n");
- return -1;
- }
- if ( (fd = open(fname, O_RDWR | O_CREAT, 0600)) < 0) {
- printf("Cannot open footer file %s for put\n", fname);
- return -1;
- }
-
- /* Seek to the start of the crypt footer */
- if (lseek64(fd, starting_off, SEEK_SET) == -1) {
- printf("Cannot seek to real block device footer\n");
- goto errout;
- }
-
- if ((cnt = write(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr))) != sizeof(struct crypt_mnt_ftr)) {
- printf("Cannot write real block device footer\n");
- goto errout;
- }
-
- fstat(fd, &statbuf);
- /* If the keys are kept on a raw block device, do not try to truncate it. */
- if (S_ISREG(statbuf.st_mode)) {
- if (ftruncate(fd, 0x4000)) {
- printf("Cannot set footer file size\n");
- goto errout;
- }
- }
-
- /* Success! */
- rc = 0;
-
-errout:
- close(fd);
- return rc;
-
-}
-
static inline int unix_read(int fd, void* buff, int len)
{
return TEMP_FAILURE_RETRY(read(fd, buff, len));
@@ -554,75 +432,6 @@ static void init_empty_persist_data(struct crypt_persist_data *pdata, int len)
pdata->persist_valid_entries = 0;
}
-/* A routine to update the passed in crypt_ftr to the lastest version.
- * fd is open read/write on the device that holds the crypto footer and persistent
- * data, crypt_ftr is a pointer to the struct to be updated, and offset is the
- * absolute offset to the start of the crypt_mnt_ftr on the passed in fd.
- */
-static void upgrade_crypt_ftr(int fd, struct crypt_mnt_ftr *crypt_ftr, off64_t offset)
-{
- int orig_major = crypt_ftr->major_version;
- int orig_minor = crypt_ftr->minor_version;
-printf("TWRP NOT upgrading crypto footer\n");
-return; // do not upgrade in recovery
- if ((crypt_ftr->major_version == 1) && (crypt_ftr->minor_version == 0)) {
- struct crypt_persist_data *pdata;
- off64_t pdata_offset = offset + CRYPT_FOOTER_TO_PERSIST_OFFSET;
-
- printf("upgrading crypto footer to 1.1");
-
- pdata = malloc(CRYPT_PERSIST_DATA_SIZE);
- if (pdata == NULL) {
- printf("Cannot allocate persisent data\n");
- return;
- }
- memset(pdata, 0, CRYPT_PERSIST_DATA_SIZE);
-
- /* Need to initialize the persistent data area */
- if (lseek64(fd, pdata_offset, SEEK_SET) == -1) {
- printf("Cannot seek to persisent data offset\n");
- return;
- }
- /* Write all zeros to the first copy, making it invalid */
- unix_write(fd, pdata, CRYPT_PERSIST_DATA_SIZE);
-
- /* Write a valid but empty structure to the second copy */
- init_empty_persist_data(pdata, CRYPT_PERSIST_DATA_SIZE);
- unix_write(fd, pdata, CRYPT_PERSIST_DATA_SIZE);
-
- /* Update the footer */
- crypt_ftr->persist_data_size = CRYPT_PERSIST_DATA_SIZE;
- crypt_ftr->persist_data_offset[0] = pdata_offset;
- crypt_ftr->persist_data_offset[1] = pdata_offset + CRYPT_PERSIST_DATA_SIZE;
- crypt_ftr->minor_version = 1;
- }
-
- if ((crypt_ftr->major_version == 1) && (crypt_ftr->minor_version == 1)) {
- printf("upgrading crypto footer to 1.2");
- /* But keep the old kdf_type.
- * It will get updated later to KDF_SCRYPT after the password has been verified.
- */
- crypt_ftr->kdf_type = KDF_PBKDF2;
- get_device_scrypt_params(crypt_ftr);
- crypt_ftr->minor_version = 2;
- }
-
- if ((crypt_ftr->major_version == 1) && (crypt_ftr->minor_version == 2)) {
- printf("upgrading crypto footer to 1.3");
- crypt_ftr->crypt_type = CRYPT_TYPE_PASSWORD;
- crypt_ftr->minor_version = 3;
- }
-
- if ((orig_major != crypt_ftr->major_version) || (orig_minor != crypt_ftr->minor_version)) {
- if (lseek64(fd, offset, SEEK_SET) == -1) {
- printf("Cannot seek to crypt footer\n");
- return;
- }
- unix_write(fd, crypt_ftr, sizeof(struct crypt_mnt_ftr));
- }
-}
-
-
static int get_crypt_ftr_and_key(struct crypt_mnt_ftr *crypt_ftr)
{
int fd;
@@ -682,9 +491,9 @@ static int get_crypt_ftr_and_key(struct crypt_mnt_ftr *crypt_ftr)
/* If this is a verion 1.0 crypt_ftr, make it a 1.1 crypt footer, and update the
* copy on disk before returning.
*/
- if (crypt_ftr->minor_version < CURRENT_MINOR_VERSION) {
+ /*if (crypt_ftr->minor_version < CURRENT_MINOR_VERSION) {
upgrade_crypt_ftr(fd, crypt_ftr, starting_off);
- }
+ }*/
/* Success! */
rc = 0;
@@ -694,229 +503,6 @@ errout:
return rc;
}
-static int validate_persistent_data_storage(struct crypt_mnt_ftr *crypt_ftr)
-{
- if (crypt_ftr->persist_data_offset[0] + crypt_ftr->persist_data_size >
- crypt_ftr->persist_data_offset[1]) {
- printf("Crypt_ftr persist data regions overlap");
- return -1;
- }
-
- if (crypt_ftr->persist_data_offset[0] >= crypt_ftr->persist_data_offset[1]) {
- printf("Crypt_ftr persist data region 0 starts after region 1");
- return -1;
- }
-
- if (((crypt_ftr->persist_data_offset[1] + crypt_ftr->persist_data_size) -
- (crypt_ftr->persist_data_offset[0] - CRYPT_FOOTER_TO_PERSIST_OFFSET)) >
- CRYPT_FOOTER_OFFSET) {
- printf("Persistent data extends past crypto footer");
- return -1;
- }
-
- return 0;
-}
-
-static int load_persistent_data(void)
-{
- struct crypt_mnt_ftr crypt_ftr;
- struct crypt_persist_data *pdata = NULL;
- char encrypted_state[PROPERTY_VALUE_MAX];
- char *fname;
- int found = 0;
- int fd;
- int ret;
- int i;
-
- if (persist_data) {
- /* Nothing to do, we've already loaded or initialized it */
- return 0;
- }
-
-
- /* If not encrypted, just allocate an empty table and initialize it */
- property_get("ro.crypto.state", encrypted_state, "");
- if (strcmp(encrypted_state, "encrypted") ) {
- pdata = malloc(CRYPT_PERSIST_DATA_SIZE);
- if (pdata) {
- init_empty_persist_data(pdata, CRYPT_PERSIST_DATA_SIZE);
- persist_data = pdata;
- return 0;
- }
- return -1;
- }
-
- if(get_crypt_ftr_and_key(&crypt_ftr)) {
- return -1;
- }
-
- if ((crypt_ftr.major_version < 1)
- || (crypt_ftr.major_version == 1 && crypt_ftr.minor_version < 1)) {
- printf("Crypt_ftr version doesn't support persistent data");
- return -1;
- }
-
- if (get_crypt_ftr_info(&fname, NULL)) {
- return -1;
- }
-
- ret = validate_persistent_data_storage(&crypt_ftr);
- if (ret) {
- return -1;
- }
-
- fd = open(fname, O_RDONLY);
- if (fd < 0) {
- printf("Cannot open %s metadata file", fname);
- return -1;
- }
-
- if (persist_data == NULL) {
- pdata = malloc(crypt_ftr.persist_data_size);
- if (pdata == NULL) {
- printf("Cannot allocate memory for persistent data");
- goto err;
- }
- }
-
- for (i = 0; i < 2; i++) {
- if (lseek64(fd, crypt_ftr.persist_data_offset[i], SEEK_SET) < 0) {
- printf("Cannot seek to read persistent data on %s", fname);
- goto err2;
- }
- if (unix_read(fd, pdata, crypt_ftr.persist_data_size) < 0){
- printf("Error reading persistent data on iteration %d", i);
- goto err2;
- }
- if (pdata->persist_magic == PERSIST_DATA_MAGIC) {
- found = 1;
- break;
- }
- }
-
- if (!found) {
- printf("Could not find valid persistent data, creating");
- init_empty_persist_data(pdata, crypt_ftr.persist_data_size);
- }
-
- /* Success */
- persist_data = pdata;
- close(fd);
- return 0;
-
-err2:
- free(pdata);
-
-err:
- close(fd);
- return -1;
-}
-
-static int save_persistent_data(void)
-{
- struct crypt_mnt_ftr crypt_ftr;
- struct crypt_persist_data *pdata;
- char *fname;
- off64_t write_offset;
- off64_t erase_offset;
- int found = 0;
- int fd;
- int ret;
-
- if (persist_data == NULL) {
- printf("No persistent data to save");
- return -1;
- }
-
- if(get_crypt_ftr_and_key(&crypt_ftr)) {
- return -1;
- }
-
- if ((crypt_ftr.major_version < 1)
- || (crypt_ftr.major_version == 1 && crypt_ftr.minor_version < 1)) {
- printf("Crypt_ftr version doesn't support persistent data");
- return -1;
- }
-
- ret = validate_persistent_data_storage(&crypt_ftr);
- if (ret) {
- return -1;
- }
-
- if (get_crypt_ftr_info(&fname, NULL)) {
- return -1;
- }
-
- fd = open(fname, O_RDWR);
- if (fd < 0) {
- printf("Cannot open %s metadata file", fname);
- return -1;
- }
-
- pdata = malloc(crypt_ftr.persist_data_size);
- if (pdata == NULL) {
- printf("Cannot allocate persistant data");
- goto err;
- }
-
- if (lseek64(fd, crypt_ftr.persist_data_offset[0], SEEK_SET) < 0) {
- printf("Cannot seek to read persistent data on %s", fname);
- goto err2;
- }
-
- if (unix_read(fd, pdata, crypt_ftr.persist_data_size) < 0) {
- printf("Error reading persistent data before save");
- goto err2;
- }
-
- if (pdata->persist_magic == PERSIST_DATA_MAGIC) {
- /* The first copy is the curent valid copy, so write to
- * the second copy and erase this one */
- write_offset = crypt_ftr.persist_data_offset[1];
- erase_offset = crypt_ftr.persist_data_offset[0];
- } else {
- /* The second copy must be the valid copy, so write to
- * the first copy, and erase the second */
- write_offset = crypt_ftr.persist_data_offset[0];
- erase_offset = crypt_ftr.persist_data_offset[1];
- }
-
- /* Write the new copy first, if successful, then erase the old copy */
- if (lseek(fd, write_offset, SEEK_SET) < 0) {
- printf("Cannot seek to write persistent data");
- goto err2;
- }
- if (unix_write(fd, persist_data, crypt_ftr.persist_data_size) ==
- (int) crypt_ftr.persist_data_size) {
- if (lseek(fd, erase_offset, SEEK_SET) < 0) {
- printf("Cannot seek to erase previous persistent data");
- goto err2;
- }
- fsync(fd);
- memset(pdata, 0, crypt_ftr.persist_data_size);
- if (unix_write(fd, pdata, crypt_ftr.persist_data_size) !=
- (int) crypt_ftr.persist_data_size) {
- printf("Cannot write to erase previous persistent data");
- goto err2;
- }
- fsync(fd);
- } else {
- printf("Cannot write to save persistent data");
- goto err2;
- }
-
- /* Success */
- free(pdata);
- close(fd);
- return 0;
-
-err2:
- free(pdata);
-err:
- close(fd);
- return -1;
-}
-
static int hexdigit (char c)
{
if (c >= '0' && c <= '9') return c - '0';
@@ -1424,321 +1010,12 @@ static int decrypt_master_key(char *passwd, unsigned char *decrypted_master_key,
return ret;
}
-static int create_encrypted_random_key(char *passwd, unsigned char *master_key, unsigned char *salt,
- struct crypt_mnt_ftr *crypt_ftr) {
- int fd;
- unsigned char key_buf[KEY_LEN_BYTES];
- EVP_CIPHER_CTX e_ctx;
- int encrypted_len, final_len;
-
- /* Get some random bits for a key */
- fd = open("/dev/urandom", O_RDONLY);
- read(fd, key_buf, sizeof(key_buf));
- read(fd, salt, SALT_LEN);
- close(fd);
-
- /* Now encrypt it with the password */
- return encrypt_master_key(passwd, salt, key_buf, master_key, crypt_ftr);
-}
-
-static int wait_and_unmount(char *mountpoint, bool kill)
-{
- int i, err, rc;
-#define WAIT_UNMOUNT_COUNT 20
-
- /* Now umount the tmpfs filesystem */
- for (i=0; i<WAIT_UNMOUNT_COUNT; i++) {
- if (umount(mountpoint) == 0) {
- break;
- }
-
- if (errno == EINVAL) {
- /* EINVAL is returned if the directory is not a mountpoint,
- * i.e. there is no filesystem mounted there. So just get out.
- */
- break;
- }
-
- err = errno;
-
- /* If allowed, be increasingly aggressive before the last two retries */
- if (kill) {
- if (i == (WAIT_UNMOUNT_COUNT - 3)) {
- printf("sending SIGHUP to processes with open files\n");
- //vold_killProcessesWithOpenFiles(mountpoint, 1);
- } else if (i == (WAIT_UNMOUNT_COUNT - 2)) {
- printf("sending SIGKILL to processes with open files\n");
- //vold_killProcessesWithOpenFiles(mountpoint, 2);
- }
- }
-
- sleep(1);
- }
-
- if (i < WAIT_UNMOUNT_COUNT) {
- printf("unmounting %s succeeded\n", mountpoint);
- rc = 0;
- } else {
- //vold_killProcessesWithOpenFiles(mountpoint, 0);
- printf("unmounting %s failed: %s\n", mountpoint, strerror(err));
- rc = -1;
- }
-
- return rc;
-}
-
-#define DATA_PREP_TIMEOUT 200
-static int prep_data_fs(void)
-{
- int i;
-
- /* Do the prep of the /data filesystem */
- property_set("vold.post_fs_data_done", "0");
- property_set("vold.decrypt", "trigger_post_fs_data");
- printf("Just triggered post_fs_data\n");
-
- /* Wait a max of 50 seconds, hopefully it takes much less */
- for (i=0; i<DATA_PREP_TIMEOUT; i++) {
- char p[PROPERTY_VALUE_MAX];
-
- property_get("vold.post_fs_data_done", p, "0");
- if (*p == '1') {
- break;
- } else {
- usleep(250000);
- }
- }
- if (i == DATA_PREP_TIMEOUT) {
- /* Ugh, we failed to prep /data in time. Bail. */
- printf("post_fs_data timed out!\n");
- return -1;
- } else {
- printf("post_fs_data done\n");
- return 0;
- }
-}
-
-static void cryptfs_set_corrupt()
-{
- // Mark the footer as bad
- struct crypt_mnt_ftr crypt_ftr;
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Failed to get crypto footer - panic");
- return;
- }
-
- crypt_ftr.flags |= CRYPT_DATA_CORRUPT;
- if (put_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Failed to set crypto footer - panic");
- return;
- }
-}
-
-static void cryptfs_trigger_restart_min_framework()
-{
- if (fs_mgr_do_tmpfs_mount(DATA_MNT_POINT)) {
- printf("Failed to mount tmpfs on data - panic");
- return;
- }
-
- if (property_set("vold.decrypt", "trigger_post_fs_data")) {
- printf("Failed to trigger post fs data - panic");
- return;
- }
-
- if (property_set("vold.decrypt", "trigger_restart_min_framework")) {
- printf("Failed to trigger restart min framework - panic");
- return;
- }
-}
-
-/* returns < 0 on failure */
-static int cryptfs_restart_internal(int restart_main)
-{
- char fs_type[32];
- char real_blkdev[MAXPATHLEN];
- char crypto_blkdev[MAXPATHLEN];
- char fs_options[256];
- unsigned long mnt_flags;
- struct stat statbuf;
- int rc = -1, i;
- static int restart_successful = 0;
-
- /* Validate that it's OK to call this routine */
- if (! master_key_saved) {
- printf("Encrypted filesystem not validated, aborting");
- return -1;
- }
-
- if (restart_successful) {
- printf("System already restarted with encrypted disk, aborting");
- return -1;
- }
-
- if (restart_main) {
- /* Here is where we shut down the framework. The init scripts
- * start all services in one of three classes: core, main or late_start.
- * On boot, we start core and main. Now, we stop main, but not core,
- * as core includes vold and a few other really important things that
- * we need to keep running. Once main has stopped, we should be able
- * to umount the tmpfs /data, then mount the encrypted /data.
- * We then restart the class main, and also the class late_start.
- * At the moment, I've only put a few things in late_start that I know
- * are not needed to bring up the framework, and that also cause problems
- * with unmounting the tmpfs /data, but I hope to add add more services
- * to the late_start class as we optimize this to decrease the delay
- * till the user is asked for the password to the filesystem.
- */
-
- /* The init files are setup to stop the class main when vold.decrypt is
- * set to trigger_reset_main.
- */
- property_set("vold.decrypt", "trigger_reset_main");
- printf("Just asked init to shut down class main\n");
-
- /* Ugh, shutting down the framework is not synchronous, so until it
- * can be fixed, this horrible hack will wait a moment for it all to
- * shut down before proceeding. Without it, some devices cannot
- * restart the graphics services.
- */
- sleep(2);
- }
-
- /* Now that the framework is shutdown, we should be able to umount()
- * the tmpfs filesystem, and mount the real one.
- */
-
- property_get("ro.crypto.fs_crypto_blkdev", crypto_blkdev, "");
- if (strlen(crypto_blkdev) == 0) {
- printf("fs_crypto_blkdev not set\n");
- return -1;
- }
-
- if (! (rc = wait_and_unmount(DATA_MNT_POINT, true)) ) {
- /* If ro.crypto.readonly is set to 1, mount the decrypted
- * filesystem readonly. This is used when /data is mounted by
- * recovery mode.
- */
- char ro_prop[PROPERTY_VALUE_MAX];
- property_get("ro.crypto.readonly", ro_prop, "");
- if (strlen(ro_prop) > 0 && atoi(ro_prop)) {
- struct fstab_rec* rec = fs_mgr_get_entry_for_mount_point(fstab, DATA_MNT_POINT);
- rec->flags |= MS_RDONLY;
- }
-
- /* If that succeeded, then mount the decrypted filesystem */
- int retries = RETRY_MOUNT_ATTEMPTS;
- int mount_rc;
- while ((mount_rc = fs_mgr_do_mount(fstab, DATA_MNT_POINT,
- crypto_blkdev, 0))
- != 0) {
- if (mount_rc == FS_MGR_DOMNT_BUSY) {
- /* TODO: invoke something similar to
- Process::killProcessWithOpenFiles(DATA_MNT_POINT,
- retries > RETRY_MOUNT_ATTEMPT/2 ? 1 : 2 ) */
- printf("Failed to mount %s because it is busy - waiting",
- crypto_blkdev);
- if (--retries) {
- sleep(RETRY_MOUNT_DELAY_SECONDS);
- } else {
- /* Let's hope that a reboot clears away whatever is keeping
- the mount busy */
- cryptfs_reboot(reboot);
- }
- } else {
- printf("Failed to mount decrypted data");
- cryptfs_set_corrupt();
- cryptfs_trigger_restart_min_framework();
- printf("Started framework to offer wipe");
- return -1;
- }
- }
-
- property_set("vold.decrypt", "trigger_load_persist_props");
- /* Create necessary paths on /data */
- if (prep_data_fs()) {
- return -1;
- }
-
- /* startup service classes main and late_start */
- property_set("vold.decrypt", "trigger_restart_framework");
- printf("Just triggered restart_framework\n");
-
- /* Give it a few moments to get started */
- sleep(1);
- }
-
- if (rc == 0) {
- restart_successful = 1;
- }
-
- return rc;
-}
-
-int cryptfs_restart(void)
-{
- /* Call internal implementation forcing a restart of main service group */
- return cryptfs_restart_internal(1);
-}
-
-static int do_crypto_complete(char *mount_point UNUSED)
-{
- struct crypt_mnt_ftr crypt_ftr;
- char encrypted_state[PROPERTY_VALUE_MAX];
- char key_loc[PROPERTY_VALUE_MAX];
-
- property_get("ro.crypto.state", encrypted_state, "");
- if (strcmp(encrypted_state, "encrypted") ) {
- printf("not running with encryption, aborting");
- return CRYPTO_COMPLETE_NOT_ENCRYPTED;
- }
-
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- fs_mgr_get_crypt_info(fstab, key_loc, 0, sizeof(key_loc));
-
- /*
- * Only report this error if key_loc is a file and it exists.
- * If the device was never encrypted, and /data is not mountable for
- * some reason, returning 1 should prevent the UI from presenting the
- * a "enter password" screen, or worse, a "press button to wipe the
- * device" screen.
- */
- if ((key_loc[0] == '/') && (access("key_loc", F_OK) == -1)) {
- printf("master key file does not exist, aborting");
- return CRYPTO_COMPLETE_NOT_ENCRYPTED;
- } else {
- printf("Error getting crypt footer and key\n");
- return CRYPTO_COMPLETE_BAD_METADATA;
- }
- }
-
- // Test for possible error flags
- if (crypt_ftr.flags & CRYPT_ENCRYPTION_IN_PROGRESS){
- printf("Encryption process is partway completed\n");
- return CRYPTO_COMPLETE_PARTIAL;
- }
-
- if (crypt_ftr.flags & CRYPT_INCONSISTENT_STATE){
- printf("Encryption process was interrupted but cannot continue\n");
- return CRYPTO_COMPLETE_INCONSISTENT;
- }
-
- if (crypt_ftr.flags & CRYPT_DATA_CORRUPT){
- printf("Encryption is successful but data is corrupt\n");
- return CRYPTO_COMPLETE_CORRUPT;
- }
-
- /* We passed the test! We shall diminish, and return to the west */
- return CRYPTO_COMPLETE_ENCRYPTED;
-}
-
static int test_mount_encrypted_fs(struct crypt_mnt_ftr* crypt_ftr,
char *passwd, char *mount_point, char *label)
{
/* Allocate enough space for a 256 bit key, but we may use less */
unsigned char decrypted_master_key[32];
char crypto_blkdev[MAXPATHLEN];
- char real_blkdev[MAXPATHLEN];
char tmp_mount_point[64];
unsigned int orig_failed_decrypt_count;
int rc;
@@ -1761,8 +1038,6 @@ static int test_mount_encrypted_fs(struct crypt_mnt_ftr* crypt_ftr,
}
}
- fs_mgr_get_crypt_info(fstab, 0, real_blkdev, sizeof(real_blkdev));
-
// Create crypto block device - all (non fatal) code paths
// need it
if (create_crypto_blk_dev(crypt_ftr, decrypted_master_key,
@@ -1795,7 +1070,7 @@ static int test_mount_encrypted_fs(struct crypt_mnt_ftr* crypt_ftr,
* the footer, not the key. */
sprintf(tmp_mount_point, "%s/tmp_mnt", mount_point);
mkdir(tmp_mount_point, 0755);
- if (fs_mgr_do_mount(fstab, DATA_MNT_POINT, crypto_blkdev, tmp_mount_point)) {
+ if (mount(crypto_blkdev, tmp_mount_point, file_system, NULL, NULL) != 0) {
printf("Error temp mounting decrypted block device '%s'\n", crypto_blkdev);
delete_crypto_blk_dev(label);
@@ -1877,52 +1152,6 @@ int cryptfs_revert_volume(const char *label)
return delete_crypto_blk_dev((char *)label);
}
-/*
- * Called by vold when it's asked to mount an encrypted, nonremovable volume.
- * Setup a dm-crypt mapping, use the saved master key from
- * setting up the /data mapping, and return the new device path.
- */
-int cryptfs_setup_volume(const char *label, int major, int minor,
- char *crypto_sys_path, unsigned int max_path,
- int *new_major, int *new_minor)
-{
- char real_blkdev[MAXPATHLEN], crypto_blkdev[MAXPATHLEN];
- struct crypt_mnt_ftr sd_crypt_ftr;
- struct stat statbuf;
- int nr_sec, fd;
-
- sprintf(real_blkdev, "/dev/block/vold/%d:%d", major, minor);
-
- get_crypt_ftr_and_key(&sd_crypt_ftr);
-
- /* Update the fs_size field to be the size of the volume */
- fd = open(real_blkdev, O_RDONLY);
- nr_sec = get_blkdev_size(fd);
- close(fd);
- if (nr_sec == 0) {
- printf("Cannot get size of volume %s\n", real_blkdev);
- return -1;
- }
-
- sd_crypt_ftr.fs_size = nr_sec;
- create_crypto_blk_dev(&sd_crypt_ftr, saved_master_key, real_blkdev,
- crypto_blkdev, label);
-
- stat(crypto_blkdev, &statbuf);
- *new_major = MAJOR(statbuf.st_rdev);
- *new_minor = MINOR(statbuf.st_rdev);
-
- /* Create path to sys entry for this block device */
- snprintf(crypto_sys_path, max_path, "/devices/virtual/block/%s", strrchr(crypto_blkdev, '/')+1);
-
- return 0;
-}
-
-int cryptfs_crypto_complete(void)
-{
- return do_crypto_complete("/data");
-}
-
int check_unmounted_and_get_ftr(struct crypt_mnt_ftr* crypt_ftr)
{
char encrypted_state[PROPERTY_VALUE_MAX];
@@ -2034,24 +1263,11 @@ char* hexadj_passwd(const char* passwd)
return hex;
}
-#define FSTAB_PREFIX "/fstab."
-
-int cryptfs_check_footer(void)
+int cryptfs_check_footer()
{
int rc = -1;
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
- char propbuf[PROPERTY_VALUE_MAX];
struct crypt_mnt_ftr crypt_ftr;
- property_get("ro.hardware", propbuf, "");
- snprintf(fstab_filename, sizeof(fstab_filename), FSTAB_PREFIX"%s", propbuf);
-
- fstab = fs_mgr_read_fstab(fstab_filename);
- if (!fstab) {
- printf("failed to open %s\n", fstab_filename);
- return -1;
- }
-
rc = get_crypt_ftr_and_key(&crypt_ftr);
return rc;
@@ -2061,17 +1277,6 @@ int cryptfs_check_passwd(char *passwd)
{
struct crypt_mnt_ftr crypt_ftr;
int rc;
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
- char propbuf[PROPERTY_VALUE_MAX];
-
- property_get("ro.hardware", propbuf, "");
- snprintf(fstab_filename, sizeof(fstab_filename), FSTAB_PREFIX"%s", propbuf);
-
- fstab = fs_mgr_read_fstab(fstab_filename);
- if (!fstab) {
- printf("failed to open %s\n", fstab_filename);
- return -1;
- }
rc = check_unmounted_and_get_ftr(&crypt_ftr);
if (rc)
@@ -2223,1366 +1428,11 @@ static int cryptfs_init_crypt_mnt_ftr(struct crypt_mnt_ftr *ftr)
return 0;
}
-static int cryptfs_enable_wipe(char *crypto_blkdev, off64_t size, int type)
-{
- const char *args[10];
- char size_str[32]; /* Must be large enough to hold a %lld and null byte */
- int num_args;
- int status;
- int tmp;
- int rc = -1;
-
- if (type == EXT4_FS) {
- args[0] = "/system/bin/make_ext4fs";
- args[1] = "-a";
- args[2] = "/data";
- args[3] = "-l";
- snprintf(size_str, sizeof(size_str), "%" PRId64, size * 512);
- args[4] = size_str;
- args[5] = crypto_blkdev;
- num_args = 6;
- printf("Making empty filesystem with command %s %s %s %s %s %s\n",
- args[0], args[1], args[2], args[3], args[4], args[5]);
- } else if (type == F2FS_FS) {
- args[0] = "/system/bin/mkfs.f2fs";
- args[1] = "-t";
- args[2] = "-d1";
- args[3] = crypto_blkdev;
- snprintf(size_str, sizeof(size_str), "%" PRId64, size);
- args[4] = size_str;
- num_args = 5;
- printf("Making empty filesystem with command %s %s %s %s %s\n",
- args[0], args[1], args[2], args[3], args[4]);
- } else {
- printf("cryptfs_enable_wipe(): unknown filesystem type %d\n", type);
- return -1;
- }
-
- tmp = android_fork_execvp(num_args, (char **)args, &status, false, true);
-
- if (tmp != 0) {
- printf("Error creating empty filesystem on %s due to logwrap error\n", crypto_blkdev);
- } else {
- if (WIFEXITED(status)) {
- if (WEXITSTATUS(status)) {
- printf("Error creating filesystem on %s, exit status %d ",
- crypto_blkdev, WEXITSTATUS(status));
- } else {
- printf("Successfully created filesystem on %s\n", crypto_blkdev);
- rc = 0;
- }
- } else {
- printf("Error creating filesystem on %s, did not exit normally\n", crypto_blkdev);
- }
- }
-
- return rc;
-}
-
-#define CRYPT_INPLACE_BUFSIZE 4096
-#define CRYPT_SECTORS_PER_BUFSIZE (CRYPT_INPLACE_BUFSIZE / CRYPT_SECTOR_SIZE)
-#define CRYPT_SECTOR_SIZE 512
-
-/* aligned 32K writes tends to make flash happy.
- * SD card association recommends it.
- */
-#define BLOCKS_AT_A_TIME 8
-
-struct encryptGroupsData
-{
- int realfd;
- int cryptofd;
- off64_t numblocks;
- off64_t one_pct, cur_pct, new_pct;
- off64_t blocks_already_done, tot_numblocks;
- off64_t used_blocks_already_done, tot_used_blocks;
- char* real_blkdev, * crypto_blkdev;
- int count;
- off64_t offset;
- char* buffer;
- off64_t last_written_sector;
- int completed;
- time_t time_started;
- int remaining_time;
-};
-
-static void update_progress(struct encryptGroupsData* data, int is_used)
-{
- data->blocks_already_done++;
-
- if (is_used) {
- data->used_blocks_already_done++;
- }
- if (data->tot_used_blocks) {
- data->new_pct = data->used_blocks_already_done / data->one_pct;
- } else {
- data->new_pct = data->blocks_already_done / data->one_pct;
- }
-
- if (data->new_pct > data->cur_pct) {
- char buf[8];
- data->cur_pct = data->new_pct;
- snprintf(buf, sizeof(buf), "%" PRId64, data->cur_pct);
- property_set("vold.encrypt_progress", buf);
- }
-
- if (data->cur_pct >= 5) {
- struct timespec time_now;
- if (clock_gettime(CLOCK_MONOTONIC, &time_now)) {
- printf("Error getting time");
- } else {
- double elapsed_time = difftime(time_now.tv_sec, data->time_started);
- off64_t remaining_blocks = data->tot_used_blocks
- - data->used_blocks_already_done;
- int remaining_time = (int)(elapsed_time * remaining_blocks
- / data->used_blocks_already_done);
-
- // Change time only if not yet set, lower, or a lot higher for
- // best user experience
- if (data->remaining_time == -1
- || remaining_time < data->remaining_time
- || remaining_time > data->remaining_time + 60) {
- char buf[8];
- snprintf(buf, sizeof(buf), "%d", remaining_time);
- property_set("vold.encrypt_time_remaining", buf);
- data->remaining_time = remaining_time;
- }
- }
- }
-}
-
-static void log_progress(struct encryptGroupsData const* data, bool completed)
-{
- // Precondition - if completed data = 0 else data != 0
-
- // Track progress so we can skip logging blocks
- static off64_t offset = -1;
-
- // Need to close existing 'Encrypting from' log?
- if (completed || (offset != -1 && data->offset != offset)) {
- printf("Encrypted to sector %" PRId64,
- offset / info.block_size * CRYPT_SECTOR_SIZE);
- offset = -1;
- }
-
- // Need to start new 'Encrypting from' log?
- if (!completed && offset != data->offset) {
- printf("Encrypting from sector %" PRId64,
- data->offset / info.block_size * CRYPT_SECTOR_SIZE);
- }
-
- // Update offset
- if (!completed) {
- offset = data->offset + (off64_t)data->count * info.block_size;
- }
-}
-
-static int flush_outstanding_data(struct encryptGroupsData* data)
-{
- if (data->count == 0) {
- return 0;
- }
-
- printf("Copying %d blocks at offset %" PRIx64, data->count, data->offset);
-
- if (pread64(data->realfd, data->buffer,
- info.block_size * data->count, data->offset)
- <= 0) {
- printf("Error reading real_blkdev %s for inplace encrypt",
- data->real_blkdev);
- return -1;
- }
-
- if (pwrite64(data->cryptofd, data->buffer,
- info.block_size * data->count, data->offset)
- <= 0) {
- printf("Error writing crypto_blkdev %s for inplace encrypt",
- data->crypto_blkdev);
- return -1;
- } else {
- log_progress(data, false);
- }
-
- data->count = 0;
- data->last_written_sector = (data->offset + data->count)
- / info.block_size * CRYPT_SECTOR_SIZE - 1;
- return 0;
-}
-
-static int encrypt_groups(struct encryptGroupsData* data)
-{
- unsigned int i;
- u8 *block_bitmap = 0;
- unsigned int block;
- off64_t ret;
- int rc = -1;
-
- data->buffer = malloc(info.block_size * BLOCKS_AT_A_TIME);
- if (!data->buffer) {
- printf("Failed to allocate crypto buffer");
- goto errout;
- }
-
- block_bitmap = malloc(info.block_size);
- if (!block_bitmap) {
- printf("failed to allocate block bitmap");
- goto errout;
- }
-
- for (i = 0; i < aux_info.groups; ++i) {
- printf("Encrypting group %d", i);
-
- u32 first_block = aux_info.first_data_block + i * info.blocks_per_group;
- u32 block_count = min(info.blocks_per_group,
- aux_info.len_blocks - first_block);
-
- off64_t offset = (u64)info.block_size
- * aux_info.bg_desc[i].bg_block_bitmap;
-
- ret = pread64(data->realfd, block_bitmap, info.block_size, offset);
- if (ret != (int)info.block_size) {
- printf("failed to read all of block group bitmap %d", i);
- goto errout;
- }
-
- offset = (u64)info.block_size * first_block;
-
- data->count = 0;
-
- for (block = 0; block < block_count; block++) {
- int used = bitmap_get_bit(block_bitmap, block);
- update_progress(data, used);
- if (used) {
- if (data->count == 0) {
- data->offset = offset;
- }
- data->count++;
- } else {
- if (flush_outstanding_data(data)) {
- goto errout;
- }
- }
-
- offset += info.block_size;
-
- /* Write data if we are aligned or buffer size reached */
- if (offset % (info.block_size * BLOCKS_AT_A_TIME) == 0
- || data->count == BLOCKS_AT_A_TIME) {
- if (flush_outstanding_data(data)) {
- goto errout;
- }
- }
-
- if (1) {
- printf("Stopping encryption due to low battery");
- rc = 0;
- goto errout;
- }
-
- }
- if (flush_outstanding_data(data)) {
- goto errout;
- }
- }
-
- data->completed = 1;
- rc = 0;
-
-errout:
- log_progress(0, true);
- free(data->buffer);
- free(block_bitmap);
- return rc;
-}
-
-static int cryptfs_enable_inplace_ext4(char *crypto_blkdev,
- char *real_blkdev,
- off64_t size,
- off64_t *size_already_done,
- off64_t tot_size,
- off64_t previously_encrypted_upto)
-{
- u32 i;
- struct encryptGroupsData data;
- int rc; // Can't initialize without causing warning -Wclobbered
-
- if (previously_encrypted_upto > *size_already_done) {
- printf("Not fast encrypting since resuming part way through");
- return -1;
- }
-
- memset(&data, 0, sizeof(data));
- data.real_blkdev = real_blkdev;
- data.crypto_blkdev = crypto_blkdev;
-
- if ( (data.realfd = open(real_blkdev, O_RDWR)) < 0) {
- printf("Error opening real_blkdev %s for inplace encrypt. err=%d(%s)\n",
- real_blkdev, errno, strerror(errno));
- rc = -1;
- goto errout;
- }
-
- if ( (data.cryptofd = open(crypto_blkdev, O_WRONLY)) < 0) {
- printf("Error opening crypto_blkdev %s for ext4 inplace encrypt. err=%d(%s)\n",
- crypto_blkdev, errno, strerror(errno));
- rc = ENABLE_INPLACE_ERR_DEV;
- goto errout;
- }
-
- if (setjmp(setjmp_env)) {
- printf("Reading ext4 extent caused an exception\n");
- rc = -1;
- goto errout;
- }
-
- if (read_ext(data.realfd, 0) != 0) {
- printf("Failed to read ext4 extent\n");
- rc = -1;
- goto errout;
- }
-
- data.numblocks = size / CRYPT_SECTORS_PER_BUFSIZE;
- data.tot_numblocks = tot_size / CRYPT_SECTORS_PER_BUFSIZE;
- data.blocks_already_done = *size_already_done / CRYPT_SECTORS_PER_BUFSIZE;
-
- printf("Encrypting ext4 filesystem in place...");
-
- data.tot_used_blocks = data.numblocks;
- for (i = 0; i < aux_info.groups; ++i) {
- data.tot_used_blocks -= aux_info.bg_desc[i].bg_free_blocks_count;
- }
-
- data.one_pct = data.tot_used_blocks / 100;
- data.cur_pct = 0;
-
- struct timespec time_started = {0};
- if (clock_gettime(CLOCK_MONOTONIC, &time_started)) {
- printf("Error getting time at start");
- // Note - continue anyway - we'll run with 0
- }
- data.time_started = time_started.tv_sec;
- data.remaining_time = -1;
-
- rc = encrypt_groups(&data);
- if (rc) {
- printf("Error encrypting groups");
- goto errout;
- }
-
- *size_already_done += data.completed ? size : data.last_written_sector;
- rc = 0;
-
-errout:
- close(data.realfd);
- close(data.cryptofd);
-
- return rc;
-}
-
-static void log_progress_f2fs(u64 block, bool completed)
-{
- // Precondition - if completed data = 0 else data != 0
-
- // Track progress so we can skip logging blocks
- static u64 last_block = (u64)-1;
-
- // Need to close existing 'Encrypting from' log?
- if (completed || (last_block != (u64)-1 && block != last_block + 1)) {
- printf("Encrypted to block %" PRId64, last_block);
- last_block = -1;
- }
-
- // Need to start new 'Encrypting from' log?
- if (!completed && (last_block == (u64)-1 || block != last_block + 1)) {
- printf("Encrypting from block %" PRId64, block);
- }
-
- // Update offset
- if (!completed) {
- last_block = block;
- }
-}
-
-static int encrypt_one_block_f2fs(u64 pos, void *data)
-{
- struct encryptGroupsData *priv_dat = (struct encryptGroupsData *)data;
-
- priv_dat->blocks_already_done = pos - 1;
- update_progress(priv_dat, 1);
-
- off64_t offset = pos * CRYPT_INPLACE_BUFSIZE;
-
- if (pread64(priv_dat->realfd, priv_dat->buffer, CRYPT_INPLACE_BUFSIZE, offset) <= 0) {
- printf("Error reading real_blkdev %s for f2fs inplace encrypt", priv_dat->crypto_blkdev);
- return -1;
- }
-
- if (pwrite64(priv_dat->cryptofd, priv_dat->buffer, CRYPT_INPLACE_BUFSIZE, offset) <= 0) {
- printf("Error writing crypto_blkdev %s for f2fs inplace encrypt", priv_dat->crypto_blkdev);
- return -1;
- } else {
- log_progress_f2fs(pos, false);
- }
-
- return 0;
-}
-
-static int cryptfs_enable_inplace_f2fs(char *crypto_blkdev,
- char *real_blkdev,
- off64_t size,
- off64_t *size_already_done,
- off64_t tot_size,
- off64_t previously_encrypted_upto)
-{
- u32 i;
- struct encryptGroupsData data;
- struct f2fs_info *f2fs_info = NULL;
- int rc = ENABLE_INPLACE_ERR_OTHER;
- if (previously_encrypted_upto > *size_already_done) {
- printf("Not fast encrypting since resuming part way through");
- return ENABLE_INPLACE_ERR_OTHER;
- }
- memset(&data, 0, sizeof(data));
- data.real_blkdev = real_blkdev;
- data.crypto_blkdev = crypto_blkdev;
- data.realfd = -1;
- data.cryptofd = -1;
- if ( (data.realfd = open64(real_blkdev, O_RDWR)) < 0) {
- printf("Error opening real_blkdev %s for f2fs inplace encrypt\n",
- real_blkdev);
- goto errout;
- }
- if ( (data.cryptofd = open64(crypto_blkdev, O_WRONLY)) < 0) {
- printf("Error opening crypto_blkdev %s for f2fs inplace encrypt. err=%d(%s)\n",
- crypto_blkdev, errno, strerror(errno));
- rc = ENABLE_INPLACE_ERR_DEV;
- goto errout;
- }
-
- f2fs_info = generate_f2fs_info(data.realfd);
- if (!f2fs_info)
- goto errout;
-
- data.numblocks = size / CRYPT_SECTORS_PER_BUFSIZE;
- data.tot_numblocks = tot_size / CRYPT_SECTORS_PER_BUFSIZE;
- data.blocks_already_done = *size_already_done / CRYPT_SECTORS_PER_BUFSIZE;
-
- data.tot_used_blocks = get_num_blocks_used(f2fs_info);
-
- data.one_pct = data.tot_used_blocks / 100;
- data.cur_pct = 0;
- data.time_started = time(NULL);
- data.remaining_time = -1;
-
- data.buffer = malloc(f2fs_info->block_size);
- if (!data.buffer) {
- printf("Failed to allocate crypto buffer");
- goto errout;
- }
-
- data.count = 0;
-
- /* Currently, this either runs to completion, or hits a nonrecoverable error */
- rc = run_on_used_blocks(data.blocks_already_done, f2fs_info, &encrypt_one_block_f2fs, &data);
-
- if (rc) {
- printf("Error in running over f2fs blocks");
- rc = ENABLE_INPLACE_ERR_OTHER;
- goto errout;
- }
-
- *size_already_done += size;
- rc = 0;
-
-errout:
- if (rc)
- printf("Failed to encrypt f2fs filesystem on %s", real_blkdev);
-
- log_progress_f2fs(0, true);
- free(f2fs_info);
- free(data.buffer);
- close(data.realfd);
- close(data.cryptofd);
-
- return rc;
-}
-
-static int cryptfs_enable_inplace_full(char *crypto_blkdev, char *real_blkdev,
- off64_t size, off64_t *size_already_done,
- off64_t tot_size,
- off64_t previously_encrypted_upto)
-{
- int realfd, cryptofd;
- char *buf[CRYPT_INPLACE_BUFSIZE];
- int rc = ENABLE_INPLACE_ERR_OTHER;
- off64_t numblocks, i, remainder;
- off64_t one_pct, cur_pct, new_pct;
- off64_t blocks_already_done, tot_numblocks;
-
- if ( (realfd = open(real_blkdev, O_RDONLY)) < 0) {
- printf("Error opening real_blkdev %s for inplace encrypt\n", real_blkdev);
- return ENABLE_INPLACE_ERR_OTHER;
- }
-
- if ( (cryptofd = open(crypto_blkdev, O_WRONLY)) < 0) {
- printf("Error opening crypto_blkdev %s for inplace encrypt. err=%d(%s)\n",
- crypto_blkdev, errno, strerror(errno));
- close(realfd);
- return ENABLE_INPLACE_ERR_DEV;
- }
-
- /* This is pretty much a simple loop of reading 4K, and writing 4K.
- * The size passed in is the number of 512 byte sectors in the filesystem.
- * So compute the number of whole 4K blocks we should read/write,
- * and the remainder.
- */
- numblocks = size / CRYPT_SECTORS_PER_BUFSIZE;
- remainder = size % CRYPT_SECTORS_PER_BUFSIZE;
- tot_numblocks = tot_size / CRYPT_SECTORS_PER_BUFSIZE;
- blocks_already_done = *size_already_done / CRYPT_SECTORS_PER_BUFSIZE;
-
- printf("Encrypting filesystem in place...");
-
- i = previously_encrypted_upto + 1 - *size_already_done;
-
- if (lseek64(realfd, i * CRYPT_SECTOR_SIZE, SEEK_SET) < 0) {
- printf("Cannot seek to previously encrypted point on %s", real_blkdev);
- goto errout;
- }
-
- if (lseek64(cryptofd, i * CRYPT_SECTOR_SIZE, SEEK_SET) < 0) {
- printf("Cannot seek to previously encrypted point on %s", crypto_blkdev);
- goto errout;
- }
-
- for (;i < size && i % CRYPT_SECTORS_PER_BUFSIZE != 0; ++i) {
- if (unix_read(realfd, buf, CRYPT_SECTOR_SIZE) <= 0) {
- printf("Error reading initial sectors from real_blkdev %s for "
- "inplace encrypt\n", crypto_blkdev);
- goto errout;
- }
- if (unix_write(cryptofd, buf, CRYPT_SECTOR_SIZE) <= 0) {
- printf("Error writing initial sectors to crypto_blkdev %s for "
- "inplace encrypt\n", crypto_blkdev);
- goto errout;
- } else {
- printf("Encrypted 1 block at %" PRId64, i);
- }
- }
-
- one_pct = tot_numblocks / 100;
- cur_pct = 0;
- /* process the majority of the filesystem in blocks */
- for (i/=CRYPT_SECTORS_PER_BUFSIZE; i<numblocks; i++) {
- new_pct = (i + blocks_already_done) / one_pct;
- if (new_pct > cur_pct) {
- char buf[8];
-
- cur_pct = new_pct;
- snprintf(buf, sizeof(buf), "%" PRId64, cur_pct);
- property_set("vold.encrypt_progress", buf);
- }
- if (unix_read(realfd, buf, CRYPT_INPLACE_BUFSIZE) <= 0) {
- printf("Error reading real_blkdev %s for inplace encrypt", crypto_blkdev);
- goto errout;
- }
- if (unix_write(cryptofd, buf, CRYPT_INPLACE_BUFSIZE) <= 0) {
- printf("Error writing crypto_blkdev %s for inplace encrypt", crypto_blkdev);
- goto errout;
- } else {
- printf("Encrypted %d block at %" PRId64,
- CRYPT_SECTORS_PER_BUFSIZE,
- i * CRYPT_SECTORS_PER_BUFSIZE);
- }
-
- if (1) {
- printf("Stopping encryption due to low battery");
- *size_already_done += (i + 1) * CRYPT_SECTORS_PER_BUFSIZE - 1;
- rc = 0;
- goto errout;
- }
- }
-
- /* Do any remaining sectors */
- for (i=0; i<remainder; i++) {
- if (unix_read(realfd, buf, CRYPT_SECTOR_SIZE) <= 0) {
- printf("Error reading final sectors from real_blkdev %s for inplace encrypt", crypto_blkdev);
- goto errout;
- }
- if (unix_write(cryptofd, buf, CRYPT_SECTOR_SIZE) <= 0) {
- printf("Error writing final sectors to crypto_blkdev %s for inplace encrypt", crypto_blkdev);
- goto errout;
- } else {
- printf("Encrypted 1 block at next location");
- }
- }
-
- *size_already_done += size;
- rc = 0;
-
-errout:
- close(realfd);
- close(cryptofd);
-
- return rc;
-}
-
-/* returns on of the ENABLE_INPLACE_* return codes */
-static int cryptfs_enable_inplace(char *crypto_blkdev, char *real_blkdev,
- off64_t size, off64_t *size_already_done,
- off64_t tot_size,
- off64_t previously_encrypted_upto)
-{
- int rc_ext4, rc_f2fs, rc_full;
- if (previously_encrypted_upto) {
- printf("Continuing encryption from %" PRId64, previously_encrypted_upto);
- }
-
- if (*size_already_done + size < previously_encrypted_upto) {
- *size_already_done += size;
- return 0;
- }
-
- /* TODO: identify filesystem type.
- * As is, cryptfs_enable_inplace_ext4 will fail on an f2fs partition, and
- * then we will drop down to cryptfs_enable_inplace_f2fs.
- * */
- if ((rc_ext4 = cryptfs_enable_inplace_ext4(crypto_blkdev, real_blkdev,
- size, size_already_done,
- tot_size, previously_encrypted_upto)) == 0) {
- return 0;
- }
- printf("cryptfs_enable_inplace_ext4()=%d\n", rc_ext4);
-
- if ((rc_f2fs = cryptfs_enable_inplace_f2fs(crypto_blkdev, real_blkdev,
- size, size_already_done,
- tot_size, previously_encrypted_upto)) == 0) {
- return 0;
- }
- printf("cryptfs_enable_inplace_f2fs()=%d\n", rc_f2fs);
-
- rc_full = cryptfs_enable_inplace_full(crypto_blkdev, real_blkdev,
- size, size_already_done, tot_size,
- previously_encrypted_upto);
- printf("cryptfs_enable_inplace_full()=%d\n", rc_full);
-
- /* Hack for b/17898962, the following is the symptom... */
- if (rc_ext4 == ENABLE_INPLACE_ERR_DEV
- && rc_f2fs == ENABLE_INPLACE_ERR_DEV
- && rc_full == ENABLE_INPLACE_ERR_DEV) {
- return ENABLE_INPLACE_ERR_DEV;
- }
- return rc_full;
-}
-
-#define CRYPTO_ENABLE_WIPE 1
-#define CRYPTO_ENABLE_INPLACE 2
-
-#define FRAMEWORK_BOOT_WAIT 60
-
-static inline int should_encrypt(struct volume_info *volume)
-{
- return (volume->flags & (VOL_ENCRYPTABLE | VOL_NONREMOVABLE)) ==
- (VOL_ENCRYPTABLE | VOL_NONREMOVABLE);
-}
-
-static int cryptfs_SHA256_fileblock(const char* filename, __le8* buf)
-{
- int fd = open(filename, O_RDONLY);
- if (fd == -1) {
- printf("Error opening file %s", filename);
- return -1;
- }
-
- char block[CRYPT_INPLACE_BUFSIZE];
- memset(block, 0, sizeof(block));
- if (unix_read(fd, block, sizeof(block)) < 0) {
- printf("Error reading file %s", filename);
- close(fd);
- return -1;
- }
-
- close(fd);
-
- SHA256_CTX c;
- SHA256_Init(&c);
- SHA256_Update(&c, block, sizeof(block));
- SHA256_Final(buf, &c);
-
- return 0;
-}
-
-static int get_fs_type(struct fstab_rec *rec)
-{
- if (!strcmp(rec->fs_type, "ext4")) {
- return EXT4_FS;
- } else if (!strcmp(rec->fs_type, "f2fs")) {
- return F2FS_FS;
- } else {
- return -1;
- }
-}
-
-static int cryptfs_enable_all_volumes(struct crypt_mnt_ftr *crypt_ftr, int how,
- char *crypto_blkdev, char *real_blkdev,
- int previously_encrypted_upto)
-{
- off64_t cur_encryption_done=0, tot_encryption_size=0;
- int i, rc = -1;
-
- if (1) {
- printf("Not starting encryption due to low battery");
- return 0;
- }
-
- /* The size of the userdata partition, and add in the vold volumes below */
- tot_encryption_size = crypt_ftr->fs_size;
-
- if (how == CRYPTO_ENABLE_WIPE) {
- struct fstab_rec* rec = fs_mgr_get_entry_for_mount_point(fstab, DATA_MNT_POINT);
- int fs_type = get_fs_type(rec);
- if (fs_type < 0) {
- printf("cryptfs_enable: unsupported fs type %s\n", rec->fs_type);
- return -1;
- }
- rc = cryptfs_enable_wipe(crypto_blkdev, crypt_ftr->fs_size, fs_type);
- } else if (how == CRYPTO_ENABLE_INPLACE) {
- rc = cryptfs_enable_inplace(crypto_blkdev, real_blkdev,
- crypt_ftr->fs_size, &cur_encryption_done,
- tot_encryption_size,
- previously_encrypted_upto);
-
- if (rc == ENABLE_INPLACE_ERR_DEV) {
- /* Hack for b/17898962 */
- printf("cryptfs_enable: crypto block dev failure. Must reboot...\n");
- cryptfs_reboot(reboot);
- }
-
- if (!rc) {
- crypt_ftr->encrypted_upto = cur_encryption_done;
- }
-
- if (!rc && crypt_ftr->encrypted_upto == crypt_ftr->fs_size) {
- /* The inplace routine never actually sets the progress to 100% due
- * to the round down nature of integer division, so set it here */
- property_set("vold.encrypt_progress", "100");
- }
- } else {
- /* Shouldn't happen */
- printf("cryptfs_enable: internal error, unknown option\n");
- rc = -1;
- }
-
- return rc;
-}
-
-int cryptfs_enable_internal(char *howarg, int crypt_type, char *passwd,
- int allow_reboot)
-{
- int how = 0;
- char crypto_blkdev[MAXPATHLEN], real_blkdev[MAXPATHLEN];
- unsigned long nr_sec;
- unsigned char decrypted_master_key[KEY_LEN_BYTES];
- int rc=-1, fd, i, ret;
- struct crypt_mnt_ftr crypt_ftr;
- struct crypt_persist_data *pdata;
- char encrypted_state[PROPERTY_VALUE_MAX];
- char lockid[32] = { 0 };
- char key_loc[PROPERTY_VALUE_MAX];
- char fuse_sdcard[PROPERTY_VALUE_MAX];
- char *sd_mnt_point;
- int num_vols;
- struct volume_info *vol_list = 0;
- off64_t previously_encrypted_upto = 0;
-printf("cryptfs_enable_internal disabled by TWRP\n");
-return -1;
- if (!strcmp(howarg, "wipe")) {
- how = CRYPTO_ENABLE_WIPE;
- } else if (! strcmp(howarg, "inplace")) {
- how = CRYPTO_ENABLE_INPLACE;
- } else {
- /* Shouldn't happen, as CommandListener vets the args */
- goto error_unencrypted;
- }
-
- /* See if an encryption was underway and interrupted */
- if (how == CRYPTO_ENABLE_INPLACE
- && get_crypt_ftr_and_key(&crypt_ftr) == 0
- && (crypt_ftr.flags & CRYPT_ENCRYPTION_IN_PROGRESS)) {
- previously_encrypted_upto = crypt_ftr.encrypted_upto;
- crypt_ftr.encrypted_upto = 0;
- crypt_ftr.flags &= ~CRYPT_ENCRYPTION_IN_PROGRESS;
-
- /* At this point, we are in an inconsistent state. Until we successfully
- complete encryption, a reboot will leave us broken. So mark the
- encryption failed in case that happens.
- On successfully completing encryption, remove this flag */
- crypt_ftr.flags |= CRYPT_INCONSISTENT_STATE;
-
- put_crypt_ftr_and_key(&crypt_ftr);
- }
-
- property_get("ro.crypto.state", encrypted_state, "");
- if (!strcmp(encrypted_state, "encrypted") && !previously_encrypted_upto) {
- printf("Device is already running encrypted, aborting");
- goto error_unencrypted;
- }
-
- // TODO refactor fs_mgr_get_crypt_info to get both in one call
- fs_mgr_get_crypt_info(fstab, key_loc, 0, sizeof(key_loc));
- fs_mgr_get_crypt_info(fstab, 0, real_blkdev, sizeof(real_blkdev));
-
- /* Get the size of the real block device */
- fd = open(real_blkdev, O_RDONLY);
- if ( (nr_sec = get_blkdev_size(fd)) == 0) {
- printf("Cannot get size of block device %s\n", real_blkdev);
- goto error_unencrypted;
- }
- close(fd);
-
- /* If doing inplace encryption, make sure the orig fs doesn't include the crypto footer */
- if ((how == CRYPTO_ENABLE_INPLACE) && (!strcmp(key_loc, KEY_IN_FOOTER))) {
- unsigned int fs_size_sec, max_fs_size_sec;
- fs_size_sec = get_fs_size(real_blkdev);
- if (fs_size_sec == 0)
- fs_size_sec = get_f2fs_filesystem_size_sec(real_blkdev);
-
- max_fs_size_sec = nr_sec - (CRYPT_FOOTER_OFFSET / CRYPT_SECTOR_SIZE);
-
- if (fs_size_sec > max_fs_size_sec) {
- printf("Orig filesystem overlaps crypto footer region. Cannot encrypt in place.");
- goto error_unencrypted;
- }
- }
-
- /* Get a wakelock as this may take a while, and we don't want the
- * device to sleep on us. We'll grab a partial wakelock, and if the UI
- * wants to keep the screen on, it can grab a full wakelock.
- */
- snprintf(lockid, sizeof(lockid), "enablecrypto%d", (int) getpid());
- acquire_wake_lock(PARTIAL_WAKE_LOCK, lockid);
-
- /* Get the sdcard mount point */
- sd_mnt_point = getenv("EMULATED_STORAGE_SOURCE");
- if (!sd_mnt_point) {
- sd_mnt_point = getenv("EXTERNAL_STORAGE");
- }
- if (!sd_mnt_point) {
- sd_mnt_point = "/mnt/sdcard";
- }
-
- /* TODO
- * Currently do not have test devices with multiple encryptable volumes.
- * When we acquire some, re-add support.
- */
- num_vols=0/*vold_getNumDirectVolumes()*/;
- vol_list = malloc(sizeof(struct volume_info) * num_vols);
- //vold_getDirectVolumeList(vol_list);
-
- for (i=0; i<num_vols; i++) {
- if (should_encrypt(&vol_list[i])) {
- printf("Cannot encrypt if there are multiple encryptable volumes"
- "%s\n", vol_list[i].label);
- goto error_unencrypted;
- }
- }
-
- /* The init files are setup to stop the class main and late start when
- * vold sets trigger_shutdown_framework.
- */
- property_set("vold.decrypt", "trigger_shutdown_framework");
- printf("Just asked init to shut down class main\n");
-
- if (1 /*vold_unmountAllAsecs()*/) {
- /* Just report the error. If any are left mounted,
- * umounting /data below will fail and handle the error.
- */
- printf("Error unmounting internal asecs");
- }
-
- property_get("ro.crypto.fuse_sdcard", fuse_sdcard, "");
- if (!strcmp(fuse_sdcard, "true")) {
- /* This is a device using the fuse layer to emulate the sdcard semantics
- * on top of the userdata partition. vold does not manage it, it is managed
- * by the sdcard service. The sdcard service was killed by the property trigger
- * above, so just unmount it now. We must do this _AFTER_ killing the framework,
- * unlike the case for vold managed devices above.
- */
- if (wait_and_unmount(sd_mnt_point, false)) {
- goto error_shutting_down;
- }
- }
-
- /* Now unmount the /data partition. */
- if (wait_and_unmount(DATA_MNT_POINT, false)) {
- if (allow_reboot) {
- goto error_shutting_down;
- } else {
- goto error_unencrypted;
- }
- }
-
- /* Do extra work for a better UX when doing the long inplace encryption */
- if (how == CRYPTO_ENABLE_INPLACE) {
- /* Now that /data is unmounted, we need to mount a tmpfs
- * /data, set a property saying we're doing inplace encryption,
- * and restart the framework.
- */
- if (fs_mgr_do_tmpfs_mount(DATA_MNT_POINT)) {
- goto error_shutting_down;
- }
- /* Tells the framework that inplace encryption is starting */
- property_set("vold.encrypt_progress", "0");
-
- /* restart the framework. */
- /* Create necessary paths on /data */
- if (prep_data_fs()) {
- goto error_shutting_down;
- }
-
- /* Ugh, shutting down the framework is not synchronous, so until it
- * can be fixed, this horrible hack will wait a moment for it all to
- * shut down before proceeding. Without it, some devices cannot
- * restart the graphics services.
- */
- sleep(2);
-
- /* startup service classes main and late_start */
- property_set("vold.decrypt", "trigger_restart_min_framework");
- printf("Just triggered restart_min_framework\n");
-
- /* OK, the framework is restarted and will soon be showing a
- * progress bar. Time to setup an encrypted mapping, and
- * either write a new filesystem, or encrypt in place updating
- * the progress bar as we work.
- */
- }
-
- /* Start the actual work of making an encrypted filesystem */
- /* Initialize a crypt_mnt_ftr for the partition */
- if (previously_encrypted_upto == 0) {
- if (cryptfs_init_crypt_mnt_ftr(&crypt_ftr)) {
- goto error_shutting_down;
- }
-
- if (!strcmp(key_loc, KEY_IN_FOOTER)) {
- crypt_ftr.fs_size = nr_sec
- - (CRYPT_FOOTER_OFFSET / CRYPT_SECTOR_SIZE);
- } else {
- crypt_ftr.fs_size = nr_sec;
- }
- /* At this point, we are in an inconsistent state. Until we successfully
- complete encryption, a reboot will leave us broken. So mark the
- encryption failed in case that happens.
- On successfully completing encryption, remove this flag */
- crypt_ftr.flags |= CRYPT_INCONSISTENT_STATE;
- crypt_ftr.crypt_type = crypt_type;
- strcpy((char *)crypt_ftr.crypto_type_name, "aes-cbc-essiv:sha256");
-
- /* Make an encrypted master key */
- if (create_encrypted_random_key(passwd, crypt_ftr.master_key, crypt_ftr.salt, &crypt_ftr)) {
- printf("Cannot create encrypted master key\n");
- goto error_shutting_down;
- }
-
- /* Write the key to the end of the partition */
- put_crypt_ftr_and_key(&crypt_ftr);
-
- /* If any persistent data has been remembered, save it.
- * If none, create a valid empty table and save that.
- */
- if (!persist_data) {
- pdata = malloc(CRYPT_PERSIST_DATA_SIZE);
- if (pdata) {
- init_empty_persist_data(pdata, CRYPT_PERSIST_DATA_SIZE);
- persist_data = pdata;
- }
- }
- if (persist_data) {
- save_persistent_data();
- }
- }
-
- decrypt_master_key(passwd, decrypted_master_key, &crypt_ftr, 0, 0);
- create_crypto_blk_dev(&crypt_ftr, decrypted_master_key, real_blkdev, crypto_blkdev,
- "userdata");
-
- /* If we are continuing, check checksums match */
- rc = 0;
- if (previously_encrypted_upto) {
- __le8 hash_first_block[SHA256_DIGEST_LENGTH];
- rc = cryptfs_SHA256_fileblock(crypto_blkdev, hash_first_block);
-
- if (!rc && memcmp(hash_first_block, crypt_ftr.hash_first_block,
- sizeof(hash_first_block)) != 0) {
- printf("Checksums do not match - trigger wipe");
- rc = -1;
- }
- }
-
- if (!rc) {
- rc = cryptfs_enable_all_volumes(&crypt_ftr, how,
- crypto_blkdev, real_blkdev,
- previously_encrypted_upto);
- }
-
- /* Calculate checksum if we are not finished */
- if (!rc && crypt_ftr.encrypted_upto != crypt_ftr.fs_size) {
- rc = cryptfs_SHA256_fileblock(crypto_blkdev,
- crypt_ftr.hash_first_block);
- if (rc) {
- printf("Error calculating checksum for continuing encryption");
- rc = -1;
- }
- }
-
- /* Undo the dm-crypt mapping whether we succeed or not */
- delete_crypto_blk_dev("userdata");
-
- free(vol_list);
-
- if (! rc) {
- /* Success */
- crypt_ftr.flags &= ~CRYPT_INCONSISTENT_STATE;
-
- if (crypt_ftr.encrypted_upto != crypt_ftr.fs_size) {
- printf("Encrypted up to sector %lld - will continue after reboot",
- crypt_ftr.encrypted_upto);
- crypt_ftr.flags |= CRYPT_ENCRYPTION_IN_PROGRESS;
- }
-
- put_crypt_ftr_and_key(&crypt_ftr);
-
- if (crypt_ftr.encrypted_upto == crypt_ftr.fs_size) {
- char value[PROPERTY_VALUE_MAX];
- property_get("ro.crypto.state", value, "");
- if (!strcmp(value, "")) {
- /* default encryption - continue first boot sequence */
- property_set("ro.crypto.state", "encrypted");
- release_wake_lock(lockid);
- cryptfs_check_passwd(DEFAULT_PASSWORD);
- cryptfs_restart_internal(1);
- return 0;
- } else {
- sleep(2); /* Give the UI a chance to show 100% progress */
- cryptfs_reboot(reboot);
- }
- } else {
- sleep(2); /* Partially encrypted, ensure writes flushed to ssd */
- cryptfs_reboot(shutdown);
- }
- } else {
- char value[PROPERTY_VALUE_MAX];
-
- property_get("ro.vold.wipe_on_crypt_fail", value, "0");
- if (!strcmp(value, "1")) {
- /* wipe data if encryption failed */
- printf("encryption failed - rebooting into recovery to wipe data\n");
- mkdir("/cache/recovery", 0700);
- int fd = open("/cache/recovery/command", O_RDWR|O_CREAT|O_TRUNC, 0600);
- if (fd >= 0) {
- write(fd, "--wipe_data\n", strlen("--wipe_data\n") + 1);
- write(fd, "--reason=cryptfs_enable_internal\n", strlen("--reason=cryptfs_enable_internal\n") + 1);
- close(fd);
- } else {
- printf("could not open /cache/recovery/command\n");
- }
- cryptfs_reboot(recovery);
- } else {
- /* set property to trigger dialog */
- property_set("vold.encrypt_progress", "error_partially_encrypted");
- release_wake_lock(lockid);
- }
- return -1;
- }
-
- /* hrm, the encrypt step claims success, but the reboot failed.
- * This should not happen.
- * Set the property and return. Hope the framework can deal with it.
- */
- property_set("vold.encrypt_progress", "error_reboot_failed");
- release_wake_lock(lockid);
- return rc;
-
-error_unencrypted:
- free(vol_list);
- property_set("vold.encrypt_progress", "error_not_encrypted");
- if (lockid[0]) {
- release_wake_lock(lockid);
- }
- return -1;
-
-error_shutting_down:
- /* we failed, and have not encrypted anthing, so the users's data is still intact,
- * but the framework is stopped and not restarted to show the error, so it's up to
- * vold to restart the system.
- */
- printf("Error enabling encryption after framework is shutdown, no data changed, restarting system");
- cryptfs_reboot(reboot);
-
- /* shouldn't get here */
- property_set("vold.encrypt_progress", "error_shutting_down");
- free(vol_list);
- if (lockid[0]) {
- release_wake_lock(lockid);
- }
- return -1;
-}
-
-int cryptfs_enable(char *howarg, int type, char *passwd, int allow_reboot)
-{
- char* adjusted_passwd = adjust_passwd(passwd);
- if (adjusted_passwd) {
- passwd = adjusted_passwd;
- }
-
- int rc = cryptfs_enable_internal(howarg, type, passwd, allow_reboot);
-
- free(adjusted_passwd);
- return rc;
-}
-
-int cryptfs_enable_default(char *howarg, int allow_reboot)
-{
- return cryptfs_enable_internal(howarg, CRYPT_TYPE_DEFAULT,
- DEFAULT_PASSWORD, allow_reboot);
-}
-
-int cryptfs_changepw(int crypt_type, const char *newpw)
-{
- struct crypt_mnt_ftr crypt_ftr;
- unsigned char decrypted_master_key[KEY_LEN_BYTES];
-
- /* This is only allowed after we've successfully decrypted the master key */
- if (!master_key_saved) {
- printf("Key not saved, aborting");
- return -1;
- }
-
- if (crypt_type < 0 || crypt_type > CRYPT_TYPE_MAX_TYPE) {
- printf("Invalid crypt_type %d", crypt_type);
- return -1;
- }
-
- /* get key */
- if (get_crypt_ftr_and_key(&crypt_ftr)) {
- printf("Error getting crypt footer and key");
- return -1;
- }
-
- crypt_ftr.crypt_type = crypt_type;
-
- char* adjusted_passwd = adjust_passwd(newpw);
- if (adjusted_passwd) {
- newpw = adjusted_passwd;
- }
-
- encrypt_master_key(crypt_type == CRYPT_TYPE_DEFAULT ? DEFAULT_PASSWORD
- : newpw,
- crypt_ftr.salt,
- saved_master_key,
- crypt_ftr.master_key,
- &crypt_ftr);
-
- /* save the key */
- put_crypt_ftr_and_key(&crypt_ftr);
-
- free(adjusted_passwd);
- return 0;
-}
-
-static int persist_get_key(char *fieldname, char *value)
-{
- unsigned int i;
-
- if (persist_data == NULL) {
- return -1;
- }
- for (i = 0; i < persist_data->persist_valid_entries; i++) {
- if (!strncmp(persist_data->persist_entry[i].key, fieldname, PROPERTY_KEY_MAX)) {
- /* We found it! */
- strlcpy(value, persist_data->persist_entry[i].val, PROPERTY_VALUE_MAX);
- return 0;
- }
- }
-
- return -1;
-}
-
-static int persist_set_key(char *fieldname, char *value, int encrypted)
-{
- unsigned int i;
- unsigned int num;
- struct crypt_mnt_ftr crypt_ftr;
- unsigned int max_persistent_entries;
- unsigned int dsize;
-
- if (persist_data == NULL) {
- return -1;
- }
-
- /* If encrypted, use the values from the crypt_ftr, otherwise
- * use the values for the current spec.
- */
- if (encrypted) {
- if(get_crypt_ftr_and_key(&crypt_ftr)) {
- return -1;
- }
- dsize = crypt_ftr.persist_data_size;
- } else {
- dsize = CRYPT_PERSIST_DATA_SIZE;
- }
- max_persistent_entries = (dsize - sizeof(struct crypt_persist_data)) /
- sizeof(struct crypt_persist_entry);
-
- num = persist_data->persist_valid_entries;
-
- for (i = 0; i < num; i++) {
- if (!strncmp(persist_data->persist_entry[i].key, fieldname, PROPERTY_KEY_MAX)) {
- /* We found an existing entry, update it! */
- memset(persist_data->persist_entry[i].val, 0, PROPERTY_VALUE_MAX);
- strlcpy(persist_data->persist_entry[i].val, value, PROPERTY_VALUE_MAX);
- return 0;
- }
- }
-
- /* We didn't find it, add it to the end, if there is room */
- if (persist_data->persist_valid_entries < max_persistent_entries) {
- memset(&persist_data->persist_entry[num], 0, sizeof(struct crypt_persist_entry));
- strlcpy(persist_data->persist_entry[num].key, fieldname, PROPERTY_KEY_MAX);
- strlcpy(persist_data->persist_entry[num].val, value, PROPERTY_VALUE_MAX);
- persist_data->persist_valid_entries++;
- return 0;
- }
-
- return -1;
-}
-
-/* Return the value of the specified field. */
-int cryptfs_getfield(char *fieldname, char *value, int len)
-{
- char temp_value[PROPERTY_VALUE_MAX];
- char real_blkdev[MAXPATHLEN];
- /* 0 is success, 1 is not encrypted,
- * -1 is value not set, -2 is any other error
- */
- int rc = -2;
-
- if (persist_data == NULL) {
- load_persistent_data();
- if (persist_data == NULL) {
- printf("Getfield error, cannot load persistent data");
- goto out;
- }
- }
-
- if (!persist_get_key(fieldname, temp_value)) {
- /* We found it, copy it to the caller's buffer and return */
- strlcpy(value, temp_value, len);
- rc = 0;
- } else {
- /* Sadness, it's not there. Return the error */
- rc = -1;
- }
-
-out:
- return rc;
-}
-
-/* Set the value of the specified field. */
-int cryptfs_setfield(char *fieldname, char *value)
-{
- struct crypt_persist_data stored_pdata;
- struct crypt_persist_data *pdata_p;
- struct crypt_mnt_ftr crypt_ftr;
- char encrypted_state[PROPERTY_VALUE_MAX];
- /* 0 is success, -1 is an error */
- int rc = -1;
- int encrypted = 0;
-
- if (persist_data == NULL) {
- load_persistent_data();
- if (persist_data == NULL) {
- printf("Setfield error, cannot load persistent data");
- goto out;
- }
- }
-
- property_get("ro.crypto.state", encrypted_state, "");
- if (!strcmp(encrypted_state, "encrypted") ) {
- encrypted = 1;
- }
-
- if (persist_set_key(fieldname, value, encrypted)) {
- goto out;
- }
-
- /* If we are running encrypted, save the persistent data now */
- if (encrypted) {
- if (save_persistent_data()) {
- printf("Setfield error, cannot save persistent data");
- goto out;
- }
- }
-
- rc = 0;
-
-out:
- return rc;
-}
-
-/* Checks userdata. Attempt to mount the volume if default-
- * encrypted.
- * On success trigger next init phase and return 0.
- * Currently do not handle failure - see TODO below.
- */
-int cryptfs_mount_default_encrypted(void)
-{
- char decrypt_state[PROPERTY_VALUE_MAX];
- property_get("vold.decrypt", decrypt_state, "0");
- if (!strcmp(decrypt_state, "0")) {
- printf("Not encrypted - should not call here");
- } else {
- int crypt_type = cryptfs_get_password_type();
- if (crypt_type < 0 || crypt_type > CRYPT_TYPE_MAX_TYPE) {
- printf("Bad crypt type - error");
- } else if (crypt_type != CRYPT_TYPE_DEFAULT) {
- printf("Password is not default - "
- "starting min framework to prompt");
- property_set("vold.decrypt", "trigger_restart_min_framework");
- return 0;
- } else if (cryptfs_check_passwd(DEFAULT_PASSWORD) == 0) {
- printf("Password is default - restarting filesystem");
- cryptfs_restart_internal(0);
- return 0;
- } else {
- printf("Encrypted, default crypt type but can't decrypt");
- }
- }
-
- /** Corrupt. Allow us to boot into framework, which will detect bad
- crypto when it calls do_crypto_complete, then do a factory reset
- */
- property_set("vold.decrypt", "trigger_restart_min_framework");
- return 0;
-}
-
/* Returns type of the password, default, pattern, pin or password.
*/
int cryptfs_get_password_type(void)
{
struct crypt_mnt_ftr crypt_ftr;
- char fstab_filename[PROPERTY_VALUE_MAX + sizeof(FSTAB_PREFIX)];
- char propbuf[PROPERTY_VALUE_MAX];
-
- property_get("ro.hardware", propbuf, "");
- snprintf(fstab_filename, sizeof(fstab_filename), FSTAB_PREFIX"%s", propbuf);
-
- fstab = fs_mgr_read_fstab(fstab_filename);
- if (!fstab) {
- printf("failed to open %s\n", fstab_filename);
- return -1;
- }
if (get_crypt_ftr_and_key(&crypt_ftr)) {
printf("Error getting crypt footer and key\n");
@@ -3595,26 +1445,3 @@ int cryptfs_get_password_type(void)
return crypt_ftr.crypt_type;
}
-
-char* cryptfs_get_password()
-{
- struct timespec now;
- clock_gettime(CLOCK_MONOTONIC, &now);
- if (now.tv_sec < password_expiry_time) {
- return password;
- } else {
- cryptfs_clear_password();
- return 0;
- }
-}
-
-void cryptfs_clear_password()
-{
- if (password) {
- size_t len = strlen(password);
- memset(password, 0, len);
- free(password);
- password = 0;
- password_expiry_time = 0;
- }
-}
diff --git a/crypto/lollipop/cryptfs.h b/crypto/lollipop/cryptfs.h
index b95a290cf..8cb8a7a32 100644
--- a/crypto/lollipop/cryptfs.h
+++ b/crypto/lollipop/cryptfs.h
@@ -208,24 +208,11 @@ extern "C" {
typedef int (*kdf_func)(const char *passwd, const unsigned char *salt,
unsigned char *ikey, void *params);
- int cryptfs_crypto_complete(void);
- int cryptfs_check_footer(void);
+ void set_partition_data(const char* block_device, const char* key_location, const char* fs);
+ int cryptfs_check_footer();
int cryptfs_check_passwd(char *pw);
int cryptfs_verify_passwd(char *newpw);
- int cryptfs_restart(void);
- int cryptfs_enable(char *flag, int type, char *passwd, int allow_reboot);
- int cryptfs_changepw(int type, const char *newpw);
- int cryptfs_enable_default(char *flag, int allow_reboot);
- int cryptfs_setup_volume(const char *label, int major, int minor,
- char *crypto_dev_path, unsigned int max_pathlen,
- int *new_major, int *new_minor);
- int cryptfs_revert_volume(const char *label);
- int cryptfs_getfield(char *fieldname, char *value, int len);
- int cryptfs_setfield(char *fieldname, char *value);
- int cryptfs_mount_default_encrypted(void);
int cryptfs_get_password_type(void);
- char* cryptfs_get_password(void);
- void cryptfs_clear_password(void);
#ifdef __cplusplus
}
#endif
diff --git a/crypto/scrypt/Android.mk b/crypto/scrypt/Android.mk
index a427de655..4514f9467 100644
--- a/crypto/scrypt/Android.mk
+++ b/crypto/scrypt/Android.mk
@@ -1,5 +1,4 @@
LOCAL_PATH := $(call my-dir)
-#include $(call all-named-subdir-makefiles,tests)
# Enable to be able to use ALOG* with #include "cutils/log.h"
#log_c_includes += system/core/include
@@ -10,3 +9,5 @@ LOCAL_PATH := $(call my-dir)
# that import_openssl.sh import won't remove them.
include $(LOCAL_PATH)/build-config.mk
include $(LOCAL_PATH)/Scrypt.mk
+
+include $(LOCAL_PATH)/tests/Android.mk
diff --git a/crypto/scrypt/Scrypt-config.mk b/crypto/scrypt/Scrypt-config.mk
index c0b00d873..bbe10631e 100644
--- a/crypto/scrypt/Scrypt-config.mk
+++ b/crypto/scrypt/Scrypt-config.mk
@@ -77,7 +77,7 @@ target_arch := unknown_arch
endif
target_c_flags := $(common_c_flags) $($(target_arch)_c_flags) $(local_c_flags)
-target_c_includes := $(addprefix $(commands_recovery_local_path)/crypto/scrypt/,$(common_c_includes)) $(local_c_includes)
+target_c_includes := $(addprefix external/scrypt/,$(common_c_includes)) $(local_c_includes)
target_src_files := $(common_src_files) $($(target_arch)_src_files)
target_src_files := $(filter-out $($(target_arch)_exclude_files), $(target_src_files))
@@ -97,7 +97,7 @@ host_arch := unknown_arch
endif
host_c_flags := $(common_c_flags) $($(host_arch)_c_flags) $(local_c_flags)
-host_c_includes := $(addprefix $(commands_recovery_local_path)/crypto/scrypt/,$(common_c_includes)) $(local_c_includes)
+host_c_includes := $(addprefix external/scrypt/,$(common_c_includes)) $(local_c_includes)
host_src_files := $(common_src_files) $($(host_arch)_src_files)
host_src_files := $(filter-out $($(host_arch)_exclude_files), $(host_src_files))
diff --git a/crypto/scrypt/tests/Android.mk b/crypto/scrypt/tests/Android.mk
index 60257e0f9..07c21023d 100644
--- a/crypto/scrypt/tests/Android.mk
+++ b/crypto/scrypt/tests/Android.mk
@@ -3,6 +3,8 @@
LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
+LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk
+
LOCAL_SRC_FILES:= \
scrypt_test.cpp
@@ -18,6 +20,6 @@ LOCAL_STATIC_LIBRARIES := \
libgtest \
libgtest_main
-LOCAL_MODULE := scrypt_test_twrp
+LOCAL_MODULE := scrypttwrp_test
include $(BUILD_NATIVE_TEST)
diff --git a/crypto/scrypt/tests/scrypt_test.cpp b/crypto/scrypt/tests/scrypt_test.cpp
index 28334d6f5..ffb568df9 100644
--- a/crypto/scrypt/tests/scrypt_test.cpp
+++ b/crypto/scrypt/tests/scrypt_test.cpp
@@ -15,8 +15,8 @@
*/
#define LOG_TAG "scrypt_test"
+#include <UniquePtr.h>
#include <utils/Log.h>
-#include <utils/UniquePtr.h>
#include <gtest/gtest.h>