1 /* 2 * Copyright 2005 Sun Microsystems, Inc. All rights reserved. 3 * Use is subject to license terms. 4 */ 5 6 /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ 7 /* All Rights Reserved */ 8 9 /* 10 * Copyright (c) 1980, 1986, 1990 The Regents of the University of California. 11 * All rights reserved. 12 * 13 * Redistribution and use in source and binary forms are permitted 14 * provided that: (1) source distributions retain this entire copyright 15 * notice and comment, and (2) distributions including binaries display 16 * the following acknowledgement: ``This product includes software 17 * developed by the University of California, Berkeley and its contributors'' 18 * in the documentation or other materials provided with the distribution 19 * and in all advertising materials mentioning features or use of this 20 * software. Neither the name of the University nor the names of its 21 * contributors may be used to endorse or promote products derived 22 * from this software without specific prior written permission. 23 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 24 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 25 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 26 */ 27 28 #include <stdio.h> 29 #include <stdlib.h> 30 #include <unistd.h> 31 #include <string.h> 32 #include <sys/param.h> 33 #include <sys/types.h> 34 #include <sys/mntent.h> 35 #include <sys/fs/ufs_fs.h> 36 #include <sys/vnode.h> 37 #include <sys/fs/ufs_inode.h> 38 #define _KERNEL 39 #include <sys/fs/ufs_fsdir.h> 40 #undef _KERNEL 41 #include "fsck.h" 42 43 static int pass3acheck(struct inodesc *); 44 static void setcurino(struct inodesc *, struct dinode *, struct inoinfo *); 45 46 void 47 pass3a(void) 48 { 49 caddr_t flow; 50 struct inoinfo **inpp, *inp; 51 fsck_ino_t orphan; 52 int loopcnt; 53 int state; 54 struct shadowclientinfo *sci, *sci_victim, *sci_prev, **sci_rootp; 55 struct inodesc curino; 56 struct dinode *dp; 57 struct inodesc idesc; 58 char namebuf[MAXNAMLEN + 1]; 59 60 for (inpp = &inpsort[inplast - 1]; inpp >= inpsort; inpp--) { 61 inp = *inpp; 62 state = statemap[inp->i_number]; 63 if (inp->i_number == UFSROOTINO || 64 (inp->i_parent != 0 && !S_IS_DUNFOUND(state))) 65 continue; 66 if (state == DCLEAR || state == USTATE || (state & INORPHAN)) 67 continue; 68 /* 69 * If we are running with logging and we come 70 * across unreferenced directories, we just leave 71 * them in DSTATE which will cause them to be pitched 72 * in pass 4. 73 */ 74 if (preen && !iscorrupt && islog && S_IS_DUNFOUND(state)) { 75 if (inp->i_dotdot >= UFSROOTINO) { 76 LINK_RANGE(flow, lncntp[inp->i_dotdot], 1); 77 if (flow != NULL) { 78 dp = ginode(inp->i_dotdot); 79 LINK_CLEAR(flow, inp->i_dotdot, 80 dp->di_mode, &idesc); 81 if (statemap[inp->i_dotdot] == USTATE) 82 continue; 83 } 84 TRACK_LNCNTP(inp->i_dotdot, 85 lncntp[inp->i_dotdot]++); 86 } 87 continue; 88 } 89 90 for (loopcnt = 0; ; loopcnt++) { 91 orphan = inp->i_number; 92 /* 93 * Skip out if we aren't connected to the name 94 * space, or our parent is connected, or we've 95 * looked at too many directories. Our parent 96 * being connected means that orphan is the 97 * first ancestor of *inpp with questionable 98 * antecedents. 99 */ 100 if (inp->i_parent == 0 || 101 !INO_IS_DUNFOUND(inp->i_parent) || 102 loopcnt > numdirs) 103 break; 104 inp = getinoinfo(inp->i_parent); 105 /* 106 * Can't happen, because a non-zero parent's already 107 * been seen and therefore cached. 108 */ 109 if (inp == NULL) 110 errexit("pass3 could not find cached " 111 "inode I=%d\n", 112 inp->i_parent); 113 } 114 115 /* 116 * Already did this one. Don't bother the user 117 * with redundant questions. 118 */ 119 if (statemap[orphan] & INORPHAN) 120 continue; 121 122 /* 123 * A link count of 0 with parent and .. inodes of 0 124 * indicates a partly deleted directory. 125 * Clear it. 126 */ 127 dp = ginode(orphan); 128 if (dp->di_nlink == 0 && inp->i_dotdot == 0 && 129 inp->i_parent == 0) { 130 /* 131 * clri() just uses curino.id_number; in other 132 * words, it won't use the callback that setcurino() 133 * puts in. 134 */ 135 setcurino(&curino, dp, inp); 136 clri(&curino, "UNREF", CLRI_VERBOSE, CLRI_NOP_OK); 137 138 /* 139 * If we didn't clear it, at least mark it so 140 * we don't waste time on it again. 141 */ 142 if (statemap[orphan] != USTATE) { 143 statemap[orphan] |= INORPHAN; 144 } 145 continue; 146 } 147 148 /* 149 * We can call linkup() multiple times on the same directory 150 * inode, if we were told not to reconnect it the first time. 151 * This is because we find it as a disconnected parent of 152 * of its children (and mark it found), and then finally get 153 * to it in the inpsort array. This is better than in the 154 * past, where we'd call it every time we found it as a 155 * child's parent. Ideally, we'd suppress even the second 156 * query, but that confuses pass 4's interpretation of 157 * the state flags. 158 */ 159 if (loopcnt <= countdirs) { 160 if (linkup(orphan, inp->i_dotdot, NULL)) { 161 /* 162 * Bookkeeping for any sort of relinked 163 * directory. 164 */ 165 inp->i_dotdot = lfdir; 166 inp->i_parent = inp->i_dotdot; 167 statemap[orphan] &= ~(INORPHAN); 168 } else { 169 statemap[orphan] |= INORPHAN; 170 } 171 propagate(); 172 continue; 173 } 174 175 /* 176 * We visited more directories than exist in the 177 * filesystem. The only way to do that is if there's 178 * a loop. 179 */ 180 pfatal("ORPHANED DIRECTORY LOOP DETECTED I=%d\n", orphan); 181 182 /* 183 * Can never get here with inp->i_parent zero, because 184 * of the interactions between the for() and the 185 * if (loopcnt <= countdirs) above. 186 */ 187 init_inodesc(&idesc); 188 idesc.id_type = DATA; 189 idesc.id_number = inp->i_parent; 190 idesc.id_parent = orphan; 191 idesc.id_func = findname; 192 idesc.id_name = namebuf; 193 namebuf[0] = '\0'; 194 195 /* 196 * Theoretically, this lookup via ckinode can't fail 197 * (if orphan doesn't exist in i_parent, then i_parent 198 * would not have been filled in by pass2check()). 199 * However, if we're interactive, we want to at least 200 * attempt to continue. The worst case is that it 201 * gets reconnected as #nnn into lost+found instead of 202 * to its old parent with its old name. 203 */ 204 if ((ckinode(ginode(inp->i_parent), 205 &idesc, CKI_TRAVERSE) & FOUND) == 0) 206 pfatal("COULD NOT FIND NAME IN PARENT DIRECTORY"); 207 208 if (linkup(orphan, inp->i_parent, namebuf)) { 209 if (cleardirentry(inp->i_parent, orphan) & FOUND) { 210 LFDIR_LINK_RANGE_NORVAL(flow, lncntp[lfdir], 1, 211 &idesc); 212 TRACK_LNCNTP(orphan, lncntp[orphan]++); 213 } 214 inp->i_parent = inp->i_dotdot = lfdir; 215 LFDIR_LINK_RANGE_NORVAL(flow, lncntp[lfdir], -1, 216 &idesc); 217 TRACK_LNCNTP(lfdir, lncntp[lfdir]--); 218 statemap[orphan] = DFOUND; 219 } else { 220 /* 221 * Represents a on-disk leak, not an inconsistency, 222 * so don't set iscorrupt. Such leaks are harmless 223 * in the context of discrepancies that the kernel 224 * will panic over. 225 * 226 * We don't care if tsearch() returns non-NULL 227 * != orphan, since there's no dynamic memory 228 * to free here. 229 */ 230 if (tsearch((void *)orphan, &limbo_dirs, 231 ino_t_cmp) == NULL) 232 errexit("out of memory"); 233 statemap[orphan] |= INORPHAN; 234 continue; 235 } 236 propagate(); 237 } 238 239 /* 240 * The essence of the inner loop is to update the inode of 241 * every shadow or attribute inode's lncntp[] by the number of 242 * links we've found to them in pass 2 and above. Logically, 243 * all that is needed is just the one line: 244 * 245 * lncntp[sci->shadow] -= sci->totalclients; 246 * 247 * However, there's the possibility of wrapping the link count 248 * (this is especially true for shadows, which are expected to 249 * be shared amongst many files). This means that we have to 250 * range-check before changing anything, and if the check 251 * fails, offer to clear the shadow or attribute. If we do 252 * clear it, then we have to remove it from the linked list of 253 * all of the type of inodes that we're going through. 254 * 255 * Just to make things a little more complicated, these are 256 * singly-linked lists, so we have to do all the extra 257 * bookkeeping that goes along with that as well. 258 * 259 * The only connection between the shadowclientinfo and 260 * attrclientinfo lists is that they use the same underlying 261 * struct. Both need this scan, so the outer loop is just to 262 * pick which one we're working on at the moment. There is no 263 * requirement as to which of these lists is scanned first. 264 */ 265 for (loopcnt = 0; loopcnt < 2; loopcnt++) { 266 if (loopcnt == 0) 267 sci_rootp = &shadowclientinfo; 268 else 269 sci_rootp = &attrclientinfo; 270 271 sci = *sci_rootp; 272 sci_prev = NULL; 273 while (sci != NULL) { 274 sci_victim = NULL; 275 LINK_RANGE(flow, lncntp[sci->shadow], 276 -(sci->totalClients)); 277 if (flow != NULL) { 278 /* 279 * Overflowed the link count. 280 */ 281 dp = ginode(sci->shadow); 282 LINK_CLEAR(flow, sci->shadow, dp->di_mode, 283 &idesc); 284 if (statemap[sci->shadow] == USTATE) { 285 /* 286 * It's been cleared, fix the 287 * lists. 288 */ 289 if (sci_prev == NULL) { 290 *sci_rootp = sci->next; 291 } else { 292 sci_prev->next = sci->next; 293 } 294 sci_victim = sci; 295 } 296 } 297 298 /* 299 * If we did not clear the shadow, then we 300 * need to update the count and advance the 301 * previous pointer. Otherwise, finish the 302 * clean up once we're done with the struct. 303 */ 304 if (sci_victim == NULL) { 305 TRACK_LNCNTP(sci->shadow, 306 lncntp[sci->shadow] -= sci->totalClients); 307 sci_prev = sci; 308 } 309 sci = sci->next; 310 if (sci_victim != NULL) 311 deshadow(sci_victim, NULL); 312 } 313 } 314 } 315 316 317 /* 318 * This is used to verify the cflags of files 319 * under a directory that used to be an attrdir. 320 */ 321 322 static int 323 pass3acheck(struct inodesc *idesc) 324 { 325 struct direct *dirp = idesc->id_dirp; 326 int n = 0, ret = 0; 327 struct dinode *dp, *pdirp; 328 int isattr; 329 int dirtype; 330 int inotype; 331 332 if (dirp->d_ino == 0) 333 return (KEEPON); 334 335 idesc->id_entryno++; 336 if ((strcmp(dirp->d_name, ".") == 0) || 337 (strcmp(dirp->d_name, "..") == 0)) { 338 return (KEEPON); 339 } 340 341 switch (statemap[dirp->d_ino] & ~(INDELAYD)) { 342 case DSTATE: 343 case DFOUND: 344 case FSTATE: 345 /* 346 * Accept DSTATE and DFOUND so we can handle normal 347 * directories as well as xattr directories. 348 * 349 * For extended attribute directories .. may point 350 * to a file. In this situation we don't want 351 * to decrement link count as it was already 352 * decremented when the entry was seen and decremented 353 * in the directory it actually lives in. 354 */ 355 dp = ginode(dirp->d_ino); 356 isattr = (dp->di_cflags & IXATTR); 357 inotype = (dp->di_mode & IFMT); 358 pdirp = ginode(idesc->id_number); 359 dirtype = (pdirp->di_mode & IFMT); 360 /* 361 * IXATTR indicates that an object is itself an extended 362 * attribute. An IFMT of IFATTRDIR means we are looking 363 * at a directory which contains files which should all 364 * have IXATTR set. The IFATTRDIR case was handled in 365 * pass 2b. 366 * 367 * Note that the following code actually handles 368 * anything that's marked as an extended attribute but 369 * in a regular directory, not just files. 370 */ 371 if ((dirtype == IFDIR) && isattr) { 372 fileerror(idesc->id_number, dirp->d_ino, 373 "%s I=%d should NOT be marked as extended attribute\n", 374 (inotype == IFDIR) ? "Directory" : "File", 375 dirp->d_ino); 376 dp = ginode(dirp->d_ino); 377 dp->di_cflags &= ~IXATTR; 378 if ((n = reply("FIX")) == 1) { 379 inodirty(); 380 } else { 381 iscorrupt = 1; 382 } 383 if (n != 0) 384 return (KEEPON | ALTERED); 385 } 386 break; 387 default: 388 errexit("PASS3: BAD STATE %d FOR INODE I=%d", 389 statemap[dirp->d_ino], dirp->d_ino); 390 /* NOTREACHED */ 391 } 392 if (n == 0) 393 return (ret|KEEPON); 394 return (ret|KEEPON|ALTERED); 395 } 396 397 static void 398 setcurino(struct inodesc *idesc, struct dinode *dp, struct inoinfo *inp) 399 { 400 (void) memmove((void *)&dp->di_db[0], (void *)&inp->i_blks[0], 401 inp->i_blkssize); 402 403 init_inodesc(idesc); 404 idesc->id_number = inp->i_number; 405 idesc->id_parent = inp->i_parent; 406 idesc->id_fix = DONTKNOW; 407 idesc->id_type = DATA; 408 idesc->id_func = pass3acheck; 409 } 410 411 void 412 maybe_convert_attrdir_to_dir(fsck_ino_t orphan) 413 { 414 struct dinode *dp = ginode(orphan); 415 struct inoinfo *inp = getinoinfo(orphan); 416 struct inodesc idesc; 417 418 if (dp->di_cflags & IXATTR) { 419 dp->di_cflags &= ~IXATTR; 420 inodirty(); 421 } 422 423 if ((dp->di_mode & IFMT) == IFATTRDIR) { 424 dp->di_mode &= ~IFATTRDIR; 425 dp->di_mode |= IFDIR; 426 inodirty(); 427 428 setcurino(&idesc, dp, inp); 429 idesc.id_fix = FIX; 430 idesc.id_filesize = dp->di_size; 431 (void) ckinode(dp, &idesc, CKI_TRAVERSE); 432 } 433 } 434