diff options
author | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2008-01-11 14:49:31 -0500 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2008-01-11 14:49:31 -0500 |
commit | 460c54b779fce3490ab70a84fd2ef59250ca3d57 (patch) | |
tree | 174f7a702fd765871678aa6ae82ab8f72ed34a67 | |
parent | 5d0381e21ebf55df88e1cdca2810f4a49fe0ee62 (diff) | |
parent | aea6ad0ce5e215ce99fe9e3edd9268f696862d8f (diff) |
Merge branch 'for-linus' of git://oss.sgi.com:8090/xfs/xfs-2.6
* 'for-linus' of git://oss.sgi.com:8090/xfs/xfs-2.6:
[XFS] fix unaligned access in readdir
-rw-r--r-- | fs/xfs/linux-2.6/xfs_file.c | 16 |
1 files changed, 10 insertions, 6 deletions
diff --git a/fs/xfs/linux-2.6/xfs_file.c b/fs/xfs/linux-2.6/xfs_file.c index 4847eb83fc18..21a1c2b1c5fc 100644 --- a/fs/xfs/linux-2.6/xfs_file.c +++ b/fs/xfs/linux-2.6/xfs_file.c | |||
@@ -261,9 +261,9 @@ xfs_file_readdir( | |||
261 | #else | 261 | #else |
262 | 262 | ||
263 | struct hack_dirent { | 263 | struct hack_dirent { |
264 | int namlen; | ||
265 | loff_t offset; | ||
266 | u64 ino; | 264 | u64 ino; |
265 | loff_t offset; | ||
266 | int namlen; | ||
267 | unsigned int d_type; | 267 | unsigned int d_type; |
268 | char name[]; | 268 | char name[]; |
269 | }; | 269 | }; |
@@ -285,8 +285,10 @@ xfs_hack_filldir( | |||
285 | { | 285 | { |
286 | struct hack_callback *buf = __buf; | 286 | struct hack_callback *buf = __buf; |
287 | struct hack_dirent *de = (struct hack_dirent *)(buf->dirent + buf->used); | 287 | struct hack_dirent *de = (struct hack_dirent *)(buf->dirent + buf->used); |
288 | unsigned int reclen; | ||
288 | 289 | ||
289 | if (buf->used + sizeof(struct hack_dirent) + namlen > buf->len) | 290 | reclen = ALIGN(sizeof(struct hack_dirent) + namlen, sizeof(u64)); |
291 | if (buf->used + reclen > buf->len) | ||
290 | return -EINVAL; | 292 | return -EINVAL; |
291 | 293 | ||
292 | de->namlen = namlen; | 294 | de->namlen = namlen; |
@@ -294,7 +296,7 @@ xfs_hack_filldir( | |||
294 | de->ino = ino; | 296 | de->ino = ino; |
295 | de->d_type = d_type; | 297 | de->d_type = d_type; |
296 | memcpy(de->name, name, namlen); | 298 | memcpy(de->name, name, namlen); |
297 | buf->used += sizeof(struct hack_dirent) + namlen; | 299 | buf->used += reclen; |
298 | return 0; | 300 | return 0; |
299 | } | 301 | } |
300 | 302 | ||
@@ -334,7 +336,8 @@ xfs_file_readdir( | |||
334 | offset = filp->f_pos; | 336 | offset = filp->f_pos; |
335 | 337 | ||
336 | while (!eof) { | 338 | while (!eof) { |
337 | int reclen; | 339 | unsigned int reclen; |
340 | |||
338 | start_offset = offset; | 341 | start_offset = offset; |
339 | 342 | ||
340 | buf.used = 0; | 343 | buf.used = 0; |
@@ -355,7 +358,8 @@ xfs_file_readdir( | |||
355 | goto done; | 358 | goto done; |
356 | } | 359 | } |
357 | 360 | ||
358 | reclen = sizeof(struct hack_dirent) + de->namlen; | 361 | reclen = ALIGN(sizeof(struct hack_dirent) + de->namlen, |
362 | sizeof(u64)); | ||
359 | size -= reclen; | 363 | size -= reclen; |
360 | de = (struct hack_dirent *)((char *)de + reclen); | 364 | de = (struct hack_dirent *)((char *)de + reclen); |
361 | curr_offset = de->offset /* & 0x7fffffff */; | 365 | curr_offset = de->offset /* & 0x7fffffff */; |