1
0
mirror of https://github.com/codership/wsrep-lib.git synced 2025-07-30 07:23:07 +03:00

Provide additional provider error status. Fixed IST handling.

This commit is contained in:
Teemu Ollakka
2018-07-05 11:31:47 +03:00
parent b3de50fa05
commit fcefe9f03b
6 changed files with 60 additions and 18 deletions

View File

@ -622,6 +622,10 @@ namespace wsrep
return current_error_; return current_error_;
} }
enum wsrep::provider::status current_error_status() const
{
return current_error_status_;
}
protected: protected:
/** /**
* Client context constuctor. This is protected so that it * Client context constuctor. This is protected so that it
@ -651,6 +655,7 @@ namespace wsrep
, last_written_gtid_() , last_written_gtid_()
, debug_log_level_(0) , debug_log_level_(0)
, current_error_(wsrep::e_success) , current_error_(wsrep::e_success)
, current_error_status_(wsrep::provider::success)
{ } { }
private: private:
@ -666,7 +671,13 @@ namespace wsrep
void debug_log_state(const char*) const; void debug_log_state(const char*) const;
void state(wsrep::unique_lock<wsrep::mutex>& lock, enum state state); void state(wsrep::unique_lock<wsrep::mutex>& lock, enum state state);
void mode(wsrep::unique_lock<wsrep::mutex>& lock, enum mode mode); void mode(wsrep::unique_lock<wsrep::mutex>& lock, enum mode mode);
void override_error(enum wsrep::client_error error);
// Override current client error status. Optionally provide
// an error status from the provider if the error was caused
// by the provider call.
void override_error(enum wsrep::client_error error,
enum wsrep::provider::status status =
wsrep::provider::success);
wsrep::thread::id owning_thread_id_; wsrep::thread::id owning_thread_id_;
wsrep::thread::id current_thread_id_; wsrep::thread::id current_thread_id_;
@ -685,7 +696,8 @@ namespace wsrep
wsrep::gtid sync_wait_gtid_; wsrep::gtid sync_wait_gtid_;
wsrep::gtid last_written_gtid_; wsrep::gtid last_written_gtid_;
int debug_log_level_; int debug_log_level_;
wsrep::client_error current_error_; enum wsrep::client_error current_error_;
enum wsrep::provider::status current_error_status_;
}; };
static inline const char* to_c_string( static inline const char* to_c_string(

View File

@ -428,6 +428,14 @@ namespace wsrep
*/ */
void initialized(); void initialized();
/**
* Return true if the server has been initialized.
*/
bool is_initialized() const
{
wsrep::unique_lock<wsrep::mutex> lock(mutex_);
return init_initialized_;
}
/** /**
* *
*/ */

View File

@ -48,7 +48,8 @@ void wsrep::client_state::cleanup()
debug_log_state("cleanup: leave"); debug_log_state("cleanup: leave");
} }
void wsrep::client_state::override_error(enum wsrep::client_error error) void wsrep::client_state::override_error(enum wsrep::client_error error,
enum wsrep::provider::status status)
{ {
assert(wsrep::this_thread::get_id() == owning_thread_id_); assert(wsrep::this_thread::get_id() == owning_thread_id_);
if (current_error_ != wsrep::e_success && if (current_error_ != wsrep::e_success &&
@ -57,6 +58,7 @@ void wsrep::client_state::override_error(enum wsrep::client_error error)
throw wsrep::runtime_error("Overriding error with success"); throw wsrep::runtime_error("Overriding error with success");
} }
current_error_ = error; current_error_ = error;
current_error_status_ = status;
} }
@ -254,7 +256,8 @@ int wsrep::client_state::enter_toi(const wsrep::key_array& keys,
break; break;
} }
default: default:
override_error(wsrep::e_error_during_commit); override_error(wsrep::e_error_during_commit,
wsrep::provider::error_certification_failed);
ret = 1; ret = 1;
break; break;
} }
@ -283,7 +286,8 @@ int wsrep::client_state::leave_toi()
break; break;
default: default:
assert(0); assert(0);
override_error(wsrep::e_error_during_commit); override_error(wsrep::e_error_during_commit,
wsrep::provider::error_unknown);
ret = 1; ret = 1;
break; break;
} }

View File

