Commit 548b4535 authored by Andrew Morton's avatar Andrew Morton Committed by Linus Torvalds

[PATCH] fatfs: fix printk storm during I/O errors

From: OGAWA Hirofumi <hirofumi@mail.parknet.co.jp>

The fatfs was ignoring the I/O error on two points. If I/O error
happen while checking a free block entries, this checks the all
entries, and reports an I/O error on each entry.

This problem became cause of the disk full by syslogd.
parent 992d50d5
......@@ -1047,7 +1047,7 @@ int fat_fill_super(struct super_block *sb, void *data, int silent,
int fat_statfs(struct super_block *sb, struct kstatfs *buf)
{
int free, nr;
int free, nr, ret;
if (MSDOS_SB(sb)->free_clusters != -1)
free = MSDOS_SB(sb)->free_clusters;
......@@ -1057,9 +1057,14 @@ int fat_statfs(struct super_block *sb, struct kstatfs *buf)
free = MSDOS_SB(sb)->free_clusters;
else {
free = 0;
for (nr = 2; nr < MSDOS_SB(sb)->clusters + 2; nr++)
if (fat_access(sb, nr, -1) == FAT_ENT_FREE)
for (nr = 2; nr < MSDOS_SB(sb)->clusters + 2; nr++) {
ret = fat_access(sb, nr, -1);
if (ret < 0) {
unlock_fat(sb);
return ret;
} else if (ret == FAT_ENT_FREE)
free++;
}
MSDOS_SB(sb)->free_clusters = free;
}
unlock_fat(sb);
......
......@@ -88,7 +88,7 @@ void fat_clusters_flush(struct super_block *sb)
int fat_add_cluster(struct inode *inode)
{
struct super_block *sb = inode->i_sb;
int count, limit, new_dclus, new_fclus, last;
int ret, count, limit, new_dclus, new_fclus, last;
int cluster_bits = MSDOS_SB(sb)->cluster_bits;
/*
......@@ -123,7 +123,12 @@ int fat_add_cluster(struct inode *inode)
new_dclus = new_dclus % limit;
if (new_dclus < 2)
new_dclus = 2;
if (fat_access(sb, new_dclus, -1) == FAT_ENT_FREE)
ret = fat_access(sb, new_dclus, -1);
if (ret < 0) {
unlock_fat(sb);
return ret;
} else if (ret == FAT_ENT_FREE)
break;
}
if (count >= MSDOS_SB(sb)->clusters) {
......@@ -131,9 +136,14 @@ int fat_add_cluster(struct inode *inode)
unlock_fat(sb);
return -ENOSPC;
}
MSDOS_SB(sb)->prev_free = new_dclus;
fat_access(sb, new_dclus, FAT_ENT_EOF);
ret = fat_access(sb, new_dclus, FAT_ENT_EOF);
if (ret < 0) {
unlock_fat(sb);
return ret;
}
MSDOS_SB(sb)->prev_free = new_dclus;
if (MSDOS_SB(sb)->free_clusters != -1)
MSDOS_SB(sb)->free_clusters--;
fat_clusters_flush(sb);
......@@ -142,7 +152,9 @@ int fat_add_cluster(struct inode *inode)
/* add new one to the last of the cluster chain */
if (last) {
fat_access(sb, last, new_dclus);
ret = fat_access(sb, last, new_dclus);
if (ret < 0)
return ret;
fat_cache_add(inode, new_fclus, new_dclus);
} else {
MSDOS_I(inode)->i_start = new_dclus;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment