/fs/jfs/jfs_xtree.c

https://bitbucket.org/cyanogenmod/android_kernel_asus_tf300t · C · 3905 lines · 2020 code · 510 blank · 1375 comment · 374 complexity · 4c5575c4be9470acfa2d51e22e5d234c MD5 · raw file

Large files are truncated click here to view the full file

  1. /*
  2. * Copyright (C) International Business Machines Corp., 2000-2005
  3. *
  4. * This program is free software; you can redistribute it and/or modify
  5. * it under the terms of the GNU General Public License as published by
  6. * the Free Software Foundation; either version 2 of the License, or
  7. * (at your option) any later version.
  8. *
  9. * This program is distributed in the hope that it will be useful,
  10. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
  12. * the GNU General Public License for more details.
  13. *
  14. * You should have received a copy of the GNU General Public License
  15. * along with this program; if not, write to the Free Software
  16. * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  17. */
  18. /*
  19. * jfs_xtree.c: extent allocation descriptor B+-tree manager
  20. */
  21. #include <linux/fs.h>
  22. #include <linux/module.h>
  23. #include <linux/quotaops.h>
  24. #include <linux/seq_file.h>
  25. #include "jfs_incore.h"
  26. #include "jfs_filsys.h"
  27. #include "jfs_metapage.h"
  28. #include "jfs_dmap.h"
  29. #include "jfs_dinode.h"
  30. #include "jfs_superblock.h"
  31. #include "jfs_debug.h"
  32. /*
  33. * xtree local flag
  34. */
  35. #define XT_INSERT 0x00000001
  36. /*
  37. * xtree key/entry comparison: extent offset
  38. *
  39. * return:
  40. * -1: k < start of extent
  41. * 0: start_of_extent <= k <= end_of_extent
  42. * 1: k > end_of_extent
  43. */
  44. #define XT_CMP(CMP, K, X, OFFSET64)\
  45. {\
  46. OFFSET64 = offsetXAD(X);\
  47. (CMP) = ((K) >= OFFSET64 + lengthXAD(X)) ? 1 :\
  48. ((K) < OFFSET64) ? -1 : 0;\
  49. }
  50. /* write a xad entry */
  51. #define XT_PUTENTRY(XAD, FLAG, OFF, LEN, ADDR)\
  52. {\
  53. (XAD)->flag = (FLAG);\
  54. XADoffset((XAD), (OFF));\
  55. XADlength((XAD), (LEN));\
  56. XADaddress((XAD), (ADDR));\
  57. }
  58. #define XT_PAGE(IP, MP) BT_PAGE(IP, MP, xtpage_t, i_xtroot)
  59. /* get page buffer for specified block address */
  60. /* ToDo: Replace this ugly macro with a function */
  61. #define XT_GETPAGE(IP, BN, MP, SIZE, P, RC)\
  62. {\
  63. BT_GETPAGE(IP, BN, MP, xtpage_t, SIZE, P, RC, i_xtroot)\
  64. if (!(RC))\
  65. {\
  66. if ((le16_to_cpu((P)->header.nextindex) < XTENTRYSTART) ||\
  67. (le16_to_cpu((P)->header.nextindex) > le16_to_cpu((P)->header.maxentry)) ||\
  68. (le16_to_cpu((P)->header.maxentry) > (((BN)==0)?XTROOTMAXSLOT:PSIZE>>L2XTSLOTSIZE)))\
  69. {\
  70. jfs_error((IP)->i_sb, "XT_GETPAGE: xtree page corrupt");\
  71. BT_PUTPAGE(MP);\
  72. MP = NULL;\
  73. RC = -EIO;\
  74. }\
  75. }\
  76. }
  77. /* for consistency */
  78. #define XT_PUTPAGE(MP) BT_PUTPAGE(MP)
  79. #define XT_GETSEARCH(IP, LEAF, BN, MP, P, INDEX) \
  80. BT_GETSEARCH(IP, LEAF, BN, MP, xtpage_t, P, INDEX, i_xtroot)
  81. /* xtree entry parameter descriptor */
  82. struct xtsplit {
  83. struct metapage *mp;
  84. s16 index;
  85. u8 flag;
  86. s64 off;
  87. s64 addr;
  88. int len;
  89. struct pxdlist *pxdlist;
  90. };
  91. /*
  92. * statistics
  93. */
  94. #ifdef CONFIG_JFS_STATISTICS
  95. static struct {
  96. uint search;
  97. uint fastSearch;
  98. uint split;
  99. } xtStat;
  100. #endif
  101. /*
  102. * forward references
  103. */
  104. static int xtSearch(struct inode *ip, s64 xoff, s64 *next, int *cmpp,
  105. struct btstack * btstack, int flag);
  106. static int xtSplitUp(tid_t tid,
  107. struct inode *ip,
  108. struct xtsplit * split, struct btstack * btstack);
  109. static int xtSplitPage(tid_t tid, struct inode *ip, struct xtsplit * split,
  110. struct metapage ** rmpp, s64 * rbnp);
  111. static int xtSplitRoot(tid_t tid, struct inode *ip,
  112. struct xtsplit * split, struct metapage ** rmpp);
  113. #ifdef _STILL_TO_PORT
  114. static int xtDeleteUp(tid_t tid, struct inode *ip, struct metapage * fmp,
  115. xtpage_t * fp, struct btstack * btstack);
  116. static int xtSearchNode(struct inode *ip,
  117. xad_t * xad,
  118. int *cmpp, struct btstack * btstack, int flag);
  119. static int xtRelink(tid_t tid, struct inode *ip, xtpage_t * fp);
  120. #endif /* _STILL_TO_PORT */
  121. /*
  122. * xtLookup()
  123. *
  124. * function: map a single page into a physical extent;
  125. */
  126. int xtLookup(struct inode *ip, s64 lstart,
  127. s64 llen, int *pflag, s64 * paddr, s32 * plen, int no_check)
  128. {
  129. int rc = 0;
  130. struct btstack btstack;
  131. int cmp;
  132. s64 bn;
  133. struct metapage *mp;
  134. xtpage_t *p;
  135. int index;
  136. xad_t *xad;
  137. s64 next, size, xoff, xend;
  138. int xlen;
  139. s64 xaddr;
  140. *paddr = 0;
  141. *plen = llen;
  142. if (!no_check) {
  143. /* is lookup offset beyond eof ? */
  144. size = ((u64) ip->i_size + (JFS_SBI(ip->i_sb)->bsize - 1)) >>
  145. JFS_SBI(ip->i_sb)->l2bsize;
  146. if (lstart >= size)
  147. return 0;
  148. }
  149. /*
  150. * search for the xad entry covering the logical extent
  151. */
  152. //search:
  153. if ((rc = xtSearch(ip, lstart, &next, &cmp, &btstack, 0))) {
  154. jfs_err("xtLookup: xtSearch returned %d", rc);
  155. return rc;
  156. }
  157. /*
  158. * compute the physical extent covering logical extent
  159. *
  160. * N.B. search may have failed (e.g., hole in sparse file),
  161. * and returned the index of the next entry.
  162. */
  163. /* retrieve search result */
  164. XT_GETSEARCH(ip, btstack.top, bn, mp, p, index);
  165. /* is xad found covering start of logical extent ?
  166. * lstart is a page start address,
  167. * i.e., lstart cannot start in a hole;
  168. */
  169. if (cmp) {
  170. if (next)
  171. *plen = min(next - lstart, llen);
  172. goto out;
  173. }
  174. /*
  175. * lxd covered by xad
  176. */
  177. xad = &p->xad[index];
  178. xoff = offsetXAD(xad);
  179. xlen = lengthXAD(xad);
  180. xend = xoff + xlen;
  181. xaddr = addressXAD(xad);
  182. /* initialize new pxd */
  183. *pflag = xad->flag;
  184. *paddr = xaddr + (lstart - xoff);
  185. /* a page must be fully covered by an xad */
  186. *plen = min(xend - lstart, llen);
  187. out:
  188. XT_PUTPAGE(mp);
  189. return rc;
  190. }
  191. /*
  192. * xtSearch()
  193. *
  194. * function: search for the xad entry covering specified offset.
  195. *
  196. * parameters:
  197. * ip - file object;
  198. * xoff - extent offset;
  199. * nextp - address of next extent (if any) for search miss
  200. * cmpp - comparison result:
  201. * btstack - traverse stack;
  202. * flag - search process flag (XT_INSERT);
  203. *
  204. * returns:
  205. * btstack contains (bn, index) of search path traversed to the entry.
  206. * *cmpp is set to result of comparison with the entry returned.
  207. * the page containing the entry is pinned at exit.
  208. */
  209. static int xtSearch(struct inode *ip, s64 xoff, s64 *nextp,
  210. int *cmpp, struct btstack * btstack, int flag)
  211. {
  212. struct jfs_inode_info *jfs_ip = JFS_IP(ip);
  213. int rc = 0;
  214. int cmp = 1; /* init for empty page */
  215. s64 bn; /* block number */
  216. struct metapage *mp; /* page buffer */
  217. xtpage_t *p; /* page */
  218. xad_t *xad;
  219. int base, index, lim, btindex;
  220. struct btframe *btsp;
  221. int nsplit = 0; /* number of pages to split */
  222. s64 t64;
  223. s64 next = 0;
  224. INCREMENT(xtStat.search);
  225. BT_CLR(btstack);
  226. btstack->nsplit = 0;
  227. /*
  228. * search down tree from root:
  229. *
  230. * between two consecutive entries of <Ki, Pi> and <Kj, Pj> of
  231. * internal page, child page Pi contains entry with k, Ki <= K < Kj.
  232. *
  233. * if entry with search key K is not found
  234. * internal page search find the entry with largest key Ki
  235. * less than K which point to the child page to search;
  236. * leaf page search find the entry with smallest key Kj
  237. * greater than K so that the returned index is the position of
  238. * the entry to be shifted right for insertion of new entry.
  239. * for empty tree, search key is greater than any key of the tree.
  240. *
  241. * by convention, root bn = 0.
  242. */
  243. for (bn = 0;;) {
  244. /* get/pin the page to search */
  245. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  246. if (rc)
  247. return rc;
  248. /* try sequential access heuristics with the previous
  249. * access entry in target leaf page:
  250. * once search narrowed down into the target leaf,
  251. * key must either match an entry in the leaf or
  252. * key entry does not exist in the tree;
  253. */
  254. //fastSearch:
  255. if ((jfs_ip->btorder & BT_SEQUENTIAL) &&
  256. (p->header.flag & BT_LEAF) &&
  257. (index = jfs_ip->btindex) <
  258. le16_to_cpu(p->header.nextindex)) {
  259. xad = &p->xad[index];
  260. t64 = offsetXAD(xad);
  261. if (xoff < t64 + lengthXAD(xad)) {
  262. if (xoff >= t64) {
  263. *cmpp = 0;
  264. goto out;
  265. }
  266. /* stop sequential access heuristics */
  267. goto binarySearch;
  268. } else { /* (t64 + lengthXAD(xad)) <= xoff */
  269. /* try next sequential entry */
  270. index++;
  271. if (index <
  272. le16_to_cpu(p->header.nextindex)) {
  273. xad++;
  274. t64 = offsetXAD(xad);
  275. if (xoff < t64 + lengthXAD(xad)) {
  276. if (xoff >= t64) {
  277. *cmpp = 0;
  278. goto out;
  279. }
  280. /* miss: key falls between
  281. * previous and this entry
  282. */
  283. *cmpp = 1;
  284. next = t64;
  285. goto out;
  286. }
  287. /* (xoff >= t64 + lengthXAD(xad));
  288. * matching entry may be further out:
  289. * stop heuristic search
  290. */
  291. /* stop sequential access heuristics */
  292. goto binarySearch;
  293. }
  294. /* (index == p->header.nextindex);
  295. * miss: key entry does not exist in
  296. * the target leaf/tree
  297. */
  298. *cmpp = 1;
  299. goto out;
  300. }
  301. /*
  302. * if hit, return index of the entry found, and
  303. * if miss, where new entry with search key is
  304. * to be inserted;
  305. */
  306. out:
  307. /* compute number of pages to split */
  308. if (flag & XT_INSERT) {
  309. if (p->header.nextindex == /* little-endian */
  310. p->header.maxentry)
  311. nsplit++;
  312. else
  313. nsplit = 0;
  314. btstack->nsplit = nsplit;
  315. }
  316. /* save search result */
  317. btsp = btstack->top;
  318. btsp->bn = bn;
  319. btsp->index = index;
  320. btsp->mp = mp;
  321. /* update sequential access heuristics */
  322. jfs_ip->btindex = index;
  323. if (nextp)
  324. *nextp = next;
  325. INCREMENT(xtStat.fastSearch);
  326. return 0;
  327. }
  328. /* well, ... full search now */
  329. binarySearch:
  330. lim = le16_to_cpu(p->header.nextindex) - XTENTRYSTART;
  331. /*
  332. * binary search with search key K on the current page
  333. */
  334. for (base = XTENTRYSTART; lim; lim >>= 1) {
  335. index = base + (lim >> 1);
  336. XT_CMP(cmp, xoff, &p->xad[index], t64);
  337. if (cmp == 0) {
  338. /*
  339. * search hit
  340. */
  341. /* search hit - leaf page:
  342. * return the entry found
  343. */
  344. if (p->header.flag & BT_LEAF) {
  345. *cmpp = cmp;
  346. /* compute number of pages to split */
  347. if (flag & XT_INSERT) {
  348. if (p->header.nextindex ==
  349. p->header.maxentry)
  350. nsplit++;
  351. else
  352. nsplit = 0;
  353. btstack->nsplit = nsplit;
  354. }
  355. /* save search result */
  356. btsp = btstack->top;
  357. btsp->bn = bn;
  358. btsp->index = index;
  359. btsp->mp = mp;
  360. /* init sequential access heuristics */
  361. btindex = jfs_ip->btindex;
  362. if (index == btindex ||
  363. index == btindex + 1)
  364. jfs_ip->btorder = BT_SEQUENTIAL;
  365. else
  366. jfs_ip->btorder = BT_RANDOM;
  367. jfs_ip->btindex = index;
  368. return 0;
  369. }
  370. /* search hit - internal page:
  371. * descend/search its child page
  372. */
  373. if (index < le16_to_cpu(p->header.nextindex)-1)
  374. next = offsetXAD(&p->xad[index + 1]);
  375. goto next;
  376. }
  377. if (cmp > 0) {
  378. base = index + 1;
  379. --lim;
  380. }
  381. }
  382. /*
  383. * search miss
  384. *
  385. * base is the smallest index with key (Kj) greater than
  386. * search key (K) and may be zero or maxentry index.
  387. */
  388. if (base < le16_to_cpu(p->header.nextindex))
  389. next = offsetXAD(&p->xad[base]);
  390. /*
  391. * search miss - leaf page:
  392. *
  393. * return location of entry (base) where new entry with
  394. * search key K is to be inserted.
  395. */
  396. if (p->header.flag & BT_LEAF) {
  397. *cmpp = cmp;
  398. /* compute number of pages to split */
  399. if (flag & XT_INSERT) {
  400. if (p->header.nextindex ==
  401. p->header.maxentry)
  402. nsplit++;
  403. else
  404. nsplit = 0;
  405. btstack->nsplit = nsplit;
  406. }
  407. /* save search result */
  408. btsp = btstack->top;
  409. btsp->bn = bn;
  410. btsp->index = base;
  411. btsp->mp = mp;
  412. /* init sequential access heuristics */
  413. btindex = jfs_ip->btindex;
  414. if (base == btindex || base == btindex + 1)
  415. jfs_ip->btorder = BT_SEQUENTIAL;
  416. else
  417. jfs_ip->btorder = BT_RANDOM;
  418. jfs_ip->btindex = base;
  419. if (nextp)
  420. *nextp = next;
  421. return 0;
  422. }
  423. /*
  424. * search miss - non-leaf page:
  425. *
  426. * if base is non-zero, decrement base by one to get the parent
  427. * entry of the child page to search.
  428. */
  429. index = base ? base - 1 : base;
  430. /*
  431. * go down to child page
  432. */
  433. next:
  434. /* update number of pages to split */
  435. if (p->header.nextindex == p->header.maxentry)
  436. nsplit++;
  437. else
  438. nsplit = 0;
  439. /* push (bn, index) of the parent page/entry */
  440. if (BT_STACK_FULL(btstack)) {
  441. jfs_error(ip->i_sb, "stack overrun in xtSearch!");
  442. XT_PUTPAGE(mp);
  443. return -EIO;
  444. }
  445. BT_PUSH(btstack, bn, index);
  446. /* get the child page block number */
  447. bn = addressXAD(&p->xad[index]);
  448. /* unpin the parent page */
  449. XT_PUTPAGE(mp);
  450. }
  451. }
  452. /*
  453. * xtInsert()
  454. *
  455. * function:
  456. *
  457. * parameter:
  458. * tid - transaction id;
  459. * ip - file object;
  460. * xflag - extent flag (XAD_NOTRECORDED):
  461. * xoff - extent offset;
  462. * xlen - extent length;
  463. * xaddrp - extent address pointer (in/out):
  464. * if (*xaddrp)
  465. * caller allocated data extent at *xaddrp;
  466. * else
  467. * allocate data extent and return its xaddr;
  468. * flag -
  469. *
  470. * return:
  471. */
  472. int xtInsert(tid_t tid, /* transaction id */
  473. struct inode *ip, int xflag, s64 xoff, s32 xlen, s64 * xaddrp,
  474. int flag)
  475. {
  476. int rc = 0;
  477. s64 xaddr, hint;
  478. struct metapage *mp; /* meta-page buffer */
  479. xtpage_t *p; /* base B+-tree index page */
  480. s64 bn;
  481. int index, nextindex;
  482. struct btstack btstack; /* traverse stack */
  483. struct xtsplit split; /* split information */
  484. xad_t *xad;
  485. int cmp;
  486. s64 next;
  487. struct tlock *tlck;
  488. struct xtlock *xtlck;
  489. jfs_info("xtInsert: nxoff:0x%lx nxlen:0x%x", (ulong) xoff, xlen);
  490. /*
  491. * search for the entry location at which to insert:
  492. *
  493. * xtFastSearch() and xtSearch() both returns (leaf page
  494. * pinned, index at which to insert).
  495. * n.b. xtSearch() may return index of maxentry of
  496. * the full page.
  497. */
  498. if ((rc = xtSearch(ip, xoff, &next, &cmp, &btstack, XT_INSERT)))
  499. return rc;
  500. /* retrieve search result */
  501. XT_GETSEARCH(ip, btstack.top, bn, mp, p, index);
  502. /* This test must follow XT_GETSEARCH since mp must be valid if
  503. * we branch to out: */
  504. if ((cmp == 0) || (next && (xlen > next - xoff))) {
  505. rc = -EEXIST;
  506. goto out;
  507. }
  508. /*
  509. * allocate data extent requested
  510. *
  511. * allocation hint: last xad
  512. */
  513. if ((xaddr = *xaddrp) == 0) {
  514. if (index > XTENTRYSTART) {
  515. xad = &p->xad[index - 1];
  516. hint = addressXAD(xad) + lengthXAD(xad) - 1;
  517. } else
  518. hint = 0;
  519. if ((rc = dquot_alloc_block(ip, xlen)))
  520. goto out;
  521. if ((rc = dbAlloc(ip, hint, (s64) xlen, &xaddr))) {
  522. dquot_free_block(ip, xlen);
  523. goto out;
  524. }
  525. }
  526. /*
  527. * insert entry for new extent
  528. */
  529. xflag |= XAD_NEW;
  530. /*
  531. * if the leaf page is full, split the page and
  532. * propagate up the router entry for the new page from split
  533. *
  534. * The xtSplitUp() will insert the entry and unpin the leaf page.
  535. */
  536. nextindex = le16_to_cpu(p->header.nextindex);
  537. if (nextindex == le16_to_cpu(p->header.maxentry)) {
  538. split.mp = mp;
  539. split.index = index;
  540. split.flag = xflag;
  541. split.off = xoff;
  542. split.len = xlen;
  543. split.addr = xaddr;
  544. split.pxdlist = NULL;
  545. if ((rc = xtSplitUp(tid, ip, &split, &btstack))) {
  546. /* undo data extent allocation */
  547. if (*xaddrp == 0) {
  548. dbFree(ip, xaddr, (s64) xlen);
  549. dquot_free_block(ip, xlen);
  550. }
  551. return rc;
  552. }
  553. *xaddrp = xaddr;
  554. return 0;
  555. }
  556. /*
  557. * insert the new entry into the leaf page
  558. */
  559. /*
  560. * acquire a transaction lock on the leaf page;
  561. *
  562. * action: xad insertion/extension;
  563. */
  564. BT_MARK_DIRTY(mp, ip);
  565. /* if insert into middle, shift right remaining entries. */
  566. if (index < nextindex)
  567. memmove(&p->xad[index + 1], &p->xad[index],
  568. (nextindex - index) * sizeof(xad_t));
  569. /* insert the new entry: mark the entry NEW */
  570. xad = &p->xad[index];
  571. XT_PUTENTRY(xad, xflag, xoff, xlen, xaddr);
  572. /* advance next available entry index */
  573. le16_add_cpu(&p->header.nextindex, 1);
  574. /* Don't log it if there are no links to the file */
  575. if (!test_cflag(COMMIT_Nolink, ip)) {
  576. tlck = txLock(tid, ip, mp, tlckXTREE | tlckGROW);
  577. xtlck = (struct xtlock *) & tlck->lock;
  578. xtlck->lwm.offset =
  579. (xtlck->lwm.offset) ? min(index,
  580. (int)xtlck->lwm.offset) : index;
  581. xtlck->lwm.length =
  582. le16_to_cpu(p->header.nextindex) - xtlck->lwm.offset;
  583. }
  584. *xaddrp = xaddr;
  585. out:
  586. /* unpin the leaf page */
  587. XT_PUTPAGE(mp);
  588. return rc;
  589. }
  590. /*
  591. * xtSplitUp()
  592. *
  593. * function:
  594. * split full pages as propagating insertion up the tree
  595. *
  596. * parameter:
  597. * tid - transaction id;
  598. * ip - file object;
  599. * split - entry parameter descriptor;
  600. * btstack - traverse stack from xtSearch()
  601. *
  602. * return:
  603. */
  604. static int
  605. xtSplitUp(tid_t tid,
  606. struct inode *ip, struct xtsplit * split, struct btstack * btstack)
  607. {
  608. int rc = 0;
  609. struct metapage *smp;
  610. xtpage_t *sp; /* split page */
  611. struct metapage *rmp;
  612. s64 rbn; /* new right page block number */
  613. struct metapage *rcmp;
  614. xtpage_t *rcp; /* right child page */
  615. s64 rcbn; /* right child page block number */
  616. int skip; /* index of entry of insertion */
  617. int nextindex; /* next available entry index of p */
  618. struct btframe *parent; /* parent page entry on traverse stack */
  619. xad_t *xad;
  620. s64 xaddr;
  621. int xlen;
  622. int nsplit; /* number of pages split */
  623. struct pxdlist pxdlist;
  624. pxd_t *pxd;
  625. struct tlock *tlck;
  626. struct xtlock *xtlck;
  627. smp = split->mp;
  628. sp = XT_PAGE(ip, smp);
  629. /* is inode xtree root extension/inline EA area free ? */
  630. if ((sp->header.flag & BT_ROOT) && (!S_ISDIR(ip->i_mode)) &&
  631. (le16_to_cpu(sp->header.maxentry) < XTROOTMAXSLOT) &&
  632. (JFS_IP(ip)->mode2 & INLINEEA)) {
  633. sp->header.maxentry = cpu_to_le16(XTROOTMAXSLOT);
  634. JFS_IP(ip)->mode2 &= ~INLINEEA;
  635. BT_MARK_DIRTY(smp, ip);
  636. /*
  637. * acquire a transaction lock on the leaf page;
  638. *
  639. * action: xad insertion/extension;
  640. */
  641. /* if insert into middle, shift right remaining entries. */
  642. skip = split->index;
  643. nextindex = le16_to_cpu(sp->header.nextindex);
  644. if (skip < nextindex)
  645. memmove(&sp->xad[skip + 1], &sp->xad[skip],
  646. (nextindex - skip) * sizeof(xad_t));
  647. /* insert the new entry: mark the entry NEW */
  648. xad = &sp->xad[skip];
  649. XT_PUTENTRY(xad, split->flag, split->off, split->len,
  650. split->addr);
  651. /* advance next available entry index */
  652. le16_add_cpu(&sp->header.nextindex, 1);
  653. /* Don't log it if there are no links to the file */
  654. if (!test_cflag(COMMIT_Nolink, ip)) {
  655. tlck = txLock(tid, ip, smp, tlckXTREE | tlckGROW);
  656. xtlck = (struct xtlock *) & tlck->lock;
  657. xtlck->lwm.offset = (xtlck->lwm.offset) ?
  658. min(skip, (int)xtlck->lwm.offset) : skip;
  659. xtlck->lwm.length =
  660. le16_to_cpu(sp->header.nextindex) -
  661. xtlck->lwm.offset;
  662. }
  663. return 0;
  664. }
  665. /*
  666. * allocate new index blocks to cover index page split(s)
  667. *
  668. * allocation hint: ?
  669. */
  670. if (split->pxdlist == NULL) {
  671. nsplit = btstack->nsplit;
  672. split->pxdlist = &pxdlist;
  673. pxdlist.maxnpxd = pxdlist.npxd = 0;
  674. pxd = &pxdlist.pxd[0];
  675. xlen = JFS_SBI(ip->i_sb)->nbperpage;
  676. for (; nsplit > 0; nsplit--, pxd++) {
  677. if ((rc = dbAlloc(ip, (s64) 0, (s64) xlen, &xaddr))
  678. == 0) {
  679. PXDaddress(pxd, xaddr);
  680. PXDlength(pxd, xlen);
  681. pxdlist.maxnpxd++;
  682. continue;
  683. }
  684. /* undo allocation */
  685. XT_PUTPAGE(smp);
  686. return rc;
  687. }
  688. }
  689. /*
  690. * Split leaf page <sp> into <sp> and a new right page <rp>.
  691. *
  692. * The split routines insert the new entry into the leaf page,
  693. * and acquire txLock as appropriate.
  694. * return <rp> pinned and its block number <rpbn>.
  695. */
  696. rc = (sp->header.flag & BT_ROOT) ?
  697. xtSplitRoot(tid, ip, split, &rmp) :
  698. xtSplitPage(tid, ip, split, &rmp, &rbn);
  699. XT_PUTPAGE(smp);
  700. if (rc)
  701. return -EIO;
  702. /*
  703. * propagate up the router entry for the leaf page just split
  704. *
  705. * insert a router entry for the new page into the parent page,
  706. * propagate the insert/split up the tree by walking back the stack
  707. * of (bn of parent page, index of child page entry in parent page)
  708. * that were traversed during the search for the page that split.
  709. *
  710. * the propagation of insert/split up the tree stops if the root
  711. * splits or the page inserted into doesn't have to split to hold
  712. * the new entry.
  713. *
  714. * the parent entry for the split page remains the same, and
  715. * a new entry is inserted at its right with the first key and
  716. * block number of the new right page.
  717. *
  718. * There are a maximum of 3 pages pinned at any time:
  719. * right child, left parent and right parent (when the parent splits)
  720. * to keep the child page pinned while working on the parent.
  721. * make sure that all pins are released at exit.
  722. */
  723. while ((parent = BT_POP(btstack)) != NULL) {
  724. /* parent page specified by stack frame <parent> */
  725. /* keep current child pages <rcp> pinned */
  726. rcmp = rmp;
  727. rcbn = rbn;
  728. rcp = XT_PAGE(ip, rcmp);
  729. /*
  730. * insert router entry in parent for new right child page <rp>
  731. */
  732. /* get/pin the parent page <sp> */
  733. XT_GETPAGE(ip, parent->bn, smp, PSIZE, sp, rc);
  734. if (rc) {
  735. XT_PUTPAGE(rcmp);
  736. return rc;
  737. }
  738. /*
  739. * The new key entry goes ONE AFTER the index of parent entry,
  740. * because the split was to the right.
  741. */
  742. skip = parent->index + 1;
  743. /*
  744. * split or shift right remaining entries of the parent page
  745. */
  746. nextindex = le16_to_cpu(sp->header.nextindex);
  747. /*
  748. * parent page is full - split the parent page
  749. */
  750. if (nextindex == le16_to_cpu(sp->header.maxentry)) {
  751. /* init for parent page split */
  752. split->mp = smp;
  753. split->index = skip; /* index at insert */
  754. split->flag = XAD_NEW;
  755. split->off = offsetXAD(&rcp->xad[XTENTRYSTART]);
  756. split->len = JFS_SBI(ip->i_sb)->nbperpage;
  757. split->addr = rcbn;
  758. /* unpin previous right child page */
  759. XT_PUTPAGE(rcmp);
  760. /* The split routines insert the new entry,
  761. * and acquire txLock as appropriate.
  762. * return <rp> pinned and its block number <rpbn>.
  763. */
  764. rc = (sp->header.flag & BT_ROOT) ?
  765. xtSplitRoot(tid, ip, split, &rmp) :
  766. xtSplitPage(tid, ip, split, &rmp, &rbn);
  767. if (rc) {
  768. XT_PUTPAGE(smp);
  769. return rc;
  770. }
  771. XT_PUTPAGE(smp);
  772. /* keep new child page <rp> pinned */
  773. }
  774. /*
  775. * parent page is not full - insert in parent page
  776. */
  777. else {
  778. /*
  779. * insert router entry in parent for the right child
  780. * page from the first entry of the right child page:
  781. */
  782. /*
  783. * acquire a transaction lock on the parent page;
  784. *
  785. * action: router xad insertion;
  786. */
  787. BT_MARK_DIRTY(smp, ip);
  788. /*
  789. * if insert into middle, shift right remaining entries
  790. */
  791. if (skip < nextindex)
  792. memmove(&sp->xad[skip + 1], &sp->xad[skip],
  793. (nextindex -
  794. skip) << L2XTSLOTSIZE);
  795. /* insert the router entry */
  796. xad = &sp->xad[skip];
  797. XT_PUTENTRY(xad, XAD_NEW,
  798. offsetXAD(&rcp->xad[XTENTRYSTART]),
  799. JFS_SBI(ip->i_sb)->nbperpage, rcbn);
  800. /* advance next available entry index. */
  801. le16_add_cpu(&sp->header.nextindex, 1);
  802. /* Don't log it if there are no links to the file */
  803. if (!test_cflag(COMMIT_Nolink, ip)) {
  804. tlck = txLock(tid, ip, smp,
  805. tlckXTREE | tlckGROW);
  806. xtlck = (struct xtlock *) & tlck->lock;
  807. xtlck->lwm.offset = (xtlck->lwm.offset) ?
  808. min(skip, (int)xtlck->lwm.offset) : skip;
  809. xtlck->lwm.length =
  810. le16_to_cpu(sp->header.nextindex) -
  811. xtlck->lwm.offset;
  812. }
  813. /* unpin parent page */
  814. XT_PUTPAGE(smp);
  815. /* exit propagate up */
  816. break;
  817. }
  818. }
  819. /* unpin current right page */
  820. XT_PUTPAGE(rmp);
  821. return 0;
  822. }
  823. /*
  824. * xtSplitPage()
  825. *
  826. * function:
  827. * split a full non-root page into
  828. * original/split/left page and new right page
  829. * i.e., the original/split page remains as left page.
  830. *
  831. * parameter:
  832. * int tid,
  833. * struct inode *ip,
  834. * struct xtsplit *split,
  835. * struct metapage **rmpp,
  836. * u64 *rbnp,
  837. *
  838. * return:
  839. * Pointer to page in which to insert or NULL on error.
  840. */
  841. static int
  842. xtSplitPage(tid_t tid, struct inode *ip,
  843. struct xtsplit * split, struct metapage ** rmpp, s64 * rbnp)
  844. {
  845. int rc = 0;
  846. struct metapage *smp;
  847. xtpage_t *sp;
  848. struct metapage *rmp;
  849. xtpage_t *rp; /* new right page allocated */
  850. s64 rbn; /* new right page block number */
  851. struct metapage *mp;
  852. xtpage_t *p;
  853. s64 nextbn;
  854. int skip, maxentry, middle, righthalf, n;
  855. xad_t *xad;
  856. struct pxdlist *pxdlist;
  857. pxd_t *pxd;
  858. struct tlock *tlck;
  859. struct xtlock *sxtlck = NULL, *rxtlck = NULL;
  860. int quota_allocation = 0;
  861. smp = split->mp;
  862. sp = XT_PAGE(ip, smp);
  863. INCREMENT(xtStat.split);
  864. pxdlist = split->pxdlist;
  865. pxd = &pxdlist->pxd[pxdlist->npxd];
  866. pxdlist->npxd++;
  867. rbn = addressPXD(pxd);
  868. /* Allocate blocks to quota. */
  869. rc = dquot_alloc_block(ip, lengthPXD(pxd));
  870. if (rc)
  871. goto clean_up;
  872. quota_allocation += lengthPXD(pxd);
  873. /*
  874. * allocate the new right page for the split
  875. */
  876. rmp = get_metapage(ip, rbn, PSIZE, 1);
  877. if (rmp == NULL) {
  878. rc = -EIO;
  879. goto clean_up;
  880. }
  881. jfs_info("xtSplitPage: ip:0x%p smp:0x%p rmp:0x%p", ip, smp, rmp);
  882. BT_MARK_DIRTY(rmp, ip);
  883. /*
  884. * action: new page;
  885. */
  886. rp = (xtpage_t *) rmp->data;
  887. rp->header.self = *pxd;
  888. rp->header.flag = sp->header.flag & BT_TYPE;
  889. rp->header.maxentry = sp->header.maxentry; /* little-endian */
  890. rp->header.nextindex = cpu_to_le16(XTENTRYSTART);
  891. BT_MARK_DIRTY(smp, ip);
  892. /* Don't log it if there are no links to the file */
  893. if (!test_cflag(COMMIT_Nolink, ip)) {
  894. /*
  895. * acquire a transaction lock on the new right page;
  896. */
  897. tlck = txLock(tid, ip, rmp, tlckXTREE | tlckNEW);
  898. rxtlck = (struct xtlock *) & tlck->lock;
  899. rxtlck->lwm.offset = XTENTRYSTART;
  900. /*
  901. * acquire a transaction lock on the split page
  902. */
  903. tlck = txLock(tid, ip, smp, tlckXTREE | tlckGROW);
  904. sxtlck = (struct xtlock *) & tlck->lock;
  905. }
  906. /*
  907. * initialize/update sibling pointers of <sp> and <rp>
  908. */
  909. nextbn = le64_to_cpu(sp->header.next);
  910. rp->header.next = cpu_to_le64(nextbn);
  911. rp->header.prev = cpu_to_le64(addressPXD(&sp->header.self));
  912. sp->header.next = cpu_to_le64(rbn);
  913. skip = split->index;
  914. /*
  915. * sequential append at tail (after last entry of last page)
  916. *
  917. * if splitting the last page on a level because of appending
  918. * a entry to it (skip is maxentry), it's likely that the access is
  919. * sequential. adding an empty page on the side of the level is less
  920. * work and can push the fill factor much higher than normal.
  921. * if we're wrong it's no big deal - we will do the split the right
  922. * way next time.
  923. * (it may look like it's equally easy to do a similar hack for
  924. * reverse sorted data, that is, split the tree left, but it's not.
  925. * Be my guest.)
  926. */
  927. if (nextbn == 0 && skip == le16_to_cpu(sp->header.maxentry)) {
  928. /*
  929. * acquire a transaction lock on the new/right page;
  930. *
  931. * action: xad insertion;
  932. */
  933. /* insert entry at the first entry of the new right page */
  934. xad = &rp->xad[XTENTRYSTART];
  935. XT_PUTENTRY(xad, split->flag, split->off, split->len,
  936. split->addr);
  937. rp->header.nextindex = cpu_to_le16(XTENTRYSTART + 1);
  938. if (!test_cflag(COMMIT_Nolink, ip)) {
  939. /* rxtlck->lwm.offset = XTENTRYSTART; */
  940. rxtlck->lwm.length = 1;
  941. }
  942. *rmpp = rmp;
  943. *rbnp = rbn;
  944. jfs_info("xtSplitPage: sp:0x%p rp:0x%p", sp, rp);
  945. return 0;
  946. }
  947. /*
  948. * non-sequential insert (at possibly middle page)
  949. */
  950. /*
  951. * update previous pointer of old next/right page of <sp>
  952. */
  953. if (nextbn != 0) {
  954. XT_GETPAGE(ip, nextbn, mp, PSIZE, p, rc);
  955. if (rc) {
  956. XT_PUTPAGE(rmp);
  957. goto clean_up;
  958. }
  959. BT_MARK_DIRTY(mp, ip);
  960. /*
  961. * acquire a transaction lock on the next page;
  962. *
  963. * action:sibling pointer update;
  964. */
  965. if (!test_cflag(COMMIT_Nolink, ip))
  966. tlck = txLock(tid, ip, mp, tlckXTREE | tlckRELINK);
  967. p->header.prev = cpu_to_le64(rbn);
  968. /* sibling page may have been updated previously, or
  969. * it may be updated later;
  970. */
  971. XT_PUTPAGE(mp);
  972. }
  973. /*
  974. * split the data between the split and new/right pages
  975. */
  976. maxentry = le16_to_cpu(sp->header.maxentry);
  977. middle = maxentry >> 1;
  978. righthalf = maxentry - middle;
  979. /*
  980. * skip index in old split/left page - insert into left page:
  981. */
  982. if (skip <= middle) {
  983. /* move right half of split page to the new right page */
  984. memmove(&rp->xad[XTENTRYSTART], &sp->xad[middle],
  985. righthalf << L2XTSLOTSIZE);
  986. /* shift right tail of left half to make room for new entry */
  987. if (skip < middle)
  988. memmove(&sp->xad[skip + 1], &sp->xad[skip],
  989. (middle - skip) << L2XTSLOTSIZE);
  990. /* insert new entry */
  991. xad = &sp->xad[skip];
  992. XT_PUTENTRY(xad, split->flag, split->off, split->len,
  993. split->addr);
  994. /* update page header */
  995. sp->header.nextindex = cpu_to_le16(middle + 1);
  996. if (!test_cflag(COMMIT_Nolink, ip)) {
  997. sxtlck->lwm.offset = (sxtlck->lwm.offset) ?
  998. min(skip, (int)sxtlck->lwm.offset) : skip;
  999. }
  1000. rp->header.nextindex =
  1001. cpu_to_le16(XTENTRYSTART + righthalf);
  1002. }
  1003. /*
  1004. * skip index in new right page - insert into right page:
  1005. */
  1006. else {
  1007. /* move left head of right half to right page */
  1008. n = skip - middle;
  1009. memmove(&rp->xad[XTENTRYSTART], &sp->xad[middle],
  1010. n << L2XTSLOTSIZE);
  1011. /* insert new entry */
  1012. n += XTENTRYSTART;
  1013. xad = &rp->xad[n];
  1014. XT_PUTENTRY(xad, split->flag, split->off, split->len,
  1015. split->addr);
  1016. /* move right tail of right half to right page */
  1017. if (skip < maxentry)
  1018. memmove(&rp->xad[n + 1], &sp->xad[skip],
  1019. (maxentry - skip) << L2XTSLOTSIZE);
  1020. /* update page header */
  1021. sp->header.nextindex = cpu_to_le16(middle);
  1022. if (!test_cflag(COMMIT_Nolink, ip)) {
  1023. sxtlck->lwm.offset = (sxtlck->lwm.offset) ?
  1024. min(middle, (int)sxtlck->lwm.offset) : middle;
  1025. }
  1026. rp->header.nextindex = cpu_to_le16(XTENTRYSTART +
  1027. righthalf + 1);
  1028. }
  1029. if (!test_cflag(COMMIT_Nolink, ip)) {
  1030. sxtlck->lwm.length = le16_to_cpu(sp->header.nextindex) -
  1031. sxtlck->lwm.offset;
  1032. /* rxtlck->lwm.offset = XTENTRYSTART; */
  1033. rxtlck->lwm.length = le16_to_cpu(rp->header.nextindex) -
  1034. XTENTRYSTART;
  1035. }
  1036. *rmpp = rmp;
  1037. *rbnp = rbn;
  1038. jfs_info("xtSplitPage: sp:0x%p rp:0x%p", sp, rp);
  1039. return rc;
  1040. clean_up:
  1041. /* Rollback quota allocation. */
  1042. if (quota_allocation)
  1043. dquot_free_block(ip, quota_allocation);
  1044. return (rc);
  1045. }
  1046. /*
  1047. * xtSplitRoot()
  1048. *
  1049. * function:
  1050. * split the full root page into original/root/split page and new
  1051. * right page
  1052. * i.e., root remains fixed in tree anchor (inode) and the root is
  1053. * copied to a single new right child page since root page <<
  1054. * non-root page, and the split root page contains a single entry
  1055. * for the new right child page.
  1056. *
  1057. * parameter:
  1058. * int tid,
  1059. * struct inode *ip,
  1060. * struct xtsplit *split,
  1061. * struct metapage **rmpp)
  1062. *
  1063. * return:
  1064. * Pointer to page in which to insert or NULL on error.
  1065. */
  1066. static int
  1067. xtSplitRoot(tid_t tid,
  1068. struct inode *ip, struct xtsplit * split, struct metapage ** rmpp)
  1069. {
  1070. xtpage_t *sp;
  1071. struct metapage *rmp;
  1072. xtpage_t *rp;
  1073. s64 rbn;
  1074. int skip, nextindex;
  1075. xad_t *xad;
  1076. pxd_t *pxd;
  1077. struct pxdlist *pxdlist;
  1078. struct tlock *tlck;
  1079. struct xtlock *xtlck;
  1080. int rc;
  1081. sp = &JFS_IP(ip)->i_xtroot;
  1082. INCREMENT(xtStat.split);
  1083. /*
  1084. * allocate a single (right) child page
  1085. */
  1086. pxdlist = split->pxdlist;
  1087. pxd = &pxdlist->pxd[pxdlist->npxd];
  1088. pxdlist->npxd++;
  1089. rbn = addressPXD(pxd);
  1090. rmp = get_metapage(ip, rbn, PSIZE, 1);
  1091. if (rmp == NULL)
  1092. return -EIO;
  1093. /* Allocate blocks to quota. */
  1094. rc = dquot_alloc_block(ip, lengthPXD(pxd));
  1095. if (rc) {
  1096. release_metapage(rmp);
  1097. return rc;
  1098. }
  1099. jfs_info("xtSplitRoot: ip:0x%p rmp:0x%p", ip, rmp);
  1100. /*
  1101. * acquire a transaction lock on the new right page;
  1102. *
  1103. * action: new page;
  1104. */
  1105. BT_MARK_DIRTY(rmp, ip);
  1106. rp = (xtpage_t *) rmp->data;
  1107. rp->header.flag =
  1108. (sp->header.flag & BT_LEAF) ? BT_LEAF : BT_INTERNAL;
  1109. rp->header.self = *pxd;
  1110. rp->header.nextindex = cpu_to_le16(XTENTRYSTART);
  1111. rp->header.maxentry = cpu_to_le16(PSIZE >> L2XTSLOTSIZE);
  1112. /* initialize sibling pointers */
  1113. rp->header.next = 0;
  1114. rp->header.prev = 0;
  1115. /*
  1116. * copy the in-line root page into new right page extent
  1117. */
  1118. nextindex = le16_to_cpu(sp->header.maxentry);
  1119. memmove(&rp->xad[XTENTRYSTART], &sp->xad[XTENTRYSTART],
  1120. (nextindex - XTENTRYSTART) << L2XTSLOTSIZE);
  1121. /*
  1122. * insert the new entry into the new right/child page
  1123. * (skip index in the new right page will not change)
  1124. */
  1125. skip = split->index;
  1126. /* if insert into middle, shift right remaining entries */
  1127. if (skip != nextindex)
  1128. memmove(&rp->xad[skip + 1], &rp->xad[skip],
  1129. (nextindex - skip) * sizeof(xad_t));
  1130. xad = &rp->xad[skip];
  1131. XT_PUTENTRY(xad, split->flag, split->off, split->len, split->addr);
  1132. /* update page header */
  1133. rp->header.nextindex = cpu_to_le16(nextindex + 1);
  1134. if (!test_cflag(COMMIT_Nolink, ip)) {
  1135. tlck = txLock(tid, ip, rmp, tlckXTREE | tlckNEW);
  1136. xtlck = (struct xtlock *) & tlck->lock;
  1137. xtlck->lwm.offset = XTENTRYSTART;
  1138. xtlck->lwm.length = le16_to_cpu(rp->header.nextindex) -
  1139. XTENTRYSTART;
  1140. }
  1141. /*
  1142. * reset the root
  1143. *
  1144. * init root with the single entry for the new right page
  1145. * set the 1st entry offset to 0, which force the left-most key
  1146. * at any level of the tree to be less than any search key.
  1147. */
  1148. /*
  1149. * acquire a transaction lock on the root page (in-memory inode);
  1150. *
  1151. * action: root split;
  1152. */
  1153. BT_MARK_DIRTY(split->mp, ip);
  1154. xad = &sp->xad[XTENTRYSTART];
  1155. XT_PUTENTRY(xad, XAD_NEW, 0, JFS_SBI(ip->i_sb)->nbperpage, rbn);
  1156. /* update page header of root */
  1157. sp->header.flag &= ~BT_LEAF;
  1158. sp->header.flag |= BT_INTERNAL;
  1159. sp->header.nextindex = cpu_to_le16(XTENTRYSTART + 1);
  1160. if (!test_cflag(COMMIT_Nolink, ip)) {
  1161. tlck = txLock(tid, ip, split->mp, tlckXTREE | tlckGROW);
  1162. xtlck = (struct xtlock *) & tlck->lock;
  1163. xtlck->lwm.offset = XTENTRYSTART;
  1164. xtlck->lwm.length = 1;
  1165. }
  1166. *rmpp = rmp;
  1167. jfs_info("xtSplitRoot: sp:0x%p rp:0x%p", sp, rp);
  1168. return 0;
  1169. }
  1170. /*
  1171. * xtExtend()
  1172. *
  1173. * function: extend in-place;
  1174. *
  1175. * note: existing extent may or may not have been committed.
  1176. * caller is responsible for pager buffer cache update, and
  1177. * working block allocation map update;
  1178. * update pmap: alloc whole extended extent;
  1179. */
  1180. int xtExtend(tid_t tid, /* transaction id */
  1181. struct inode *ip, s64 xoff, /* delta extent offset */
  1182. s32 xlen, /* delta extent length */
  1183. int flag)
  1184. {
  1185. int rc = 0;
  1186. int cmp;
  1187. struct metapage *mp; /* meta-page buffer */
  1188. xtpage_t *p; /* base B+-tree index page */
  1189. s64 bn;
  1190. int index, nextindex, len;
  1191. struct btstack btstack; /* traverse stack */
  1192. struct xtsplit split; /* split information */
  1193. xad_t *xad;
  1194. s64 xaddr;
  1195. struct tlock *tlck;
  1196. struct xtlock *xtlck = NULL;
  1197. jfs_info("xtExtend: nxoff:0x%lx nxlen:0x%x", (ulong) xoff, xlen);
  1198. /* there must exist extent to be extended */
  1199. if ((rc = xtSearch(ip, xoff - 1, NULL, &cmp, &btstack, XT_INSERT)))
  1200. return rc;
  1201. /* retrieve search result */
  1202. XT_GETSEARCH(ip, btstack.top, bn, mp, p, index);
  1203. if (cmp != 0) {
  1204. XT_PUTPAGE(mp);
  1205. jfs_error(ip->i_sb, "xtExtend: xtSearch did not find extent");
  1206. return -EIO;
  1207. }
  1208. /* extension must be contiguous */
  1209. xad = &p->xad[index];
  1210. if ((offsetXAD(xad) + lengthXAD(xad)) != xoff) {
  1211. XT_PUTPAGE(mp);
  1212. jfs_error(ip->i_sb, "xtExtend: extension is not contiguous");
  1213. return -EIO;
  1214. }
  1215. /*
  1216. * acquire a transaction lock on the leaf page;
  1217. *
  1218. * action: xad insertion/extension;
  1219. */
  1220. BT_MARK_DIRTY(mp, ip);
  1221. if (!test_cflag(COMMIT_Nolink, ip)) {
  1222. tlck = txLock(tid, ip, mp, tlckXTREE | tlckGROW);
  1223. xtlck = (struct xtlock *) & tlck->lock;
  1224. }
  1225. /* extend will overflow extent ? */
  1226. xlen = lengthXAD(xad) + xlen;
  1227. if ((len = xlen - MAXXLEN) <= 0)
  1228. goto extendOld;
  1229. /*
  1230. * extent overflow: insert entry for new extent
  1231. */
  1232. //insertNew:
  1233. xoff = offsetXAD(xad) + MAXXLEN;
  1234. xaddr = addressXAD(xad) + MAXXLEN;
  1235. nextindex = le16_to_cpu(p->header.nextindex);
  1236. /*
  1237. * if the leaf page is full, insert the new entry and
  1238. * propagate up the router entry for the new page from split
  1239. *
  1240. * The xtSplitUp() will insert the entry and unpin the leaf page.
  1241. */
  1242. if (nextindex == le16_to_cpu(p->header.maxentry)) {
  1243. /* xtSpliUp() unpins leaf pages */
  1244. split.mp = mp;
  1245. split.index = index + 1;
  1246. split.flag = XAD_NEW;
  1247. split.off = xoff; /* split offset */
  1248. split.len = len;
  1249. split.addr = xaddr;
  1250. split.pxdlist = NULL;
  1251. if ((rc = xtSplitUp(tid, ip, &split, &btstack)))
  1252. return rc;
  1253. /* get back old page */
  1254. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1255. if (rc)
  1256. return rc;
  1257. /*
  1258. * if leaf root has been split, original root has been
  1259. * copied to new child page, i.e., original entry now
  1260. * resides on the new child page;
  1261. */
  1262. if (p->header.flag & BT_INTERNAL) {
  1263. ASSERT(p->header.nextindex ==
  1264. cpu_to_le16(XTENTRYSTART + 1));
  1265. xad = &p->xad[XTENTRYSTART];
  1266. bn = addressXAD(xad);
  1267. XT_PUTPAGE(mp);
  1268. /* get new child page */
  1269. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1270. if (rc)
  1271. return rc;
  1272. BT_MARK_DIRTY(mp, ip);
  1273. if (!test_cflag(COMMIT_Nolink, ip)) {
  1274. tlck = txLock(tid, ip, mp, tlckXTREE|tlckGROW);
  1275. xtlck = (struct xtlock *) & tlck->lock;
  1276. }
  1277. }
  1278. }
  1279. /*
  1280. * insert the new entry into the leaf page
  1281. */
  1282. else {
  1283. /* insert the new entry: mark the entry NEW */
  1284. xad = &p->xad[index + 1];
  1285. XT_PUTENTRY(xad, XAD_NEW, xoff, len, xaddr);
  1286. /* advance next available entry index */
  1287. le16_add_cpu(&p->header.nextindex, 1);
  1288. }
  1289. /* get back old entry */
  1290. xad = &p->xad[index];
  1291. xlen = MAXXLEN;
  1292. /*
  1293. * extend old extent
  1294. */
  1295. extendOld:
  1296. XADlength(xad, xlen);
  1297. if (!(xad->flag & XAD_NEW))
  1298. xad->flag |= XAD_EXTENDED;
  1299. if (!test_cflag(COMMIT_Nolink, ip)) {
  1300. xtlck->lwm.offset =
  1301. (xtlck->lwm.offset) ? min(index,
  1302. (int)xtlck->lwm.offset) : index;
  1303. xtlck->lwm.length =
  1304. le16_to_cpu(p->header.nextindex) - xtlck->lwm.offset;
  1305. }
  1306. /* unpin the leaf page */
  1307. XT_PUTPAGE(mp);
  1308. return rc;
  1309. }
  1310. #ifdef _NOTYET
  1311. /*
  1312. * xtTailgate()
  1313. *
  1314. * function: split existing 'tail' extent
  1315. * (split offset >= start offset of tail extent), and
  1316. * relocate and extend the split tail half;
  1317. *
  1318. * note: existing extent may or may not have been committed.
  1319. * caller is responsible for pager buffer cache update, and
  1320. * working block allocation map update;
  1321. * update pmap: free old split tail extent, alloc new extent;
  1322. */
  1323. int xtTailgate(tid_t tid, /* transaction id */
  1324. struct inode *ip, s64 xoff, /* split/new extent offset */
  1325. s32 xlen, /* new extent length */
  1326. s64 xaddr, /* new extent address */
  1327. int flag)
  1328. {
  1329. int rc = 0;
  1330. int cmp;
  1331. struct metapage *mp; /* meta-page buffer */
  1332. xtpage_t *p; /* base B+-tree index page */
  1333. s64 bn;
  1334. int index, nextindex, llen, rlen;
  1335. struct btstack btstack; /* traverse stack */
  1336. struct xtsplit split; /* split information */
  1337. xad_t *xad;
  1338. struct tlock *tlck;
  1339. struct xtlock *xtlck = 0;
  1340. struct tlock *mtlck;
  1341. struct maplock *pxdlock;
  1342. /*
  1343. printf("xtTailgate: nxoff:0x%lx nxlen:0x%x nxaddr:0x%lx\n",
  1344. (ulong)xoff, xlen, (ulong)xaddr);
  1345. */
  1346. /* there must exist extent to be tailgated */
  1347. if ((rc = xtSearch(ip, xoff, NULL, &cmp, &btstack, XT_INSERT)))
  1348. return rc;
  1349. /* retrieve search result */
  1350. XT_GETSEARCH(ip, btstack.top, bn, mp, p, index);
  1351. if (cmp != 0) {
  1352. XT_PUTPAGE(mp);
  1353. jfs_error(ip->i_sb, "xtTailgate: couldn't find extent");
  1354. return -EIO;
  1355. }
  1356. /* entry found must be last entry */
  1357. nextindex = le16_to_cpu(p->header.nextindex);
  1358. if (index != nextindex - 1) {
  1359. XT_PUTPAGE(mp);
  1360. jfs_error(ip->i_sb,
  1361. "xtTailgate: the entry found is not the last entry");
  1362. return -EIO;
  1363. }
  1364. BT_MARK_DIRTY(mp, ip);
  1365. /*
  1366. * acquire tlock of the leaf page containing original entry
  1367. */
  1368. if (!test_cflag(COMMIT_Nolink, ip)) {
  1369. tlck = txLock(tid, ip, mp, tlckXTREE | tlckGROW);
  1370. xtlck = (struct xtlock *) & tlck->lock;
  1371. }
  1372. /* completely replace extent ? */
  1373. xad = &p->xad[index];
  1374. /*
  1375. printf("xtTailgate: xoff:0x%lx xlen:0x%x xaddr:0x%lx\n",
  1376. (ulong)offsetXAD(xad), lengthXAD(xad), (ulong)addressXAD(xad));
  1377. */
  1378. if ((llen = xoff - offsetXAD(xad)) == 0)
  1379. goto updateOld;
  1380. /*
  1381. * partially replace extent: insert entry for new extent
  1382. */
  1383. //insertNew:
  1384. /*
  1385. * if the leaf page is full, insert the new entry and
  1386. * propagate up the router entry for the new page from split
  1387. *
  1388. * The xtSplitUp() will insert the entry and unpin the leaf page.
  1389. */
  1390. if (nextindex == le16_to_cpu(p->header.maxentry)) {
  1391. /* xtSpliUp() unpins leaf pages */
  1392. split.mp = mp;
  1393. split.index = index + 1;
  1394. split.flag = XAD_NEW;
  1395. split.off = xoff; /* split offset */
  1396. split.len = xlen;
  1397. split.addr = xaddr;
  1398. split.pxdlist = NULL;
  1399. if ((rc = xtSplitUp(tid, ip, &split, &btstack)))
  1400. return rc;
  1401. /* get back old page */
  1402. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1403. if (rc)
  1404. return rc;
  1405. /*
  1406. * if leaf root has been split, original root has been
  1407. * copied to new child page, i.e., original entry now
  1408. * resides on the new child page;
  1409. */
  1410. if (p->header.flag & BT_INTERNAL) {
  1411. ASSERT(p->header.nextindex ==
  1412. cpu_to_le16(XTENTRYSTART + 1));
  1413. xad = &p->xad[XTENTRYSTART];
  1414. bn = addressXAD(xad);
  1415. XT_PUTPAGE(mp);
  1416. /* get new child page */
  1417. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1418. if (rc)
  1419. return rc;
  1420. BT_MARK_DIRTY(mp, ip);
  1421. if (!test_cflag(COMMIT_Nolink, ip)) {
  1422. tlck = txLock(tid, ip, mp, tlckXTREE|tlckGROW);
  1423. xtlck = (struct xtlock *) & tlck->lock;
  1424. }
  1425. }
  1426. }
  1427. /*
  1428. * insert the new entry into the leaf page
  1429. */
  1430. else {
  1431. /* insert the new entry: mark the entry NEW */
  1432. xad = &p->xad[index + 1];
  1433. XT_PUTENTRY(xad, XAD_NEW, xoff, xlen, xaddr);
  1434. /* advance next available entry index */
  1435. le16_add_cpu(&p->header.nextindex, 1);
  1436. }
  1437. /* get back old XAD */
  1438. xad = &p->xad[index];
  1439. /*
  1440. * truncate/relocate old extent at split offset
  1441. */
  1442. updateOld:
  1443. /* update dmap for old/committed/truncated extent */
  1444. rlen = lengthXAD(xad) - llen;
  1445. if (!(xad->flag & XAD_NEW)) {
  1446. /* free from PWMAP at commit */
  1447. if (!test_cflag(COMMIT_Nolink, ip)) {
  1448. mtlck = txMaplock(tid, ip, tlckMAP);
  1449. pxdlock = (struct maplock *) & mtlck->lock;
  1450. pxdlock->flag = mlckFREEPXD;
  1451. PXDaddress(&pxdlock->pxd, addressXAD(xad) + llen);
  1452. PXDlength(&pxdlock->pxd, rlen);
  1453. pxdlock->index = 1;
  1454. }
  1455. } else
  1456. /* free from WMAP */
  1457. dbFree(ip, addressXAD(xad) + llen, (s64) rlen);
  1458. if (llen)
  1459. /* truncate */
  1460. XADlength(xad, llen);
  1461. else
  1462. /* replace */
  1463. XT_PUTENTRY(xad, XAD_NEW, xoff, xlen, xaddr);
  1464. if (!test_cflag(COMMIT_Nolink, ip)) {
  1465. xtlck->lwm.offset = (xtlck->lwm.offset) ?
  1466. min(index, (int)xtlck->lwm.offset) : index;
  1467. xtlck->lwm.length = le16_to_cpu(p->header.nextindex) -
  1468. xtlck->lwm.offset;
  1469. }
  1470. /* unpin the leaf page */
  1471. XT_PUTPAGE(mp);
  1472. return rc;
  1473. }
  1474. #endif /* _NOTYET */
  1475. /*
  1476. * xtUpdate()
  1477. *
  1478. * function: update XAD;
  1479. *
  1480. * update extent for allocated_but_not_recorded or
  1481. * compressed extent;
  1482. *
  1483. * parameter:
  1484. * nxad - new XAD;
  1485. * logical extent of the specified XAD must be completely
  1486. * contained by an existing XAD;
  1487. */
  1488. int xtUpdate(tid_t tid, struct inode *ip, xad_t * nxad)
  1489. { /* new XAD */
  1490. int rc = 0;
  1491. int cmp;
  1492. struct metapage *mp; /* meta-page buffer */
  1493. xtpage_t *p; /* base B+-tree index page */
  1494. s64 bn;
  1495. int index0, index, newindex, nextindex;
  1496. struct btstack btstack; /* traverse stack */
  1497. struct xtsplit split; /* split information */
  1498. xad_t *xad, *lxad, *rxad;
  1499. int xflag;
  1500. s64 nxoff, xoff;
  1501. int nxlen, xlen, lxlen, rxlen;
  1502. s64 nxaddr, xaddr;
  1503. struct tlock *tlck;
  1504. struct xtlock *xtlck = NULL;
  1505. int newpage = 0;
  1506. /* there must exist extent to be tailgated */
  1507. nxoff = offsetXAD(nxad);
  1508. nxlen = lengthXAD(nxad);
  1509. nxaddr = addressXAD(nxad);
  1510. if ((rc = xtSearch(ip, nxoff, NULL, &cmp, &btstack, XT_INSERT)))
  1511. return rc;
  1512. /* retrieve search result */
  1513. XT_GETSEARCH(ip, btstack.top, bn, mp, p, index0);
  1514. if (cmp != 0) {
  1515. XT_PUTPAGE(mp);
  1516. jfs_error(ip->i_sb, "xtUpdate: Could not find extent");
  1517. return -EIO;
  1518. }
  1519. BT_MARK_DIRTY(mp, ip);
  1520. /*
  1521. * acquire tlock of the leaf page containing original entry
  1522. */
  1523. if (!test_cflag(COMMIT_Nolink, ip)) {
  1524. tlck = txLock(tid, ip, mp, tlckXTREE | tlckGROW);
  1525. xtlck = (struct xtlock *) & tlck->lock;
  1526. }
  1527. xad = &p->xad[index0];
  1528. xflag = xad->flag;
  1529. xoff = offsetXAD(xad);
  1530. xlen = lengthXAD(xad);
  1531. xaddr = addressXAD(xad);
  1532. /* nXAD must be completely contained within XAD */
  1533. if ((xoff > nxoff) ||
  1534. (nxoff + nxlen > xoff + xlen)) {
  1535. XT_PUTPAGE(mp);
  1536. jfs_error(ip->i_sb,
  1537. "xtUpdate: nXAD in not completely contained within XAD");
  1538. return -EIO;
  1539. }
  1540. index = index0;
  1541. newindex = index + 1;
  1542. nextindex = le16_to_cpu(p->header.nextindex);
  1543. #ifdef _JFS_WIP_NOCOALESCE
  1544. if (xoff < nxoff)
  1545. goto updateRight;
  1546. /*
  1547. * replace XAD with nXAD
  1548. */
  1549. replace: /* (nxoff == xoff) */
  1550. if (nxlen == xlen) {
  1551. /* replace XAD with nXAD:recorded */
  1552. *xad = *nxad;
  1553. xad->flag = xflag & ~XAD_NOTRECORDED;
  1554. goto out;
  1555. } else /* (nxlen < xlen) */
  1556. goto updateLeft;
  1557. #endif /* _JFS_WIP_NOCOALESCE */
  1558. /* #ifdef _JFS_WIP_COALESCE */
  1559. if (xoff < nxoff)
  1560. goto coalesceRight;
  1561. /*
  1562. * coalesce with left XAD
  1563. */
  1564. //coalesceLeft: /* (xoff == nxoff) */
  1565. /* is XAD first entry of page ? */
  1566. if (index == XTENTRYSTART)
  1567. goto replace;
  1568. /* is nXAD logically and physically contiguous with lXAD ? */
  1569. lxad = &p->xad[index - 1];
  1570. lxlen = lengthXAD(lxad);
  1571. if (!(lxad->flag & XAD_NOTRECORDED) &&
  1572. (nxoff == offsetXAD(lxad) + lxlen) &&
  1573. (nxaddr == addressXAD(lxad) + lxlen) &&
  1574. (lxlen + nxlen < MAXXLEN)) {
  1575. /* extend right lXAD */
  1576. index0 = index - 1;
  1577. XADlength(lxad, lxlen + nxlen);
  1578. /* If we just merged two extents together, need to make sure the
  1579. * right extent gets logged. If the left one is marked XAD_NEW,
  1580. * then we know it will be logged. Otherwise, mark as
  1581. * XAD_EXTENDED
  1582. */
  1583. if (!(lxad->flag & XAD_NEW))
  1584. lxad->flag |= XAD_EXTENDED;
  1585. if (xlen > nxlen) {
  1586. /* truncate XAD */
  1587. XADoffset(xad, xoff + nxlen);
  1588. XADlength(xad, xlen - nxlen);
  1589. XADaddress(xad, xaddr + nxlen);
  1590. goto out;
  1591. } else { /* (xlen == nxlen) */
  1592. /* remove XAD */
  1593. if (index < nextindex - 1)
  1594. memmove(&p->xad[index], &p->xad[index + 1],
  1595. (nextindex - index -
  1596. 1) << L2XTSLOTSIZE);
  1597. p->header.nextindex =
  1598. cpu_to_le16(le16_to_cpu(p->header.nextindex) -
  1599. 1);
  1600. index = index0;
  1601. newindex = index + 1;
  1602. nextindex = le16_to_cpu(p->header.nextindex);
  1603. xoff = nxoff = offsetXAD(lxad);
  1604. xlen = nxlen = lxlen + nxlen;
  1605. xaddr = nxaddr = addressXAD(lxad);
  1606. goto coalesceRight;
  1607. }
  1608. }
  1609. /*
  1610. * replace XAD with nXAD
  1611. */
  1612. replace: /* (nxoff == xoff) */
  1613. if (nxlen == xlen) {
  1614. /* replace XAD with nXAD:recorded */
  1615. *xad = *nxad;
  1616. xad->flag = xflag & ~XAD_NOTRECORDED;
  1617. goto coalesceRight;
  1618. } else /* (nxlen < xlen) */
  1619. goto updateLeft;
  1620. /*
  1621. * coalesce with right XAD
  1622. */
  1623. coalesceRight: /* (xoff <= nxoff) */
  1624. /* is XAD last entry of page ? */
  1625. if (newindex == nextindex) {
  1626. if (xoff == nxoff)
  1627. goto out;
  1628. goto updateRight;
  1629. }
  1630. /* is nXAD logically and physically contiguous with rXAD ? */
  1631. rxad = &p->xad[index + 1];
  1632. rxlen = lengthXAD(rxad);
  1633. if (!(rxad->flag & XAD_NOTRECORDED) &&
  1634. (nxoff + nxlen == offsetXAD(rxad)) &&
  1635. (nxaddr + nxlen == addressXAD(rxad)) &&
  1636. (rxlen + nxlen < MAXXLEN)) {
  1637. /* extend left rXAD */
  1638. XADoffset(rxad, nxoff);
  1639. XADlength(rxad, rxlen + nxlen);
  1640. XADaddress(rxad, nxaddr);
  1641. /* If we just merged two extents together, need to make sure
  1642. * the left extent gets logged. If the right one is marked
  1643. * XAD_NEW, then we know it will be logged. Otherwise, mark as
  1644. * XAD_EXTENDED
  1645. */
  1646. if (!(rxad->flag & XAD_NEW))
  1647. rxad->flag |= XAD_EXTENDED;
  1648. if (xlen > nxlen)
  1649. /* truncate XAD */
  1650. XADlength(xad, xlen - nxlen);
  1651. else { /* (xlen == nxlen) */
  1652. /* remove XAD */
  1653. memmove(&p->xad[index], &p->xad[index + 1],
  1654. (nextindex - index - 1) << L2XTSLOTSIZE);
  1655. p->header.nextindex =
  1656. cpu_to_le16(le16_to_cpu(p->header.nextindex) -
  1657. 1);
  1658. }
  1659. goto out;
  1660. } else if (xoff == nxoff)
  1661. goto out;
  1662. if (xoff >= nxoff) {
  1663. XT_PUTPAGE(mp);
  1664. jfs_error(ip->i_sb, "xtUpdate: xoff >= nxoff");
  1665. return -EIO;
  1666. }
  1667. /* #endif _JFS_WIP_COALESCE */
  1668. /*
  1669. * split XAD into (lXAD, nXAD):
  1670. *
  1671. * |---nXAD--->
  1672. * --|----------XAD----------|--
  1673. * |-lXAD-|
  1674. */
  1675. updateRight: /* (xoff < nxoff) */
  1676. /* truncate old XAD as lXAD:not_recorded */
  1677. xad = &p->xad[index];
  1678. XADlength(xad, nxoff - xoff);
  1679. /* insert nXAD:recorded */
  1680. if (nextindex == le16_to_cpu(p->header.maxentry)) {
  1681. /* xtSpliUp() unpins leaf pages */
  1682. split.mp = mp;
  1683. split.index = newindex;
  1684. split.flag = xflag & ~XAD_NOTRECORDED;
  1685. split.off = nxoff;
  1686. split.len = nxlen;
  1687. split.addr = nxaddr;
  1688. split.pxdlist = NULL;
  1689. if ((rc = xtSplitUp(tid, ip, &split, &btstack)))
  1690. return rc;
  1691. /* get back old page */
  1692. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1693. if (rc)
  1694. return rc;
  1695. /*
  1696. * if leaf root has been split, original root has been
  1697. * copied to new child page, i.e., original entry now
  1698. * resides on the new child page;
  1699. */
  1700. if (p->header.flag & BT_INTERNAL) {
  1701. ASSERT(p->header.nextindex ==
  1702. cpu_to_le16(XTENTRYSTART + 1));
  1703. xad = &p->xad[XTENTRYSTART];
  1704. bn = addressXAD(xad);
  1705. XT_PUTPAGE(mp);
  1706. /* get new child page */
  1707. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1708. if (rc)
  1709. return rc;
  1710. BT_MARK_DIRTY(mp, ip);
  1711. if (!test_cflag(COMMIT_Nolink, ip)) {
  1712. tlck = txLock(tid, ip, mp, tlckXTREE|tlckGROW);
  1713. xtlck = (struct xtlock *) & tlck->lock;
  1714. }
  1715. } else {
  1716. /* is nXAD on new page ? */
  1717. if (newindex >
  1718. (le16_to_cpu(p->header.maxentry) >> 1)) {
  1719. newindex =
  1720. newindex -
  1721. le16_to_cpu(p->header.nextindex) +
  1722. XTENTRYSTART;
  1723. newpage = 1;
  1724. }
  1725. }
  1726. } else {
  1727. /* if insert into middle, shift right remaining entries */
  1728. if (newindex < nextindex)
  1729. memmove(&p->xad[newindex + 1], &p->xad[newindex],
  1730. (nextindex - newindex) << L2XTSLOTSIZE);
  1731. /* insert the entry */
  1732. xad = &p->xad[newindex];
  1733. *xad = *nxad;
  1734. xad->flag = xflag & ~XAD_NOTRECORDED;
  1735. /* advance next available entry index. */
  1736. p->header.nextindex =
  1737. cpu_to_le16(le16_to_cpu(p->header.nextindex) + 1);
  1738. }
  1739. /*
  1740. * does nXAD force 3-way split ?
  1741. *
  1742. * |---nXAD--->|
  1743. * --|----------XAD-------------|--
  1744. * |-lXAD-| |-rXAD -|
  1745. */
  1746. if (nxoff + nxlen == xoff + xlen)
  1747. goto out;
  1748. /* reorient nXAD as XAD for further split XAD into (nXAD, rXAD) */
  1749. if (newpage) {
  1750. /* close out old page */
  1751. if (!test_cflag(COMMIT_Nolink, ip)) {
  1752. xtlck->lwm.offset = (xtlck->lwm.offset) ?
  1753. min(index0, (int)xtlck->lwm.offset) : index0;
  1754. xtlck->lwm.length =
  1755. le16_to_cpu(p->header.nextindex) -
  1756. xtlck->lwm.offset;
  1757. }
  1758. bn = le64_to_cpu(p->header.next);
  1759. XT_PUTPAGE(mp);
  1760. /* get new right page */
  1761. XT_GETPAGE(ip, bn, mp, PSIZE, p, rc);
  1762. if (rc)
  1763. return rc;
  1764. BT_MARK_DIRTY(mp, ip);
  1765. if (!test_cflag(COMMIT_Nolink, ip)) {
  1766. tlck = txLock(tid, ip, mp, tlckXTREE | tlckGROW);
  1767. xtlck = (struct xtlock *) & tlck->lock;
  1768. }
  1769. index0 = index = newindex;
  1770. } else