0.9.8.10
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
PhantomRange.cc
Go to the documentation of this file.
1 /* -*- c++ -*-
2  * Copyright (C) 2007-2015 Hypertable, Inc.
3  *
4  * This file is part of Hypertable.
5  *
6  * Hypertable is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; version 3 of the
9  * License, or any later version.
10  *
11  * Hypertable is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19  * 02110-1301, USA.
20  */
21 
26 
27 #include <Common/Compat.h>
28 
29 #include "PhantomRange.h"
30 
32 
33 #include <Common/md5.h>
34 
35 #include <mutex>
36 #include <sstream>
37 
38 using namespace Hypertable;
39 using namespace std;
40 
42  const RangeState &state,
43  SchemaPtr &schema,
44  const vector<int32_t> &fragments)
45  : m_range_spec(spec), m_range_state(state), m_schema(schema),
46  m_outstanding(fragments.size()), m_state(LOADED) {
47  for (int32_t fragment : fragments) {
48  HT_ASSERT(m_fragments.count(fragment) == 0);
49  m_fragments[fragment] = make_shared<FragmentData>();
50  }
51 }
52 
54  lock_guard<mutex> lock(m_mutex);
55  return m_state;
56 }
57 
58 bool PhantomRange::add(int32_t fragment, EventPtr &event) {
59  lock_guard<mutex> lock(m_mutex);
60  FragmentMap::iterator it = m_fragments.find(fragment);
61 
62  HT_ASSERT(it != m_fragments.end());
64 
65  it->second->add(event);
66 
67  return true;
68 }
69 
71  lock_guard<mutex> lock(m_mutex);
72  FragmentMap::iterator it = m_fragments.begin();
73  for(; it != m_fragments.end(); ++it)
74  it->second->clear();
75 }
76 
78  TableInfoPtr &table_info, FilesystemPtr &log_dfs) {
79  lock_guard<mutex> lock(m_mutex);
80 
81  m_range = make_shared<Range>(master_client, m_range_spec.table, m_schema,
82  m_range_spec.range, table_info.get(),
83  m_range_state, true);
84  m_range->deferred_initialization();
85  m_range->metalog_entity()->set_state_bits(RangeState::PHANTOM);
87 }
88 
90  int64_t recovery_id,
91  bool *is_empty) {
92  lock_guard<mutex> lock(m_mutex);
93 
94  m_range->recovery_initialize();
95 
96  *is_empty = true;
97 
98  MetaLogEntityRangePtr metalog_entity = m_range->metalog_entity();
99 
100  m_phantom_logname = create_log(log_dfs, recovery_id, metalog_entity);
101 
102  CommitLogPtr phantom_log = make_shared<CommitLog>(log_dfs, m_phantom_logname,
104 
105  {
106  lock_guard<Range> range_lock(*m_range);
107  for (auto &entry : m_fragments)
108  entry.second->merge(m_range_spec.table, m_range, phantom_log);
109  }
110 
111  phantom_log->sync();
112  phantom_log->close();
113 
114  m_range->recovery_finalize();
115 
116  std::stringstream sout;
117 
118  RangeStateManaged range_state;
119  metalog_entity->get_range_state(range_state);
120  sout << "Created phantom log " << m_phantom_logname
121  << " for range " << m_range_spec << ", state="
122  << range_state;
123  HT_INFOF("%s", sout.str().c_str());
124 
125  // Scan log to load blocks and determine if log is empty
126  m_phantom_log = make_shared<CommitLogReader>(log_dfs, m_phantom_logname);
127  BlockHeaderCommitLog header;
128  const uint8_t *base;
129  size_t len;
130  while (m_phantom_log->next(&base, &len, &header))
131  ;
132  *is_empty = m_phantom_log->get_latest_revision() == TIMESTAMP_MIN;
133 
134 }
135 
137  lock_guard<mutex> lock(m_mutex);
138  return m_phantom_logname;
139 }
140 
142  lock_guard<mutex> lock(m_mutex);
143  return m_phantom_log;
144 }
145 
146 
148  lock_guard<mutex> lock(m_mutex);
149  HT_ASSERT((m_state & REPLAYED) == 0);
150  m_state |= REPLAYED;
151 }
152 
154  lock_guard<mutex> lock(m_mutex);
155  return (m_state & REPLAYED) == REPLAYED;
156 }
157 
159  lock_guard<mutex> lock(m_mutex);
160  HT_ASSERT((m_state & PREPARED) == 0);
161  m_state |= PREPARED;
162 }
163 
165  lock_guard<mutex> lock(m_mutex);
166  return (m_state & PREPARED) == PREPARED;
167 }
168 
170  lock_guard<mutex> lock(m_mutex);
171  HT_ASSERT((m_state & COMMITTED) == 0);
172  m_state |= COMMITTED;
173 }
174 
176  lock_guard<mutex> lock(m_mutex);
177  return (m_state & COMMITTED) == COMMITTED;
178 }
179 
181  int64_t recovery_id,
182  MetaLogEntityRangePtr &range_entity) {
183  TableIdentifier table;
184  String start_row, end_row;
185  char md5DigestStr[33];
186  String logname;
187 
188  range_entity->get_table_identifier(table);
189  range_entity->get_boundary_rows(start_row, end_row);
190 
191  md5_trunc_modified_base64(end_row.c_str(), md5DigestStr);
192  md5DigestStr[16] = 0;
193 
194  logname = format("%s/tables/%s/_xfer/%s_phantom_%lld",
195  Global::toplevel_dir.c_str(),
196  table.id, md5DigestStr, (Lld)recovery_id);
197 
198  // Remove from prior attempt
199  log_dfs->rmdir(logname);
200 
201  log_dfs->mkdirs(logname);
202 
203  return logname;
204 }
bool add(int32_t fragment, EventPtr &event)
Definition: PhantomRange.cc:58
QualifiedRangeSpec m_range_spec
Definition: PhantomRange.h:109
std::string String
A String is simply a typedef to std::string.
Definition: String.h:44
String format(const char *fmt,...)
Returns a String using printf like format facilities Vanilla snprintf is about 1.5x faster than this...
Definition: String.cc:37
std::shared_ptr< Event > EventPtr
Smart pointer to Event.
Definition: Event.h:228
STL namespace.
static const int64_t TIMESTAMP_MIN
Definition: KeySpec.h:34
std::shared_ptr< CommitLogReader > CommitLogReaderPtr
Smart pointer to CommitLogReader.
void md5_trunc_modified_base64(const char *input, char output[17])
Get the modified base64 encoded string of the first 12 Bytes of the 16 Byte MD5 code of a null termin...
Definition: md5.cc:425
std::shared_ptr< Client > ClientPtr
Definition: Client.h:156
#define HT_ASSERT(_e_)
Definition: Logger.h:396
Declarations for PhantomRange.
static std::string toplevel_dir
Definition: Global.h:108
Compatibility Macros for C/C++.
CommitLogReaderPtr m_phantom_log
Definition: PhantomRange.h:114
String create_log(FilesystemPtr &log_dfs, int64_t recovery_id, MetaLogEntityRangePtr &range_entity)
uint8_t state
Range state value (see StateType)
Definition: RangeState.h:102
CommitLogReaderPtr get_phantom_log()
void create_range(Lib::Master::ClientPtr &master_client, TableInfoPtr &table_info, FilesystemPtr &log_dfs)
Definition: PhantomRange.cc:77
const String & get_phantom_logname()
Hypertable definitions
long long int Lld
Shortcut for printf formats.
Definition: String.h:53
std::shared_ptr< MetaLogEntityRange > MetaLogEntityRangePtr
Smart pointer to MetaLogEntityRange.
std::shared_ptr< Filesystem > FilesystemPtr
Smart pointer to Filesystem.
Definition: Filesystem.h:572
void populate_range_and_log(FilesystemPtr &log_dfs, int64_t recovery_id, bool *is_empty)
Definition: PhantomRange.cc:89
std::shared_ptr< TableInfo > TableInfoPtr
Smart pointer to TableInfo.
Definition: TableInfo.h:312
#define HT_INFOF(msg,...)
Definition: Logger.h:272
std::shared_ptr< CommitLog > CommitLogPtr
Smart pointer to CommitLog.
Definition: CommitLog.h:223
Qualified (with table identifier) range specification.
PhantomRange(const QualifiedRangeSpec &spec, const RangeState &state, SchemaPtr &schema, const vector< int32_t > &fragments)
Definition: PhantomRange.cc:41
std::shared_ptr< Schema > SchemaPtr
Smart pointer to Schema.
Definition: Schema.h:465
Range state.
Definition: RangeState.h:48
md5 digest routines.
Range state with memory management.
Definition: RangeState.h:166