diff options
author | Tobias Stoeckmann <tobias@cvs.openbsd.org> | 2014-06-18 17:29:08 +0000 |
---|---|---|
committer | Tobias Stoeckmann <tobias@cvs.openbsd.org> | 2014-06-18 17:29:08 +0000 |
commit | 9802c1340125bbb2877e684e6a88360e099f0b4e (patch) | |
tree | 9c5176a90d62ba86f9015b911d4bf62cfbe2323c | |
parent | 97d7ed8e5ab617c099737cd491ed46054dd988e6 (diff) |
Always keep length of cluster chain up to date, otherwise the drop of
superfluous clusters can lead to out of boundary access.
ok krw@
-rw-r--r-- | sbin/fsck_msdos/dir.c | 12 | ||||
-rw-r--r-- | sbin/fsck_msdos/fat.c | 11 |
2 files changed, 18 insertions, 5 deletions
diff --git a/sbin/fsck_msdos/dir.c b/sbin/fsck_msdos/dir.c index 38baedc8042..0459a7f96d2 100644 --- a/sbin/fsck_msdos/dir.c +++ b/sbin/fsck_msdos/dir.c @@ -1,4 +1,4 @@ -/* $OpenBSD: dir.c,v 1.22 2014/06/16 18:33:33 tobias Exp $ */ +/* $OpenBSD: dir.c,v 1.23 2014/06/18 17:29:07 tobias Exp $ */ /* $NetBSD: dir.c,v 1.11 1997/10/17 11:19:35 ws Exp $ */ /* @@ -374,7 +374,7 @@ checksize(struct bootblock *boot, struct fatEntry *fat, u_char *p, /* * Check size on ordinary files */ - int32_t physicalSize; + u_int32_t physicalSize; if (dir->head == CLUST_FREE) physicalSize = 0; @@ -400,12 +400,16 @@ checksize(struct bootblock *boot, struct fatEntry *fat, u_char *p, fullpath(dir)); if (ask(1, "Drop superfluous clusters")) { cl_t cl; - u_int32_t sz = 0; + u_int32_t len, sz; - for (cl = dir->head; (sz += boot->ClusterSize) < dir->size;) + len = sz = 0; + for (cl = dir->head; (sz += boot->ClusterSize) < dir->size;) { cl = fat[cl].next; + len++; + } clearchain(boot, fat, fat[cl].next); fat[cl].next = CLUST_EOF; + fat[dir->head].length = len; return (FSFATMOD); } else return (FSERROR); diff --git a/sbin/fsck_msdos/fat.c b/sbin/fsck_msdos/fat.c index 1eb517bf641..1ab8c7380f2 100644 --- a/sbin/fsck_msdos/fat.c +++ b/sbin/fsck_msdos/fat.c @@ -1,4 +1,4 @@ -/* $OpenBSD: fat.c,v 1.23 2014/06/16 18:33:33 tobias Exp $ */ +/* $OpenBSD: fat.c,v 1.24 2014/06/18 17:29:07 tobias Exp $ */ /* $NetBSD: fat.c,v 1.8 1997/10/17 11:19:53 ws Exp $ */ /* @@ -302,11 +302,20 @@ clearchain(struct bootblock *boot, struct fatEntry *fat, cl_t head) int tryclear(struct bootblock *boot, struct fatEntry *fat, cl_t head, cl_t *trunc) { + u_int len; + cl_t p; + if (ask(0, "Clear chain starting at %u", head)) { clearchain(boot, fat, head); return FSFATMOD; } else if (ask(0, "Truncate")) { *trunc = CLUST_EOF; + len = 0; + for (p = head; p >= CLUST_FIRST && p < boot->NumClusters; + p = fat[p].next) { + len++; + } + fat[head].length = len; return FSFATMOD; } else return FSERROR; |