Class INodeReference

java.lang.Object
org.apache.hadoop.hdfs.server.namenode.INode
org.apache.hadoop.hdfs.server.namenode.INodeReference
All Implemented Interfaces:
Comparable<byte[]>, INodeAttributes, Diff.Element<byte[]>
Direct Known Subclasses:
INodeReference.DstReference, INodeReference.WithCount, INodeReference.WithName

public abstract class INodeReference extends INode
A reference to an inode.

This class and its subclasses are used to support multiple access paths. A file/directory may have multiple access paths when it is stored in some snapshots, and it is renamed/moved to other locations.

For example, (1) Suppose we have /abc/foo and the inode is inode(id=1000,name=foo). Suppose foo is created after snapshot s0, i.e. foo is not in s0 and inode(id=1000,name=foo) is in the create-list of /abc for the s0 diff entry. (2) Create snapshot s1, s2 for /abc, i.e. foo is in s1 and s2. Suppose sDst is the last snapshot /xyz. (3) mv /abc/foo /xyz/bar, i.e. inode(id=1000,name=...) is renamed from "foo" to "bar" and its parent becomes /xyz.

Then, /xyz/bar, /abc/.snapshot/s1/foo and /abc/.snapshot/s2/foo are different access paths to the same inode, inode(id=1000,name=bar). Inside the inode tree, /abc/.snapshot/s1/foo and /abc/.snapshot/s2/foo indeed have the same resolved path, but /xyz/bar has a different resolved path.

With references, we have the following - The source /abc/foo inode(id=1000,name=foo) is replaced with a WithName(name=foo,lastSnapshot=s2) and then it is moved to the delete-list of /abc for the s2 diff entry. The replacement also replaces inode(id=1000,name=foo) in the create-list of /abc for the s0 diff entry with the WithName. The same as before, /abc/foo is in s1 and s2, but not in s0. - The destination /xyz adds a child DstReference(dstSnapshot=sDst). DstReference is added to the create-list of /xyz for the sDst diff entry. /xyz/bar is not in sDst. - Both WithName and DstReference point to another reference WithCount(count=2). - Finally, WithCount(count=2) points to inode(id=1000,name=bar) Note that the inode name is changed to "bar".

