PageRenderTime 46ms CodeModel.GetById 23ms app.highlight 17ms RepoModel.GetById 1ms app.codeStats 0ms

/src/inode.h

http://ext3grep.googlecode.com/
C++ Header | 131 lines | 83 code | 15 blank | 33 comment | 13 complexity | c9ba8849ee46d60ae77a2d68deea32e1 MD5 | raw file
  1// ext3grep -- An ext3 file system investigation and undelete tool
  2//
  3//! @file inode.h Declaration of class InodePointer and function get_inode.
  4//
  5// Copyright (C) 2008, by
  6// 
  7// Carlo Wood, Run on IRC <carlo@alinoe.com>
  8// RSA-1024 0x624ACAD5 1997-01-26                    Sign & Encrypt
  9// Fingerprint16 = 32 EC A7 B6 AC DB 65 A6  F6 F6 55 DD 1C DC FF 61
 10// 
 11// This program is free software: you can redistribute it and/or modify
 12// it under the terms of the GNU General Public License as published by
 13// the Free Software Foundation, either version 2 of the License, or
 14// (at your option) any later version.
 15// 
 16// This program is distributed in the hope that it will be useful,
 17// but WITHOUT ANY WARRANTY; without even the implied warranty of
 18// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 19// GNU General Public License for more details.
 20// 
 21// You should have received a copy of the GNU General Public License
 22// along with this program.  If not, see <http://www.gnu.org/licenses/>.
 23
 24#ifndef INODE_H
 25#define INODE_H
 26
 27#ifndef USE_PCH
 28#include "ext3.h"	// Needed for Inode
 29#include "debug.h"
 30#endif
 31
 32#include "globals.h"
 33#include "load_meta_data.h"
 34
 35#if USE_MMAP
 36void inode_mmap(int group);
 37void inode_unmap(int group);
 38#endif
 39
 40class InodePointer {
 41  private:
 42    Inode const* M_inode;
 43    int M_group;
 44    static Inode S_fake_inode;
 45
 46  public:
 47    // Default constructor.
 48    InodePointer(void) : M_inode(NULL), M_group(-1) { }
 49
 50    // Copy constructor.
 51    InodePointer(InodePointer const& ref) : M_inode(ref.M_inode), M_group(ref.M_group)
 52    {
 53#if USE_MMAP
 54      if (M_group != -1)
 55        refs_to_mmap[M_group]++;
 56#endif
 57    }
 58
 59    // Create an InodePointer to a fake inode.
 60    InodePointer(int) : M_inode(&S_fake_inode), M_group(-1) { }
 61
 62    // Destructor.
 63    ~InodePointer()
 64    {
 65#if USE_MMAP
 66      if (M_group != -1)
 67        refs_to_mmap[M_group]--;
 68#endif
 69    }
 70
 71    InodePointer& operator=(InodePointer const& inode_reference)
 72    {
 73      M_inode = inode_reference.M_inode;
 74#if USE_MMAP
 75      if (M_group != -1)
 76	refs_to_mmap[M_group]--;
 77#endif
 78      M_group = inode_reference.M_group;
 79#if USE_MMAP
 80      if (M_group != -1)
 81	refs_to_mmap[M_group]++;
 82#endif
 83      return *this;
 84    }
 85
 86    // Accessors.
 87    Inode const* operator->(void) const { return M_inode; }
 88    Inode const& operator*(void) const { return *M_inode; }
 89
 90  private:
 91    friend InodePointer get_inode(uint32_t inode);
 92    InodePointer(Inode const& inode, int group) : M_inode(&inode), M_group(group)
 93    {
 94      ASSERT(M_group != -1);
 95#if USE_MMAP
 96      refs_to_mmap[M_group]++;
 97#endif
 98    }
 99};
100
101inline unsigned int bit_to_all_inodes_group_index(unsigned int bit)
102{
103#if USE_MMAP
104  // If bit is incremented by one, we need to skip inode_size_ bytes in the (mmap-ed) inode table.
105  // Since the type of the table is Inode* the index needs to be incremented with the number of Inode structs that we need to skip.
106  // Because both inode_size_ and sizeof(Inode) are a power of 2 and inode_size_ >= sizeof(Inode), this amounts to inode_size_ / sizeof(Inode)
107  // index incrementation per bit.
108  return bit * (inode_size_ / sizeof(Inode));
109#else
110  // If no mmap is used, the table only contains the first 128 bytes of each inode.
111  return bit;
112#endif
113}
114
115inline InodePointer get_inode(uint32_t inode)
116{
117  int group = (inode - 1) / inodes_per_group_;
118  unsigned int bit = inode - 1 - group * inodes_per_group_;
119  // The bit in the bit mask must fit inside a single block.
120  ASSERT(bit < 8U * block_size_);
121#if USE_MMAP
122  if (all_inodes[group] == NULL)
123    inode_mmap(group);
124#else
125  if (block_bitmap[group] == NULL)
126    load_meta_data(group);
127#endif
128  return InodePointer(all_inodes[group][bit_to_all_inodes_group_index(bit)], group);
129}
130
131#endif // INODE_H