diff --git a/fs/jbd2/checkpoint.c b/fs/jbd2/checkpoint.c
index a1909066bde6..da0920cbc1d3 100644
--- a/fs/jbd2/checkpoint.c
+++ b/fs/jbd2/checkpoint.c
@@ -105,12 +105,12 @@ static int __try_to_free_cp_buf(struct journal_head *jh)
  * Called under j-state_lock *only*.  It will be unlocked if we have to wait
  * for a checkpoint to free up some space in the log.
  */
-void __jbd2_log_wait_for_space(journal_t *journal)
+void __jbd2_log_wait_for_space(journal_t *journal, int scale)
 {
 	int nblocks, space_left;
 	/* assert_spin_locked(&journal->j_state_lock); */
 
-	nblocks = jbd2_space_needed(journal);
+	nblocks = jbd2_space_needed(journal) * scale;
 	while (jbd2_log_space_left(journal) < nblocks) {
 		write_unlock(&journal->j_state_lock);
 		mutex_lock_io(&journal->j_checkpoint_mutex);
diff --git a/fs/jbd2/journal.c b/fs/jbd2/journal.c
index 953990eb70a9..871c3d251fdb 100644
--- a/fs/jbd2/journal.c
+++ b/fs/jbd2/journal.c
@@ -1100,6 +1100,21 @@ static void jbd2_stats_proc_exit(journal_t *journal)
 	remove_proc_entry(journal->j_devname, proc_jbd2_stats);
 }
 
+/*
+ * Start to reclaim journal space asynchronously.
+ */
+void jbd2_reclaim_log_space_async(struct work_struct *work)
+{
+	journal_t *journal = container_of(work, journal_t, j_reclaim_work);
+
+	write_lock(&journal->j_state_lock);
+	/* See comments in add_transaction_credits() */
+	if (jbd2_log_space_left(journal) < jbd2_space_needed(journal) * 2)
+		__jbd2_log_wait_for_space(journal, 2);
+	journal->j_async_reclaim_run = 0;
+	write_unlock(&journal->j_state_lock);
+}
+
 /*
  * Management for journal control blocks: functions to create and
  * destroy journal_t structures, and to initialise and read existing
@@ -1142,6 +1157,15 @@ static journal_t *journal_init_common(struct block_device *bdev,
 	/* The journal is marked for error until we succeed with recovery! */
 	journal->j_flags = JBD2_ABORT;
 
+	journal->j_reclaim_wq = alloc_workqueue("jbd2-reclaim-wq",
+					WQ_MEM_RECLAIM | WQ_UNBOUND, 1);
+	if (!journal->j_reclaim_wq) {
+		pr_err("%s: failed to create workqueue\n", __func__);
+		goto err_cleanup;
+	}
+	INIT_WORK(&journal->j_reclaim_work, jbd2_reclaim_log_space_async);
+	journal->j_async_reclaim_run = 0;
+
 	/* Set up a default-sized revoke table for the new mount. */
 	err = jbd2_journal_init_revoke(journal, JOURNAL_REVOKE_DEFAULT_HASH);
 	if (err)
@@ -1718,6 +1742,7 @@ int jbd2_journal_destroy(journal_t *journal)
 	if (journal->j_running_transaction)
 		jbd2_journal_commit_transaction(journal);
 
+	flush_workqueue(journal->j_reclaim_wq);
 	/* Force any old transactions to disk */
 
 	/* Totally anal locking here... */
@@ -1768,6 +1793,7 @@ int jbd2_journal_destroy(journal_t *journal)
 		jbd2_journal_destroy_revoke(journal);
 	if (journal->j_chksum_driver)
 		crypto_free_shash(journal->j_chksum_driver);
+	destroy_workqueue(journal->j_reclaim_wq);
 	kfree(journal->j_wbuf);
 	kfree(journal);
 
diff --git a/fs/jbd2/transaction.c b/fs/jbd2/transaction.c
index 990e7b5062e7..27f9d47c620e 100644
--- a/fs/jbd2/transaction.c
+++ b/fs/jbd2/transaction.c
@@ -247,6 +247,16 @@ static int add_transaction_credits(journal_t *journal, int blocks,
 		return 1;
 	}
 
+	/*
+	 * If free journal space is lower than (jbd2_space_needed(journal) * 2),
+	 * let's reclaim some journal space early and do it asynchronously.
+	 */
+	if (journal->j_async_reclaim_run == 0 &&
+	    jbd2_log_space_left(journal) < (jbd2_space_needed(journal) * 2)) {
+		journal->j_async_reclaim_run = 1;
+		queue_work(journal->j_reclaim_wq, &journal->j_reclaim_work);
+	}
+
 	/*
 	 * The commit code assumes that it can get enough log space
 	 * without forcing a checkpoint.  This is *critical* for
@@ -264,7 +274,7 @@ static int add_transaction_credits(journal_t *journal, int blocks,
 		jbd2_might_wait_for_commit(journal);
 		write_lock(&journal->j_state_lock);
 		if (jbd2_log_space_left(journal) < jbd2_space_needed(journal))
-			__jbd2_log_wait_for_space(journal);
+			__jbd2_log_wait_for_space(journal, 1);
 		write_unlock(&journal->j_state_lock);
 		return 1;
 	}
diff --git a/include/linux/jbd2.h b/include/linux/jbd2.h
index df03825ad1a1..acc93597271b 100644
--- a/include/linux/jbd2.h
+++ b/include/linux/jbd2.h
@@ -1152,6 +1152,27 @@ struct journal_s
 	 */
 	__u32 j_csum_seed;
 
+	/**
+	 * @j_async_reclaim_run:
+	 *
+	 * Is there a work running asynchronously to reclaim journal space.
+	 */
+	int j_async_reclaim_run;
+
+	/**
+	 * @j_reclaim_work:
+	 *
+	 * Work_struct to reclaim journal space.
+	 */
+	struct work_struct j_reclaim_work;
+
+	/**
+	 * @j_reclaim_wq:
+	 *
+	 * Workqueue for reclaim journal space asynchronously.
+	 */
+	struct workqueue_struct *j_reclaim_wq;
+
 #ifdef CONFIG_DEBUG_LOCK_ALLOC
 	/**
 	 * @j_trans_commit_map:
@@ -1498,7 +1519,7 @@ int jbd2_complete_transaction(journal_t *journal, tid_t tid);
 int jbd2_log_do_checkpoint(journal_t *journal);
 int jbd2_trans_will_send_data_barrier(journal_t *journal, tid_t tid);
 
-void __jbd2_log_wait_for_space(journal_t *journal);
+void __jbd2_log_wait_for_space(journal_t *journal, int scale);
 extern void __jbd2_journal_drop_transaction(journal_t *, transaction_t *);
 extern int jbd2_cleanup_journal_tail(journal_t *);
 