@ -342,6 +342,7 @@ std::string wsrep::server_state::prepare_for_sst()
{ {
wsrep::unique_lock<wsrep::mutex> lock(mutex_); wsrep::unique_lock<wsrep::mutex> lock(mutex_);
state(lock, s_joiner); state(lock, s_joiner);
lock.unlock();
return server_service_.sst_request(); return server_service_.sst_request();
} }
@ -517,6 +518,12 @@ void wsrep::server_state::on_view(const wsrep::view& view)
state(lock, s_joiner); state(lock, s_joiner);
state(lock, s_initializing); state(lock, s_initializing);
} }
else if (state_ == s_joiner)
{
// Got partiioned from the cluster, got IST and
// started applying actions.
state(lock, s_joined);
}
} }
else else
{ {
@ -739,7 +746,7 @@ void wsrep::server_state::state(
{ 1, 0, 0, 1, 0, 1, 0, 0, 0}, /* ized */ { 1, 0, 0, 1, 0, 1, 0, 0, 0}, /* ized */
{ 1, 0, 0, 1, 1, 0, 0, 1, 0}, /* cted */ { 1, 0, 0, 1, 1, 0, 0, 1, 0}, /* cted */
{ 1, 1, 0, 0, 0, 1, 0, 0, 0}, /* jer */ { 1, 1, 0, 0, 0, 1, 0, 0, 0}, /* jer */
{ 1, 0, 0, 0, 0, 0, 0, 1, 1}, /* jed */ { 1, 0, 0, 1, 0, 0, 0, 1, 1}, /* jed */
{ 1, 0, 0, 0, 0, 1, 0, 0, 1}, /* dor */ { 1, 0, 0, 0, 0, 1, 0, 0, 1}, /* dor */
{ 1, 0, 0, 1, 0, 1, 1, 0, 1}, /* sed */ { 1, 0, 0, 1, 0, 1, 1, 0, 1}, /* sed */
{ 1, 0, 0, 0, 0, 0, 0, 0, 0} /* ding */ { 1, 0, 0, 0, 0, 0, 0, 0, 0} /* ding */

View File

@ -175,7 +175,9 @@ int wsrep::transaction::before_prepare(
lock.unlock(); lock.unlock();
if (client_service_.statement_allowed_for_streaming() == false) if (client_service_.statement_allowed_for_streaming() == false)
{ {
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(
wsrep::e_error_during_commit,
wsrep::provider::error_not_allowed);
ret = 1; ret = 1;
} }
else else
@ -897,14 +899,14 @@ int wsrep::transaction::certify_commit(
case wsrep::provider::error_warning: case wsrep::provider::error_warning:
assert(ordered() == false); assert(ordered() == false);
state(lock, s_must_abort); state(lock, s_must_abort);
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
break; break;
case wsrep::provider::error_transaction_missing: case wsrep::provider::error_transaction_missing:
state(lock, s_must_abort); state(lock, s_must_abort);
// The execution should never reach this point if the // The execution should never reach this point if the
// transaction has not generated any keys or data. // transaction has not generated any keys or data.
wsrep::log_warning() << "Transaction was missing in provider"; wsrep::log_warning() << "Transaction was missing in provider";
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
break; break;
case wsrep::provider::error_bf_abort: case wsrep::provider::error_bf_abort:
// Transaction was replicated succesfully and it was either // Transaction was replicated succesfully and it was either
@ -925,7 +927,7 @@ int wsrep::transaction::certify_commit(
break; break;
case wsrep::provider::error_size_exceeded: case wsrep::provider::error_size_exceeded:
state(lock, s_must_abort); state(lock, s_must_abort);
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
break; break;
case wsrep::provider::error_connection_failed: case wsrep::provider::error_connection_failed:
// Galera provider may return CONN_FAIL if the trx is // Galera provider may return CONN_FAIL if the trx is
@ -938,7 +940,8 @@ int wsrep::transaction::certify_commit(
} }
else else
{ {
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit,
cert_ret);
state(lock, s_must_abort); state(lock, s_must_abort);
} }
break; break;
@ -947,16 +950,16 @@ int wsrep::transaction::certify_commit(
{ {
state(lock, s_must_abort); state(lock, s_must_abort);
} }
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
break; break;
case wsrep::provider::error_fatal: case wsrep::provider::error_fatal:
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
state(lock, s_must_abort); state(lock, s_must_abort);
client_service_.emergency_shutdown(); client_service_.emergency_shutdown();
break; break;
case wsrep::provider::error_not_implemented: case wsrep::provider::error_not_implemented:
case wsrep::provider::error_not_allowed: case wsrep::provider::error_not_allowed:
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
state(lock, s_must_abort); state(lock, s_must_abort);
wsrep::log_warning() << "Certification operation was not allowed: " wsrep::log_warning() << "Certification operation was not allowed: "
<< "id: " << id().get() << "id: " << id().get()
@ -964,7 +967,7 @@ int wsrep::transaction::certify_commit(
break; break;
default: default:
state(lock, s_must_abort); state(lock, s_must_abort);
client_state_.override_error(wsrep::e_error_during_commit); client_state_.override_error(wsrep::e_error_during_commit, cert_ret);
break; break;
} }

View File

@ -337,9 +337,17 @@ namespace
try try
{ {
std::string req(server_state.prepare_for_sst()); std::string req(server_state.prepare_for_sst());
*sst_req = ::malloc(req.size() + 1); if (req.size() > 0)
memcpy(*sst_req, req.data(), req.size() + 1); {
*sst_req_len = req.size() + 1; *sst_req = ::malloc(req.size() + 1);
memcpy(*sst_req, req.data(), req.size() + 1);
*sst_req_len = req.size() + 1;
}
else
{
*sst_req = 0;
*sst_req_len = 0;
}
return WSREP_CB_SUCCESS; return WSREP_CB_SUCCESS;
} }
catch (const wsrep::runtime_error& e) catch (const wsrep::runtime_error& e)