Line data Source code
1 : // SPDX-License-Identifier: GPL-2.0-or-later
2 : /*
3 : * Copyright (C) 2020-2023 Oracle. All Rights Reserved.
4 : * Author: Darrick J. Wong <djwong@kernel.org>
5 : */
6 : #include "xfs.h"
7 : #include "xfs_fs.h"
8 : #include "xfs_shared.h"
9 : #include "xfs_format.h"
10 : #include "xfs_trans_resv.h"
11 : #include "xfs_mount.h"
12 : #include "xfs_defer.h"
13 : #include "xfs_bit.h"
14 : #include "xfs_log_format.h"
15 : #include "xfs_trans.h"
16 : #include "xfs_sb.h"
17 : #include "xfs_inode.h"
18 : #include "xfs_icache.h"
19 : #include "xfs_da_format.h"
20 : #include "xfs_da_btree.h"
21 : #include "xfs_dir2.h"
22 : #include "xfs_bmap_btree.h"
23 : #include "xfs_dir2_priv.h"
24 : #include "xfs_trans_space.h"
25 : #include "xfs_health.h"
26 : #include "xfs_swapext.h"
27 : #include "xfs_parent.h"
28 : #include "xfs_attr.h"
29 : #include "xfs_bmap.h"
30 : #include "scrub/xfs_scrub.h"
31 : #include "scrub/scrub.h"
32 : #include "scrub/common.h"
33 : #include "scrub/trace.h"
34 : #include "scrub/repair.h"
35 : #include "scrub/iscan.h"
36 : #include "scrub/findparent.h"
37 : #include "scrub/readdir.h"
38 : #include "scrub/tempfile.h"
39 : #include "scrub/tempswap.h"
40 : #include "scrub/orphanage.h"
41 : #include "scrub/xfile.h"
42 : #include "scrub/xfarray.h"
43 : #include "scrub/xfblob.h"
44 : #include "scrub/attr_repair.h"
45 : #include "scrub/listxattr.h"
46 :
47 : /*
48 : * Repairing The Directory Parent Pointer
49 : * ======================================
50 : *
51 : * Currently, only directories support parent pointers (in the form of '..'
52 : * entries), so we simply scan the filesystem and update the '..' entry.
53 : *
54 : * Note that because the only parent pointer is the dotdot entry, we won't
55 : * touch an unhealthy directory, since the directory repair code is perfectly
56 : * capable of rebuilding a directory with the proper parent inode.
57 : *
58 : * See the section on locking issues in dir_repair.c for more information about
59 : * conflicts with the VFS. The findparent code wll keep our incore parent
60 : * inode up to date.
61 : *
62 : * If parent pointers are enabled, we instead reconstruct the parent pointer
63 : * information by visiting every directory entry of every directory in the
64 : * system and translating the relevant dirents into parent pointers. In this
65 : * case, it is advantageous to stash all parent pointers created from dirents
66 : * from a single parent file before replaying them into the temporary file. To
67 : * save memory, the live filesystem scan reuses the findparent object. Parent
68 : * pointer repair chooses either directory scanning or findparent, but not
69 : * both.
70 : *
71 : * When salvaging completes, the remaining stashed entries are replayed to the
72 : * temporary file. All non-parent pointer extended attributes are copied to
73 : * the temporary file's extended attributes. An atomic extent swap is used to
74 : * commit the new directory blocks to the directory being repaired. This will
75 : * disrupt attrmulti cursors.
76 : */
77 :
78 : /* Create a parent pointer in the tempfile. */
79 : #define XREP_PPTR_ADD (1)
80 :
81 : /* Remove a parent pointer from the tempfile. */
82 : #define XREP_PPTR_REMOVE (2)
83 :
84 : /* A stashed parent pointer update. */
85 : struct xrep_pptr {
86 : /* Cookie for retrieval of the pptr name. */
87 : xfblob_cookie name_cookie;
88 :
89 : /* Parent pointer attr key. */
90 : xfs_ino_t p_ino;
91 : uint32_t p_gen;
92 :
93 : /* Length of the pptr name. */
94 : uint8_t namelen;
95 :
96 : /* XREP_PPTR_{ADD,REMOVE} */
97 : uint8_t action;
98 : };
99 :
100 : /*
101 : * Stash up to 8 pages of recovered parent pointers in pptr_recs and
102 : * pptr_names before we write them to the temp file.
103 : */
104 : #define XREP_PARENT_MAX_STASH_BYTES (PAGE_SIZE * 8)
105 :
106 : struct xrep_parent {
107 : struct xfs_scrub *sc;
108 :
109 : /* Fixed-size array of xrep_pptr structures. */
110 : struct xfarray *pptr_recs;
111 :
112 : /* Blobs containing parent pointer names. */
113 : struct xfblob *pptr_names;
114 :
115 : /* xattr keys */
116 : struct xfarray *xattr_records;
117 :
118 : /* xattr values */
119 : struct xfblob *xattr_blobs;
120 :
121 : /* Scratch buffers for saving extended attributes */
122 : unsigned char *xattr_name;
123 : void *xattr_value;
124 : unsigned int xattr_value_sz;
125 :
126 : /*
127 : * Information used to swap the attr fork, if the fs supports parent
128 : * pointers.
129 : */
130 : struct xrep_tempswap tx;
131 :
132 : /*
133 : * Information used to scan the filesystem to find the inumber of the
134 : * dotdot entry for this directory. On filesystems without parent
135 : * pointers, we use the findparent_* functions on this object and
136 : * access only the parent_ino field directly.
137 : *
138 : * When parent pointers are enabled, the directory entry scanner uses
139 : * the iscan, hooks, and lock fields of this object directly.
140 : * @pscan.lock coordinates access to pptr_recs, pptr_names, pptr, and
141 : * pptr_scratch. This reduces the memory requirements of this
142 : * structure.
143 : *
144 : * The lock also controls access to xattr_records and xattr_blobs(?)
145 : */
146 : struct xrep_parent_scan_info pscan;
147 :
148 : /* Orphanage reparenting request. */
149 : struct xrep_adoption adoption;
150 :
151 : /* Have we seen any live updates of parent pointers recently? */
152 : bool saw_pptr_updates;
153 :
154 : /* xattr key and da args for parent pointer replay. */
155 : struct xfs_parent_scratch pptr_scratch;
156 :
157 : /*
158 : * Scratch buffer for scanning dirents to create pptr xattrs. At the
159 : * very end of the repair, it can also be used to compute the
160 : * lost+found filename if we need to reparent the file.
161 : */
162 : struct xfs_parent_name_irec pptr;
163 : };
164 :
165 : struct xrep_parent_xattr {
166 : /* Cookie for retrieval of the xattr name. */
167 : xfblob_cookie name_cookie;
168 :
169 : /* Cookie for retrieval of the xattr value. */
170 : xfblob_cookie value_cookie;
171 :
172 : /* XFS_ATTR_* flags */
173 : int flags;
174 :
175 : /* Length of the value and name. */
176 : uint32_t valuelen;
177 : uint16_t namelen;
178 : };
179 :
180 : /*
181 : * Stash up to 8 pages of attrs in xattr_records/xattr_blobs before we write
182 : * them to the temp file.
183 : */
184 : #define XREP_PARENT_XATTR_MAX_STASH_BYTES (PAGE_SIZE * 8)
185 :
186 : /* Tear down all the incore stuff we created. */
187 : static void
188 77611 : xrep_parent_teardown(
189 : struct xrep_parent *rp)
190 : {
191 77611 : xrep_findparent_scan_teardown(&rp->pscan);
192 77622 : kvfree(rp->xattr_name);
193 77622 : rp->xattr_name = NULL;
194 77622 : kvfree(rp->xattr_value);
195 77619 : rp->xattr_value = NULL;
196 77619 : if (rp->xattr_blobs)
197 77619 : xfblob_destroy(rp->xattr_blobs);
198 77616 : rp->xattr_blobs = NULL;
199 77616 : if (rp->xattr_records)
200 77616 : xfarray_destroy(rp->xattr_records);
201 77613 : rp->xattr_records = NULL;
202 77613 : if (rp->pptr_names)
203 77613 : xfblob_destroy(rp->pptr_names);
204 77624 : rp->pptr_names = NULL;
205 77624 : if (rp->pptr_recs)
206 77624 : xfarray_destroy(rp->pptr_recs);
207 77623 : rp->pptr_recs = NULL;
208 77623 : }
209 :
210 : /* Set up for a parent repair. */
211 : int
212 3416265 : xrep_setup_parent(
213 : struct xfs_scrub *sc)
214 : {
215 3416265 : struct xrep_parent *rp;
216 3416265 : int error;
217 :
218 3416265 : xchk_fsgates_enable(sc, XCHK_FSGATES_DIRENTS);
219 :
220 3415318 : rp = kvzalloc(sizeof(struct xrep_parent), XCHK_GFP_FLAGS);
221 3413831 : if (!rp)
222 : return -ENOMEM;
223 3413831 : rp->sc = sc;
224 3413831 : sc->buf = rp;
225 :
226 3413831 : error = xrep_tempfile_create(sc, S_IFREG);
227 3416275 : if (error)
228 : return error;
229 :
230 3416277 : return xrep_orphanage_try_create(sc);
231 : }
232 :
233 : /*
234 : * Scan all files in the filesystem for a child dirent that we can turn into
235 : * the dotdot entry for this directory.
236 : */
237 : STATIC int
238 0 : xrep_parent_find_dotdot(
239 : struct xrep_parent *rp)
240 : {
241 0 : struct xfs_scrub *sc = rp->sc;
242 0 : xfs_ino_t ino;
243 0 : unsigned int sick, checked;
244 0 : int error;
245 :
246 : /*
247 : * Avoid sick directories. There shouldn't be anyone else clearing the
248 : * directory's sick status.
249 : */
250 0 : xfs_inode_measure_sickness(sc->ip, &sick, &checked);
251 0 : if (sick & XFS_SICK_INO_DIR)
252 : return -EFSCORRUPTED;
253 :
254 0 : ino = xrep_findparent_self_reference(sc);
255 0 : if (ino != NULLFSINO) {
256 0 : xrep_findparent_scan_finish_early(&rp->pscan, ino);
257 0 : return 0;
258 : }
259 :
260 : /*
261 : * Drop the ILOCK on this directory so that we can scan for the dotdot
262 : * entry. Figure out who is going to be the parent of this directory,
263 : * then retake the ILOCK so that we can salvage directory entries.
264 : */
265 0 : xchk_iunlock(sc, XFS_ILOCK_EXCL);
266 :
267 : /* Does the VFS dcache have an answer for us? */
268 0 : ino = xrep_findparent_from_dcache(sc);
269 0 : if (ino != NULLFSINO) {
270 0 : error = xrep_findparent_confirm(sc, &ino);
271 0 : if (!error && ino != NULLFSINO) {
272 0 : xrep_findparent_scan_finish_early(&rp->pscan, ino);
273 0 : goto out_relock;
274 : }
275 : }
276 :
277 : /* Scan the entire filesystem for a parent. */
278 0 : error = xrep_findparent_scan(&rp->pscan);
279 0 : out_relock:
280 0 : xchk_ilock(sc, XFS_ILOCK_EXCL);
281 :
282 0 : return error;
283 : }
284 :
285 : /*
286 : * Add this stashed incore parent pointer to the temporary file.
287 : * The caller must hold the tempdir's IOLOCK, must not hold any ILOCKs, and
288 : * must not be in transaction context.
289 : */
290 : STATIC int
291 89324 : xrep_parent_replay_update(
292 : struct xrep_parent *rp,
293 : const struct xrep_pptr *pptr)
294 : {
295 89324 : struct xfs_scrub *sc = rp->sc;
296 89324 : int error;
297 :
298 89324 : rp->pptr.p_ino = pptr->p_ino;
299 89324 : rp->pptr.p_gen = pptr->p_gen;
300 89324 : rp->pptr.p_namelen = pptr->namelen;
301 89324 : xfs_parent_irec_hashname(sc->mp, &rp->pptr);
302 :
303 89324 : switch (pptr->action) {
304 89324 : case XREP_PPTR_ADD:
305 : /* Create parent pointer. */
306 89324 : trace_xrep_parent_replay_parentadd(sc->tempip, &rp->pptr);
307 :
308 89323 : error = xfs_parent_set(sc->tempip, sc->ip->i_ino, &rp->pptr,
309 : &rp->pptr_scratch);
310 89325 : if (error)
311 0 : return error;
312 : break;
313 0 : case XREP_PPTR_REMOVE:
314 : /* Remove parent pointer. */
315 0 : trace_xrep_parent_replay_parentremove(sc->tempip, &rp->pptr);
316 :
317 0 : error = xfs_parent_unset(sc->tempip, sc->ip->i_ino, &rp->pptr,
318 : &rp->pptr_scratch);
319 0 : if (error)
320 0 : return error;
321 : break;
322 0 : default:
323 0 : ASSERT(0);
324 0 : return -EIO;
325 : }
326 :
327 : return 0;
328 : }
329 :
330 : /*
331 : * Flush stashed parent pointer updates that have been recorded by the scanner.
332 : * This is done to reduce the memory requirements of the parent pointer
333 : * rebuild, since files can have a lot of hardlinks and the fs can be busy.
334 : *
335 : * Caller must not hold transactions or ILOCKs. Caller must hold the tempfile
336 : * IOLOCK.
337 : */
338 : STATIC int
339 77593 : xrep_parent_replay_updates(
340 : struct xrep_parent *rp)
341 : {
342 77593 : xfarray_idx_t array_cur;
343 77593 : int error;
344 :
345 77593 : mutex_lock(&rp->pscan.lock);
346 244511 : foreach_xfarray_idx(rp->pptr_recs, array_cur) {
347 89323 : struct xrep_pptr pptr;
348 :
349 89323 : error = xfarray_load(rp->pptr_recs, array_cur, &pptr);
350 89324 : if (error)
351 0 : goto out_unlock;
352 :
353 89324 : error = xfblob_load(rp->pptr_names, pptr.name_cookie,
354 89324 : rp->pptr.p_name, pptr.namelen);
355 89325 : if (error)
356 0 : goto out_unlock;
357 89325 : rp->pptr.p_name[MAXNAMELEN - 1] = 0;
358 89325 : mutex_unlock(&rp->pscan.lock);
359 :
360 89324 : error = xrep_parent_replay_update(rp, &pptr);
361 89325 : if (error)
362 0 : return error;
363 :
364 89325 : mutex_lock(&rp->pscan.lock);
365 : }
366 :
367 : /* Empty out both arrays now that we've added the entries. */
368 77595 : xfarray_truncate(rp->pptr_recs);
369 77580 : xfblob_truncate(rp->pptr_names);
370 77595 : mutex_unlock(&rp->pscan.lock);
371 77595 : return 0;
372 : out_unlock:
373 0 : mutex_unlock(&rp->pscan.lock);
374 0 : return error;
375 : }
376 :
377 : /*
378 : * Remember that we want to create a parent pointer in the tempfile. These
379 : * stashed actions will be replayed later.
380 : */
381 : STATIC int
382 89345 : xrep_parent_stash_parentadd(
383 : struct xrep_parent *rp,
384 : const struct xfs_name *name,
385 : const struct xfs_inode *dp)
386 : {
387 89345 : struct xrep_pptr pptr = {
388 : .action = XREP_PPTR_ADD,
389 89345 : .namelen = name->len,
390 89345 : .p_ino = dp->i_ino,
391 89345 : .p_gen = VFS_IC(dp)->i_generation,
392 : };
393 89345 : int error;
394 :
395 89345 : trace_xrep_parent_stash_parentadd(rp->sc->tempip, dp, name);
396 :
397 89345 : error = xfblob_store(rp->pptr_names, &pptr.name_cookie, name->name,
398 89345 : name->len);
399 89343 : if (error)
400 : return error;
401 :
402 89343 : return xfarray_append(rp->pptr_recs, &pptr);
403 : }
404 :
405 : /*
406 : * Remember that we want to remove a parent pointer from the tempfile. These
407 : * stashed actions will be replayed later.
408 : */
409 : STATIC int
410 0 : xrep_parent_stash_parentremove(
411 : struct xrep_parent *rp,
412 : const struct xfs_name *name,
413 : const struct xfs_inode *dp)
414 : {
415 0 : struct xrep_pptr pptr = {
416 : .action = XREP_PPTR_REMOVE,
417 0 : .namelen = name->len,
418 0 : .p_ino = dp->i_ino,
419 0 : .p_gen = VFS_IC(dp)->i_generation,
420 : };
421 0 : int error;
422 :
423 0 : trace_xrep_parent_stash_parentremove(rp->sc->tempip, dp, name);
424 :
425 0 : error = xfblob_store(rp->pptr_names, &pptr.name_cookie, name->name,
426 0 : name->len);
427 0 : if (error)
428 : return error;
429 :
430 0 : return xfarray_append(rp->pptr_recs, &pptr);
431 : }
432 :
433 : /*
434 : * Examine an entry of a directory. If this dirent leads us back to the file
435 : * whose parent pointers we're rebuilding, add a pptr to the temporary
436 : * directory.
437 : */
438 : STATIC int
439 2654988101 : xrep_parent_scan_dirent(
440 : struct xfs_scrub *sc,
441 : struct xfs_inode *dp,
442 : xfs_dir2_dataptr_t dapos,
443 : const struct xfs_name *name,
444 : xfs_ino_t ino,
445 : void *priv)
446 : {
447 2654988101 : struct xrep_parent *rp = priv;
448 2654988101 : int error;
449 :
450 : /* Dirent doesn't point to this directory. */
451 2654988101 : if (ino != rp->sc->ip->i_ino)
452 : return 0;
453 :
454 : /* No weird looking names. */
455 112261 : if (!xfs_dir2_namecheck(name->name, name->len))
456 : return -EFSCORRUPTED;
457 :
458 : /* No mismatching ftypes. */
459 112261 : if (name->type != xfs_mode_to_ftype(VFS_I(sc->ip)->i_mode))
460 : return -EFSCORRUPTED;
461 :
462 : /* Don't pick up dot or dotdot entries; we only want child dirents. */
463 201606 : if (xfs_dir2_samename(name, &xfs_name_dotdot) ||
464 89345 : xfs_dir2_samename(name, &xfs_name_dot))
465 22916 : return 0;
466 :
467 : /*
468 : * Transform this dirent into a parent pointer and queue it for later
469 : * addition to the temporary file.
470 : */
471 89345 : mutex_lock(&rp->pscan.lock);
472 89345 : error = xrep_parent_stash_parentadd(rp, name, dp);
473 89344 : mutex_unlock(&rp->pscan.lock);
474 89344 : return error;
475 : }
476 :
477 : /*
478 : * Decide if we want to look for dirents in this directory. Skip the file
479 : * being repaired and any files being used to stage repairs.
480 : */
481 : static inline bool
482 3505286455 : xrep_parent_want_scan(
483 : struct xrep_parent *rp,
484 : const struct xfs_inode *ip)
485 : {
486 3505286455 : return ip != rp->sc->ip && !xrep_is_tempfile(ip);
487 : }
488 :
489 : /*
490 : * Take ILOCK on a file that we want to scan.
491 : *
492 : * Select ILOCK_EXCL if the file is a directory with an unloaded data bmbt.
493 : * Otherwise, take ILOCK_SHARED.
494 : */
495 : static inline unsigned int
496 1755829384 : xrep_parent_scan_ilock(
497 : struct xrep_parent *rp,
498 : struct xfs_inode *ip)
499 : {
500 1755829384 : uint lock_mode = XFS_ILOCK_SHARED;
501 :
502 : /* Still need to take the shared ILOCK to advance the iscan cursor. */
503 1755829384 : if (!xrep_parent_want_scan(rp, ip))
504 224535 : goto lock;
505 :
506 2101909853 : if (S_ISDIR(VFS_I(ip)->i_mode) && xfs_need_iread_extents(&ip->i_df)) {
507 0 : lock_mode = XFS_ILOCK_EXCL;
508 0 : goto lock;
509 : }
510 :
511 1754505004 : lock:
512 1754729539 : xfs_ilock(ip, lock_mode);
513 1755333617 : return lock_mode;
514 : }
515 :
516 : /*
517 : * Scan this file for relevant child dirents that point to the file whose
518 : * parent pointers we're rebuilding.
519 : */
520 : STATIC int
521 1755463593 : xrep_parent_scan_file(
522 : struct xrep_parent *rp,
523 : struct xfs_inode *ip)
524 : {
525 1755463593 : unsigned int lock_mode;
526 1755463593 : int error = 0;
527 :
528 1755463593 : lock_mode = xrep_parent_scan_ilock(rp, ip);
529 :
530 1755115506 : if (!xrep_parent_want_scan(rp, ip))
531 224536 : goto scan_done;
532 :
533 1755375353 : if (S_ISDIR(VFS_I(ip)->i_mode)) {
534 347661623 : error = xchk_dir_walk(rp->sc, ip, xrep_parent_scan_dirent, rp);
535 347524485 : if (error)
536 0 : goto scan_done;
537 : }
538 :
539 1755238215 : scan_done:
540 1755462751 : xchk_iscan_mark_visited(&rp->pscan.iscan, ip);
541 1754088836 : xfs_iunlock(ip, lock_mode);
542 1756324610 : return error;
543 : }
544 :
545 : /* Decide if we've stashed too much pptr data in memory. */
546 : static inline bool
547 1756768736 : xrep_parent_want_flush_stashed(
548 : struct xrep_parent *rp)
549 : {
550 1756768736 : unsigned long long bytes;
551 :
552 1756768736 : bytes = xfarray_bytes(rp->pptr_recs) + xfblob_bytes(rp->pptr_names);
553 1756929131 : return bytes > XREP_PARENT_MAX_STASH_BYTES;
554 : }
555 :
556 : /*
557 : * Scan all directories in the filesystem to look for dirents that we can turn
558 : * into parent pointers.
559 : */
560 : STATIC int
561 77622 : xrep_parent_scan_dirtree(
562 : struct xrep_parent *rp)
563 : {
564 77622 : struct xfs_scrub *sc = rp->sc;
565 77622 : struct xfs_inode *ip;
566 77622 : int error;
567 :
568 : /*
569 : * Filesystem scans are time consuming. Drop the file ILOCK and all
570 : * other resources for the duration of the scan and hope for the best.
571 : * The live update hooks will keep our scan information up to date.
572 : */
573 77622 : xchk_trans_cancel(sc);
574 77621 : if (sc->ilock_flags & (XFS_ILOCK_SHARED | XFS_ILOCK_EXCL))
575 77622 : xchk_iunlock(sc, sc->ilock_flags & (XFS_ILOCK_SHARED |
576 : XFS_ILOCK_EXCL));
577 77620 : error = xchk_trans_alloc_empty(sc);
578 77622 : if (error)
579 : return error;
580 :
581 1756436184 : while ((error = xchk_iscan_iter(&rp->pscan.iscan, &ip)) == 1) {
582 1756354232 : bool flush;
583 :
584 1756354232 : error = xrep_parent_scan_file(rp, ip);
585 1757445905 : xchk_irele(sc, ip);
586 1756568426 : if (error)
587 : break;
588 :
589 : /* Flush stashed pptr updates to constrain memory usage. */
590 1756568426 : mutex_lock(&rp->pscan.lock);
591 1756830739 : flush = xrep_parent_want_flush_stashed(rp);
592 1756683762 : mutex_unlock(&rp->pscan.lock);
593 1756394396 : if (flush) {
594 0 : xchk_trans_cancel(sc);
595 :
596 0 : error = xrep_tempfile_iolock_polled(sc);
597 0 : if (error)
598 : break;
599 :
600 0 : error = xrep_parent_replay_updates(rp);
601 0 : xrep_tempfile_iounlock(sc);
602 0 : if (error)
603 : break;
604 :
605 0 : error = xchk_trans_alloc_empty(sc);
606 0 : if (error)
607 : break;
608 : }
609 :
610 1756394396 : if (xchk_should_terminate(sc, &error))
611 : break;
612 : }
613 77624 : xchk_iscan_iter_finish(&rp->pscan.iscan);
614 77624 : if (error) {
615 : /*
616 : * If we couldn't grab an inode that was busy with a state
617 : * change, change the error code so that we exit to userspace
618 : * as quickly as possible.
619 : */
620 29 : if (error == -EBUSY)
621 : return -ECANCELED;
622 29 : return error;
623 : }
624 :
625 : /*
626 : * Retake sc->ip's ILOCK now that we're done flushing stashed parent
627 : * pointers. We end this function with an empty transaction and the
628 : * ILOCK.
629 : */
630 77595 : xchk_ilock(rp->sc, XFS_ILOCK_EXCL);
631 77595 : return 0;
632 : }
633 :
634 : /*
635 : * Capture dirent updates being made by other threads which are relevant to the
636 : * file being repaired.
637 : */
638 : STATIC int
639 46626893 : xrep_parent_live_update(
640 : struct notifier_block *nb,
641 : unsigned long action,
642 : void *data)
643 : {
644 46626893 : struct xfs_dir_update_params *p = data;
645 46626893 : struct xrep_parent *rp;
646 46626893 : struct xfs_scrub *sc;
647 46626893 : int error;
648 :
649 46626893 : rp = container_of(nb, struct xrep_parent, pscan.hooks.dirent_hook.nb);
650 46626893 : sc = rp->sc;
651 :
652 : /*
653 : * This thread updated a dirent that points to the file that we're
654 : * repairing, so stash the update for replay against the temporary
655 : * file.
656 : */
657 46626893 : if (p->ip->i_ino == sc->ip->i_ino &&
658 0 : xchk_iscan_want_live_update(&rp->pscan.iscan, p->dp->i_ino)) {
659 0 : mutex_lock(&rp->pscan.lock);
660 0 : if (p->delta > 0)
661 0 : error = xrep_parent_stash_parentadd(rp, p->name, p->dp);
662 : else
663 0 : error = xrep_parent_stash_parentremove(rp, p->name,
664 : p->dp);
665 0 : if (!error)
666 0 : rp->saw_pptr_updates = true;
667 0 : mutex_unlock(&rp->pscan.lock);
668 0 : if (error)
669 0 : goto out_abort;
670 : }
671 :
672 : return NOTIFY_DONE;
673 : out_abort:
674 0 : xchk_iscan_abort(&rp->pscan.iscan);
675 0 : return NOTIFY_DONE;
676 : }
677 :
678 : /* Reset a directory's dotdot entry, if needed. */
679 : STATIC int
680 17736 : xrep_parent_reset_dotdot(
681 : struct xrep_parent *rp)
682 : {
683 17736 : struct xfs_scrub *sc = rp->sc;
684 17736 : xfs_ino_t ino;
685 17736 : unsigned int spaceres;
686 17736 : int error = 0;
687 :
688 17736 : ASSERT(sc->ilock_flags & XFS_ILOCK_EXCL);
689 :
690 17736 : error = xchk_dir_lookup(sc, sc->ip, &xfs_name_dotdot, &ino);
691 17737 : if (error || ino == rp->pscan.parent_ino)
692 : return error;
693 :
694 0 : xfs_trans_ijoin(sc->tp, sc->ip, 0);
695 :
696 0 : trace_xrep_parent_reset_dotdot(sc->ip, rp->pscan.parent_ino);
697 :
698 : /*
699 : * Reserve more space just in case we have to expand the dir. We're
700 : * allowed to exceed quota to repair inconsistent metadata.
701 : */
702 0 : spaceres = xfs_rename_space_res(sc->mp, 0, false, xfs_name_dotdot.len,
703 : false);
704 0 : error = xfs_trans_reserve_more_inode(sc->tp, sc->ip, spaceres, 0,
705 : true);
706 0 : if (error)
707 : return error;
708 :
709 0 : return xfs_dir_replace(sc->tp, sc->ip, &xfs_name_dotdot,
710 : rp->pscan.parent_ino, spaceres);
711 : }
712 :
713 : /*
714 : * Move the current file to the orphanage.
715 : *
716 : * Caller must hold IOLOCK_EXCL on @sc->ip, and no other inode locks. Upon
717 : * successful return, the scrub transaction will have enough extra reservation
718 : * to make the move; it will hold IOLOCK_EXCL and ILOCK_EXCL of @sc->ip and the
719 : * orphanage; and both inodes will be ijoined.
720 : */
721 : STATIC int
722 1 : xrep_parent_move_to_orphanage(
723 : struct xrep_parent *rp)
724 : {
725 1 : struct xfs_scrub *sc = rp->sc;
726 1 : xfs_ino_t orig_parent, new_parent;
727 1 : int error;
728 :
729 : /* No orphanage? We can't fix this. */
730 1 : if (!sc->orphanage)
731 : return -EFSCORRUPTED;
732 :
733 1 : if (S_ISDIR(VFS_I(sc->ip)->i_mode)) {
734 : /*
735 : * We are about to drop the ILOCK on sc->ip to lock the
736 : * orphanage and prepare for the adoption. Therefore, look up
737 : * the old dotdot entry for sc->ip so that we can compare it
738 : * after we re-lock sc->ip.
739 : */
740 0 : error = xchk_dir_lookup(sc, sc->ip, &xfs_name_dotdot,
741 : &orig_parent);
742 0 : if (error)
743 : return error;
744 : } else {
745 : /*
746 : * We haven't dropped the ILOCK since we swapped in the new
747 : * parent pointers, which means that the file cannot have been
748 : * moved in the directory tree, and there are no parents.
749 : */
750 1 : orig_parent = NULLFSINO;
751 : }
752 :
753 : /*
754 : * Because the orphanage is just another directory in the filesystem,
755 : * we must take its IOLOCK to coordinate with the VFS. We cannot take
756 : * an IOLOCK while holding an ILOCK, so we must drop the ILOCK. We
757 : * may have to drop the IOLOCK as well.
758 : */
759 1 : xchk_iunlock(sc, XFS_ILOCK_EXCL);
760 :
761 1 : error = xrep_adoption_init(sc, &rp->adoption);
762 1 : if (error)
763 : return error;
764 :
765 : /* If we can take the orphanage's iolock then we're ready to move. */
766 1 : if (!xrep_orphanage_ilock_nowait(sc, XFS_IOLOCK_EXCL)) {
767 1 : xchk_iunlock(sc, sc->ilock_flags);
768 1 : error = xrep_orphanage_iolock_two(sc);
769 1 : if (error)
770 0 : goto err_adoption;
771 : }
772 :
773 : /* Prepare for the adoption and lock both down. */
774 1 : error = xrep_adoption_prep(&rp->adoption);
775 1 : if (error)
776 0 : goto err_adoption;
777 :
778 1 : error = xrep_adoption_compute_name(&rp->adoption, rp->pptr.p_name);
779 1 : if (error)
780 0 : goto err_adoption;
781 :
782 : /*
783 : * Now that we've reacquired the ILOCK on sc->ip, look up the dotdot
784 : * entry again. If the parent changed or the child was unlinked while
785 : * the child directory was unlocked, we don't need to move the child to
786 : * the orphanage after all. For a non-directory, we have to scan for
787 : * the first parent pointer to see if one has been added.
788 : */
789 1 : if (S_ISDIR(VFS_I(sc->ip)->i_mode))
790 0 : error = xchk_dir_lookup(sc, sc->ip, &xfs_name_dotdot,
791 : &new_parent);
792 : else
793 1 : error = xrep_findparent_from_pptrs(sc, &new_parent);
794 1 : if (error)
795 0 : goto err_adoption;
796 1 : if (orig_parent != new_parent || VFS_I(sc->ip)->i_nlink == 0) {
797 1 : error = 0;
798 1 : goto err_adoption;
799 : }
800 :
801 0 : return xrep_adoption_commit(&rp->adoption);
802 1 : err_adoption:
803 1 : xrep_adoption_cancel(&rp->adoption, error);
804 1 : return error;
805 : }
806 :
807 : /* Ensure that the xattr value buffer is large enough. */
808 : STATIC int
809 77624 : xrep_parent_alloc_xattr_value(
810 : struct xrep_parent *rp,
811 : size_t bufsize)
812 : {
813 77624 : void *new_val;
814 :
815 77624 : if (rp->xattr_value_sz >= bufsize)
816 : return 0;
817 :
818 77624 : if (rp->xattr_value) {
819 0 : kvfree(rp->xattr_value);
820 0 : rp->xattr_value = NULL;
821 0 : rp->xattr_value_sz = 0;
822 : }
823 :
824 77624 : new_val = kvmalloc(bufsize, XCHK_GFP_FLAGS);
825 77624 : if (!new_val)
826 : return -ENOMEM;
827 :
828 77624 : rp->xattr_value = new_val;
829 77624 : rp->xattr_value_sz = bufsize;
830 77624 : return 0;
831 : }
832 :
833 : /* Retrieve the (remote) value of a non-pptr xattr. */
834 : STATIC int
835 0 : xrep_parent_fetch_xattr_remote(
836 : struct xrep_parent *rp,
837 : struct xfs_inode *ip,
838 : unsigned int attr_flags,
839 : const unsigned char *name,
840 : unsigned int namelen,
841 : unsigned int valuelen)
842 : {
843 0 : struct xfs_scrub *sc = rp->sc;
844 0 : struct xfs_da_args args = {
845 : .op_flags = XFS_DA_OP_NOTIME,
846 0 : .attr_filter = attr_flags & XFS_ATTR_NSP_ONDISK_MASK,
847 0 : .geo = sc->mp->m_attr_geo,
848 : .whichfork = XFS_ATTR_FORK,
849 : .dp = ip,
850 : .name = name,
851 : .namelen = namelen,
852 0 : .hashval = xfs_da_hashname(name, namelen),
853 0 : .trans = sc->tp,
854 : .valuelen = valuelen,
855 0 : .owner = ip->i_ino,
856 : };
857 0 : int error;
858 :
859 : /*
860 : * If we need a larger value buffer, try to allocate one. If that
861 : * fails, return with -EDEADLOCK to try harder.
862 : */
863 0 : error = xrep_parent_alloc_xattr_value(rp, valuelen);
864 0 : if (error == -ENOMEM)
865 : return -EDEADLOCK;
866 0 : if (error)
867 : return error;
868 :
869 0 : args.value = rp->xattr_value;
870 0 : return xfs_attr_get_ilocked(&args);
871 : }
872 :
873 : /* Stash non-pptr attributes for later replay into the temporary file. */
874 : STATIC int
875 98925 : xrep_parent_stash_xattr(
876 : struct xfs_scrub *sc,
877 : struct xfs_inode *ip,
878 : unsigned int attr_flags,
879 : const unsigned char *name,
880 : unsigned int namelen,
881 : const void *value,
882 : unsigned int valuelen,
883 : void *priv)
884 : {
885 98925 : struct xrep_parent_xattr key = {
886 : .valuelen = valuelen,
887 : .namelen = namelen,
888 98925 : .flags = attr_flags & XFS_ATTR_NSP_ONDISK_MASK,
889 : };
890 98925 : struct xrep_parent *rp = priv;
891 98925 : int error;
892 :
893 98925 : if (attr_flags & (XFS_ATTR_INCOMPLETE | XFS_ATTR_PARENT))
894 : return 0;
895 :
896 9600 : if (!value) {
897 0 : error = xrep_parent_fetch_xattr_remote(rp, ip, attr_flags,
898 : name, namelen, valuelen);
899 0 : if (error)
900 : return error;
901 :
902 0 : value = rp->xattr_value;
903 : }
904 :
905 9600 : trace_xrep_parent_stash_xattr(rp->sc->tempip, key.flags, (void *)name,
906 9600 : key.namelen, key.valuelen);
907 :
908 9600 : error = xfblob_store(rp->xattr_blobs, &key.name_cookie, name,
909 9600 : key.namelen);
910 9600 : if (error)
911 : return error;
912 :
913 9600 : error = xfblob_store(rp->xattr_blobs, &key.value_cookie, value,
914 : key.valuelen);
915 9600 : if (error)
916 : return error;
917 :
918 9600 : return xfarray_append(rp->xattr_records, &key);
919 : }
920 :
921 : /* Insert one xattr key/value. */
922 : STATIC int
923 9600 : xrep_parent_insert_xattr(
924 : struct xrep_parent *rp,
925 : const struct xrep_parent_xattr *key)
926 : {
927 9600 : struct xfs_da_args args = {
928 9600 : .dp = rp->sc->tempip,
929 9600 : .attr_filter = key->flags,
930 9600 : .namelen = key->namelen,
931 9600 : .valuelen = key->valuelen,
932 : .op_flags = XFS_DA_OP_NOTIME,
933 9600 : .owner = rp->sc->ip->i_ino,
934 : };
935 9600 : int error;
936 :
937 9600 : ASSERT(!(key->flags & XFS_ATTR_PARENT));
938 :
939 : /*
940 : * Grab pointers to the scrub buffer so that we can use them to insert
941 : * attrs into the temp file.
942 : */
943 9600 : args.name = rp->xattr_name;
944 9600 : args.value = rp->xattr_value;
945 :
946 : /*
947 : * The attribute name is stored near the end of the in-core buffer,
948 : * though we reserve one more byte to ensure null termination.
949 : */
950 9600 : rp->xattr_name[XATTR_NAME_MAX] = 0;
951 :
952 9600 : error = xfblob_load(rp->xattr_blobs, key->name_cookie, rp->xattr_name,
953 9600 : key->namelen);
954 9600 : if (error)
955 : return error;
956 :
957 9600 : error = xfblob_free(rp->xattr_blobs, key->name_cookie);
958 9600 : if (error)
959 : return error;
960 :
961 9600 : error = xfblob_load(rp->xattr_blobs, key->value_cookie, args.value,
962 9600 : key->valuelen);
963 9600 : if (error)
964 : return error;
965 :
966 9600 : error = xfblob_free(rp->xattr_blobs, key->value_cookie);
967 9600 : if (error)
968 : return error;
969 :
970 9600 : rp->xattr_name[key->namelen] = 0;
971 :
972 9600 : trace_xrep_parent_insert_xattr(rp->sc->tempip, key->flags,
973 9600 : rp->xattr_name, key->namelen, key->valuelen);
974 :
975 9600 : error = xfs_attr_set(&args);
976 9600 : if (error) {
977 0 : ASSERT(error != -EEXIST);
978 0 : return error;
979 : }
980 :
981 : return 0;
982 : }
983 :
984 : /*
985 : * Periodically flush salvaged attributes to the temporary file. This is done
986 : * to reduce the memory requirements of the xattr rebuild because files can
987 : * contain millions of attributes.
988 : */
989 : STATIC int
990 7831 : xrep_parent_flush_xattrs(
991 : struct xrep_parent *rp)
992 : {
993 7831 : xfarray_idx_t array_cur;
994 7831 : int error;
995 :
996 : /*
997 : * Entering this function, the scrub context has a reference to the
998 : * inode being repaired, the temporary file, and the empty scrub
999 : * transaction that we created for the xattr scan. We hold ILOCK_EXCL
1000 : * on the inode being repaired.
1001 : *
1002 : * To constrain kernel memory use, we occasionally flush salvaged
1003 : * xattrs from the xfarray and xfblob structures into the temporary
1004 : * file in preparation for swapping the xattr structures at the end.
1005 : * Updating the temporary file requires a transaction, so we commit the
1006 : * scrub transaction and drop the ILOCK so that xfs_attr_set can
1007 : * allocate whatever transaction it wants.
1008 : *
1009 : * We still hold IOLOCK_EXCL on the inode being repaired, which
1010 : * prevents anyone from adding xattrs (or parent pointers) while we're
1011 : * flushing.
1012 : */
1013 7831 : xchk_trans_cancel(rp->sc);
1014 7831 : xchk_iunlock(rp->sc, XFS_ILOCK_EXCL);
1015 :
1016 : /*
1017 : * Take the IOLOCK of the temporary file while we modify xattrs. This
1018 : * isn't strictly required because the temporary file is never revealed
1019 : * to userspace, but we follow the same locking rules. We still hold
1020 : * sc->ip's IOLOCK.
1021 : */
1022 7831 : error = xrep_tempfile_iolock_polled(rp->sc);
1023 7831 : if (error)
1024 : return error;
1025 :
1026 : /* Add all the salvaged attrs to the temporary file. */
1027 17431 : foreach_xfarray_idx(rp->xattr_records, array_cur) {
1028 9600 : struct xrep_parent_xattr key;
1029 :
1030 9600 : error = xfarray_load(rp->xattr_records, array_cur, &key);
1031 9600 : if (error)
1032 0 : return error;
1033 :
1034 9600 : error = xrep_parent_insert_xattr(rp, &key);
1035 9600 : if (error)
1036 0 : return error;
1037 : }
1038 :
1039 : /* Empty out both arrays now that we've added the entries. */
1040 7831 : xfarray_truncate(rp->xattr_records);
1041 7831 : xfblob_truncate(rp->xattr_blobs);
1042 :
1043 7831 : xrep_tempfile_iounlock(rp->sc);
1044 :
1045 : /* Recreate the empty transaction and relock the inode. */
1046 7831 : error = xchk_trans_alloc_empty(rp->sc);
1047 7831 : if (error)
1048 : return error;
1049 7831 : xchk_ilock(rp->sc, XFS_ILOCK_EXCL);
1050 7831 : return 0;
1051 : }
1052 :
1053 : /* Decide if we've stashed too much xattr data in memory. */
1054 : static inline bool
1055 0 : xrep_parent_want_flush_xattrs(
1056 : struct xrep_parent *rp)
1057 : {
1058 0 : unsigned long long bytes;
1059 :
1060 0 : bytes = xfarray_bytes(rp->xattr_records) +
1061 0 : xfblob_bytes(rp->xattr_blobs);
1062 0 : return bytes > XREP_PARENT_XATTR_MAX_STASH_BYTES;
1063 : }
1064 :
1065 : /* Flush staged attributes to the temporary file if we're over the limit. */
1066 : STATIC int
1067 0 : xrep_parent_try_flush_xattrs(
1068 : struct xfs_scrub *sc,
1069 : void *priv)
1070 : {
1071 0 : struct xrep_parent *rp = priv;
1072 0 : int error;
1073 :
1074 0 : if (!xrep_parent_want_flush_xattrs(rp))
1075 : return 0;
1076 :
1077 0 : error = xrep_parent_flush_xattrs(rp);
1078 0 : if (error)
1079 : return error;
1080 :
1081 : /*
1082 : * If there were any parent pointer updates to the xattr structure
1083 : * while we dropped the ILOCK, the xattr structure is now stale.
1084 : * Signal to the attr copy process that we need to start over, but
1085 : * this time without opportunistic attr flushing.
1086 : *
1087 : * This is unlikely to happen, so we're ok with restarting the copy.
1088 : */
1089 0 : mutex_lock(&rp->pscan.lock);
1090 0 : if (rp->saw_pptr_updates)
1091 0 : error = -ESTALE;
1092 0 : mutex_unlock(&rp->pscan.lock);
1093 0 : return error;
1094 : }
1095 :
1096 : /* Copy all the non-pptr extended attributes into the temporary file. */
1097 : STATIC int
1098 77595 : xrep_parent_copy_xattrs(
1099 : struct xrep_parent *rp)
1100 : {
1101 77595 : struct xfs_scrub *sc = rp->sc;
1102 77595 : int error;
1103 :
1104 : /*
1105 : * Clear the pptr updates flag. We hold sc->ip ILOCKed, so there
1106 : * can't be any parent pointer updates in progress.
1107 : */
1108 77595 : mutex_lock(&rp->pscan.lock);
1109 77595 : rp->saw_pptr_updates = false;
1110 77595 : mutex_unlock(&rp->pscan.lock);
1111 :
1112 : /* Copy xattrs, stopping periodically to flush the incore buffers. */
1113 77594 : error = xchk_xattr_walk(sc, sc->ip, xrep_parent_stash_xattr,
1114 : xrep_parent_try_flush_xattrs, rp);
1115 77595 : if (error && error != -ESTALE)
1116 : return error;
1117 :
1118 77595 : if (error == -ESTALE) {
1119 : /*
1120 : * The xattr copy collided with a parent pointer update.
1121 : * Restart the copy, but this time hold the ILOCK all the way
1122 : * to the end to lock out any directory parent pointer updates.
1123 : */
1124 0 : error = xchk_xattr_walk(sc, sc->ip, xrep_parent_stash_xattr,
1125 : NULL, rp);
1126 0 : if (error)
1127 : return error;
1128 : }
1129 :
1130 : /* Flush any remaining stashed xattrs to the temporary file. */
1131 77595 : if (xfarray_bytes(rp->xattr_records) == 0)
1132 : return 0;
1133 :
1134 7831 : return xrep_parent_flush_xattrs(rp);
1135 : }
1136 :
1137 : /*
1138 : * Ensure that @sc->ip and @sc->tempip both have attribute forks before we
1139 : * head into the attr fork swap transaction. All files on a filesystem with
1140 : * parent pointers must have an attr fork because the parent pointer code
1141 : * does not itself add attribute forks.
1142 : *
1143 : * Note: Unlinkable unlinked files don't need one, but the overhead of having
1144 : * an unnecessary attr fork is not justified by the additional code complexity
1145 : * that would be needed to track that state correctly.
1146 : */
1147 : STATIC int
1148 77594 : xrep_parent_ensure_attr_fork(
1149 : struct xrep_parent *rp)
1150 : {
1151 77594 : struct xfs_scrub *sc = rp->sc;
1152 77594 : int error;
1153 :
1154 77594 : error = xfs_bmap_add_attrfork(sc->tempip,
1155 : sizeof(struct xfs_attr_sf_hdr), 1);
1156 77595 : if (error)
1157 : return error;
1158 77595 : return xfs_bmap_add_attrfork(sc->ip, sizeof(struct xfs_attr_sf_hdr), 1);
1159 : }
1160 :
1161 : /*
1162 : * Finish replaying stashed parent pointer updates, allocate a transaction for
1163 : * swapping extents, and take the ILOCKs of both files before we commit the new
1164 : * attribute structure.
1165 : */
1166 : STATIC int
1167 77593 : xrep_parent_finalize_tempfile(
1168 : struct xrep_parent *rp)
1169 : {
1170 77593 : struct xfs_scrub *sc = rp->sc;
1171 77593 : int error;
1172 :
1173 77593 : error = xrep_parent_replay_updates(rp);
1174 77594 : if (error)
1175 : return error;
1176 :
1177 77594 : error = xrep_parent_ensure_attr_fork(rp);
1178 77595 : if (error)
1179 : return error;
1180 :
1181 77594 : error = xrep_tempswap_trans_alloc(sc, XFS_ATTR_FORK, &rp->tx);
1182 77579 : if (error)
1183 : return error;
1184 :
1185 : /*
1186 : * We rely on the caller's hold on @sc->ip's IOLOCK_EXCL to quiesce all
1187 : * possible parent pointer updates during the time when we did not hold
1188 : * the ILOCK. There should not be any pptr updates to replay, but
1189 : * check anyway.
1190 : */
1191 77578 : if (xfarray_length(rp->pptr_recs) != 0) {
1192 0 : ASSERT(xfarray_length(rp->pptr_recs) == 0);
1193 0 : return -EFSCORRUPTED;
1194 : }
1195 :
1196 : return 0;
1197 : }
1198 :
1199 : /*
1200 : * Replay all the stashed parent pointers into the temporary file, copy all
1201 : * the non-pptr xattrs from the file being repaired into the temporary file,
1202 : * and swap the extents atomically.
1203 : */
1204 : STATIC int
1205 77594 : xrep_parent_rebuild_pptrs(
1206 : struct xrep_parent *rp)
1207 : {
1208 77594 : struct xfs_scrub *sc = rp->sc;
1209 77594 : xfs_ino_t parent_ino = NULLFSINO;
1210 77594 : int error;
1211 :
1212 : /*
1213 : * Copy non-ppttr xattrs from the file being repaired into the
1214 : * temporary file's xattr structure. We hold sc->ip's IOLOCK, which
1215 : * prevents setxattr/removexattr calls from occurring, but renames
1216 : * update the parent pointers without holding IOLOCK. If we detect
1217 : * stale attr structures, we restart the scan but only flush at the
1218 : * end.
1219 : */
1220 77594 : error = xrep_parent_copy_xattrs(rp);
1221 77595 : if (error)
1222 : return error;
1223 :
1224 : /*
1225 : * Cancel the empty transaction that we used to walk and copy attrs,
1226 : * and drop the ILOCK so that we can take the IOLOCK on the temporary
1227 : * file. We still hold sc->ip's IOLOCK.
1228 : */
1229 77594 : xchk_trans_cancel(sc);
1230 77595 : xchk_iunlock(sc, XFS_ILOCK_EXCL);
1231 :
1232 77594 : error = xrep_tempfile_iolock_polled(sc);
1233 77594 : if (error)
1234 : return error;
1235 :
1236 77592 : error = xrep_parent_finalize_tempfile(rp);
1237 77583 : if (error)
1238 : return error;
1239 :
1240 : /* Last chance to abort before we start committing pptr fixes. */
1241 77583 : if (xchk_should_terminate(sc, &error))
1242 0 : return error;
1243 :
1244 77585 : if (xchk_iscan_aborted(&rp->pscan.iscan))
1245 : return -ECANCELED;
1246 :
1247 : /*
1248 : * Swap the attr fork and junk the old attr fork contents, which are
1249 : * now in the tempfile.
1250 : */
1251 77582 : error = xrep_xattr_swap(sc, &rp->tx);
1252 77589 : if (error)
1253 : return error;
1254 77589 : error = xrep_xattr_reset_tempfile_fork(sc);
1255 77594 : if (error)
1256 : return error;
1257 :
1258 : /*
1259 : * Roll transaction to detach both inodes from the transaction, then
1260 : * drop the ILOCK of the temporary file since we no longer need it.
1261 : */
1262 77594 : error = xfs_trans_roll(&sc->tp);
1263 77595 : if (error)
1264 : return error;
1265 77594 : xrep_tempfile_iunlock(sc);
1266 :
1267 : /*
1268 : * We've committed the new parent pointers. Find at least one parent
1269 : * so that we can decide if we're moving this file to the orphanage.
1270 : * For this purpose, root directories are their own parents.
1271 : */
1272 77591 : if (sc->ip == sc->mp->m_rootip) {
1273 887 : xrep_findparent_scan_found(&rp->pscan, sc->ip->i_ino);
1274 : } else {
1275 76704 : error = xrep_findparent_from_pptrs(sc, &parent_ino);
1276 76688 : if (error)
1277 : return error;
1278 76688 : if (parent_ino != NULLFSINO)
1279 76688 : xrep_findparent_scan_found(&rp->pscan, parent_ino);
1280 : }
1281 : return 0;
1282 : }
1283 :
1284 : /*
1285 : * Commit the new parent pointer structure (currently only the dotdot entry) to
1286 : * the file that we're repairing.
1287 : */
1288 : STATIC int
1289 77592 : xrep_parent_rebuild_tree(
1290 : struct xrep_parent *rp)
1291 : {
1292 77592 : int error;
1293 :
1294 77592 : if (xfs_has_parent(rp->sc->mp)) {
1295 77594 : error = xrep_parent_rebuild_pptrs(rp);
1296 77588 : if (error)
1297 : return error;
1298 : }
1299 :
1300 77586 : if (rp->pscan.parent_ino == NULLFSINO)
1301 1 : return xrep_parent_move_to_orphanage(rp);
1302 :
1303 77585 : if (!S_ISDIR(VFS_I(rp->sc->ip)->i_mode))
1304 : return 0;
1305 :
1306 17736 : return xrep_parent_reset_dotdot(rp);
1307 : }
1308 :
1309 : /* Set up the filesystem scan so we can look for parents. */
1310 : STATIC int
1311 77623 : xrep_parent_setup_scan(
1312 : struct xrep_parent *rp)
1313 : {
1314 77623 : struct xfs_scrub *sc = rp->sc;
1315 77623 : char *descr;
1316 77623 : struct xfs_da_geometry *geo = sc->mp->m_attr_geo;
1317 77623 : int max_len;
1318 77623 : int error;
1319 :
1320 77623 : if (!xfs_has_parent(sc->mp))
1321 0 : return xrep_findparent_scan_start(sc, &rp->pscan);
1322 :
1323 : /* Buffers for copying non-pptr attrs to the tempfile */
1324 77623 : rp->xattr_name = kvmalloc(XATTR_NAME_MAX + 1, XCHK_GFP_FLAGS);
1325 77623 : if (!rp->xattr_name)
1326 : return -ENOMEM;
1327 :
1328 : /*
1329 : * Allocate enough memory to handle loading local attr values from the
1330 : * xfblob data while flushing stashed attrs to the temporary file.
1331 : * We only realloc the buffer when salvaging remote attr values, so
1332 : * TRY_HARDER means we allocate the maximal attr value size.
1333 : */
1334 77623 : if (sc->flags & XCHK_TRY_HARDER)
1335 : max_len = XATTR_SIZE_MAX;
1336 : else
1337 77624 : max_len = xfs_attr_leaf_entsize_local_max(geo->blksize);
1338 77623 : error = xrep_parent_alloc_xattr_value(rp, max_len);
1339 77624 : if (error)
1340 0 : goto out_xattr_name;
1341 :
1342 : /* Set up some staging memory for logging parent pointer updates. */
1343 77624 : descr = xchk_xfile_ino_descr(sc, "parent pointer entries");
1344 77623 : error = xfarray_create(descr, 0, sizeof(struct xrep_pptr),
1345 : &rp->pptr_recs);
1346 77624 : kfree(descr);
1347 77624 : if (error)
1348 0 : goto out_xattr_value;
1349 :
1350 77624 : descr = xchk_xfile_ino_descr(sc, "parent pointer names");
1351 77624 : error = xfblob_create(descr, &rp->pptr_names);
1352 77624 : kfree(descr);
1353 77624 : if (error)
1354 0 : goto out_recs;
1355 :
1356 : /* Set up some storage for copying attrs before the swap */
1357 77624 : descr = xchk_xfile_ino_descr(sc,
1358 : "parent pointer retained xattr entries");
1359 77624 : error = xfarray_create(descr, 0, sizeof(struct xrep_parent_xattr),
1360 : &rp->xattr_records);
1361 77624 : kfree(descr);
1362 77624 : if (error)
1363 0 : goto out_names;
1364 :
1365 77624 : descr = xchk_xfile_ino_descr(sc,
1366 : "parent pointer retained xattr values");
1367 77624 : error = xfblob_create(descr, &rp->xattr_blobs);
1368 77624 : kfree(descr);
1369 77624 : if (error)
1370 0 : goto out_attr_keys;
1371 :
1372 77624 : error = __xrep_findparent_scan_start(sc, &rp->pscan,
1373 : xrep_parent_live_update);
1374 77624 : if (error)
1375 0 : goto out_attr_values;
1376 :
1377 : return 0;
1378 :
1379 : out_attr_values:
1380 0 : xfblob_destroy(rp->xattr_blobs);
1381 0 : rp->xattr_blobs = NULL;
1382 0 : out_attr_keys:
1383 0 : xfarray_destroy(rp->xattr_records);
1384 0 : rp->xattr_records = NULL;
1385 0 : out_names:
1386 0 : xfblob_destroy(rp->pptr_names);
1387 0 : rp->pptr_names = NULL;
1388 0 : out_recs:
1389 0 : xfarray_destroy(rp->pptr_recs);
1390 0 : rp->pptr_recs = NULL;
1391 0 : out_xattr_value:
1392 0 : kvfree(rp->xattr_value);
1393 0 : rp->xattr_value = NULL;
1394 0 : out_xattr_name:
1395 0 : kvfree(rp->xattr_name);
1396 0 : rp->xattr_name = NULL;
1397 0 : return error;
1398 : }
1399 :
1400 : int
1401 3327080 : xrep_parent(
1402 : struct xfs_scrub *sc)
1403 : {
1404 3327080 : struct xrep_parent *rp = sc->buf;
1405 3327080 : int error;
1406 :
1407 : /*
1408 : * When the parent pointers feature is enabled, repairs are committed
1409 : * by atomically committing a new xattr structure and reaping the old
1410 : * attr fork. Reaping requires rmap to be enabled.
1411 : */
1412 3327080 : if (xfs_has_parent(sc->mp) && !xfs_has_rmapbt(sc->mp))
1413 : return -EOPNOTSUPP;
1414 :
1415 77683 : error = xrep_parent_setup_scan(rp);
1416 77624 : if (error)
1417 : return error;
1418 :
1419 77624 : if (xfs_has_parent(sc->mp))
1420 77624 : error = xrep_parent_scan_dirtree(rp);
1421 : else
1422 0 : error = xrep_parent_find_dotdot(rp);
1423 77624 : if (error)
1424 29 : goto out_teardown;
1425 :
1426 : /* Last chance to abort before we start committing dotdot fixes. */
1427 77595 : if (xchk_should_terminate(sc, &error))
1428 0 : goto out_teardown;
1429 :
1430 77594 : error = xrep_parent_rebuild_tree(rp);
1431 77582 : if (error)
1432 : goto out_teardown;
1433 :
1434 77582 : out_teardown:
1435 77611 : xrep_parent_teardown(rp);
1436 77614 : return error;
1437 : }
|