namei.c
上传用户:jlfgdled
上传日期:2013-04-10
资源大小:33168k
文件大小:33k
源码类别:

Linux/Unix编程

开发平台:

Unix_Linux

  1. /*
  2.  * namei.c
  3.  *
  4.  * PURPOSE
  5.  *      Inode name handling routines for the OSTA-UDF(tm) filesystem.
  6.  *
  7.  * CONTACTS
  8.  *      E-mail regarding any portion of the Linux UDF file system should be
  9.  *      directed to the development team mailing list (run by majordomo):
  10.  *              linux_udf@hpesjro.fc.hp.com
  11.  *
  12.  * COPYRIGHT
  13.  *      This file is distributed under the terms of the GNU General Public
  14.  *      License (GPL). Copies of the GPL can be obtained from:
  15.  *              ftp://prep.ai.mit.edu/pub/gnu/GPL
  16.  *      Each contributing author retains all rights to their own work.
  17.  *
  18.  *  (C) 1998-2001 Ben Fennema
  19.  *  (C) 1999-2000 Stelias Computing Inc
  20.  *
  21.  * HISTORY
  22.  *
  23.  *  12/12/98 blf  Created. Split out the lookup code from dir.c
  24.  *  04/19/99 blf  link, mknod, symlink support
  25.  */
  26. #include "udfdecl.h"
  27. #include "udf_i.h"
  28. #include "udf_sb.h"
  29. #include <linux/string.h>
  30. #include <linux/errno.h>
  31. #include <linux/mm.h>
  32. #include <linux/slab.h>
  33. #include <linux/quotaops.h>
  34. #include <linux/locks.h>
  35. #include <linux/smp_lock.h>
  36. static inline int udf_match(int len, const char * const name, struct qstr *qs)
  37. {
  38. if (len != qs->len)
  39. return 0;
  40. return !memcmp(name, qs->name, len);
  41. }
  42. int udf_write_fi(struct inode *inode, struct fileIdentDesc *cfi,
  43. struct fileIdentDesc *sfi, struct udf_fileident_bh *fibh,
  44. uint8_t *impuse, uint8_t *fileident)
  45. {
  46. uint16_t crclen = fibh->eoffset - fibh->soffset - sizeof(tag);
  47. uint16_t crc;
  48. uint8_t checksum = 0;
  49. int i;
  50. int offset;
  51. uint16_t liu = le16_to_cpu(cfi->lengthOfImpUse);
  52. uint8_t lfi = cfi->lengthFileIdent;
  53. int padlen = fibh->eoffset - fibh->soffset - liu - lfi -
  54. sizeof(struct fileIdentDesc);
  55. offset = fibh->soffset + sizeof(struct fileIdentDesc);
  56. if (impuse)
  57. {
  58. if (offset + liu < 0)
  59. memcpy((uint8_t *)sfi->impUse, impuse, liu);
  60. else if (offset >= 0)
  61. memcpy(fibh->ebh->b_data + offset, impuse, liu);
  62. else
  63. {
  64. memcpy((uint8_t *)sfi->impUse, impuse, -offset);
  65. memcpy(fibh->ebh->b_data, impuse - offset, liu + offset);
  66. }
  67. }
  68. offset += liu;
  69. if (fileident)
  70. {
  71. if (offset + lfi < 0)
  72. memcpy((uint8_t *)sfi->fileIdent + liu, fileident, lfi);
  73. else if (offset >= 0)
  74. memcpy(fibh->ebh->b_data + offset, fileident, lfi);
  75. else
  76. {
  77. memcpy((uint8_t *)sfi->fileIdent + liu, fileident, -offset);
  78. memcpy(fibh->ebh->b_data, fileident - offset, lfi + offset);
  79. }
  80. }
  81. offset += lfi;
  82. if (offset + padlen < 0)
  83. memset((uint8_t *)sfi->padding + liu + lfi, 0x00, padlen);
  84. else if (offset >= 0)
  85. memset(fibh->ebh->b_data + offset, 0x00, padlen);
  86. else
  87. {
  88. memset((uint8_t *)sfi->padding + liu + lfi, 0x00, -offset);
  89. memset(fibh->ebh->b_data, 0x00, padlen + offset);
  90. }
  91. crc = udf_crc((uint8_t *)cfi + sizeof(tag), sizeof(struct fileIdentDesc) -
  92. sizeof(tag), 0);
  93. if (fibh->sbh == fibh->ebh)
  94. crc = udf_crc((uint8_t *)sfi->impUse,
  95. crclen + sizeof(tag) - sizeof(struct fileIdentDesc), crc);
  96. else if (sizeof(struct fileIdentDesc) >= -fibh->soffset)
  97. crc = udf_crc(fibh->ebh->b_data + sizeof(struct fileIdentDesc) + fibh->soffset,
  98. crclen + sizeof(tag) - sizeof(struct fileIdentDesc), crc);
  99. else
  100. {
  101. crc = udf_crc((uint8_t *)sfi->impUse,
  102. -fibh->soffset - sizeof(struct fileIdentDesc), crc);
  103. crc = udf_crc(fibh->ebh->b_data, fibh->eoffset, crc);
  104. }
  105. cfi->descTag.descCRC = cpu_to_le32(crc);
  106. cfi->descTag.descCRCLength = cpu_to_le16(crclen);
  107. for (i=0; i<16; i++)
  108. if (i != 4)
  109. checksum += ((uint8_t *)&cfi->descTag)[i];
  110. cfi->descTag.tagChecksum = checksum;
  111. if (sizeof(struct fileIdentDesc) <= -fibh->soffset)
  112. memcpy((uint8_t *)sfi, (uint8_t *)cfi, sizeof(struct fileIdentDesc));
  113. else
  114. {
  115. memcpy((uint8_t *)sfi, (uint8_t *)cfi, -fibh->soffset);
  116. memcpy(fibh->ebh->b_data, (uint8_t *)cfi - fibh->soffset,
  117. sizeof(struct fileIdentDesc) + fibh->soffset);
  118. }
  119. if (fibh->sbh != fibh->ebh)
  120. mark_buffer_dirty_inode(fibh->ebh, inode);
  121. mark_buffer_dirty_inode(fibh->sbh, inode);
  122. return 0;
  123. }
  124. static struct fileIdentDesc *
  125. udf_find_entry(struct inode *dir, struct dentry *dentry,
  126. struct udf_fileident_bh *fibh,
  127. struct fileIdentDesc *cfi)
  128. {
  129. struct fileIdentDesc *fi=NULL;
  130. loff_t f_pos;
  131. int block, flen;
  132. char fname[255];
  133. char *nameptr;
  134. uint8_t lfi;
  135. uint16_t liu;
  136. loff_t size = (udf_ext0_offset(dir) + dir->i_size) >> 2;
  137. lb_addr bloc, eloc;
  138. uint32_t extoffset, elen, offset;
  139. struct buffer_head *bh = NULL;
  140. if (!dir)
  141. return NULL;
  142. f_pos = (udf_ext0_offset(dir) >> 2);
  143. fibh->soffset = fibh->eoffset = (f_pos & ((dir->i_sb->s_blocksize - 1) >> 2)) << 2;
  144. if (inode_bmap(dir, f_pos >> (dir->i_sb->s_blocksize_bits - 2),
  145. &bloc, &extoffset, &eloc, &elen, &offset, &bh) == (EXT_RECORDED_ALLOCATED >> 30))
  146. {
  147. offset >>= dir->i_sb->s_blocksize_bits;
  148. block = udf_get_lb_pblock(dir->i_sb, eloc, offset);
  149. if ((++offset << dir->i_sb->s_blocksize_bits) < elen)
  150. {
  151. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_SHORT)
  152. extoffset -= sizeof(short_ad);
  153. else if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_LONG)
  154. extoffset -= sizeof(long_ad);
  155. }
  156. else
  157. offset = 0;
  158. }
  159. else
  160. {
  161. udf_release_data(bh);
  162. return NULL;
  163. }
  164. if (!(fibh->sbh = fibh->ebh = udf_tread(dir->i_sb, block)))
  165. {
  166. udf_release_data(bh);
  167. return NULL;
  168. }
  169. while ( (f_pos < size) )
  170. {
  171. fi = udf_fileident_read(dir, &f_pos, fibh, cfi, &bloc, &extoffset, &eloc, &elen, &offset, &bh);
  172. if (!fi)
  173. {
  174. if (fibh->sbh != fibh->ebh)
  175. udf_release_data(fibh->ebh);
  176. udf_release_data(fibh->sbh);
  177. udf_release_data(bh);
  178. return NULL;
  179. }
  180. liu = le16_to_cpu(cfi->lengthOfImpUse);
  181. lfi = cfi->lengthFileIdent;
  182. if (fibh->sbh == fibh->ebh)
  183. {
  184. nameptr = fi->fileIdent + liu;
  185. }
  186. else
  187. {
  188. int poffset; /* Unpaded ending offset */
  189. poffset = fibh->soffset + sizeof(struct fileIdentDesc) + liu + lfi;
  190. if (poffset >= lfi)
  191. nameptr = (uint8_t *)(fibh->ebh->b_data + poffset - lfi);
  192. else
  193. {
  194. nameptr = fname;
  195. memcpy(nameptr, fi->fileIdent + liu, lfi - poffset);
  196. memcpy(nameptr + lfi - poffset, fibh->ebh->b_data, poffset);
  197. }
  198. }
  199. if ( (cfi->fileCharacteristics & FID_FILE_CHAR_DELETED) != 0 )
  200. {
  201. if ( !UDF_QUERY_FLAG(dir->i_sb, UDF_FLAG_UNDELETE) )
  202. continue;
  203. }
  204.     
  205. if ( (cfi->fileCharacteristics & FID_FILE_CHAR_HIDDEN) != 0 )
  206. {
  207. if ( !UDF_QUERY_FLAG(dir->i_sb, UDF_FLAG_UNHIDE) )
  208. continue;
  209. }
  210. if (!lfi)
  211. continue;
  212. if ((flen = udf_get_filename(dir->i_sb, nameptr, fname, lfi)))
  213. {
  214. if (udf_match(flen, fname, &(dentry->d_name)))
  215. {
  216. udf_release_data(bh);
  217. return fi;
  218. }
  219. }
  220. }
  221. if (fibh->sbh != fibh->ebh)
  222. udf_release_data(fibh->ebh);
  223. udf_release_data(fibh->sbh);
  224. udf_release_data(bh);
  225. return NULL;
  226. }
  227. /*
  228.  * udf_lookup
  229.  *
  230.  * PURPOSE
  231.  * Look-up the inode for a given name.
  232.  *
  233.  * DESCRIPTION
  234.  * Required - lookup_dentry() will return -ENOTDIR if this routine is not
  235.  * available for a directory. The filesystem is useless if this routine is
  236.  * not available for at least the filesystem's root directory.
  237.  *
  238.  * This routine is passed an incomplete dentry - it must be completed by
  239.  * calling d_add(dentry, inode). If the name does not exist, then the
  240.  * specified inode must be set to null. An error should only be returned
  241.  * when the lookup fails for a reason other than the name not existing.
  242.  * Note that the directory inode semaphore is held during the call.
  243.  *
  244.  * Refer to lookup_dentry() in fs/namei.c
  245.  * lookup_dentry() -> lookup() -> real_lookup() -> .
  246.  *
  247.  * PRE-CONDITIONS
  248.  * dir Pointer to inode of parent directory.
  249.  * dentry Pointer to dentry to complete.
  250.  *
  251.  * POST-CONDITIONS
  252.  * <return> Zero on success.
  253.  *
  254.  * HISTORY
  255.  * July 1, 1997 - Andrew E. Mileski
  256.  * Written, tested, and released.
  257.  */
  258. static struct dentry *
  259. udf_lookup(struct inode *dir, struct dentry *dentry)
  260. {
  261. struct inode *inode = NULL;
  262. struct fileIdentDesc cfi, *fi;
  263. struct udf_fileident_bh fibh;
  264. if (dentry->d_name.len > UDF_NAME_LEN)
  265. return ERR_PTR(-ENAMETOOLONG);
  266. #ifdef UDF_RECOVERY
  267. /* temporary shorthand for specifying files by inode number */
  268. if (!strncmp(dentry->d_name.name, ".B=", 3) )
  269. {
  270. lb_addr lb = { 0, simple_strtoul(dentry->d_name.name+3, NULL, 0) };
  271. inode = udf_iget(dir->i_sb, lb);
  272. if (!inode)
  273. return ERR_PTR(-EACCES);
  274. }
  275. else
  276. #endif /* UDF_RECOVERY */
  277. if ((fi = udf_find_entry(dir, dentry, &fibh, &cfi)))
  278. {
  279. if (fibh.sbh != fibh.ebh)
  280. udf_release_data(fibh.ebh);
  281. udf_release_data(fibh.sbh);
  282. inode = udf_iget(dir->i_sb, lelb_to_cpu(cfi.icb.extLocation));
  283. if ( !inode )
  284. return ERR_PTR(-EACCES);
  285. }
  286. d_add(dentry, inode);
  287. return NULL;
  288. }
  289. static struct fileIdentDesc *
  290. udf_add_entry(struct inode *dir, struct dentry *dentry,
  291. struct udf_fileident_bh *fibh,
  292. struct fileIdentDesc *cfi, int *err)
  293. {
  294. struct super_block *sb;
  295. struct fileIdentDesc *fi=NULL;
  296. struct ustr unifilename;
  297. char name[UDF_NAME_LEN], fname[UDF_NAME_LEN];
  298. int namelen;
  299. loff_t f_pos;
  300. int flen;
  301. char *nameptr;
  302. loff_t size = (udf_ext0_offset(dir) + dir->i_size) >> 2;
  303. int nfidlen;
  304. uint8_t lfi;
  305. uint16_t liu;
  306. int block;
  307. lb_addr bloc, eloc;
  308. uint32_t extoffset, elen, offset;
  309. struct buffer_head *bh = NULL;
  310. sb = dir->i_sb;
  311. if (dentry)
  312. {
  313. if (!dentry->d_name.len)
  314. {
  315. *err = -EINVAL;
  316. return NULL;
  317. }
  318. if ( !(udf_char_to_ustr(&unifilename, dentry->d_name.name, dentry->d_name.len)) )
  319. {
  320. *err = -ENAMETOOLONG;
  321. return NULL;
  322. }
  323. if (UDF_QUERY_FLAG(sb, UDF_FLAG_UTF8))
  324. {
  325. if ( !(namelen = udf_UTF8toCS0(name, &unifilename, UDF_NAME_LEN)) )
  326. {
  327. *err = -ENAMETOOLONG;
  328. return NULL;
  329. }
  330. }
  331. else if (UDF_QUERY_FLAG(sb, UDF_FLAG_NLS_MAP))
  332. {
  333. if ( !(namelen = udf_NLStoCS0(UDF_SB(sb)->s_nls_map, name, &unifilename, UDF_NAME_LEN)) )
  334. {
  335. *err = -ENAMETOOLONG;
  336. return NULL;
  337. }
  338. }
  339. else
  340. return NULL;
  341. }
  342. else
  343. namelen = 0;
  344. nfidlen = (sizeof(struct fileIdentDesc) + namelen + 3) & ~3;
  345. f_pos = (udf_ext0_offset(dir) >> 2);
  346. fibh->soffset = fibh->eoffset = (f_pos & ((dir->i_sb->s_blocksize - 1) >> 2)) << 2;
  347. if (inode_bmap(dir, f_pos >> (dir->i_sb->s_blocksize_bits - 2),
  348. &bloc, &extoffset, &eloc, &elen, &offset, &bh) == (EXT_RECORDED_ALLOCATED >> 30))
  349. {
  350. offset >>= dir->i_sb->s_blocksize_bits;
  351. block = udf_get_lb_pblock(dir->i_sb, eloc, offset);
  352. if ((++offset << dir->i_sb->s_blocksize_bits) < elen)
  353. {
  354. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_SHORT)
  355. extoffset -= sizeof(short_ad);
  356. else if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_LONG)
  357. extoffset -= sizeof(long_ad);
  358. }
  359. else
  360. offset = 0;
  361. if (!(fibh->sbh = fibh->ebh = udf_tread(dir->i_sb, block)))
  362. {
  363. udf_release_data(bh);
  364. *err = -EIO;
  365. return NULL;
  366. }
  367. block = UDF_I_LOCATION(dir).logicalBlockNum;
  368. while ( (f_pos < size) )
  369. {
  370. fi = udf_fileident_read(dir, &f_pos, fibh, cfi, &bloc, &extoffset, &eloc, &elen, &offset, &bh);
  371. if (!fi)
  372. {
  373. if (fibh->sbh != fibh->ebh)
  374. udf_release_data(fibh->ebh);
  375. udf_release_data(fibh->sbh);
  376. udf_release_data(bh);
  377. *err = -EIO;
  378. return NULL;
  379. }
  380. liu = le16_to_cpu(cfi->lengthOfImpUse);
  381. lfi = cfi->lengthFileIdent;
  382. if (fibh->sbh == fibh->ebh)
  383. nameptr = fi->fileIdent + liu;
  384. else
  385. {
  386. int poffset; /* Unpaded ending offset */
  387. poffset = fibh->soffset + sizeof(struct fileIdentDesc) + liu + lfi;
  388. if (poffset >= lfi)
  389. nameptr = (char *)(fibh->ebh->b_data + poffset - lfi);
  390. else
  391. {
  392. nameptr = fname;
  393. memcpy(nameptr, fi->fileIdent + liu, lfi - poffset);
  394. memcpy(nameptr + lfi - poffset, fibh->ebh->b_data, poffset);
  395. }
  396. }
  397. if ( (cfi->fileCharacteristics & FID_FILE_CHAR_DELETED) != 0 )
  398. {
  399. if (((sizeof(struct fileIdentDesc) + liu + lfi + 3) & ~3) == nfidlen)
  400. {
  401. udf_release_data(bh);
  402. cfi->descTag.tagSerialNum = cpu_to_le16(1);
  403. cfi->fileVersionNum = cpu_to_le16(1);
  404. cfi->fileCharacteristics = 0;
  405. cfi->lengthFileIdent = namelen;
  406. cfi->lengthOfImpUse = cpu_to_le16(0);
  407. if (!udf_write_fi(dir, cfi, fi, fibh, NULL, name))
  408. return fi;
  409. else
  410. {
  411. *err = -EIO;
  412. return NULL;
  413. }
  414. }
  415. }
  416. if (!lfi || !dentry)
  417. continue;
  418. if ((flen = udf_get_filename(dir->i_sb, nameptr, fname, lfi)) &&
  419. udf_match(flen, fname, &(dentry->d_name)))
  420. {
  421. if (fibh->sbh != fibh->ebh)
  422. udf_release_data(fibh->ebh);
  423. udf_release_data(fibh->sbh);
  424. udf_release_data(bh);
  425. *err = -EEXIST;
  426. return NULL;
  427. }
  428. }
  429. }
  430. else
  431. {
  432. block = udf_get_lb_pblock(dir->i_sb, UDF_I_LOCATION(dir), 0);
  433. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB)
  434. {
  435. fibh->sbh = fibh->ebh = udf_tread(dir->i_sb, block);
  436. fibh->soffset = fibh->eoffset = udf_file_entry_alloc_offset(dir);
  437. }
  438. else
  439. {
  440. fibh->sbh = fibh->ebh = NULL;
  441. fibh->soffset = fibh->eoffset = sb->s_blocksize;
  442. }
  443. }
  444. f_pos += nfidlen;
  445. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB &&
  446. sb->s_blocksize - fibh->eoffset < nfidlen)
  447. {
  448. udf_release_data(bh);
  449. bh = NULL;
  450. fibh->soffset -= udf_ext0_offset(dir);
  451. fibh->eoffset -= udf_ext0_offset(dir);
  452. f_pos -= (udf_ext0_offset(dir) >> 2);
  453. if (fibh->sbh != fibh->ebh)
  454. udf_release_data(fibh->ebh);
  455. udf_release_data(fibh->sbh);
  456. if (!(fibh->sbh = fibh->ebh = udf_expand_dir_adinicb(dir, &block, err)))
  457. return NULL;
  458. bloc = UDF_I_LOCATION(dir);
  459. eloc.logicalBlockNum = block;
  460. eloc.partitionReferenceNum = UDF_I_LOCATION(dir).partitionReferenceNum;
  461. elen = dir->i_sb->s_blocksize;
  462. extoffset = udf_file_entry_alloc_offset(dir);
  463. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_SHORT)
  464. extoffset += sizeof(short_ad);
  465. else if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_LONG)
  466. extoffset += sizeof(long_ad);
  467. }
  468. if (sb->s_blocksize - fibh->eoffset >= nfidlen)
  469. {
  470. fibh->soffset = fibh->eoffset;
  471. fibh->eoffset += nfidlen;
  472. if (fibh->sbh != fibh->ebh)
  473. {
  474. udf_release_data(fibh->sbh);
  475. fibh->sbh = fibh->ebh;
  476. }
  477. if (UDF_I_ALLOCTYPE(dir) != ICBTAG_FLAG_AD_IN_ICB)
  478. block = eloc.logicalBlockNum + ((elen - 1) >>
  479. dir->i_sb->s_blocksize_bits);
  480. else
  481. block = UDF_I_LOCATION(dir).logicalBlockNum;
  482. fi = (struct fileIdentDesc *)(fibh->sbh->b_data + fibh->soffset);
  483. }
  484. else
  485. {
  486. fibh->soffset = fibh->eoffset - sb->s_blocksize;
  487. fibh->eoffset += nfidlen - sb->s_blocksize;
  488. if (fibh->sbh != fibh->ebh)
  489. {
  490. udf_release_data(fibh->sbh);
  491. fibh->sbh = fibh->ebh;
  492. }
  493. block = eloc.logicalBlockNum + ((elen - 1) >>
  494. dir->i_sb->s_blocksize_bits);
  495. if (!(fibh->ebh = udf_bread(dir, f_pos >> (dir->i_sb->s_blocksize_bits - 2), 1, err)))
  496. {
  497. udf_release_data(bh);
  498. udf_release_data(fibh->sbh);
  499. return NULL;
  500. }
  501. if (!(fibh->soffset))
  502. {
  503. if (udf_next_aext(dir, &bloc, &extoffset, &eloc, &elen, &bh, 1) ==
  504. (EXT_RECORDED_ALLOCATED >> 30))
  505. {
  506. block = eloc.logicalBlockNum + ((elen - 1) >>
  507. dir->i_sb->s_blocksize_bits);
  508. }
  509. else
  510. block ++;
  511. udf_release_data(fibh->sbh);
  512. fibh->sbh = fibh->ebh;
  513. fi = (struct fileIdentDesc *)(fibh->sbh->b_data);
  514. }
  515. else
  516. {
  517. fi = (struct fileIdentDesc *)
  518. (fibh->sbh->b_data + sb->s_blocksize + fibh->soffset);
  519. }
  520. }
  521. memset(cfi, 0, sizeof(struct fileIdentDesc));
  522. if (UDF_SB_UDFREV(sb) >= 0x0200)
  523. udf_new_tag((char *)cfi, TAG_IDENT_FID, 3, 1, block, sizeof(tag));
  524. else
  525. udf_new_tag((char *)cfi, TAG_IDENT_FID, 2, 1, block, sizeof(tag));
  526. cfi->fileVersionNum = cpu_to_le16(1);
  527. cfi->lengthFileIdent = namelen;
  528. cfi->lengthOfImpUse = cpu_to_le16(0);
  529. if (!udf_write_fi(dir, cfi, fi, fibh, NULL, name))
  530. {
  531. udf_release_data(bh);
  532. dir->i_size += nfidlen;
  533. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB)
  534. UDF_I_LENALLOC(dir) += nfidlen;
  535. dir->i_version = ++event;
  536. mark_inode_dirty(dir);
  537. return fi;
  538. }
  539. else
  540. {
  541. udf_release_data(bh);
  542. if (fibh->sbh != fibh->ebh)
  543. udf_release_data(fibh->ebh);
  544. udf_release_data(fibh->sbh);
  545. *err = -EIO;
  546. return NULL;
  547. }
  548. }
  549. static int udf_delete_entry(struct inode *inode, struct fileIdentDesc *fi,
  550. struct udf_fileident_bh *fibh, struct fileIdentDesc *cfi)
  551. {
  552. cfi->fileCharacteristics |= FID_FILE_CHAR_DELETED;
  553. if (UDF_QUERY_FLAG(inode->i_sb, UDF_FLAG_STRICT))
  554. memset(&(cfi->icb), 0x00, sizeof(long_ad));
  555. return udf_write_fi(inode, cfi, fi, fibh, NULL, NULL);
  556. }
  557. static int udf_create(struct inode *dir, struct dentry *dentry, int mode)
  558. {
  559. struct udf_fileident_bh fibh;
  560. struct inode *inode;
  561. struct fileIdentDesc cfi, *fi;
  562. int err;
  563. inode = udf_new_inode(dir, mode, &err);
  564. if (!inode)
  565. return err;
  566. if (UDF_I_ALLOCTYPE(inode) == ICBTAG_FLAG_AD_IN_ICB)
  567. inode->i_data.a_ops = &udf_adinicb_aops;
  568. else
  569. inode->i_data.a_ops = &udf_aops;
  570. inode->i_op = &udf_file_inode_operations;
  571. inode->i_fop = &udf_file_operations;
  572. inode->i_mode = mode;
  573. mark_inode_dirty(inode);
  574. if (!(fi = udf_add_entry(dir, dentry, &fibh, &cfi, &err)))
  575. {
  576. inode->i_nlink --;
  577. mark_inode_dirty(inode);
  578. iput(inode);
  579. return err;
  580. }
  581. cfi.icb.extLength = cpu_to_le32(inode->i_sb->s_blocksize);
  582. cfi.icb.extLocation = cpu_to_lelb(UDF_I_LOCATION(inode));
  583. *(uint32_t *)((struct allocDescImpUse *)cfi.icb.impUse)->impUse =
  584. cpu_to_le32(UDF_I_UNIQUE(inode) & 0x00000000FFFFFFFFUL);
  585. udf_write_fi(dir, &cfi, fi, &fibh, NULL, NULL);
  586. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB)
  587. {
  588. mark_inode_dirty(dir);
  589. dir->i_version = ++event;
  590. }
  591. if (fibh.sbh != fibh.ebh)
  592. udf_release_data(fibh.ebh);
  593. udf_release_data(fibh.sbh);
  594. d_instantiate(dentry, inode);
  595. return 0;
  596. }
  597. static int udf_mknod(struct inode * dir, struct dentry * dentry, int mode, int rdev)
  598. {
  599. struct inode * inode;
  600. struct udf_fileident_bh fibh;
  601. int err;
  602. struct fileIdentDesc cfi, *fi;
  603. err = -EIO;
  604. inode = udf_new_inode(dir, mode, &err);
  605. if (!inode)
  606. goto out;
  607. inode->i_uid = current->fsuid;
  608. init_special_inode(inode, mode, rdev);
  609. if (!(fi = udf_add_entry(dir, dentry, &fibh, &cfi, &err)))
  610. {
  611. inode->i_nlink --;
  612. mark_inode_dirty(inode);
  613. iput(inode);
  614. return err;
  615. }
  616. cfi.icb.extLength = cpu_to_le32(inode->i_sb->s_blocksize);
  617. cfi.icb.extLocation = cpu_to_lelb(UDF_I_LOCATION(inode));
  618. *(uint32_t *)((struct allocDescImpUse *)cfi.icb.impUse)->impUse =
  619. cpu_to_le32(UDF_I_UNIQUE(inode) & 0x00000000FFFFFFFFUL);
  620. udf_write_fi(dir, &cfi, fi, &fibh, NULL, NULL);
  621. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB)
  622. {
  623. mark_inode_dirty(dir);
  624. dir->i_version = ++event;
  625. }
  626. mark_inode_dirty(inode);
  627. if (fibh.sbh != fibh.ebh)
  628. udf_release_data(fibh.ebh);
  629. udf_release_data(fibh.sbh);
  630. d_instantiate(dentry, inode);
  631. err = 0;
  632. out:
  633. return err;
  634. }
  635. static int udf_mkdir(struct inode * dir, struct dentry * dentry, int mode)
  636. {
  637. struct inode * inode;
  638. struct udf_fileident_bh fibh;
  639. int err;
  640. struct fileIdentDesc cfi, *fi;
  641. err = -EMLINK;
  642. if (dir->i_nlink >= (256<<sizeof(dir->i_nlink))-1)
  643. goto out;
  644. err = -EIO;
  645. inode = udf_new_inode(dir, S_IFDIR, &err);
  646. if (!inode)
  647. goto out;
  648. inode->i_op = &udf_dir_inode_operations;
  649. inode->i_fop = &udf_dir_operations;
  650. if (!(fi = udf_add_entry(inode, NULL, &fibh, &cfi, &err)))
  651. {
  652. inode->i_nlink--;
  653. mark_inode_dirty(inode);
  654. iput(inode);
  655. goto out;
  656. }
  657. inode->i_nlink = 2;
  658. cfi.icb.extLength = cpu_to_le32(inode->i_sb->s_blocksize);
  659. cfi.icb.extLocation = cpu_to_lelb(UDF_I_LOCATION(dir));
  660. *(uint32_t *)((struct allocDescImpUse *)cfi.icb.impUse)->impUse =
  661. cpu_to_le32(UDF_I_UNIQUE(dir) & 0x00000000FFFFFFFFUL);
  662. cfi.fileCharacteristics = FID_FILE_CHAR_DIRECTORY | FID_FILE_CHAR_PARENT;
  663. udf_write_fi(inode, &cfi, fi, &fibh, NULL, NULL);
  664. udf_release_data(fibh.sbh);
  665. inode->i_mode = S_IFDIR | mode;
  666. if (dir->i_mode & S_ISGID)
  667. inode->i_mode |= S_ISGID;
  668. mark_inode_dirty(inode);
  669. if (!(fi = udf_add_entry(dir, dentry, &fibh, &cfi, &err)))
  670. {
  671. inode->i_nlink = 0;
  672. mark_inode_dirty(inode);
  673. iput(inode);
  674. goto out;
  675. }
  676. cfi.icb.extLength = cpu_to_le32(inode->i_sb->s_blocksize);
  677. cfi.icb.extLocation = cpu_to_lelb(UDF_I_LOCATION(inode));
  678. *(uint32_t *)((struct allocDescImpUse *)cfi.icb.impUse)->impUse =
  679. cpu_to_le32(UDF_I_UNIQUE(inode) & 0x00000000FFFFFFFFUL);
  680. cfi.fileCharacteristics |= FID_FILE_CHAR_DIRECTORY;
  681. udf_write_fi(dir, &cfi, fi, &fibh, NULL, NULL);
  682. dir->i_version = ++event;
  683. dir->i_nlink++;
  684. mark_inode_dirty(dir);
  685. d_instantiate(dentry, inode);
  686. if (fibh.sbh != fibh.ebh)
  687. udf_release_data(fibh.ebh);
  688. udf_release_data(fibh.sbh);
  689. err = 0;
  690. out:
  691. return err;
  692. }
  693. static int empty_dir(struct inode *dir)
  694. {
  695. struct fileIdentDesc *fi, cfi;
  696. struct udf_fileident_bh fibh;
  697. loff_t f_pos;
  698. loff_t size = (udf_ext0_offset(dir) + dir->i_size) >> 2;
  699. int block;
  700. lb_addr bloc, eloc;
  701. uint32_t extoffset, elen, offset;
  702. struct buffer_head *bh = NULL;
  703. f_pos = (udf_ext0_offset(dir) >> 2);
  704. fibh.soffset = fibh.eoffset = (f_pos & ((dir->i_sb->s_blocksize - 1) >> 2)) << 2;
  705. if (inode_bmap(dir, f_pos >> (dir->i_sb->s_blocksize_bits - 2),
  706. &bloc, &extoffset, &eloc, &elen, &offset, &bh) == (EXT_RECORDED_ALLOCATED >> 30))
  707. {
  708. offset >>= dir->i_sb->s_blocksize_bits;
  709. block = udf_get_lb_pblock(dir->i_sb, eloc, offset);
  710. if ((++offset << dir->i_sb->s_blocksize_bits) < elen)
  711. {
  712. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_SHORT)
  713. extoffset -= sizeof(short_ad);
  714. else if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_LONG)
  715. extoffset -= sizeof(long_ad);
  716. }
  717. else
  718. offset = 0;
  719. }
  720. else
  721. {
  722. udf_release_data(bh);
  723. return 0;
  724. }
  725. if (!(fibh.sbh = fibh.ebh = udf_tread(dir->i_sb, block)))
  726. return 0;
  727. while ( (f_pos < size) )
  728. {
  729. fi = udf_fileident_read(dir, &f_pos, &fibh, &cfi, &bloc, &extoffset, &eloc, &elen, &offset, &bh);
  730. if (!fi)
  731. {
  732. if (fibh.sbh != fibh.ebh)
  733. udf_release_data(fibh.ebh);
  734. udf_release_data(fibh.sbh);
  735. udf_release_data(bh);
  736. return 0;
  737. }
  738. if (cfi.lengthFileIdent && (cfi.fileCharacteristics & FID_FILE_CHAR_DELETED) == 0)
  739. {
  740. udf_release_data(bh);
  741. return 0;
  742. }
  743. }
  744. if (fibh.sbh != fibh.ebh)
  745. udf_release_data(fibh.ebh);
  746. udf_release_data(fibh.sbh);
  747. udf_release_data(bh);
  748. return 1;
  749. }
  750. static int udf_rmdir(struct inode * dir, struct dentry * dentry)
  751. {
  752. int retval;
  753. struct inode * inode = dentry->d_inode;
  754. struct udf_fileident_bh fibh;
  755. struct fileIdentDesc *fi, cfi;
  756. retval = -ENOENT;
  757. fi = udf_find_entry(dir, dentry, &fibh, &cfi);
  758. if (!fi)
  759. goto out;
  760. retval = -EIO;
  761. if (udf_get_lb_pblock(dir->i_sb, lelb_to_cpu(cfi.icb.extLocation), 0) != inode->i_ino)
  762. goto end_rmdir;
  763. retval = -ENOTEMPTY;
  764. if (!empty_dir(inode))
  765. goto end_rmdir;
  766. retval = udf_delete_entry(dir, fi, &fibh, &cfi);
  767. dir->i_version = ++event;
  768. if (retval)
  769. goto end_rmdir;
  770. if (inode->i_nlink != 2)
  771. udf_warning(inode->i_sb, "udf_rmdir",
  772. "empty directory has nlink != 2 (%d)",
  773. inode->i_nlink);
  774. inode->i_version = ++event;
  775. inode->i_nlink = 0;
  776. inode->i_size = 0;
  777. mark_inode_dirty(inode);
  778. dir->i_nlink --;
  779. inode->i_ctime = dir->i_ctime = dir->i_mtime = CURRENT_TIME;
  780. UDF_I_UCTIME(inode) = UDF_I_UCTIME(dir) = UDF_I_UMTIME(dir) = CURRENT_UTIME;
  781. mark_inode_dirty(dir);
  782. end_rmdir:
  783. if (fibh.sbh != fibh.ebh)
  784. udf_release_data(fibh.ebh);
  785. udf_release_data(fibh.sbh);
  786. out:
  787. return retval;
  788. }
  789. static int udf_unlink(struct inode * dir, struct dentry * dentry)
  790. {
  791. int retval;
  792. struct inode * inode = dentry->d_inode;
  793. struct udf_fileident_bh fibh;
  794. struct fileIdentDesc *fi;
  795. struct fileIdentDesc cfi;
  796. retval = -ENOENT;
  797. fi = udf_find_entry(dir, dentry, &fibh, &cfi);
  798. if (!fi)
  799. goto out;
  800. retval = -EIO;
  801. if (udf_get_lb_pblock(dir->i_sb, lelb_to_cpu(cfi.icb.extLocation), 0) !=
  802. inode->i_ino)
  803. {
  804. goto end_unlink;
  805. }
  806. if (!inode->i_nlink)
  807. {
  808. udf_debug("Deleting nonexistent file (%lu), %dn",
  809. inode->i_ino, inode->i_nlink);
  810. inode->i_nlink = 1;
  811. }
  812. retval = udf_delete_entry(dir, fi, &fibh, &cfi);
  813. if (retval)
  814. goto end_unlink;
  815. dir->i_ctime = dir->i_mtime = CURRENT_TIME;
  816. UDF_I_UCTIME(dir) = UDF_I_UMTIME(dir) = CURRENT_UTIME;
  817. mark_inode_dirty(dir);
  818. inode->i_nlink--;
  819. mark_inode_dirty(inode);
  820. inode->i_ctime = dir->i_ctime;
  821. retval = 0;
  822. end_unlink:
  823. if (fibh.sbh != fibh.ebh)
  824. udf_release_data(fibh.ebh);
  825. udf_release_data(fibh.sbh);
  826. out:
  827. return retval;
  828. }
  829. static int udf_symlink(struct inode * dir, struct dentry * dentry, const char * symname)
  830. {
  831. struct inode * inode;
  832. struct pathComponent *pc;
  833. char *compstart;
  834. struct udf_fileident_bh fibh;
  835. struct buffer_head *bh = NULL;
  836. int eoffset, elen = 0;
  837. struct fileIdentDesc *fi;
  838. struct fileIdentDesc cfi;
  839. char *ea;
  840. int err;
  841. int block;
  842. if (!(inode = udf_new_inode(dir, S_IFLNK, &err)))
  843. goto out;
  844. inode->i_mode = S_IFLNK | S_IRWXUGO;
  845. inode->i_data.a_ops = &udf_symlink_aops;
  846. inode->i_op = &page_symlink_inode_operations;
  847. if (UDF_I_ALLOCTYPE(inode) != ICBTAG_FLAG_AD_IN_ICB)
  848. {
  849. struct buffer_head *bh = NULL;
  850. lb_addr bloc, eloc;
  851. uint32_t elen, extoffset;
  852. block = udf_new_block(inode->i_sb, inode,
  853. UDF_I_LOCATION(inode).partitionReferenceNum,
  854. UDF_I_LOCATION(inode).logicalBlockNum, &err);
  855. if (!block)
  856. goto out_no_entry;
  857. bloc = UDF_I_LOCATION(inode);
  858. eloc.logicalBlockNum = block;
  859. eloc.partitionReferenceNum = UDF_I_LOCATION(inode).partitionReferenceNum;
  860. elen = inode->i_sb->s_blocksize;
  861. UDF_I_LENEXTENTS(inode) = elen;
  862. extoffset = udf_file_entry_alloc_offset(inode);
  863. udf_add_aext(inode, &bloc, &extoffset, eloc, elen, &bh, 0);
  864. udf_release_data(bh);
  865. block = udf_get_pblock(inode->i_sb, block,
  866. UDF_I_LOCATION(inode).partitionReferenceNum, 0);
  867. bh = udf_tread(inode->i_sb, block);
  868. lock_buffer(bh);
  869. memset(bh->b_data, 0x00, inode->i_sb->s_blocksize);
  870. mark_buffer_uptodate(bh, 1);
  871. unlock_buffer(bh);
  872. mark_buffer_dirty_inode(bh, inode);
  873. }
  874. else
  875. {
  876. block = udf_get_lb_pblock(inode->i_sb, UDF_I_LOCATION(inode), 0);
  877. bh = udf_tread(inode->i_sb, block);
  878. }
  879. ea = bh->b_data + udf_ext0_offset(inode);
  880. eoffset = inode->i_sb->s_blocksize - udf_ext0_offset(inode);
  881. pc = (struct pathComponent *)ea;
  882. if (*symname == '/')
  883. {
  884. do
  885. {
  886. symname++;
  887. } while (*symname == '/');
  888. pc->componentType = 1;
  889. pc->lengthComponentIdent = 0;
  890. pc->componentFileVersionNum = 0;
  891. pc += sizeof(struct pathComponent);
  892. elen += sizeof(struct pathComponent);
  893. }
  894. err = -ENAMETOOLONG;
  895. while (*symname)
  896. {
  897. if (elen + sizeof(struct pathComponent) > eoffset)
  898. goto out_no_entry;
  899. pc = (struct pathComponent *)(ea + elen);
  900. compstart = (char *)symname;
  901. do
  902. {
  903. symname++;
  904. } while (*symname && *symname != '/');
  905. pc->componentType = 5;
  906. pc->lengthComponentIdent = 0;
  907. pc->componentFileVersionNum = 0;
  908. if (pc->componentIdent[0] == '.')
  909. {
  910. if (pc->lengthComponentIdent == 1)
  911. pc->componentType = 4;
  912. else if (pc->lengthComponentIdent == 2 && pc->componentIdent[1] == '.')
  913. pc->componentType = 3;
  914. }
  915. if (pc->componentType == 5)
  916. {
  917. if (elen + sizeof(struct pathComponent) + symname - compstart > eoffset)
  918. goto out_no_entry;
  919. else
  920. pc->lengthComponentIdent = symname - compstart;
  921. memcpy(pc->componentIdent, compstart, pc->lengthComponentIdent);
  922. }
  923. elen += sizeof(struct pathComponent) + pc->lengthComponentIdent;
  924. if (*symname)
  925. {
  926. do
  927. {
  928. symname++;
  929. } while (*symname == '/');
  930. }
  931. }
  932. udf_release_data(bh);
  933. inode->i_size = elen;
  934. if (UDF_I_ALLOCTYPE(inode) == ICBTAG_FLAG_AD_IN_ICB)
  935. UDF_I_LENALLOC(inode) = inode->i_size;
  936. mark_inode_dirty(inode);
  937. if (!(fi = udf_add_entry(dir, dentry, &fibh, &cfi, &err)))
  938. goto out_no_entry;
  939. cfi.icb.extLength = cpu_to_le32(inode->i_sb->s_blocksize);
  940. cfi.icb.extLocation = cpu_to_lelb(UDF_I_LOCATION(inode));
  941. if (UDF_SB_LVIDBH(inode->i_sb))
  942. {
  943. struct logicalVolHeaderDesc *lvhd;
  944. uint64_t uniqueID;
  945. lvhd = (struct logicalVolHeaderDesc *)(UDF_SB_LVID(inode->i_sb)->logicalVolContentsUse);
  946. uniqueID = le64_to_cpu(lvhd->uniqueID);
  947. *(uint32_t *)((struct allocDescImpUse *)cfi.icb.impUse)->impUse =
  948. cpu_to_le32(uniqueID & 0x00000000FFFFFFFFUL);
  949. if (!(++uniqueID & 0x00000000FFFFFFFFUL))
  950. uniqueID += 16;
  951. lvhd->uniqueID = cpu_to_le64(uniqueID);
  952. mark_buffer_dirty(UDF_SB_LVIDBH(inode->i_sb));
  953. }
  954. udf_write_fi(dir, &cfi, fi, &fibh, NULL, NULL);
  955. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB)
  956. {
  957. mark_inode_dirty(dir);
  958. dir->i_version = ++event;
  959. }
  960. if (fibh.sbh != fibh.ebh)
  961. udf_release_data(fibh.ebh);
  962. udf_release_data(fibh.sbh);
  963. d_instantiate(dentry, inode);
  964. err = 0;
  965. out:
  966. return err;
  967. out_no_entry:
  968. inode->i_nlink--;
  969. mark_inode_dirty(inode);
  970. iput(inode);
  971. goto out;
  972. }
  973. static int udf_link(struct dentry * old_dentry, struct inode * dir,
  974.  struct dentry *dentry)
  975. {
  976. struct inode *inode = old_dentry->d_inode;
  977. struct udf_fileident_bh fibh;
  978. int err;
  979. struct fileIdentDesc cfi, *fi;
  980. if (S_ISDIR(inode->i_mode))
  981. return -EPERM;
  982. if (inode->i_nlink >= (256<<sizeof(inode->i_nlink))-1)
  983. return -EMLINK;
  984. if (!(fi = udf_add_entry(dir, dentry, &fibh, &cfi, &err)))
  985. return err;
  986. cfi.icb.extLength = cpu_to_le32(inode->i_sb->s_blocksize);
  987. cfi.icb.extLocation = cpu_to_lelb(UDF_I_LOCATION(inode));
  988. if (UDF_SB_LVIDBH(inode->i_sb))
  989. {
  990. struct logicalVolHeaderDesc *lvhd;
  991. uint64_t uniqueID;
  992. lvhd = (struct logicalVolHeaderDesc *)(UDF_SB_LVID(inode->i_sb)->logicalVolContentsUse);
  993. uniqueID = le64_to_cpu(lvhd->uniqueID);
  994. *(uint32_t *)((struct allocDescImpUse *)cfi.icb.impUse)->impUse =
  995. cpu_to_le32(uniqueID & 0x00000000FFFFFFFFUL);
  996. if (!(++uniqueID & 0x00000000FFFFFFFFUL))
  997. uniqueID += 16;
  998. lvhd->uniqueID = cpu_to_le64(uniqueID);
  999. mark_buffer_dirty(UDF_SB_LVIDBH(inode->i_sb));
  1000. }
  1001. udf_write_fi(dir, &cfi, fi, &fibh, NULL, NULL);
  1002. if (UDF_I_ALLOCTYPE(dir) == ICBTAG_FLAG_AD_IN_ICB)
  1003. {
  1004. mark_inode_dirty(dir);
  1005. dir->i_version = ++event;
  1006. }
  1007. if (fibh.sbh != fibh.ebh)
  1008. udf_release_data(fibh.ebh);
  1009. udf_release_data(fibh.sbh);
  1010. inode->i_nlink ++;
  1011. inode->i_ctime = CURRENT_TIME;
  1012. UDF_I_UCTIME(inode) = CURRENT_UTIME;
  1013. mark_inode_dirty(inode);
  1014. atomic_inc(&inode->i_count);
  1015. d_instantiate(dentry, inode);
  1016. return 0;
  1017. }
  1018. /* Anybody can rename anything with this: the permission checks are left to the
  1019.  * higher-level routines.
  1020.  */
  1021. static int udf_rename (struct inode * old_dir, struct dentry * old_dentry,
  1022. struct inode * new_dir, struct dentry * new_dentry)
  1023. {
  1024. struct inode * old_inode = old_dentry->d_inode;
  1025. struct inode * new_inode = new_dentry->d_inode;
  1026. struct udf_fileident_bh ofibh, nfibh;
  1027. struct fileIdentDesc *ofi = NULL, *nfi = NULL, *dir_fi = NULL, ocfi, ncfi;
  1028. struct buffer_head *dir_bh = NULL;
  1029. int retval = -ENOENT;
  1030. if ((ofi = udf_find_entry(old_dir, old_dentry, &ofibh, &ocfi)))
  1031. {
  1032. if (ofibh.sbh != ofibh.ebh)
  1033. udf_release_data(ofibh.ebh);
  1034. udf_release_data(ofibh.sbh);
  1035. }
  1036. if (!ofi || udf_get_lb_pblock(old_dir->i_sb, lelb_to_cpu(ocfi.icb.extLocation), 0) !=
  1037. old_inode->i_ino)
  1038. {
  1039. goto end_rename;
  1040. }
  1041. nfi = udf_find_entry(new_dir, new_dentry, &nfibh, &ncfi);
  1042. if (nfi)
  1043. {
  1044. if (!new_inode)
  1045. {
  1046. if (nfibh.sbh != nfibh.ebh)
  1047. udf_release_data(nfibh.ebh);
  1048. udf_release_data(nfibh.sbh);
  1049. nfi = NULL;
  1050. }
  1051. }
  1052. if (S_ISDIR(old_inode->i_mode))
  1053. {
  1054. uint32_t offset = udf_ext0_offset(old_inode);
  1055. if (new_inode)
  1056. {
  1057. retval = -ENOTEMPTY;
  1058. if (!empty_dir(new_inode))
  1059. goto end_rename;
  1060. }
  1061. retval = -EIO;
  1062. dir_bh = udf_bread(old_inode, 0, 0, &retval);
  1063. if (!dir_bh)
  1064. goto end_rename;
  1065. dir_fi = udf_get_fileident(dir_bh->b_data, old_inode->i_sb->s_blocksize, &offset);
  1066. if (!dir_fi)
  1067. goto end_rename;
  1068. if (udf_get_lb_pblock(old_inode->i_sb, cpu_to_lelb(dir_fi->icb.extLocation), 0) !=
  1069. old_dir->i_ino)
  1070. {
  1071. goto end_rename;
  1072. }
  1073. retval = -EMLINK;
  1074. if (!new_inode && new_dir->i_nlink >= (256<<sizeof(new_dir->i_nlink))-1)
  1075. goto end_rename;
  1076. }
  1077. if (!nfi)
  1078. {
  1079. nfi = udf_add_entry(new_dir, new_dentry, &nfibh, &ncfi, &retval);
  1080. if (!nfi)
  1081. goto end_rename;
  1082. }
  1083. new_dir->i_version = ++event;
  1084. /*
  1085.  * Like most other Unix systems, set the ctime for inodes on a
  1086.  * rename.
  1087.  */
  1088. old_inode->i_ctime = CURRENT_TIME;
  1089. UDF_I_UCTIME(old_inode) = CURRENT_UTIME;
  1090. mark_inode_dirty(old_inode);
  1091. /*
  1092.  * ok, that's it
  1093.  */
  1094. ncfi.fileVersionNum = ocfi.fileVersionNum;
  1095. ncfi.fileCharacteristics = ocfi.fileCharacteristics;
  1096. memcpy(&(ncfi.icb), &(ocfi.icb), sizeof(long_ad));
  1097. udf_write_fi(new_dir, &ncfi, nfi, &nfibh, NULL, NULL);
  1098. /* The old fid may have moved - find it again */
  1099. ofi = udf_find_entry(old_dir, old_dentry, &ofibh, &ocfi);
  1100. udf_delete_entry(old_dir, ofi, &ofibh, &ocfi);
  1101. old_dir->i_version = ++event;
  1102. if (new_inode)
  1103. {
  1104. new_inode->i_nlink--;
  1105. new_inode->i_ctime = CURRENT_TIME;
  1106. UDF_I_UCTIME(new_inode) = CURRENT_UTIME;
  1107. mark_inode_dirty(new_inode);
  1108. }
  1109. old_dir->i_ctime = old_dir->i_mtime = CURRENT_TIME;
  1110. UDF_I_UCTIME(old_dir) = UDF_I_UMTIME(old_dir) = CURRENT_UTIME;
  1111. mark_inode_dirty(old_dir);
  1112. if (dir_bh)
  1113. {
  1114. dir_fi->icb.extLocation = lelb_to_cpu(UDF_I_LOCATION(new_dir));
  1115. udf_update_tag((char *)dir_fi, (sizeof(struct fileIdentDesc) +
  1116. cpu_to_le16(dir_fi->lengthOfImpUse) + 3) & ~3);
  1117. if (UDF_I_ALLOCTYPE(old_inode) == ICBTAG_FLAG_AD_IN_ICB)
  1118. {
  1119. old_inode->i_version = ++event;
  1120. mark_inode_dirty(old_inode);
  1121. }
  1122. else
  1123. mark_buffer_dirty_inode(dir_bh, old_inode);
  1124. old_dir->i_nlink --;
  1125. mark_inode_dirty(old_dir);
  1126. if (new_inode)
  1127. {
  1128. new_inode->i_nlink --;
  1129. mark_inode_dirty(new_inode);
  1130. }
  1131. else
  1132. {
  1133. new_dir->i_nlink ++;
  1134. mark_inode_dirty(new_dir);
  1135. }
  1136. }
  1137. if (ofi)
  1138. {
  1139. if (ofibh.sbh != ofibh.ebh)
  1140. udf_release_data(ofibh.ebh);
  1141. udf_release_data(ofibh.sbh);
  1142. }
  1143. retval = 0;
  1144. end_rename:
  1145. udf_release_data(dir_bh);
  1146. if (nfi)
  1147. {
  1148. if (nfibh.sbh != nfibh.ebh)
  1149. udf_release_data(nfibh.ebh);
  1150. udf_release_data(nfibh.sbh);
  1151. }
  1152. return retval;
  1153. }
  1154. struct inode_operations udf_dir_inode_operations = {
  1155. lookup: udf_lookup,
  1156. create: udf_create,
  1157. link: udf_link,
  1158. unlink: udf_unlink,
  1159. symlink: udf_symlink,
  1160. mkdir: udf_mkdir,
  1161. rmdir: udf_rmdir,
  1162. mknod: udf_mknod,
  1163. rename: udf_rename,
  1164. };