aboutsummaryrefslogtreecommitdiffstats
path: root/fs/jbd2/journal.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/jbd2/journal.c')
-rw-r--r--fs/jbd2/journal.c28
1 files changed, 22 insertions, 6 deletions
diff --git a/fs/jbd2/journal.c b/fs/jbd2/journal.c
index 01c3901c3a07..783de118de92 100644
--- a/fs/jbd2/journal.c
+++ b/fs/jbd2/journal.c
@@ -1451,9 +1451,12 @@ recovery_error:
1451 * 1451 *
1452 * Release a journal_t structure once it is no longer in use by the 1452 * Release a journal_t structure once it is no longer in use by the
1453 * journaled object. 1453 * journaled object.
1454 * Return <0 if we couldn't clean up the journal.
1454 */ 1455 */
1455void jbd2_journal_destroy(journal_t *journal) 1456int jbd2_journal_destroy(journal_t *journal)
1456{ 1457{
1458 int err = 0;
1459
1457 /* Wait for the commit thread to wake up and die. */ 1460 /* Wait for the commit thread to wake up and die. */
1458 journal_kill_thread(journal); 1461 journal_kill_thread(journal);
1459 1462
@@ -1476,11 +1479,16 @@ void jbd2_journal_destroy(journal_t *journal)
1476 J_ASSERT(journal->j_checkpoint_transactions == NULL); 1479 J_ASSERT(journal->j_checkpoint_transactions == NULL);
1477 spin_unlock(&journal->j_list_lock); 1480 spin_unlock(&journal->j_list_lock);
1478 1481
1479 /* We can now mark the journal as empty. */
1480 journal->j_tail = 0;
1481 journal->j_tail_sequence = ++journal->j_transaction_sequence;
1482 if (journal->j_sb_buffer) { 1482 if (journal->j_sb_buffer) {
1483 jbd2_journal_update_superblock(journal, 1); 1483 if (!is_journal_aborted(journal)) {
1484 /* We can now mark the journal as empty. */
1485 journal->j_tail = 0;
1486 journal->j_tail_sequence =
1487 ++journal->j_transaction_sequence;
1488 jbd2_journal_update_superblock(journal, 1);
1489 } else {
1490 err = -EIO;
1491 }
1484 brelse(journal->j_sb_buffer); 1492 brelse(journal->j_sb_buffer);
1485 } 1493 }
1486 1494
@@ -1492,6 +1500,8 @@ void jbd2_journal_destroy(journal_t *journal)
1492 jbd2_journal_destroy_revoke(journal); 1500 jbd2_journal_destroy_revoke(journal);
1493 kfree(journal->j_wbuf); 1501 kfree(journal->j_wbuf);
1494 kfree(journal); 1502 kfree(journal);
1503
1504 return err;
1495} 1505}
1496 1506
1497 1507
@@ -1717,10 +1727,16 @@ int jbd2_journal_flush(journal_t *journal)
1717 spin_lock(&journal->j_list_lock); 1727 spin_lock(&journal->j_list_lock);
1718 while (!err && journal->j_checkpoint_transactions != NULL) { 1728 while (!err && journal->j_checkpoint_transactions != NULL) {
1719 spin_unlock(&journal->j_list_lock); 1729 spin_unlock(&journal->j_list_lock);
1730 mutex_lock(&journal->j_checkpoint_mutex);
1720 err = jbd2_log_do_checkpoint(journal); 1731 err = jbd2_log_do_checkpoint(journal);
1732 mutex_unlock(&journal->j_checkpoint_mutex);
1721 spin_lock(&journal->j_list_lock); 1733 spin_lock(&journal->j_list_lock);
1722 } 1734 }
1723 spin_unlock(&journal->j_list_lock); 1735 spin_unlock(&journal->j_list_lock);
1736
1737 if (is_journal_aborted(journal))
1738 return -EIO;
1739
1724 jbd2_cleanup_journal_tail(journal); 1740 jbd2_cleanup_journal_tail(journal);
1725 1741
1726 /* Finally, mark the journal as really needing no recovery. 1742 /* Finally, mark the journal as really needing no recovery.
@@ -1742,7 +1758,7 @@ int jbd2_journal_flush(journal_t *journal)
1742 J_ASSERT(journal->j_head == journal->j_tail); 1758 J_ASSERT(journal->j_head == journal->j_tail);
1743 J_ASSERT(journal->j_tail_sequence == journal->j_transaction_sequence); 1759 J_ASSERT(journal->j_tail_sequence == journal->j_transaction_sequence);
1744 spin_unlock(&journal->j_state_lock); 1760 spin_unlock(&journal->j_state_lock);
1745 return err; 1761 return 0;
1746} 1762}
1747 1763
1748/** 1764/**