diff options
Diffstat (limited to 'fs/udf/truncate.c')
-rw-r--r-- | fs/udf/truncate.c | 81 |
1 files changed, 31 insertions, 50 deletions
diff --git a/fs/udf/truncate.c b/fs/udf/truncate.c index fe61be17cdab..65e19b4f9424 100644 --- a/fs/udf/truncate.c +++ b/fs/udf/truncate.c | |||
@@ -22,7 +22,6 @@ | |||
22 | #include "udfdecl.h" | 22 | #include "udfdecl.h" |
23 | #include <linux/fs.h> | 23 | #include <linux/fs.h> |
24 | #include <linux/mm.h> | 24 | #include <linux/mm.h> |
25 | #include <linux/udf_fs.h> | ||
26 | #include <linux/buffer_head.h> | 25 | #include <linux/buffer_head.h> |
27 | 26 | ||
28 | #include "udf_i.h" | 27 | #include "udf_i.h" |
@@ -180,6 +179,24 @@ void udf_discard_prealloc(struct inode *inode) | |||
180 | brelse(epos.bh); | 179 | brelse(epos.bh); |
181 | } | 180 | } |
182 | 181 | ||
182 | static void udf_update_alloc_ext_desc(struct inode *inode, | ||
183 | struct extent_position *epos, | ||
184 | u32 lenalloc) | ||
185 | { | ||
186 | struct super_block *sb = inode->i_sb; | ||
187 | struct udf_sb_info *sbi = UDF_SB(sb); | ||
188 | |||
189 | struct allocExtDesc *aed = (struct allocExtDesc *) (epos->bh->b_data); | ||
190 | int len = sizeof(struct allocExtDesc); | ||
191 | |||
192 | aed->lengthAllocDescs = cpu_to_le32(lenalloc); | ||
193 | if (!UDF_QUERY_FLAG(sb, UDF_FLAG_STRICT) || sbi->s_udfrev >= 0x0201) | ||
194 | len += lenalloc; | ||
195 | |||
196 | udf_update_tag(epos->bh->b_data, len); | ||
197 | mark_buffer_dirty_inode(epos->bh, inode); | ||
198 | } | ||
199 | |||
183 | void udf_truncate_extents(struct inode *inode) | 200 | void udf_truncate_extents(struct inode *inode) |
184 | { | 201 | { |
185 | struct extent_position epos; | 202 | struct extent_position epos; |
@@ -187,7 +204,6 @@ void udf_truncate_extents(struct inode *inode) | |||
187 | uint32_t elen, nelen = 0, indirect_ext_len = 0, lenalloc; | 204 | uint32_t elen, nelen = 0, indirect_ext_len = 0, lenalloc; |
188 | int8_t etype; | 205 | int8_t etype; |
189 | struct super_block *sb = inode->i_sb; | 206 | struct super_block *sb = inode->i_sb; |
190 | struct udf_sb_info *sbi = UDF_SB(sb); | ||
191 | sector_t first_block = inode->i_size >> sb->s_blocksize_bits, offset; | 207 | sector_t first_block = inode->i_size >> sb->s_blocksize_bits, offset; |
192 | loff_t byte_offset; | 208 | loff_t byte_offset; |
193 | int adsize; | 209 | int adsize; |
@@ -224,35 +240,15 @@ void udf_truncate_extents(struct inode *inode) | |||
224 | if (indirect_ext_len) { | 240 | if (indirect_ext_len) { |
225 | /* We managed to free all extents in the | 241 | /* We managed to free all extents in the |
226 | * indirect extent - free it too */ | 242 | * indirect extent - free it too */ |
227 | if (!epos.bh) | 243 | BUG_ON(!epos.bh); |
228 | BUG(); | ||
229 | udf_free_blocks(sb, inode, epos.block, | 244 | udf_free_blocks(sb, inode, epos.block, |
230 | 0, indirect_ext_len); | 245 | 0, indirect_ext_len); |
231 | } else { | 246 | } else if (!epos.bh) { |
232 | if (!epos.bh) { | 247 | iinfo->i_lenAlloc = lenalloc; |
233 | iinfo->i_lenAlloc = | 248 | mark_inode_dirty(inode); |
234 | lenalloc; | 249 | } else |
235 | mark_inode_dirty(inode); | 250 | udf_update_alloc_ext_desc(inode, |
236 | } else { | 251 | &epos, lenalloc); |
237 | struct allocExtDesc *aed = | ||
238 | (struct allocExtDesc *) | ||
239 | (epos.bh->b_data); | ||
240 | int len = | ||
241 | sizeof(struct allocExtDesc); | ||
242 | |||
243 | aed->lengthAllocDescs = | ||
244 | cpu_to_le32(lenalloc); | ||
245 | if (!UDF_QUERY_FLAG(sb, | ||
246 | UDF_FLAG_STRICT) || | ||
247 | sbi->s_udfrev >= 0x0201) | ||
248 | len += lenalloc; | ||
249 | |||
250 | udf_update_tag(epos.bh->b_data, | ||
251 | len); | ||
252 | mark_buffer_dirty_inode( | ||
253 | epos.bh, inode); | ||
254 | } | ||
255 | } | ||
256 | brelse(epos.bh); | 252 | brelse(epos.bh); |
257 | epos.offset = sizeof(struct allocExtDesc); | 253 | epos.offset = sizeof(struct allocExtDesc); |
258 | epos.block = eloc; | 254 | epos.block = eloc; |
@@ -272,29 +268,14 @@ void udf_truncate_extents(struct inode *inode) | |||
272 | } | 268 | } |
273 | 269 | ||
274 | if (indirect_ext_len) { | 270 | if (indirect_ext_len) { |
275 | if (!epos.bh) | 271 | BUG_ON(!epos.bh); |
276 | BUG(); | ||
277 | udf_free_blocks(sb, inode, epos.block, 0, | 272 | udf_free_blocks(sb, inode, epos.block, 0, |
278 | indirect_ext_len); | 273 | indirect_ext_len); |
279 | } else { | 274 | } else if (!epos.bh) { |
280 | if (!epos.bh) { | 275 | iinfo->i_lenAlloc = lenalloc; |
281 | iinfo->i_lenAlloc = lenalloc; | 276 | mark_inode_dirty(inode); |
282 | mark_inode_dirty(inode); | 277 | } else |
283 | } else { | 278 | udf_update_alloc_ext_desc(inode, &epos, lenalloc); |
284 | struct allocExtDesc *aed = | ||
285 | (struct allocExtDesc *)(epos.bh->b_data); | ||
286 | aed->lengthAllocDescs = cpu_to_le32(lenalloc); | ||
287 | if (!UDF_QUERY_FLAG(sb, UDF_FLAG_STRICT) || | ||
288 | sbi->s_udfrev >= 0x0201) | ||
289 | udf_update_tag(epos.bh->b_data, | ||
290 | lenalloc + | ||
291 | sizeof(struct allocExtDesc)); | ||
292 | else | ||
293 | udf_update_tag(epos.bh->b_data, | ||
294 | sizeof(struct allocExtDesc)); | ||
295 | mark_buffer_dirty_inode(epos.bh, inode); | ||
296 | } | ||
297 | } | ||
298 | } else if (inode->i_size) { | 279 | } else if (inode->i_size) { |
299 | if (byte_offset) { | 280 | if (byte_offset) { |
300 | kernel_long_ad extent; | 281 | kernel_long_ad extent; |