Note 1: References other than WithName use the name of the referred inode, i.e. WithCount and DstReference do not have their own name. Note 2: getParent() always returns the parent in the current state, e.g. inode(id=1000,name=bar).getParent() returns /xyz but not /abc. Note 3: getId() returns the id the referred inode, e.g. all WithName, DstReference and WithCount above return id=1000.

  • Constructor Details

    • INodeReference

      public INodeReference(INode parent, INode referred)
  • Method Details

    • toDetailString

      public String toDetailString()
      Overrides:
      toDetailString in class INode
    • tryRemoveReference

      public static int tryRemoveReference(INode inode)
      Try to remove the given reference and then return the reference count. If the given inode is not a reference, return -1;
    • getReferredINode

      public final INode getReferredINode()
    • isReference

      public final boolean isReference()
      Description copied from class: INode
      Check whether it's a reference.
      Overrides:
      isReference in class INode
    • asReference

      public final INodeReference asReference()
      Description copied from class: INode
      Cast this inode to an INodeReference.
      Overrides:
      asReference in class INode
    • isFile

      public final boolean isFile()
      Description copied from class: INode
      Check whether it's a file.
      Overrides:
      isFile in class INode
    • asFile

      public final INodeFile asFile()
      Description copied from class: INode
      Cast this inode to an INodeFile.
      Overrides:
      asFile in class INode
    • isDirectory

      public final boolean isDirectory()
      Description copied from class: INode
      Check whether it's a directory
      Specified by:
      isDirectory in interface INodeAttributes
      Overrides:
      isDirectory in class INode
    • asDirectory

      public final INodeDirectory asDirectory()
      Description copied from class: INode
      Cast this inode to an INodeDirectory.
      Overrides:
      asDirectory in class INode
    • isSymlink

      public final boolean isSymlink()
      Description copied from class: INode
      Check whether it's a symlink
      Overrides:
      isSymlink in class INode
    • asSymlink

      public final INodeSymlink asSymlink()
      Description copied from class: INode
      Cast this inode to an INodeSymlink.
      Overrides:
      asSymlink in class INode
    • getLocalNameBytes

      public byte[] getLocalNameBytes()
      Returns:
      null if the local name is null; otherwise, return the local name byte array.
    • setLocalName

      public void setLocalName(byte[] name)
      Description copied from class: INode
      Set local file name
      Specified by:
      setLocalName in class INode
    • getId

      public final long getId()
      Description copied from class: INode
      Get inode id
      Specified by:
      getId in class INode
    • getPermissionStatus

      public final org.apache.hadoop.fs.permission.PermissionStatus getPermissionStatus(int snapshotId)
      Description copied from class: INode
      Get the PermissionStatus
      Specified by:
      getPermissionStatus in class INode
    • getUserName

      public final String getUserName(int snapshotId)
    • getGroupName

      public final String getGroupName(int snapshotId)
    • getFsPermission

      public final org.apache.hadoop.fs.permission.FsPermission getFsPermission(int snapshotId)
    • getFsPermissionShort

      public final short getFsPermissionShort()
      Returns:
      the permission as a short.
    • getPermissionLong

      public long getPermissionLong()
      Returns:
      the permission information as a long.
    • getModificationTime

      public final long getModificationTime(int snapshotId)
    • updateModificationTime

      public final INode updateModificationTime(long mtime, int latestSnapshotId)
      Description copied from class: INode
      Update modification time if it is larger than the current value.
      Specified by:
      updateModificationTime in class INode
    • setModificationTime

      public final void setModificationTime(long modificationTime)
      Description copied from class: INode
      Set the last modification time of inode.
      Specified by:
      setModificationTime in class INode
    • getAccessTime

      public final long getAccessTime(int snapshotId)
    • setAccessTime

      public final void setAccessTime(long accessTime)
      Description copied from class: INode
      Set last access time of inode.
      Specified by:
      setAccessTime in class INode
    • getStoragePolicyID

      public final byte getStoragePolicyID()
      Specified by:
      getStoragePolicyID in class INode
      Returns:
      the latest block storage policy id of the INode. Specifically, if a storage policy is directly specified on the INode then return the ID of that policy. Otherwise follow the latest parental path and return the ID of the first specified storage policy.
    • getLocalStoragePolicyID

      public final byte getLocalStoragePolicyID()
      Specified by:
      getLocalStoragePolicyID in class INode
      Returns:
      the storage policy directly specified on the INode. Return HdfsConstants.BLOCK_STORAGE_POLICY_ID_UNSPECIFIED if no policy has been specified.
    • cleanSubtree

      public void cleanSubtree(INode.ReclaimContext reclaimContext, int snapshot, int prior)
      Description copied from class: INode
      Clean the subtree under this inode and collect the blocks from the descents for further block deletion/update. The current inode can either resides in the current tree or be stored as a snapshot copy.
       In general, we have the following rules. 
       1. When deleting a file/directory in the current tree, we have different 
       actions according to the type of the node to delete. 
       
       1.1 The current inode (this) is an INodeFile. 
       1.1.1 If prior is null, there is no snapshot taken on ancestors 
       before. Thus we simply destroy (i.e., to delete completely, no need to save 
       snapshot copy) the current INode and collect its blocks for further 
       cleansing.
       1.1.2 Else do nothing since the current INode will be stored as a snapshot
       copy.
       
       1.2 The current inode is an INodeDirectory.
       1.2.1 If prior is null, there is no snapshot taken on ancestors 
       before. Similarly, we destroy the whole subtree and collect blocks.
       1.2.2 Else do nothing with the current INode. Recursively clean its 
       children.
       
       1.3 The current inode is a file with snapshot.
       Call recordModification(..) to capture the current states.
       Mark the INode as deleted.
       
       1.4 The current inode is an INodeDirectory with snapshot feature.
       Call recordModification(..) to capture the current states. 
       Destroy files/directories created after the latest snapshot 
       (i.e., the inodes stored in the created list of the latest snapshot).
       Recursively clean remaining children. 
      
       2. When deleting a snapshot.
       2.1 To clean INodeFile: do nothing.
       2.2 To clean INodeDirectory: recursively clean its children.
       2.3 To clean INodeFile with snapshot: delete the corresponding snapshot in
       its diff list.
       2.4 To clean INodeDirectory with snapshot: delete the corresponding 
       snapshot in its diff list. Recursively clean its children.
       
      Specified by:
      cleanSubtree in class INode
      Parameters:
      reclaimContext - Record blocks and inodes that need to be reclaimed.
      snapshot - The id of the snapshot to delete. Snapshot.CURRENT_STATE_ID means to delete the current file/directory.
      prior - The id of the latest snapshot before the to-be-deleted snapshot. When deleting a current inode, this parameter captures the latest snapshot.
    • destroyAndCollectBlocks

      public void destroyAndCollectBlocks(INode.ReclaimContext reclaimContext)
      Description copied from class: INode
      Destroy self and clear everything! If the INode is a file, this method collects its blocks for further block deletion. If the INode is a directory, the method goes down the subtree and collects blocks from the descents, and clears its parent/children references as well. The method also clears the diff list if the INode contains snapshot diff list.
      Specified by:
      destroyAndCollectBlocks in class INode
      Parameters:
      reclaimContext - Record blocks and inodes that need to be reclaimed.
    • computeContentSummary

      public ContentSummaryComputationContext computeContentSummary(int snapshotId, ContentSummaryComputationContext summary) throws org.apache.hadoop.security.AccessControlException
      Description copied from class: INode
      Count subtree content summary with a ContentCounts.
      Specified by:
      computeContentSummary in class INode
      Parameters:
      snapshotId - Specify the time range for the calculation. If this parameter equals to Snapshot.CURRENT_STATE_ID, the result covers both the current states and all the snapshots. Otherwise the result only covers all the files/directories contained in the specific snapshot.
      summary - the context object holding counts for the subtree.
      Returns:
      The same objects as summary.
      Throws:
      org.apache.hadoop.security.AccessControlException
    • computeQuotaUsage

      public QuotaCounts computeQuotaUsage(BlockStoragePolicySuite bsps, byte blockStoragePolicyId, boolean useCache, int lastSnapshotId)
      Description copied from class: INode
      Count subtree Quota.NAMESPACE and Quota.STORAGESPACE usages. With the existence of INodeReference, the same inode and its subtree may be referred by multiple INodeReference.WithName nodes and a INodeReference.DstReference node. To avoid circles while quota usage computation, we have the following rules:
       1. For a INodeReference.DstReference node, since the node must be in the current
       tree (or has been deleted as the end point of a series of rename 
       operations), we compute the quota usage of the referred node (and its 
       subtree) in the regular manner, i.e., including every inode in the current
       tree and in snapshot copies, as well as the size of diff list.
       
       2. For a INodeReference.WithName node, since the node must be in a snapshot, we 
       only count the quota usage for those nodes that still existed at the 
       creation time of the snapshot associated with the INodeReference.WithName node.
       We do not count in the size of the diff list.
       
      Specified by:
      computeQuotaUsage in class INode
      Parameters:
      bsps - Block storage policy suite to calculate intended storage type usage
      blockStoragePolicyId - block storage policy id of the current INode
      useCache - Whether to use cached quota usage. Note that INodeReference.WithName node never uses cache for its subtree.
      lastSnapshotId - Snapshot.CURRENT_STATE_ID indicates the computation is in the current tree. Otherwise the id indicates the computation range for a INodeReference.WithName node.
      Returns:
      The subtree quota counts.
    • getSnapshotINode

      public final INodeAttributes getSnapshotINode(int snapshotId)
      Overrides:
      getSnapshotINode in class INode
      Returns:
      if the given snapshot id is Snapshot.CURRENT_STATE_ID, return this; otherwise return the corresponding snapshot inode.
    • getQuotaCounts

      public QuotaCounts getQuotaCounts()
      Description copied from class: INode
      Get the quota set for this inode
      Overrides:
      getQuotaCounts in class INode
      Returns:
      the quota counts. The count is -1 if it is not set.
    • clear

      public final void clear()
      Description copied from class: INode
      Clear references to other objects.
      Overrides:
      clear in class INode
    • dumpTreeRecursively

      public void dumpTreeRecursively(PrintWriter out, StringBuilder prefix, int snapshot)
      Description copied from class: INode
      Dump tree recursively.
      Overrides:
      dumpTreeRecursively in class INode
      prefix - The prefix string that each line should print.
    • accept

      public void accept(NamespaceVisitor visitor, int snapshot)
      Description copied from class: INode
      Accept a visitor to visit this INode.
      Overrides:
      accept in class INode
    • getDstSnapshotId

      public int getDstSnapshotId()