Plug the two-megabyte-per-day memory leak.



 fs/jbd/commit.c  |    8 ++++++++
 fs/jbd/journal.c |    2 ++
 2 files changed, 10 insertions(+)

diff -puN fs/jbd/commit.c~jbd-leak-fix fs/jbd/commit.c
--- 25/fs/jbd/commit.c~jbd-leak-fix	2003-10-16 22:12:56.000000000 -0700
+++ 25-akpm/fs/jbd/commit.c	2003-10-16 22:12:56.000000000 -0700
@@ -172,6 +172,14 @@ void journal_commit_transaction(journal_
 	while (commit_transaction->t_reserved_list) {
 		jh = commit_transaction->t_reserved_list;
 		JBUFFER_TRACE(jh, "reserved, unused: refile");
+		/*
+		 * A journal_get_undo_access()+journal_release_buffer() may
+		 * leave undo-committed data.
+		 */
+		if (jh->b_committed_data) {
+			kfree(jh->b_committed_data);
+			jh->b_committed_data = NULL;
+		}
 		journal_refile_buffer(journal, jh);
 	}
 
diff -puN fs/jbd/journal.c~jbd-leak-fix fs/jbd/journal.c
--- 25/fs/jbd/journal.c~jbd-leak-fix	2003-10-16 22:12:56.000000000 -0700
+++ 25-akpm/fs/jbd/journal.c	2003-10-16 22:12:56.000000000 -0700
@@ -1729,6 +1729,8 @@ static void __journal_remove_journal_hea
 			J_ASSERT_BH(bh, buffer_jbd(bh));
 			J_ASSERT_BH(bh, jh2bh(jh) == bh);
 			BUFFER_TRACE(bh, "remove journal_head");
+			J_ASSERT_BH(bh, !jh->b_frozen_data);
+			J_ASSERT_BH(bh, !jh->b_committed_data);
 			bh->b_private = NULL;
 			jh->b_bh = NULL;	/* debug, really */
 			clear_buffer_jbd(bh);

_