Project

General

Profile

Actions

Feature #3749

closed

Remove forced synchronization from Java bindings

Added by Noah Watkins over 11 years ago. Updated over 11 years ago.

Status:
Resolved
Priority:
Normal
Assignee:
-
Category:
-
Target version:
-
% Done:

0%

Source:
Tags:
Backport:
Reviewed:
Affected Versions:
Component(FS):
Labels (FS):
Pull request ID:

Description

Remove "synchronized" keyword from native interface. This was originally added when we were seeing some pthread mutex related assertion failures, and we never removed "synchronized".

Actions #1

Updated by Noah Watkins over 11 years ago

This needs more thought than just removing synchronization. We'd like to be segfault free in Java, even though you could shoot yourself in C.

It may be that we need reader/writer style synchronization to prevent state we hold in JNI across ceph_* calls from becoming invalid due to ceph_unmount. Anything unsafe after ceph_release is fine, because the JVM will only call this in finalize().

Actions #2

Updated by Noah Watkins over 11 years ago

In libcephfs mount/unmount race against each other, and the test of the API (e.g. unmount racing against write). In C the synchronization requirements are pretty straight forward, but in Java knowing the requirements isn't sufficient; we want to guarantee that the JVM doesn't crash.

We use an r/w lock to allow concurrent access to all of the libcephfs API accept mount/unmount.

1. Mutual exclusion for mount/unmount prevents races between the two in
libcephfs, which isn't safe (access to ceph_mount_info state).

2. An extremely narrow race between unmount and ceph_* calls in
libcephfs. ThreadA calls ceph_xxx, is_mounted test passes, then ThreadB
calls unmount and destroys the client. ThreadA resumes with a bad client
pointer.

3. Race between unmount and ceph_* calls in JNI. In JNI we hold the
CephContext reference across ceph_* calls. If the ceph mount were to be
released while a thread was returning from a ceph_* call then an attempt
to write to the log (e.g. the return value) would reference bad context.
Since ceph_release is only called by finalize() then no thread can be in
JNI. So this is actually safe.

Using r/w here provides trade-off between allowing concurrency into
libcephfs, and not having to constantly update the Java bindings. The
only assumption is that unmount/mount race with the rest of the
interface.

Actions #3

Updated by Noah Watkins over 11 years ago

  • Status changed from New to Resolved
Actions

Also available in: Atom PDF