--- /dev/null
+diff --git a/src/share/vm/prims/jvmtiEnv.cpp b/src/share/vm/prims/jvmtiEnv.cpp
+index 9cafbd1..e24f8c9 100644
+--- a/src/share/vm/prims/jvmtiEnv.cpp
++++ b/src/share/vm/prims/jvmtiEnv.cpp
+@@ -298,10 +298,12 @@
+ //TODO: add locking
+ if (AllowEnhancedClassRedefinition) {
+ VM_EnhancedRedefineClasses op(class_count, class_definitions, jvmti_class_load_kind_redefine);
++ MutexLocker sd_mutex(RedefineClasses_lock);
+ VMThread::execute(&op);
+ return (op.check_error());
+ }
+ VM_RedefineClasses op(class_count, class_definitions, jvmti_class_load_kind_redefine);
++ MutexLocker sd_mutex(RedefineClasses_lock);
+ VMThread::execute(&op);
+ return (op.check_error());
+ } /* end RedefineClasses */
+diff --git a/src/share/vm/runtime/mutexLocker.cpp b/src/share/vm/runtime/mutexLocker.cpp
+index f358c75..02377a4 100644
+--- a/src/share/vm/runtime/mutexLocker.cpp
++++ b/src/share/vm/runtime/mutexLocker.cpp
+@@ -38,6 +38,7 @@
+ // Consider using GCC's __read_mostly.
+
+ Mutex* Patching_lock = NULL;
++Mutex* RedefineClasses_lock = NULL;
+ Monitor* SystemDictionary_lock = NULL;
+ Mutex* PackageTable_lock = NULL;
+ Mutex* CompiledIC_lock = NULL;
+@@ -279,6 +280,7 @@
+ def(ProfileVM_lock , Monitor, special, false); // used for profiling of the VMThread
+ def(CompileThread_lock , Monitor, nonleaf+5, false );
+ def(PeriodicTask_lock , Monitor, nonleaf+5, true);
++ def(RedefineClasses_lock , Mutex , nonleaf+7, false ); // for ensuring that class redefinition is not done in parallel
+
+ #ifdef INCLUDE_TRACE
+ def(JfrMsg_lock , Monitor, leaf, true);
+diff --git a/src/share/vm/runtime/mutexLocker.hpp b/src/share/vm/runtime/mutexLocker.hpp
+index be86bac..a77f546 100644
+--- a/src/share/vm/runtime/mutexLocker.hpp
++++ b/src/share/vm/runtime/mutexLocker.hpp
+@@ -46,6 +46,7 @@
+ // Mutexes used in the VM.
+
+ extern Mutex* Patching_lock; // a lock used to guard code patching of compiled code
++extern Mutex* RedefineClasses_lock; // a lock on class redefinition
+ extern Monitor* SystemDictionary_lock; // a lock on the system dictonary
+ extern Mutex* PackageTable_lock; // a lock on the class loader package table
+ extern Mutex* CompiledIC_lock; // a lock used to guard compiled IC patching and access
+diff --git a/src/share/vm/runtime/thread.cpp b/src/share/vm/runtime/thread.cpp
+index 0dc86d9..9f4c2e9 100644
+--- a/src/share/vm/runtime/thread.cpp
++++ b/src/share/vm/runtime/thread.cpp
+@@ -910,6 +910,15 @@
+ return false;
+ }
+
++bool Thread::owns_locks_but_redefine_classes_lock() const {
++ for(Monitor *cur = _owned_locks; cur; cur = cur->next()) {
++ if (cur != RedefineClasses_lock && cur->rank() != Mutex::redefine_classes) {
++ return true;
++ }
++ }
++ return false;
++}
++
+
+ #endif
+
+diff --git a/src/share/vm/runtime/thread.hpp b/src/share/vm/runtime/thread.hpp
+index 1117c87..77b716c 100644
+--- a/src/share/vm/runtime/thread.hpp
++++ b/src/share/vm/runtime/thread.hpp
+@@ -211,11 +211,14 @@
+ void enter_signal_handler() { _num_nested_signal++; }
+ void leave_signal_handler() { _num_nested_signal--; }
+ bool is_inside_signal_handler() const { return _num_nested_signal > 0; }
++ Mutex* redefine_classes_mutex() { return _redefine_classes_mutex; }
+
+ private:
+ // Debug tracing
+ static void trace(const char* msg, const Thread* const thread) PRODUCT_RETURN;
+
++ Mutex* _redefine_classes_mutex;
++
+ // Active_handles points to a block of handles
+ JNIHandleBlock* _active_handles;
+
+@@ -585,6 +588,7 @@
+ void print_owned_locks() const { print_owned_locks_on(tty); }
+ Monitor* owned_locks() const { return _owned_locks; }
+ bool owns_locks() const { return owned_locks() != NULL; }
++ bool owns_locks_but_redefine_classes_lock() const;
+ bool owns_locks_but_compiled_lock() const;
+
+ // Deadlock detection