aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSteve Kondik <shade@chemlab.org>2013-07-07 03:52:37 -0700
committerSteve Kondik <shade@chemlab.org>2013-07-07 14:05:13 -0700
commitf36e7c5806dbe8d96e20a4632b805d814ac14b01 (patch)
treef30bf8d20920da8e56879a93016d3a215cae1d23
parentd44bf3a4ac1ce1b56672ac9ae4a5caa3a8ee6844 (diff)
downloadandroid_external_fuse-f36e7c5806dbe8d96e20a4632b805d814ac14b01.tar.gz
android_external_fuse-f36e7c5806dbe8d96e20a4632b805d814ac14b01.tar.bz2
android_external_fuse-f36e7c5806dbe8d96e20a4632b805d814ac14b01.zip
Support for building on Android
-rw-r--r--android/statvfs.c48
-rw-r--r--android/sys/statvfs.h39
-rw-r--r--include/fuse.h3
-rw-r--r--include/fuse_common.h8
-rw-r--r--include/fuse_compat.h2
-rw-r--r--include/fuse_lowlevel_compat.h2
-rw-r--r--include/ulockmgr.h2
-rw-r--r--lib/Android.mk51
-rw-r--r--lib/buffer.c2
-rw-r--r--lib/fuse.c33
-rw-r--r--lib/fuse_loop_mt.c31
-rw-r--r--lib/fuse_mt.c2
-rw-r--r--lib/fuse_session.c9
-rw-r--r--lib/fuse_versionscript3
-rw-r--r--lib/helper.c6
-rw-r--r--lib/mount.c4
-rw-r--r--lib/mount_util.c5
17 files changed, 237 insertions, 13 deletions
diff --git a/android/statvfs.c b/android/statvfs.c
new file mode 100644
index 0000000..7cec574
--- /dev/null
+++ b/android/statvfs.c
@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2012 Freescale Semiconductor, Inc.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ */
+
+#include "sys/statvfs.h"
+#include <sys/statfs.h>
+
+#define MAP(to,from) vfs->to = sfs.from
+
+int statvfs(const char *path, struct statvfs *vfs) {
+ struct statfs sfs;
+ int ret;
+ int *fsid;
+ if ((ret = statfs(path, &sfs)) != 0)
+ return ret;
+
+ MAP(f_bsize, f_bsize);
+ MAP(f_frsize, f_frsize);
+ MAP(f_blocks, f_blocks);
+ MAP(f_bfree, f_bfree);
+ MAP(f_bavail, f_bavail);
+ MAP(f_files, f_files);
+ MAP(f_ffree, f_ffree);
+ MAP(f_namemax, f_namelen);
+
+ vfs->f_favail = 0;
+ vfs->f_flag = 0;
+
+ fsid = (int *)&sfs.f_fsid;
+ vfs->f_fsid = (fsid[0] << sizeof(fsid[0])) | fsid[1];
+
+ return ret;
+}
diff --git a/android/sys/statvfs.h b/android/sys/statvfs.h
new file mode 100644
index 0000000..0d770dd
--- /dev/null
+++ b/android/sys/statvfs.h
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2012 Freescale Semiconductor, Inc.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ *
+ */
+
+#ifndef _SYS_STATVFS_H_
+#define _SYS_STATVFS_H_
+#include <sys/types.h>
+
+struct statvfs {
+ unsigned long f_bsize; /* file system block size */
+ unsigned long f_frsize; /* fragment size */
+ fsblkcnt_t f_blocks; /* size of fs in f_frsize units */
+ fsblkcnt_t f_bfree; /* # free blocks */
+ fsblkcnt_t f_bavail; /* # free blocks for non-root */
+ fsfilcnt_t f_files; /* # inodes */
+ fsfilcnt_t f_ffree; /* # free inodes */
+ fsfilcnt_t f_favail; /* # free inodes for non-root */
+ unsigned long f_fsid; /* file system ID */
+ unsigned long f_flag; /* mount flags */
+ unsigned long f_namemax; /* maximum filename length */
+};
+
+int statvfs(const char *, struct statvfs *);
+#endif
diff --git a/include/fuse.h b/include/fuse.h
index c657e67..6ad8ee7 100644
--- a/include/fuse.h
+++ b/include/fuse.h
@@ -30,6 +30,9 @@
#include <utime.h>
#include <sys/types.h>
#include <sys/stat.h>
+#if defined(__ANDROID__)
+#include <pthread.h>
+#endif
#include <sys/statvfs.h>
#include <sys/uio.h>
diff --git a/include/fuse_common.h b/include/fuse_common.h
index a4d980d..882caf0 100644
--- a/include/fuse_common.h
+++ b/include/fuse_common.h
@@ -15,6 +15,10 @@
#ifndef _FUSE_COMMON_H_
#define _FUSE_COMMON_H_
+#if defined(__ANDROID__)
+#define _OFF_T_DEFINED_
+#endif
+
#include "fuse_opt.h"
#include <stdint.h>
#include <sys/types.h>
@@ -33,6 +37,10 @@
#error Please add -D_FILE_OFFSET_BITS=64 to your compile flags!
#endif
+#if defined(__ANDROID__)
+typedef loff_t off_t;
+#endif
+
#ifdef __cplusplus
extern "C" {
#endif
diff --git a/include/fuse_compat.h b/include/fuse_compat.h
index e7497a9..3bfaa25 100644
--- a/include/fuse_compat.h
+++ b/include/fuse_compat.h
@@ -9,6 +9,8 @@
/* these definitions provide source compatibility to prior versions.
Do not include this file directly! */
+#include "fuse_lowlevel.h"
+
struct fuse_operations_compat25 {
int (*getattr) (const char *, struct stat *);
int (*readlink) (const char *, char *, size_t);
diff --git a/include/fuse_lowlevel_compat.h b/include/fuse_lowlevel_compat.h
index 8de220b..4fff57a 100644
--- a/include/fuse_lowlevel_compat.h
+++ b/include/fuse_lowlevel_compat.h
@@ -9,6 +9,8 @@
/* these definitions provide source compatibility to prior versions.
Do not include this file directly! */
+#include "fuse_common.h"
+
struct fuse_lowlevel_ops_compat25 {
void (*init) (void *userdata);
void (*destroy) (void *userdata);
diff --git a/include/ulockmgr.h b/include/ulockmgr.h
index ad55579..c3ceef5 100644
--- a/include/ulockmgr.h
+++ b/include/ulockmgr.h
@@ -6,6 +6,8 @@
See the file COPYING.LIB.
*/
+#include "fuse_lowlevel.h"
+
#include <stdint.h>
#include <fcntl.h>
#include <sys/types.h>
diff --git a/lib/Android.mk b/lib/Android.mk
new file mode 100644
index 0000000..a2b1231
--- /dev/null
+++ b/lib/Android.mk
@@ -0,0 +1,51 @@
+# Copyright (C) 2009 The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+LOCAL_PATH := $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_SRC_FILES := \
+ ../android/statvfs.c \
+ buffer.c \
+ cuse_lowlevel.c \
+ fuse.c \
+ fuse_kern_chan.c \
+ fuse_loop.c \
+ fuse_loop_mt.c \
+ fuse_lowlevel.c \
+ fuse_mt.c fuse_opt.c \
+ fuse_session.c \
+ fuse_signals.c \
+ helper.c \
+ mount.c \
+ mount_util.c \
+ ulockmgr.c
+
+LOCAL_C_INCLUDES := \
+ external/fuse/android \
+ external/fuse/include
+
+LOCAL_SHARED_LIBRARIES := \
+ libutils libdl
+
+LOCAL_CFLAGS := \
+ -D_FILE_OFFSET_BITS=64 \
+ -DFUSE_USE_VERSION=26
+
+LOCAL_MODULE := libfuse
+LOCAL_MODULE_TAGS := optional
+
+include $(BUILD_STATIC_LIBRARY)
+
diff --git a/lib/buffer.c b/lib/buffer.c
index 17a595c..0078e11 100644
--- a/lib/buffer.c
+++ b/lib/buffer.c
@@ -45,7 +45,7 @@ static ssize_t fuse_buf_write(const struct fuse_buf *dst, size_t dst_off,
while (len) {
if (dst->flags & FUSE_BUF_FD_SEEK) {
- res = pwrite(dst->fd, src->mem + src_off, len,
+ res = pwrite64(dst->fd, src->mem + src_off, len,
dst->pos + dst_off);
} else {
res = write(dst->fd, src->mem + src_off, len);
diff --git a/lib/fuse.c b/lib/fuse.c
index 067d0dc..e456515 100644
--- a/lib/fuse.c
+++ b/lib/fuse.c
@@ -4558,11 +4558,30 @@ static int node_table_init(struct node_table *t)
return 0;
}
+static void thread_exit_handler(int sig)
+{
+ pthread_exit(0);
+}
+
static void *fuse_prune_nodes(void *fuse)
{
struct fuse *f = fuse;
int sleep_time;
+#if defined(__ANDROID__)
+ struct sigaction actions;
+ memset(&actions, 0, sizeof(actions));
+ sigemptyset(&actions.sa_mask);
+ actions.sa_flags = 0;
+ actions.sa_handler = thread_exit_handler;
+ sigaction(SIGUSR1, &actions, NULL);
+
+ sigset_t setusr1;
+ sigemptyset(&setusr1);
+ sigaddset(&setusr1, SIGUSR1);
+ pthread_sigmask(SIG_BLOCK, &setusr1, NULL);
+#endif
+
while(1) {
sleep_time = fuse_clean_cache(f);
sleep(sleep_time);
@@ -4582,7 +4601,11 @@ void fuse_stop_cleanup_thread(struct fuse *f)
{
if (lru_enabled(f)) {
pthread_mutex_lock(&f->lock);
+#if defined(__ANDROID__)
+ pthread_kill(f->prune_thread, SIGUSR1);
+#else
pthread_cancel(f->prune_thread);
+#endif
pthread_mutex_unlock(&f->lock);
pthread_join(f->prune_thread, NULL);
}
@@ -4873,11 +4896,11 @@ struct fuse *fuse_new_compat1(int fd, int flags,
11);
}
-FUSE_SYMVER(".symver fuse_exited,__fuse_exited@");
-FUSE_SYMVER(".symver fuse_process_cmd,__fuse_process_cmd@");
-FUSE_SYMVER(".symver fuse_read_cmd,__fuse_read_cmd@");
-FUSE_SYMVER(".symver fuse_set_getcontext_func,__fuse_set_getcontext_func@");
-FUSE_SYMVER(".symver fuse_new_compat2,fuse_new@");
+FUSE_SYMVER(".symver fuse_exited,__fuse_exited@FUSE_UNVERSIONED");
+FUSE_SYMVER(".symver fuse_process_cmd,__fuse_process_cmd@FUSE_UNVERSIONED");
+FUSE_SYMVER(".symver fuse_read_cmd,__fuse_read_cmd@FUSE_UNVERSIONED");
+FUSE_SYMVER(".symver fuse_set_getcontext_func,__fuse_set_getcontext_func@FUSE_UNVERSIONED");
+FUSE_SYMVER(".symver fuse_new_compat2,fuse_new@FUSE_UNVERSIONED");
FUSE_SYMVER(".symver fuse_new_compat22,fuse_new@FUSE_2.2");
#endif /* __FreeBSD__ || __NetBSD__ */
diff --git a/lib/fuse_loop_mt.c b/lib/fuse_loop_mt.c
index 82e3001..90fc1e6 100644
--- a/lib/fuse_loop_mt.c
+++ b/lib/fuse_loop_mt.c
@@ -63,11 +63,30 @@ static void list_del_worker(struct fuse_worker *w)
static int fuse_loop_start_thread(struct fuse_mt *mt);
+static void thread_exit_handler(int sig)
+{
+ pthread_exit(0);
+}
+
static void *fuse_do_work(void *data)
{
struct fuse_worker *w = (struct fuse_worker *) data;
struct fuse_mt *mt = w->mt;
+#if defined(__ANDROID__)
+ struct sigaction actions;
+ memset(&actions, 0, sizeof(actions));
+ sigemptyset(&actions.sa_mask);
+ actions.sa_flags = 0;
+ actions.sa_handler = thread_exit_handler;
+ sigaction(SIGUSR1, &actions, NULL);
+
+ sigset_t setusr1;
+ sigemptyset(&setusr1);
+ sigaddset(&setusr1, SIGUSR1);
+ pthread_sigmask(SIG_BLOCK, &setusr1, NULL);
+#endif
+
while (!fuse_session_exited(mt->se)) {
int isforget = 0;
struct fuse_chan *ch = mt->prevch;
@@ -77,9 +96,17 @@ static void *fuse_do_work(void *data)
};
int res;
+#if defined(__ANDROID__)
+ pthread_sigmask(SIG_UNBLOCK, &setusr1, NULL);
+#else
pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL);
+#endif
res = fuse_session_receive_buf(mt->se, &fbuf, &ch);
+#if defined(__ANDROID__)
+ pthread_sigmask(SIG_BLOCK, &setusr1, NULL);
+#else
pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, NULL);
+#endif
if (res == -EINTR)
continue;
if (res <= 0) {
@@ -243,7 +270,11 @@ int fuse_session_loop_mt(struct fuse_session *se)
pthread_mutex_lock(&mt.lock);
for (w = mt.main.next; w != &mt.main; w = w->next)
+#if defined(__ANDROID__)
+ pthread_kill(w->thread_id, SIGUSR1);
+#else
pthread_cancel(w->thread_id);
+#endif
mt.exit = 1;
pthread_mutex_unlock(&mt.lock);
diff --git a/lib/fuse_mt.c b/lib/fuse_mt.c
index f6dbe71..fd5ac23 100644
--- a/lib/fuse_mt.c
+++ b/lib/fuse_mt.c
@@ -119,4 +119,4 @@ int fuse_loop_mt(struct fuse *f)
return res;
}
-FUSE_SYMVER(".symver fuse_loop_mt_proc,__fuse_loop_mt@");
+FUSE_SYMVER(".symver fuse_loop_mt_proc,__fuse_loop_mt@FUSE_UNVERSIONED");
diff --git a/lib/fuse_session.c b/lib/fuse_session.c
index 6e11068..18c8c42 100644
--- a/lib/fuse_session.c
+++ b/lib/fuse_session.c
@@ -184,9 +184,12 @@ int fuse_chan_fd(struct fuse_chan *ch)
int fuse_chan_clearfd(struct fuse_chan *ch)
{
- int fd = ch->fd;
- ch->fd = -1;
- return fd;
+ if (ch == NULL)
+ return -1;
+
+ int fd = ch->fd;
+ ch->fd = -1;
+ return fd;
}
size_t fuse_chan_bufsize(struct fuse_chan *ch)
diff --git a/lib/fuse_versionscript b/lib/fuse_versionscript
index 8d91887..de16ab2 100644
--- a/lib/fuse_versionscript
+++ b/lib/fuse_versionscript
@@ -1,3 +1,6 @@
+FUSE_UNVERSIONED {
+};
+
FUSE_2.2 {
global:
fuse_destroy;
diff --git a/lib/helper.c b/lib/helper.c
index b644012..c5349bf 100644
--- a/lib/helper.c
+++ b/lib/helper.c
@@ -436,10 +436,10 @@ int fuse_mount_compat1(const char *mountpoint, const char *args[])
return fuse_mount_compat22(mountpoint, NULL);
}
-FUSE_SYMVER(".symver fuse_setup_compat2,__fuse_setup@");
+FUSE_SYMVER(".symver fuse_setup_compat2,__fuse_setup@FUSE_UNVERSIONED");
FUSE_SYMVER(".symver fuse_setup_compat22,fuse_setup@FUSE_2.2");
-FUSE_SYMVER(".symver fuse_teardown,__fuse_teardown@");
-FUSE_SYMVER(".symver fuse_main_compat2,fuse_main@");
+FUSE_SYMVER(".symver fuse_teardown,__fuse_teardown@FUSE_UNVERSIONED");
+FUSE_SYMVER(".symver fuse_main_compat2,fuse_main@FUSE_UNVERSIONED");
FUSE_SYMVER(".symver fuse_main_real_compat22,fuse_main_real@FUSE_2.2");
#endif /* __FreeBSD__ || __NetBSD__ */
diff --git a/lib/mount.c b/lib/mount.c
index 0f767c8..2a557c6 100644
--- a/lib/mount.c
+++ b/lib/mount.c
@@ -42,6 +42,10 @@
#define FUSERMOUNT_PROG "fusermount"
#define FUSE_COMMFD_ENV "_FUSE_COMMFD"
+#if defined(__ANDROID__) && !defined(FUSERMOUNT_DIR)
+# define FUSERMOUNT_DIR "/system/xbin"
+#endif
+
#ifndef HAVE_FORK
#define fork() vfork()
#endif
diff --git a/lib/mount_util.c b/lib/mount_util.c
index 3d2f4cd..e8bd538 100644
--- a/lib/mount_util.c
+++ b/lib/mount_util.c
@@ -23,10 +23,15 @@
#include <sys/wait.h>
#include <sys/mount.h>
#include <sys/param.h>
+#if defined(__ANDROID__)
+#include <paths.h>
+#endif
#ifdef __NetBSD__
#define umount2(mnt, flags) unmount(mnt, (flags == 2) ? MNT_FORCE : 0)
#define mtab_needs_update(mnt) 0
+#elif defined(__ANDROID__)
+#define mtab_needs_update(mnt) 0
#else
static int mtab_needs_update(const char *mnt)
{