diff options
Diffstat (limited to 'sdcard')
-rw-r--r-- | sdcard/Android.mk | 16 | ||||
-rw-r--r-- | sdcard/main.c | 21 | ||||
-rw-r--r-- | sdcard/sdcard.c | 85 |
3 files changed, 98 insertions, 24 deletions
diff --git a/sdcard/Android.mk b/sdcard/Android.mk index cb3a8fb..b50a818 100644 --- a/sdcard/Android.mk +++ b/sdcard/Android.mk @@ -1,11 +1,21 @@ LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) +ifeq ($(call is-vendor-board-platform,QCOM),true) +LOCAL_C_INCLUDES += $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include +LOCAL_ADDITIONAL_DEPENDENCIES += $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr +endif LOCAL_SRC_FILES := sdcard.c -LOCAL_MODULE := sdcard +LOCAL_MODULE := libsdcard LOCAL_CFLAGS := -Wall -Wno-unused-parameter -Werror +LOCAL_MODULE_TAGS := optional +include $(BUILD_STATIC_LIBRARY) -LOCAL_SHARED_LIBRARIES := libcutils - +include $(CLEAR_VARS) +LOCAL_SRC_FILES := main.c +LOCAL_MODULE := sdcard +LOCAL_CFLAGS := -Wall -Wno-unused-parameter -Werror +LOCAL_STATIC_LIBRARIES := libsdcard +LOCAL_SHARED_LIBRARIES := libc libcutils include $(BUILD_EXECUTABLE) diff --git a/sdcard/main.c b/sdcard/main.c new file mode 100644 index 0000000..ad2405b --- /dev/null +++ b/sdcard/main.c @@ -0,0 +1,21 @@ +/* + * 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. + */ + +extern int sdcard_main(int argc, char **argv); + +int main(int argc, char **argv) { + return sdcard_main(argc, argv); +} diff --git a/sdcard/sdcard.c b/sdcard/sdcard.c index 123fce6..227982c 100644 --- a/sdcard/sdcard.c +++ b/sdcard/sdcard.c @@ -41,6 +41,7 @@ #include <cutils/hashmap.h> #include <cutils/log.h> #include <cutils/multiuser.h> +#include <cutils/properties.h> #include <private/android_filesystem_config.h> @@ -1214,7 +1215,13 @@ static int handle_open(struct fuse* fuse, struct fuse_handler* handler, } out.fh = ptr_to_id(h); out.open_flags = 0; + +#if defined(FUSE_STACKED_IO) || defined(FUSE_SHORTCIRCUIT) + out.lower_fd = h->fd; +#else out.padding = 0; +#endif + fuse_reply(fuse, hdr->unique, &out, sizeof(out)); return NO_STATUS; } @@ -1378,7 +1385,13 @@ static int handle_opendir(struct fuse* fuse, struct fuse_handler* handler, } out.fh = ptr_to_id(h); out.open_flags = 0; + +#if defined(FUSE_STACKED_IO) || defined(FUSE_SHORTCIRCUIT) + out.lower_fd = -1; +#else out.padding = 0; +#endif + fuse_reply(fuse, hdr->unique, &out, sizeof(out)); return NO_STATUS; } @@ -1460,6 +1473,14 @@ static int handle_init(struct fuse* fuse, struct fuse_handler* handler, out.major = FUSE_KERNEL_VERSION; out.max_readahead = req->max_readahead; out.flags = FUSE_ATOMIC_O_TRUNC | FUSE_BIG_WRITES; + +#ifdef FUSE_SHORTCIRCUIT + out.flags |= FUSE_SHORTCIRCUIT; +#endif +#ifdef FUSE_STACKED_IO + out.flags |= FUSE_STACKED_IO; +#endif + out.max_background = 32; out.congestion_threshold = 32; out.max_write = MAX_WRITE; @@ -1756,24 +1777,39 @@ static int usage() { return 1; } -static int fuse_setup(struct fuse* fuse, gid_t gid, mode_t mask) { +static int fuse_setup(struct fuse* fuse, gid_t gid, mode_t mask, bool use_sdcardfs) { char opts[256]; - fuse->fd = open("/dev/fuse", O_RDWR); - if (fuse->fd == -1) { - ERROR("failed to open fuse device: %s\n", strerror(errno)); - return -1; + if (!use_sdcardfs) { + fuse->fd = open("/dev/fuse", O_RDWR); + if (fuse->fd == -1) { + ERROR("failed to open fuse device: %s\n", strerror(errno)); + return -1; + } } umount2(fuse->dest_path, MNT_DETACH); - snprintf(opts, sizeof(opts), - "fd=%i,rootmode=40000,default_permissions,allow_other,user_id=%d,group_id=%d", - fuse->fd, fuse->global->uid, fuse->global->gid); - if (mount("/dev/fuse", fuse->dest_path, "fuse", MS_NOSUID | MS_NODEV | MS_NOEXEC | - MS_NOATIME, opts) != 0) { - ERROR("failed to mount fuse filesystem: %s\n", strerror(errno)); - return -1; + if (use_sdcardfs) { + snprintf(opts, sizeof(opts), + "%sfsuid=%u,fsgid=%u,userid=%d,gid=%u,mask=%u,reserved_mb=20", + (fuse->global->multi_user ? "multiuser," : ""), + fuse->global->uid, fuse->global->gid, + fuse->global->root.userid, gid, mask); + if (mount(fuse->global->source_path, fuse->dest_path, "sdcardfs", + MS_NOSUID | MS_NODEV | MS_NOEXEC | MS_NOATIME, opts) != 0) { + ERROR("failed to mount sdcardfs filesystem: %s\n", strerror(errno)); + return -1; + } + } else { + snprintf(opts, sizeof(opts), + "fd=%i,rootmode=40000,default_permissions,allow_other,user_id=%d,group_id=%d", + fuse->fd, fuse->global->uid, fuse->global->gid); + if (mount("/dev/fuse", fuse->dest_path, "fuse", MS_NOSUID | MS_NODEV | MS_NOEXEC | + MS_NOATIME, opts) != 0) { + ERROR("failed to mount fuse filesystem: %s\n", strerror(errno)); + return -1; + } } fuse->gid = gid; @@ -1783,7 +1819,7 @@ static int fuse_setup(struct fuse* fuse, gid_t gid, mode_t mask) { } static void run(const char* source_path, const char* label, uid_t uid, - gid_t gid, userid_t userid, bool multi_user, bool full_write) { + gid_t gid, userid_t userid, bool multi_user, bool full_write, bool use_sdcardfs) { struct fuse_global global; struct fuse fuse_default; struct fuse fuse_read; @@ -1855,9 +1891,9 @@ static void run(const char* source_path, const char* label, uid_t uid, if (multi_user) { /* Multi-user storage is fully isolated per user, so "other" * permissions are completely masked off. */ - if (fuse_setup(&fuse_default, AID_SDCARD_RW, 0006) - || fuse_setup(&fuse_read, AID_EVERYBODY, 0027) - || fuse_setup(&fuse_write, AID_EVERYBODY, full_write ? 0007 : 0027)) { + if (fuse_setup(&fuse_default, AID_SDCARD_RW, 0006, use_sdcardfs) + || fuse_setup(&fuse_read, AID_EVERYBODY, 0027, use_sdcardfs) + || fuse_setup(&fuse_write, AID_EVERYBODY, full_write ? 0007 : 0027, use_sdcardfs)) { ERROR("failed to fuse_setup\n"); exit(1); } @@ -1865,9 +1901,9 @@ static void run(const char* source_path, const char* label, uid_t uid, /* Physical storage is readable by all users on device, but * the Android directories are masked off to a single user * deep inside attr_from_stat(). */ - if (fuse_setup(&fuse_default, AID_SDCARD_RW, 0006) - || fuse_setup(&fuse_read, AID_EVERYBODY, full_write ? 0027 : 0022) - || fuse_setup(&fuse_write, AID_EVERYBODY, full_write ? 0007 : 0022)) { + if (fuse_setup(&fuse_default, AID_SDCARD_RW, 0006, use_sdcardfs) + || fuse_setup(&fuse_read, AID_EVERYBODY, full_write ? 0027 : 0022, use_sdcardfs) + || fuse_setup(&fuse_write, AID_EVERYBODY, full_write ? 0007 : 0022, use_sdcardfs)) { ERROR("failed to fuse_setup\n"); exit(1); } @@ -1891,6 +1927,11 @@ static void run(const char* source_path, const char* label, uid_t uid, fs_prepare_dir(global.obb_path, 0775, uid, gid); } + // Nothing else for us to do if sdcardfs is in use! + if (use_sdcardfs) { + exit(0); + } + if (pthread_create(&thread_default, NULL, start_handler, &handler_default) || pthread_create(&thread_read, NULL, start_handler, &handler_read) || pthread_create(&thread_write, NULL, start_handler, &handler_write)) { @@ -1903,7 +1944,7 @@ static void run(const char* source_path, const char* label, uid_t uid, exit(1); } -int main(int argc, char **argv) { +int sdcard_main(int argc, char **argv) { const char *source_path = NULL; const char *label = NULL; uid_t uid = 0; @@ -1975,6 +2016,8 @@ int main(int argc, char **argv) { sleep(1); } - run(source_path, label, uid, gid, userid, multi_user, full_write); + bool use_sdcardfs = property_get_bool("ro.sdcardfs.enable", false); + + run(source_path, label, uid, gid, userid, multi_user, full_write, use_sdcardfs); return 1; } |