PST File Format SDK v0.4
Loading...
Searching...
No Matches
heap.h
Go to the documentation of this file.
1
5
6#ifndef PSTSDK_LTP_HEAP_H
7#define PSTSDK_LTP_HEAP_H
8
9#include <vector>
10#include <algorithm>
11#include <boost/noncopyable.hpp>
12#include <boost/iostreams/concepts.hpp>
13#ifdef _MSC_VER
14#pragma warning(push)
15#pragma warning(disable:4244)
16#endif
17#include <boost/iostreams/stream.hpp>
18#ifdef _MSC_VER
19#pragma warning(pop)
20#endif
21
22
24
25#include "pstsdk/disk/disk.h"
26
27#include "pstsdk/ndb/node.h"
28
29#ifdef _MSC_VER
30#pragma warning(push)
31#pragma warning(disable:4250)
32#endif
33
34namespace pstsdk
35{
36
39
40template<typename K, typename V>
41class bth_nonleaf_node;
42
43template<typename K, typename V>
44class bth_leaf_node;
45
46template<typename K, typename V>
47class bth_node;
48
49class heap_impl;
50typedef std::shared_ptr<heap_impl> heap_ptr;
51
58class hid_stream_device : public boost::iostreams::device<boost::iostreams::input_seekable>
59{
60public:
61 hid_stream_device() : m_pos(0), m_hid(0) { }
63 std::streamsize read(char* pbuffer, std::streamsize n);
65 std::streampos seek(boost::iostreams::stream_offset off, std::ios_base::seekdir way);
66
67private:
68 friend class heap_impl;
69 hid_stream_device(const heap_ptr& _heap, heap_id id) : m_pos(0), m_hid(id), m_pheap(_heap) { }
70
71 std::streamsize m_pos;
72 heap_id m_hid;
73 heap_ptr m_pheap;
74};
75
79typedef boost::iostreams::stream<hid_stream_device> hid_stream;
80
90class heap_impl : public std::enable_shared_from_this<heap_impl>
91{
92public:
97 size_t size(heap_id id) const;
98
101 uint get_page_count() const { return m_node.get_page_count(); }
102
112 heap_id get_root_id() const;
113
121 byte get_client_signature() const;
122
129 size_t read(std::vector<byte>& buffer, heap_id id, ulong offset) const;
130
135 std::vector<byte> read(heap_id id) const;
136
150 const node& get_node() const { return m_node; }
153 node& get_node() { return m_node; }
154
160 template<typename K, typename V>
161 std::shared_ptr<bth_node<K,V> > open_bth(heap_id root);
162
163 friend class heap;
164
165private:
166 heap_impl();
167 explicit heap_impl(const node& n);
168 heap_impl(const node& n, alias_tag);
169 heap_impl(const node& n, byte client_sig);
170 heap_impl(const node& n, byte client_sig, alias_tag);
171 heap_impl(const heap_impl& other)
172 : m_node(other.m_node) { }
173
174 node m_node;
175};
176
194class heap
195{
196public:
199 explicit heap(const node& n)
200 : m_pheap(new heap_impl(n)) { }
203 heap(const node& n, alias_tag)
204 : m_pheap(new heap_impl(n, alias_tag())) { }
209 heap(const node& n, byte client_sig)
210 : m_pheap(new heap_impl(n, client_sig)) { }
215 heap(const node& n, byte client_sig, alias_tag)
216 : m_pheap(new heap_impl(n, client_sig, alias_tag())) { }
219 heap(const heap& other)
220 : m_pheap(new heap_impl(*(other.m_pheap))) { }
223 heap(const heap& other, alias_tag)
224 : m_pheap(other.m_pheap) { }
225
226#ifndef BOOST_NO_RVALUE_REFERENCES
229 heap(heap&& other)
230 : m_pheap(std::move(other.m_pheap)) { }
231#endif
232
234 size_t size(heap_id id) const
235 { return m_pheap->size(id); }
238 { return m_pheap->get_root_id(); }
241 { return m_pheap->get_client_signature(); }
243 size_t read(std::vector<byte>& buffer, heap_id id, ulong offset) const
244 { return m_pheap->read(buffer, id, offset); }
246 std::vector<byte> read(heap_id id) const
247 { return m_pheap->read(id); }
250 { return m_pheap->open_stream(id); }
251
253 const node& get_node() const
254 { return m_pheap->get_node(); }
257 { return m_pheap->get_node(); }
258
260 template<typename K, typename V>
261 std::shared_ptr<bth_node<K,V> > open_bth(heap_id root)
262 { return m_pheap->open_bth<K,V>(root); }
263
264private:
265 heap& operator=(const heap& other); // = delete
266 heap_ptr m_pheap;
267};
268
271
290template<typename K, typename V>
291class bth_node :
292 public virtual btree_node<K,V>,
293 private boost::noncopyable
294{
295public:
301 static std::shared_ptr<bth_node<K,V> > open_root(const heap_ptr& h, heap_id bth_root);
306 static std::shared_ptr<bth_nonleaf_node<K,V> > open_nonleaf(const heap_ptr& h, heap_id id, ushort level);
310 static std::shared_ptr<bth_leaf_node<K,V> > open_leaf(const heap_ptr& h, heap_id id);
311
316 bth_node(const heap_ptr& h, heap_id id, ushort level)
317 : m_heap(h), m_id(id), m_level(level) { }
318 virtual ~bth_node() { }
319
322 heap_id get_id() const { return m_id; }
325 ushort get_level() const { return m_level; }
328 size_t get_key_size() const { return sizeof(K); }
331 size_t get_value_size() const { return sizeof(V); }
332
335 const heap_ptr get_heap_ptr() const { return m_heap; }
339
342 const node& get_node() const { return m_heap->get_node(); }
345 node& get_node() { return m_heap->get_node(); }
346
347protected:
349
350private:
351 heap_id m_id;
352 ushort m_level;
353};
354
360template<typename K, typename V>
362 public bth_node<K,V>,
363 public btree_node_nonleaf<K,V>
364{
365public:
371#ifndef BOOST_NO_RVALUE_REFERENCES
372 bth_nonleaf_node(const heap_ptr& h, heap_id id, ushort level, std::vector<std::pair<K, heap_id> > bth_info)
373 : bth_node<K,V>(h, id, level), m_bth_info(std::move(bth_info)), m_child_nodes(m_bth_info.size()) { }
374#else
375 bth_nonleaf_node(const heap_ptr& h, heap_id id, ushort level, const std::vector<std::pair<K, heap_id> >& bth_info)
376 : bth_node<K,V>(h, id, level), m_bth_info(bth_info), m_child_nodes(m_bth_info.size()) { }
377#endif
378 // btree_node_nonleaf implementation
379 const K& get_key(uint pos) const { return m_bth_info[pos].first; }
381 const bth_node<K,V>* get_child(uint pos) const;
382 uint num_values() const { return m_child_nodes.size(); }
383
384private:
385 std::vector<std::pair<K, heap_id> > m_bth_info;
386 mutable std::vector<std::shared_ptr<bth_node<K,V> > > m_child_nodes;
387};
388
394template<typename K, typename V>
396 public bth_node<K,V>,
397 public btree_node_leaf<K,V>
398{
399public:
404#ifndef BOOST_NO_RVALUE_REFERENCES
405 bth_leaf_node(const heap_ptr& h, heap_id id, std::vector<std::pair<K,V> > data)
406 : bth_node<K,V>(h, id, 0), m_bth_data(std::move(data)) { }
407#else
408 bth_leaf_node(const heap_ptr& h, heap_id id, const std::vector<std::pair<K,V> >& data)
409 : bth_node<K,V>(h, id, 0), m_bth_data(data) { }
410#endif
411
412 virtual ~bth_leaf_node() { }
413
414 // btree_node_leaf implementation
415 const V& get_value(uint pos) const
416 { return m_bth_data[pos].second; }
417 const K& get_key(uint pos) const
418 { return m_bth_data[pos].first; }
420 { return m_bth_data.size(); }
421
422private:
423 std::vector<std::pair<K,V> > m_bth_data;
424};
425
426} // end pstsdk namespace
427
428template<typename K, typename V>
429inline std::shared_ptr<pstsdk::bth_node<K,V> > pstsdk::bth_node<K,V>::open_root(const heap_ptr& h, heap_id bth_root)
430{
431 disk::bth_header* pheader;
432 std::vector<byte> buffer(sizeof(disk::bth_header));
433 pheader = (disk::bth_header*)&buffer[0];
434
435 h->read(buffer, bth_root, 0);
436
437#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
438 if(pheader->bth_signature != disk::heap_sig_bth)
439 throw sig_mismatch("bth_signature expected", 0, bth_root, pheader->bth_signature, disk::heap_sig_bth);
440
441 if(pheader->key_size != sizeof(K))
442 throw std::logic_error("invalid key size");
443
444 if(pheader->entry_size != sizeof(V))
445 throw std::logic_error("invalid entry size");
446#endif
447
448 if(pheader->num_levels > 0)
449 return open_nonleaf(h, pheader->root, pheader->num_levels);
450 else
451 return open_leaf(h, pheader->root);
452}
453
454template<typename K, typename V>
455inline std::shared_ptr<pstsdk::bth_nonleaf_node<K,V> > pstsdk::bth_node<K,V>::open_nonleaf(const heap_ptr& h, heap_id id, ushort level)
456{
457 uint num_entries = h->size(id) / sizeof(disk::bth_nonleaf_entry<K>);
458 std::vector<byte> buffer(h->size(id));
459 disk::bth_nonleaf_node<K>* pbth_nonleaf_node = (disk::bth_nonleaf_node<K>*)&buffer[0];
460 std::vector<std::pair<K, heap_id> > child_nodes;
461
462 h->read(buffer, id, 0);
463
464 child_nodes.reserve(num_entries);
465
466 for(uint i = 0; i < num_entries; ++i)
467 {
468 child_nodes.push_back(std::make_pair(pbth_nonleaf_node->entries[i].key, pbth_nonleaf_node->entries[i].page));
469 }
470
471#ifndef BOOST_NO_RVALUE_REFERENCES
472 return std::shared_ptr<bth_nonleaf_node<K,V> >(new bth_nonleaf_node<K,V>(h, id, level, std::move(child_nodes)));
473#else
474 return std::shared_ptr<bth_nonleaf_node<K,V> >(new bth_nonleaf_node<K,V>(h, id, level, child_nodes));
475#endif
476}
477
478template<typename K, typename V>
479inline std::shared_ptr<pstsdk::bth_leaf_node<K,V> > pstsdk::bth_node<K,V>::open_leaf(const heap_ptr& h, heap_id id)
480{
481 std::vector<std::pair<K, V> > entries;
482
483 if(id)
484 {
485 uint num_entries = h->size(id) / sizeof(disk::bth_leaf_entry<K,V>);
486 std::vector<byte> buffer(h->size(id));
488
489 h->read(buffer, id, 0);
490
491 entries.reserve(num_entries);
492
493 for(uint i = 0; i < num_entries; ++i)
494 {
495 entries.push_back(std::make_pair(pbth_leaf_node->entries[i].key, pbth_leaf_node->entries[i].value));
496 }
497#ifndef BOOST_NO_RVALUE_REFERENCES
498 return std::shared_ptr<bth_leaf_node<K,V> >(new bth_leaf_node<K,V>(h, id, std::move(entries)));
499#else
500 return std::shared_ptr<bth_leaf_node<K,V> >(new bth_leaf_node<K,V>(h, id, entries));
501#endif
502 }
503 else
504 {
505 // id == 0 means an empty tree
506 return std::shared_ptr<bth_leaf_node<K,V> >(new bth_leaf_node<K,V>(h, id, entries));
507 }
508}
509
510template<typename K, typename V>
512{
513 if(m_child_nodes[pos] == NULL)
514 {
515 if(this->get_level() > 1)
516 m_child_nodes[pos] = bth_node<K,V>::open_nonleaf(this->get_heap_ptr(), m_bth_info[pos].second, this->get_level()-1);
517 else
518 m_child_nodes[pos] = bth_node<K,V>::open_leaf(this->get_heap_ptr(), m_bth_info[pos].second);
519 }
520
521 return m_child_nodes[pos].get();
522}
523
524template<typename K, typename V>
526{
527 if(m_child_nodes[pos] == NULL)
528 {
529 if(this->get_level() > 1)
530 m_child_nodes[pos] = bth_node<K,V>::open_nonleaf(this->get_heap_ptr(), m_bth_info[pos].second, this->get_level()-1);
531 else
532 m_child_nodes[pos] = bth_node<K,V>::open_leaf(this->get_heap_ptr(), m_bth_info[pos].second);
533 }
534
535 return m_child_nodes[pos].get();
536}
537
538inline pstsdk::heap_impl::heap_impl(const node& n)
539: m_node(n)
540{
541 // need to throw if the node is smaller than first_header
543
544#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
545 if(first_header.signature != disk::heap_signature)
546 throw sig_mismatch("invalid heap_sig", 0, n.get_id(), first_header.signature, disk::heap_signature);
547#endif
548}
549
550inline pstsdk::heap_impl::heap_impl(const node& n, alias_tag)
551: m_node(n, alias_tag())
552{
553 // need to throw if the node is smaller than first_header
554 disk::heap_first_header first_header = m_node.read<disk::heap_first_header>(0);
555
556#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
557 if(first_header.signature != disk::heap_signature)
558 throw sig_mismatch("invalid heap_sig", 0, n.get_id(), first_header.signature, disk::heap_signature);
559#endif
560}
561
562inline pstsdk::heap_impl::heap_impl(const node& n, byte client_sig)
563: m_node(n)
564{
565 // need to throw if the node is smaller than first_header
566 disk::heap_first_header first_header = m_node.read<disk::heap_first_header>(0);
567
568#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
569 if(first_header.signature != disk::heap_signature)
570 throw sig_mismatch("invalid heap_sig", 0, n.get_id(), first_header.signature, disk::heap_signature);
571#endif
572 if(first_header.client_signature != client_sig)
573 throw sig_mismatch("invalid client_sig", 0, n.get_id(), first_header.client_signature, client_sig);
574}
575
576inline pstsdk::heap_impl::heap_impl(const node& n, byte client_sig, alias_tag)
577: m_node(n, alias_tag())
578{
579 // need to throw if the node is smaller than first_header
580 disk::heap_first_header first_header = m_node.read<disk::heap_first_header>(0);
581
582#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
583 if(first_header.signature != disk::heap_signature)
584 throw sig_mismatch("invalid heap_sig", 0, n.get_id(), first_header.signature, disk::heap_signature);
585#endif
586 if(first_header.client_signature != client_sig)
587 throw sig_mismatch("invalid client_sig", 0, n.get_id(), first_header.client_signature, client_sig);
588}
589
595
601
602inline size_t pstsdk::heap_impl::size(heap_id id) const
603{
604 if(id == 0)
605 return 0;
606
608
609#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
610 if(header.page_map_offset > m_node.get_page_size(get_heap_page(id)))
611 throw std::length_error("page_map_offset > node size");
612#endif
613
614 std::vector<byte> buffer(m_node.get_page_size(get_heap_page(id)) - header.page_map_offset);
615 m_node.read(buffer, get_heap_page(id), header.page_map_offset);
616 disk::heap_page_map* pmap = reinterpret_cast<disk::heap_page_map*>(&buffer[0]);
617
618#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
619 if(get_heap_index(id) > pmap->num_allocs)
620 throw std::length_error("index > num_allocs");
621#endif
622
623 return pmap->allocs[get_heap_index(id) + 1] - pmap->allocs[get_heap_index(id)];
624}
625
626inline size_t pstsdk::heap_impl::read(std::vector<byte>& buffer, heap_id id, ulong offset) const
627{
628 size_t hid_size = size(id);
629
630#ifdef PSTSDK_VALIDATION_LEVEL_WEAK
631 if(buffer.size() > hid_size)
632 throw std::length_error("buffer.size() > size()");
633
634 if(offset > hid_size)
635 throw std::length_error("offset > size()");
636
637 if(offset + buffer.size() > hid_size)
638 throw std::length_error("size + offset > size()");
639#endif
640
641 if(hid_size == 0)
642 return 0;
643
645 std::vector<byte> map_buffer(m_node.get_page_size(get_heap_page(id)) - header.page_map_offset);
646 m_node.read(map_buffer, get_heap_page(id), header.page_map_offset);
647 disk::heap_page_map* pmap = reinterpret_cast<disk::heap_page_map*>(&map_buffer[0]);
648
649 return m_node.read(buffer, get_heap_page(id), pmap->allocs[get_heap_index(id)] + offset);
650}
651
656
657inline std::streamsize pstsdk::hid_stream_device::read(char* pbuffer, std::streamsize n)
658{
659 if(m_hid && (static_cast<size_t>(m_pos) + n > m_pheap->size(m_hid)))
660 n = m_pheap->size(m_hid) - m_pos;
661
662 if(n == 0 || m_hid == 0)
663 return -1;
664
665 std::vector<byte> buff(static_cast<uint>(n));
666 size_t read = m_pheap->read(buff, m_hid, static_cast<ulong>(m_pos));
667
668 memcpy(pbuffer, &buff[0], read);
669
670 m_pos += read;
671
672 return read;
673}
674
675inline std::streampos pstsdk::hid_stream_device::seek(boost::iostreams::stream_offset off, std::ios_base::seekdir way)
676{
677#if defined(_MSC_VER) && (_MSC_VER < 1600)
678#pragma warning(push)
679#pragma warning(disable:4244)
680#endif
681 if(way == std::ios_base::beg)
682 m_pos = off;
683 else if(way == std::ios_base::end)
684 m_pos = m_pheap->size(m_hid) + off;
685 else
686 m_pos += off;
687#if defined(_MSC_VER) && (_MSC_VER < 1600)
688#pragma warning(pop)
689#endif
690
691 if(m_pos < 0)
692 m_pos = 0;
693 else if(static_cast<size_t>(m_pos) > m_pheap->size(m_hid))
694 m_pos = m_pheap->size(m_hid);
695
696 return m_pos;
697}
698
699inline std::vector<pstsdk::byte> pstsdk::heap_impl::read(heap_id id) const
700{
701 std::vector<byte> result(size(id));
702 read(result, id, 0);
703 return result;
704}
705
706template<typename K, typename V>
707inline std::shared_ptr<pstsdk::bth_node<K,V> > pstsdk::heap_impl::open_bth(heap_id root)
708{
710}
711
712#ifdef _MSC_VER
713#pragma warning(pop)
714#endif
715
716#endif
Contains the actual key value pairs of the BTH.
Definition heap.h:398
const V & get_value(uint pos) const
Returns the value at the associated position on this leaf node.
Definition heap.h:415
virtual ~bth_leaf_node()
Definition heap.h:412
uint num_values() const
Returns the number of entries in this btree_node.
Definition heap.h:419
const K & get_key(uint pos) const
Returns the key at the specified position.
Definition heap.h:417
bth_leaf_node(const heap_ptr &h, heap_id id, std::vector< std::pair< K, V > > data)
Construct a bth_leaf_node.
Definition heap.h:405
The object which forms the root of the BTH hierarchy.
Definition heap.h:294
heap_ptr m_heap
Definition heap.h:348
node & get_node()
Get the node underlying this BTH.
Definition heap.h:345
static std::shared_ptr< bth_leaf_node< K, V > > open_leaf(const heap_ptr &h, heap_id id)
Open a leaf BTH node.
Definition heap.h:479
const heap_ptr get_heap_ptr() const
Returns the heap this bth_node is in.
Definition heap.h:335
heap_id get_id() const
Return the heap_id of this bth_node.
Definition heap.h:322
size_t get_key_size() const
Return the key size of this bth.
Definition heap.h:328
bth_node(const heap_ptr &h, heap_id id, ushort level)
Construct a bth_node object.
Definition heap.h:316
static std::shared_ptr< bth_node< K, V > > open_root(const heap_ptr &h, heap_id bth_root)
Opens a BTH node from the specified heap at the given root.
Definition heap.h:429
virtual ~bth_node()
Definition heap.h:318
heap_ptr get_heap_ptr()
Returns the heap this bth_node is in.
Definition heap.h:338
ushort get_level() const
Return the leve of this bth_node.
Definition heap.h:325
size_t get_value_size() const
Return the value size of this bth.
Definition heap.h:331
static std::shared_ptr< bth_nonleaf_node< K, V > > open_nonleaf(const heap_ptr &h, heap_id id, ushort level)
Open a non-leaf BTH node.
Definition heap.h:455
const node & get_node() const
Get the node underlying this BTH.
Definition heap.h:342
Contains references to other bth_node allocations.
Definition heap.h:364
const K & get_key(uint pos) const
Returns the key at the specified position.
Definition heap.h:379
bth_nonleaf_node(const heap_ptr &h, heap_id id, ushort level, std::vector< std::pair< K, heap_id > > bth_info)
Construct a bth_nonleaf_node.
Definition heap.h:372
uint num_values() const
Returns the number of entries in this btree_node.
Definition heap.h:382
bth_node< K, V > * get_child(uint pos)
Returns the child btree_node at the requested location.
Definition heap.h:511
Represents a leaf node in a BTree structure.
Definition btree.h:132
Represents a non-leaf node in a BTree structure.
Definition btree.h:172
A BTree Node.
Definition btree.h:52
The HN implementation.
Definition heap.h:91
std::shared_ptr< bth_node< K, V > > open_bth(heap_id root)
Opens a BTH from this heap with the given root id.
const node & get_node() const
Get the node underlying this heap.
Definition heap.h:150
byte get_client_signature() const
Returns the client signature of the heap.
Definition heap.h:596
uint get_page_count() const
Get the count of pages (..external blocks) in this heap.
Definition heap.h:101
hid_stream_device open_stream(heap_id id)
Creates a stream device over a specified heap allocation.
Definition heap.h:652
node & get_node()
Get the node underlying this heap.
Definition heap.h:153
size_t read(std::vector< byte > &buffer, heap_id id, ulong offset) const
Read data out of a specified allocation at the specified offset.
Definition heap.h:626
heap_id get_root_id() const
Returns the client root allocation out of this heap.
Definition heap.h:590
size_t size(heap_id id) const
Get the size of the given allocation.
Definition heap.h:602
Heap-on-Node implementation.
Definition heap.h:195
size_t read(std::vector< byte > &buffer, heap_id id, ulong offset) const
Read data out of a specified allocation at the specified offset.
Definition heap.h:243
heap(const node &n)
Open a heap object on a node.
Definition heap.h:199
heap_id get_root_id() const
Returns the client root allocation out of this heap.
Definition heap.h:237
byte get_client_signature() const
Returns the client signature of the heap.
Definition heap.h:240
hid_stream_device open_stream(heap_id id)
Creates a stream device over a specified heap allocation.
Definition heap.h:249
size_t size(heap_id id) const
Get the size of the given allocation.
Definition heap.h:234
node & get_node()
Get the node underlying this heap.
Definition heap.h:256
std::shared_ptr< bth_node< K, V > > open_bth(heap_id root)
Opens a BTH from this heap with the given root id.
Definition heap.h:261
heap(heap &&other)
Move constructor.
Definition heap.h:229
const node & get_node() const
Get the node underlying this heap.
Definition heap.h:253
heap(const node &n, byte client_sig, alias_tag)
Open a heap object on the specified node (alias), and validate the client sig.
Definition heap.h:215
heap(const node &n, alias_tag)
Open a heap object on a node alias.
Definition heap.h:203
heap(const heap &other, alias_tag)
Alias constructor.
Definition heap.h:223
std::vector< byte > read(heap_id id) const
Read an entire allocation.
Definition heap.h:246
heap(const node &n, byte client_sig)
Open a heap object on the specified node, and validate the client sig.
Definition heap.h:209
heap(const heap &other)
Copy constructor.
Definition heap.h:219
Defines a stream device for a heap allocation for use by boost iostream.
Definition heap.h:59
std::streampos seek(boost::iostreams::stream_offset off, std::ios_base::seekdir way)
Move the current position in the stream.
Definition heap.h:675
std::streamsize read(char *pbuffer, std::streamsize n)
Read data from this node into the buffer at the current position.
Definition heap.h:657
An in memory representation of the "node" concept in a PST data file.
Definition node.h:320
uint get_page_count() const
Returns the number of pages in this node.
Definition node.h:430
An unexpected signature was encountered.
Definition errors.h:98
Disk data structure definitions.
const byte heap_signature
Signature of a heap.
Definition disk.h:1212
boost::iostreams::stream< hid_stream_device > hid_stream
The actual heap allocation stream, defined using the boost iostream library and the hid_stream_device...
Definition heap.h:79
ulong get_heap_page(heap_id id)
Get the heap page from the heap id.
Definition primitives.h:243
boost::uint8_t byte
Definition primitives.h:72
boost::uint32_t uint
Definition primitives.h:67
boost::uint32_t ulong
Definition primitives.h:68
ulong heap_id
Definition primitives.h:90
ulong get_heap_index(heap_id id)
Get the index from the heap id.
Definition primitives.h:251
boost::uint16_t ushort
Definition primitives.h:73
Contains the definition of all in memory representations of disk structures.
Definition disk.h:19
std::shared_ptr< heap_impl > heap_ptr
Definition heap.h:50
Node and Block definitions.
Primitive structures defined by MS-PST and MAPI.
Tag structure used to indicate a copy constructed class should be an alias (shallow copy) rather than...
Definition primitives.h:110
Describes the BTH, including the size of the keys/values and the heap_id of the root allocation.
Definition disk.h:1324
byte num_levels
Number of levels.
Definition disk.h:1328
byte entry_size
Entry size in bytes.
Definition disk.h:1327
byte bth_signature
Always heap_sig_bth.
Definition disk.h:1325
byte key_size
Key size in bytes.
Definition disk.h:1326
heap_id root
Root of the actual tree structure.
Definition disk.h:1329
EntryType entries[1]
Array of entries.
Definition disk.h:1381
Entries which make up a "non-leaf" BTH allocation.
Definition disk.h:1343
BTH Nonleaf node.
Definition disk.h:1405
Header structure on the first heap block.
Definition disk.h:1263
Header structure on non-first/non-fill blocks.
Definition disk.h:1277
Provides a map of the allocations on a heap block.
Definition disk.h:1306