📄 fsckino.c
字号:
* Clear the ACL field */ if (caf_rc == FSCK_OK) { dxd_ptr->flag = DXD_CORRUPT; /* clear the data length */ DXDlength(dxd_ptr, 0); /* clear the data address */ DXDaddress(dxd_ptr, 0); agg_recptr->blocks_this_fset -= block_count; } return (caf_rc);}/***************************************************************************** * NAME: clear_EA_field * * FUNCTION: Unrecord all storage allocated for the extended attributes * (ea) of the current inode. Clear the inode ea field to show * the inode owns no ea. * * PARAMETERS: * ino_recptr - input - pointer to an fsck inode record describing the * current inode * ino_ptr - input - pointer to the current inode * * RETURNS: * success: FSCK_OK * failure: something else */int clear_EA_field(struct fsck_inode_record *ino_recptr, struct dinode *ino_ptr){ int cef_rc = FSCK_OK; dxd_t *dxd_ptr; uint32_t block_count = 0; uint32_t extent_length; int64_t extent_address; int8_t extent_is_valid; /* * the following will be passed to extent_unrecord() which will * ignore them. */ int8_t is_EA = -1; int8_t is_ACL = 0; struct fsck_ino_msg_info *msg_info_ptr = NULL; /* locate the EA field in the inode */ dxd_ptr = &(ino_ptr->di_ea); /* * if the EA is in an out-of-line extent, release the blocks * allocated for it. */ if ((dxd_ptr->flag == DXD_EXTENT) && (!ino_recptr->ignore_ea_blks) && (!ino_recptr->ignore_alloc_blks)) { /* out of line single extent and not flagged to ignore */ extent_length = lengthDXD(dxd_ptr); extent_address = addressDXD(dxd_ptr); cef_rc = process_extent(ino_recptr, extent_length, extent_address, is_EA, is_ACL, msg_info_ptr, &block_count, &extent_is_valid, FSCK_UNRECORD); agg_recptr->blocks_for_eas -= block_count; } /* * Clear the EA field */ if (cef_rc == FSCK_OK) { dxd_ptr->flag = 0; /* clear the data length */ DXDlength(dxd_ptr, 0); /* clear the data address */ DXDaddress(dxd_ptr, 0); ino_ptr->di_nblocks -= block_count; agg_recptr->blocks_this_fset -= block_count; } return (cef_rc);}/***************************************************************************** * NAME: display_path * * FUNCTION: Issue a message to display the given inode path. * * PARAMETERS: * inoidx - input - ordinal number of the inode as an integer * inopfx - input - index (into message catalog) of prefix for * inode number when displayed in message * { A | <blank> } * ino_parent - input - the inode number for the (parent) directory * whose entry to the current inode is described * by the contents of inopath. * inopath - input - pointer to the UniCharacter path which is * to be displayed. * ino_recptr - input - pointer to an fsck inode record describing the * current inode * * RETURNS: * success: FSCK_OK * failure: something else */int display_path(uint32_t inoidx, int inopfx, uint32_t ino_parent, char *inopath, struct fsck_inode_record *ino_recptr){ int dip_rc = FSCK_OK; if ((!ino_recptr->unxpctd_prnts) || (!(ino_recptr->inode_type == directory_inode))) { /* not directory w/ mult parents */ if (ino_recptr->inode_type == directory_inode) { fsck_send_msg(fsck_INOPATHOK, fsck_ref_msg(fsck_directory), fsck_ref_msg(inopfx), inoidx, inopath); } else if (ino_recptr->inode_type == char_special_inode) { fsck_send_msg(fsck_INOPATHOK, fsck_ref_msg(fsck_char_special), fsck_ref_msg(inopfx), inoidx, inopath); } else if (ino_recptr->inode_type == block_special_inode) { fsck_send_msg(fsck_INOPATHOK, fsck_ref_msg(fsck_block_special), fsck_ref_msg(inopfx), inoidx, inopath); } else if (ino_recptr->inode_type == FIFO_inode) { fsck_send_msg(fsck_INOPATHOK, fsck_ref_msg(fsck_FIFO), fsck_ref_msg(inopfx), inoidx, inopath); } else if (ino_recptr->inode_type == SOCK_inode) { fsck_send_msg(fsck_INOPATHOK, fsck_ref_msg(fsck_SOCK), fsck_ref_msg(inopfx), inoidx, inopath); } else { /* regular file */ fsck_send_msg(fsck_INOPATHOK, fsck_ref_msg(fsck_file), fsck_ref_msg(inopfx), inoidx, inopath); } } else { /* else a directory w/ multiple parents */ if (ino_parent == ino_recptr->parent_inonum) { /* expected parent */ fsck_send_msg(fsck_INOPATHCRCT, inopath, fsck_ref_msg(inopfx), inoidx); } else { /* this is an illegal hard link */ fsck_send_msg(fsck_INOPATHBAD, fsck_ref_msg(fsck_directory), fsck_ref_msg(inopfx), inoidx, inopath); } } return (dip_rc);}/***************************************************************************** * NAME: display_paths * * FUNCTION: Display all paths to the specified inode. * * PARAMETERS: * inoidx - input - ordinal number of the inode as an integer * ino_recptr - input - pointer to an fsck inode record describing the * current inode * msg_info_ptr - input - pointer to a record with information needed * to issue messages about the current inode * * RETURNS: * success: FSCK_OK * failure: something else */int display_paths(uint32_t inoidx, struct fsck_inode_record *ino_recptr, struct fsck_ino_msg_info *msg_info_ptr){ int dips_rc = FSCK_OK; int intermed_rc; uint32_t this_parent = 0; struct fsck_inode_ext_record *this_ext = NULL; char *this_path_ptr; char **this_path_ptr_ptr; struct fsck_inode_record *parent_inorecptr; int a_path_displayed = 0; this_path_ptr_ptr = &this_path_ptr; if (inoidx == 2) { /* it's the root directory */ intermed_rc = get_path(inoidx, this_parent, this_path_ptr_ptr, ino_recptr); a_path_displayed = -1; dips_rc = display_path(inoidx, msg_info_ptr->msg_inopfx, this_parent, this_path_ptr, ino_recptr); goto out; } else if (ino_recptr->parent_inonum == 0) goto out; /* at least one parent was observed */ /* * if this is a directory with illegal hard links then the * inode number in the fsck inode record is the one stored in * the inode on disk. This routine displays only messages * for parents observed by fsck. */ if ((ino_recptr->inode_type == directory_inode) && (ino_recptr->unxpctd_prnts)) { /* dir with multiple parents */ this_ext = ino_recptr->ext_rec; while ((this_ext != NULL) && (this_ext->ext_type != parent_extension)) { this_ext = this_ext->next; } if (this_ext == NULL) { /* something is terribly wrong! */ dips_rc = FSCK_INTERNAL_ERROR_1; } } else { /* not a dir with multiple parents */ /* * the 1st parent observed is in the inode record. Any * others are in extension records. */ this_parent = ino_recptr->parent_inonum; if ((this_parent != ROOT_I) || (!agg_recptr->rootdir_rebuilt)) { /* * either this parent isn't the root or else * the root dir has not been rebuilt */ intermed_rc = get_inorecptr(0, 0, this_parent, &parent_inorecptr); if (intermed_rc != FSCK_OK) { dips_rc = intermed_rc; } else if ((parent_inorecptr->in_use) && (!parent_inorecptr->selected_to_rls) && (!parent_inorecptr->ignore_alloc_blks)) { /* got parent record and parent ok so far */ intermed_rc = get_path(inoidx, this_parent, this_path_ptr_ptr, ino_recptr); if (intermed_rc != FSCK_OK) { /* unable to obtain 1st path */ fsck_send_msg(fsck_INOCNTGETPATH, fsck_ref_msg(msg_info_ptr->msg_inopfx), this_parent, fsck_ref_msg(msg_info_ptr->msg_inotyp), fsck_ref_msg(msg_info_ptr->msg_inopfx), inoidx); if (intermed_rc < 0) { /* it's fatal */ dips_rc = intermed_rc; } } else { /* 1st path obtained */ a_path_displayed = -1; dips_rc = display_path(inoidx, msg_info_ptr-> msg_inopfx, this_parent, this_path_ptr, ino_recptr); /* * if there are any more paths to the * inode, find the next parent */ this_ext = ino_recptr->ext_rec; while ((this_ext != NULL) && (this_ext->ext_type != parent_extension)) { this_ext = this_ext->next; } } } } } while ((dips_rc == FSCK_OK) && (this_ext != NULL)) { /* there may be more parents */ if (this_ext->ext_type == parent_extension) { /* parent extension */ this_parent = this_ext->inonum; if ((this_parent != ROOT_I) || (!agg_recptr->rootdir_rebuilt)) { /* * either this parent isn't the root or else * the root dir has not been rebuilt */ intermed_rc = get_inorecptr(0, 0, this_parent, &parent_inorecptr); if (intermed_rc != 0) { /* it's fatal */ dips_rc = intermed_rc; } else if ((parent_inorecptr->in_use) && (!parent_inorecptr-> selected_to_rls) && (!parent_inorecptr-> ignore_alloc_blks)) { /* got parent record and parent seems * ok so far */ intermed_rc = get_path(inoidx, this_parent, this_path_ptr_ptr, ino_recptr); if (intermed_rc == FSCK_OK) { /* next path obtained */ a_path_displayed = -1; dips_rc = display_path(inoidx, msg_info_ptr-> msg_inopfx, this_parent, this_path_ptr, ino_recptr); } else { /* unable to obtain next path */ fsck_send_msg (fsck_INOCNTGETPATH, fsck_ref_msg(msg_info_ptr->msg_inopfx), this_parent, fsck_ref_msg(msg_info_ptr->msg_inotyp), fsck_ref_msg(msg_info_ptr->msg_inopfx), inoidx); if (intermed_rc < 0) { dips_rc = intermed_rc; } } } } } this_ext = this_ext->next; } /* * if nothing unexpected happened but we * couldn't display a path, issue a message * and go on. */ out: if ((dips_rc == FSCK_OK) && (!a_path_displayed)) { fsck_send_msg(fsck_INOCANTNAME, fsck_ref_msg(msg_info_ptr->msg_inotyp), fsck_ref_msg(msg_info_ptr->msg_inopfx), inoidx); } return (dips_rc);}/***************************************************************************** * NAME: first_ref_check_inode * * FUNCTION: Determine whether storage allocated to the given inode * includes any multiply-allocated blocks for which the * first reference is still unresolved. * * PARAMETERS: * inoptr - input - pointer to the current inode * inoidx - input - ordinal number of the inode as an integer * inorec_ptr - input - pointer to an fsck inode record describing the * current inode * msginfo_ptr - input - pointer to a record with information needed * to issue messages about the current inode * * RETURNS: * success: FSCK_OK * failure: something else */int first_ref_check_inode(struct dinode *inoptr, uint32_t inoidx, struct fsck_inode_record *inorec_ptr, struct fsck_ino_msg_info *msginfo_ptr){ int frcvi_rc = FSCK_OK; uint32_t block_count; int64_t first_fsblk; uint32_t num_fsblks; int8_t extent_is_valid; dxd_t *dxd_ptr; int is_EA; int is_ACL; /* * check the extent (if any) containing the EA */ if (inoptr->di_ea.flag == DXD_EXTENT) { /* there is an ea to record */ dxd_ptr = &(inoptr->di_ea); first_fsblk = addressDXD(dxd_ptr); num_fsblks = lengthDXD(dxd_ptr); is_EA = -1; is_ACL = 0; msginfo_ptr->msg_dxdtyp = fsck_EA; frcvi_rc = process_extent(inorec_ptr, num_fsblks, first_fsblk, is_EA, is_ACL, msginfo_ptr, &block_count, &extent_is_valid, FSCK_QUERY); } /* * check the extent (if any) containing the ACL */ if (inoptr->di_acl.flag == DXD_EXTENT) { /* there is an ACL to record */ dxd_ptr = &(inoptr->di_acl); first_fsblk = addressDXD(dxd_ptr); num_fsblks = lengthDXD(dxd_ptr); is_EA = 0; is_ACL = -1; msginfo_ptr->msg_dxdtyp = fsck_ACL; frcvi_rc = process_extent(inorec_ptr, num_fsblks, first_fsblk, is_EA, is_ACL, msginfo_ptr, &block_count, &extent_is_valid, FSCK_QUERY); } /* * check the extents (if any) described as data */ if (frcvi_rc == FSCK_OK) { if (inorec_ptr->inode_type == directory_inode) { frcvi_rc = process_valid_dir_data(inoptr, inoidx, inorec_ptr, msginfo_ptr, FSCK_QUERY); } else if (ISREG(inoptr->di_mode) || ISLNK(inoptr->di_mode)) { frcvi_rc = process_valid_data(inoptr, inoidx, inorec_ptr, msginfo_ptr, FSCK_QUERY); } } return (frcvi_rc);}/***************************************************************************** * NAME: get_path * * FUNCTION: Construct the unicode path from the root directory through * the entry in the specified parent directory. * * PARAMETERS: * inode_idx - input - ordinal number of the inode as an integer * parent_inonum - input - the inode number for the (parent) directory * whose entry to the current inode is to be * described by the contents of inopath. * addr_path_addr - input - pointer to a variable in which to return * the address of the path (in UniChars)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -