diff options
| author | Anton Altaparmakov <aia21@cantab.net> | 2005-03-17 05:51:33 -0500 |
|---|---|---|
| committer | Anton Altaparmakov <aia21@cantab.net> | 2005-05-05 06:39:30 -0400 |
| commit | 53d59aad9326199ef5749c97513db498309a057e (patch) | |
| tree | 3fc3e99673cf5c5c8f275cca1ec7ed2dfe5fa192 | |
| parent | 1ef334d372d6a7006e20f56f7e85d8f4ec32e3c2 (diff) | |
NTFS: Fix compilation when configured read-only.
- Add ifdef NTFS_RW around write specific code if fs/ntfs/runlist.[hc] and
fs/ntfs/attrib.[hc].
- Minor bugfix to fs/ntfs/attrib.c::ntfs_attr_make_non_resident() where the
runlist was not freed in all error cases.
- Add fs/ntfs/runlist.[hc]::ntfs_rl_find_vcn_nolock().
Signed-off-by: Anton Altaparmakov <aia21@cantab.net>
| -rw-r--r-- | fs/ntfs/attrib.c | 13 | ||||
| -rw-r--r-- | fs/ntfs/attrib.h | 4 | ||||
| -rw-r--r-- | fs/ntfs/lcnalloc.c | 1 | ||||
| -rw-r--r-- | fs/ntfs/runlist.c | 35 | ||||
| -rw-r--r-- | fs/ntfs/runlist.h | 9 |
5 files changed, 59 insertions, 3 deletions
diff --git a/fs/ntfs/attrib.c b/fs/ntfs/attrib.c index 97e6fb047aa0..1b95f39234a3 100644 --- a/fs/ntfs/attrib.c +++ b/fs/ntfs/attrib.c | |||
| @@ -1057,6 +1057,8 @@ void ntfs_attr_put_search_ctx(ntfs_attr_search_ctx *ctx) | |||
| 1057 | return; | 1057 | return; |
| 1058 | } | 1058 | } |
| 1059 | 1059 | ||
| 1060 | #ifdef NTFS_RW | ||
| 1061 | |||
| 1060 | /** | 1062 | /** |
| 1061 | * ntfs_attr_find_in_attrdef - find an attribute in the $AttrDef system file | 1063 | * ntfs_attr_find_in_attrdef - find an attribute in the $AttrDef system file |
| 1062 | * @vol: ntfs volume to which the attribute belongs | 1064 | * @vol: ntfs volume to which the attribute belongs |
| @@ -1243,6 +1245,13 @@ int ntfs_attr_record_resize(MFT_RECORD *m, ATTR_RECORD *a, u32 new_size) | |||
| 1243 | * -ENOSPC - Not enough disk space. | 1245 | * -ENOSPC - Not enough disk space. |
| 1244 | * -EINVAL - Attribute not defined on the volume. | 1246 | * -EINVAL - Attribute not defined on the volume. |
| 1245 | * -EIO - I/o error or other error. | 1247 | * -EIO - I/o error or other error. |
| 1248 | * Note that -ENOSPC is also returned in the case that there is not enough | ||
| 1249 | * space in the mft record to do the conversion. This can happen when the mft | ||
| 1250 | * record is already very full. The caller is responsible for trying to make | ||
| 1251 | * space in the mft record and trying again. FIXME: Do we need a separate | ||
| 1252 | * error return code for this kind of -ENOSPC or is it always worth trying | ||
| 1253 | * again in case the attribute may then fit in a resident state so no need to | ||
| 1254 | * make it non-resident at all? Ho-hum... (AIA) | ||
| 1246 | * | 1255 | * |
| 1247 | * NOTE to self: No changes in the attribute list are required to move from | 1256 | * NOTE to self: No changes in the attribute list are required to move from |
| 1248 | * a resident to a non-resident attribute. | 1257 | * a resident to a non-resident attribute. |
| @@ -1520,13 +1529,13 @@ err_out: | |||
| 1520 | rl_err_out: | 1529 | rl_err_out: |
| 1521 | if (rl) { | 1530 | if (rl) { |
| 1522 | if (ntfs_cluster_free_from_rl(vol, rl) < 0) { | 1531 | if (ntfs_cluster_free_from_rl(vol, rl) < 0) { |
| 1523 | ntfs_free(rl); | ||
| 1524 | ntfs_error(vol->sb, "Failed to release allocated " | 1532 | ntfs_error(vol->sb, "Failed to release allocated " |
| 1525 | "cluster(s) in error code path. Run " | 1533 | "cluster(s) in error code path. Run " |
| 1526 | "chkdsk to recover the lost " | 1534 | "chkdsk to recover the lost " |
| 1527 | "cluster(s)."); | 1535 | "cluster(s)."); |
| 1528 | NVolSetErrors(vol); | 1536 | NVolSetErrors(vol); |
| 1529 | } | 1537 | } |
| 1538 | ntfs_free(rl); | ||
| 1530 | page_err_out: | 1539 | page_err_out: |
| 1531 | unlock_page(page); | 1540 | unlock_page(page); |
| 1532 | page_cache_release(page); | 1541 | page_cache_release(page); |
| @@ -1680,3 +1689,5 @@ done: | |||
| 1680 | ntfs_debug("Done."); | 1689 | ntfs_debug("Done."); |
| 1681 | return 0; | 1690 | return 0; |
| 1682 | } | 1691 | } |
| 1692 | |||
| 1693 | #endif /* NTFS_RW */ | ||
diff --git a/fs/ntfs/attrib.h b/fs/ntfs/attrib.h index d73385198336..0e4ac6d3c0e7 100644 --- a/fs/ntfs/attrib.h +++ b/fs/ntfs/attrib.h | |||
| @@ -89,6 +89,8 @@ extern ntfs_attr_search_ctx *ntfs_attr_get_search_ctx(ntfs_inode *ni, | |||
| 89 | MFT_RECORD *mrec); | 89 | MFT_RECORD *mrec); |
| 90 | extern void ntfs_attr_put_search_ctx(ntfs_attr_search_ctx *ctx); | 90 | extern void ntfs_attr_put_search_ctx(ntfs_attr_search_ctx *ctx); |
| 91 | 91 | ||
| 92 | #ifdef NTFS_RW | ||
| 93 | |||
| 92 | extern int ntfs_attr_size_bounds_check(const ntfs_volume *vol, | 94 | extern int ntfs_attr_size_bounds_check(const ntfs_volume *vol, |
| 93 | const ATTR_TYPE type, const s64 size); | 95 | const ATTR_TYPE type, const s64 size); |
| 94 | extern int ntfs_attr_can_be_non_resident(const ntfs_volume *vol, | 96 | extern int ntfs_attr_can_be_non_resident(const ntfs_volume *vol, |
| @@ -103,4 +105,6 @@ extern int ntfs_attr_make_non_resident(ntfs_inode *ni); | |||
| 103 | extern int ntfs_attr_set(ntfs_inode *ni, const s64 ofs, const s64 cnt, | 105 | extern int ntfs_attr_set(ntfs_inode *ni, const s64 ofs, const s64 cnt, |
| 104 | const u8 val); | 106 | const u8 val); |
| 105 | 107 | ||
| 108 | #endif /* NTFS_RW */ | ||
| 109 | |||
| 106 | #endif /* _LINUX_NTFS_ATTRIB_H */ | 110 | #endif /* _LINUX_NTFS_ATTRIB_H */ |
diff --git a/fs/ntfs/lcnalloc.c b/fs/ntfs/lcnalloc.c index 71bf08730b05..7087b5b0e6ce 100644 --- a/fs/ntfs/lcnalloc.c +++ b/fs/ntfs/lcnalloc.c | |||
| @@ -848,7 +848,6 @@ s64 __ntfs_cluster_free(struct inode *vi, const VCN start_vcn, s64 count, | |||
| 848 | 848 | ||
| 849 | total_freed = real_freed = 0; | 849 | total_freed = real_freed = 0; |
| 850 | 850 | ||
| 851 | /* This returns with ni->runlist locked for reading on success. */ | ||
| 852 | down_read(&ni->runlist.lock); | 851 | down_read(&ni->runlist.lock); |
| 853 | rl = ntfs_attr_find_vcn_nolock(ni, start_vcn, FALSE); | 852 | rl = ntfs_attr_find_vcn_nolock(ni, start_vcn, FALSE); |
| 854 | if (IS_ERR(rl)) { | 853 | if (IS_ERR(rl)) { |
diff --git a/fs/ntfs/runlist.c b/fs/ntfs/runlist.c index 3f479f176610..396d767c2cab 100644 --- a/fs/ntfs/runlist.c +++ b/fs/ntfs/runlist.c | |||
| @@ -980,6 +980,39 @@ LCN ntfs_rl_vcn_to_lcn(const runlist_element *rl, const VCN vcn) | |||
| 980 | return LCN_ENOENT; | 980 | return LCN_ENOENT; |
| 981 | } | 981 | } |
| 982 | 982 | ||
| 983 | #ifdef NTFS_RW | ||
| 984 | |||
| 985 | /** | ||
| 986 | * ntfs_rl_find_vcn_nolock - find a vcn in a runlist | ||
| 987 | * @rl: runlist to search | ||
| 988 | * @vcn: vcn to find | ||
| 989 | * | ||
| 990 | * Find the virtual cluster number @vcn in the runlist @rl and return the | ||
| 991 | * address of the runlist element containing the @vcn on success. | ||
| 992 | * | ||
| 993 | * Return NULL if @rl is NULL or @vcn is in an unmapped part/out of bounds of | ||
| 994 | * the runlist. | ||
| 995 | * | ||
| 996 | * Locking: The runlist must be locked on entry. | ||
| 997 | */ | ||
| 998 | runlist_element *ntfs_rl_find_vcn_nolock(runlist_element *rl, const VCN vcn) | ||
| 999 | { | ||
| 1000 | BUG_ON(vcn < 0); | ||
| 1001 | if (unlikely(!rl || vcn < rl[0].vcn)) | ||
| 1002 | return NULL; | ||
| 1003 | while (likely(rl->length)) { | ||
| 1004 | if (unlikely(vcn < rl[1].vcn)) { | ||
| 1005 | if (likely(rl->lcn >= LCN_HOLE)) | ||
| 1006 | return rl; | ||
| 1007 | return NULL; | ||
| 1008 | } | ||
| 1009 | rl++; | ||
| 1010 | } | ||
| 1011 | if (likely(rl->lcn == LCN_ENOENT)) | ||
| 1012 | return rl; | ||
| 1013 | return NULL; | ||
| 1014 | } | ||
| 1015 | |||
| 983 | /** | 1016 | /** |
| 984 | * ntfs_get_nr_significant_bytes - get number of bytes needed to store a number | 1017 | * ntfs_get_nr_significant_bytes - get number of bytes needed to store a number |
| 985 | * @n: number for which to get the number of bytes for | 1018 | * @n: number for which to get the number of bytes for |
| @@ -1452,3 +1485,5 @@ int ntfs_rl_truncate_nolock(const ntfs_volume *vol, runlist *const runlist, | |||
| 1452 | ntfs_debug("Done."); | 1485 | ntfs_debug("Done."); |
| 1453 | return 0; | 1486 | return 0; |
| 1454 | } | 1487 | } |
| 1488 | |||
| 1489 | #endif /* NTFS_RW */ | ||
diff --git a/fs/ntfs/runlist.h b/fs/ntfs/runlist.h index 60c42f3a3fc4..cf5c1b44bea8 100644 --- a/fs/ntfs/runlist.h +++ b/fs/ntfs/runlist.h | |||
| @@ -2,7 +2,7 @@ | |||
| 2 | * runlist.h - Defines for runlist handling in NTFS Linux kernel driver. | 2 | * runlist.h - Defines for runlist handling in NTFS Linux kernel driver. |
| 3 | * Part of the Linux-NTFS project. | 3 | * Part of the Linux-NTFS project. |
| 4 | * | 4 | * |
| 5 | * Copyright (c) 2001-2004 Anton Altaparmakov | 5 | * Copyright (c) 2001-2005 Anton Altaparmakov |
| 6 | * Copyright (c) 2002 Richard Russon | 6 | * Copyright (c) 2002 Richard Russon |
| 7 | * | 7 | * |
| 8 | * This program/include file is free software; you can redistribute it and/or | 8 | * This program/include file is free software; you can redistribute it and/or |
| @@ -78,6 +78,11 @@ extern runlist_element *ntfs_mapping_pairs_decompress(const ntfs_volume *vol, | |||
| 78 | 78 | ||
| 79 | extern LCN ntfs_rl_vcn_to_lcn(const runlist_element *rl, const VCN vcn); | 79 | extern LCN ntfs_rl_vcn_to_lcn(const runlist_element *rl, const VCN vcn); |
| 80 | 80 | ||
| 81 | #ifdef NTFS_RW | ||
| 82 | |||
| 83 | extern runlist_element *ntfs_rl_find_vcn_nolock(runlist_element *rl, | ||
| 84 | const VCN vcn); | ||
| 85 | |||
| 81 | extern int ntfs_get_size_for_mapping_pairs(const ntfs_volume *vol, | 86 | extern int ntfs_get_size_for_mapping_pairs(const ntfs_volume *vol, |
| 82 | const runlist_element *rl, const VCN start_vcn); | 87 | const runlist_element *rl, const VCN start_vcn); |
| 83 | 88 | ||
| @@ -88,4 +93,6 @@ extern int ntfs_mapping_pairs_build(const ntfs_volume *vol, s8 *dst, | |||
| 88 | extern int ntfs_rl_truncate_nolock(const ntfs_volume *vol, | 93 | extern int ntfs_rl_truncate_nolock(const ntfs_volume *vol, |
| 89 | runlist *const runlist, const s64 new_length); | 94 | runlist *const runlist, const s64 new_length); |
| 90 | 95 | ||
| 96 | #endif /* NTFS_RW */ | ||
| 97 | |||
| 91 | #endif /* _LINUX_NTFS_RUNLIST_H */ | 98 | #endif /* _LINUX_NTFS_RUNLIST_H */ |
