用于EagleEye3.0 规则集漏报和误报测试的示例项目,项目收集于github和gitee
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

447 lines
14 KiB

/* Copyright (c) 2010, 2019, Oracle and/or its affiliates. All rights reserved.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License, version 2.0,
as published by the Free Software Foundation.
This program is also distributed with certain software (including
but not limited to OpenSSL) that is licensed under separate terms,
as designated in a particular file or component or in included license
documentation. The authors of MySQL hereby grant you an additional
permission to link the program and your derivative works with the
separately licensed software that they have included with MySQL.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License, version 2.0, for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
#ifndef RPL_INFO_HANDLER_H
#define RPL_INFO_HANDLER_H
#include <stddef.h>
#include <sys/types.h>
#include <type_traits>
#include "my_bitmap.h"
#include "my_inttypes.h"
class Rpl_info_values;
class Server_ids;
enum enum_info_repository {
INFO_REPOSITORY_FILE = 0,
INFO_REPOSITORY_TABLE,
INFO_REPOSITORY_DUMMY,
/*
Add new types of repository before this
entry.
*/
INVALID_INFO_REPOSITORY
};
/*
Defines status on the repository.
*/
enum enum_return_check {
REPOSITORY_DOES_NOT_EXIST = 1,
REPOSITORY_EXISTS,
ERROR_CHECKING_REPOSITORY
};
class Rpl_info_handler {
friend class Rpl_info_factory;
public:
/*
* enum class to indicate the status of getting field using
* do_get_info() of handler classes.
*/
enum class enum_field_get_status : int {
/* status is success but field has NULL value. */
FIELD_VALUE_NOT_NULL = 0,
FIELD_VALUE_IS_NULL = 1,
FAILURE = 2
};
Rpl_info_handler(const Rpl_info_handler &handler) = delete;
Rpl_info_handler &operator=(const Rpl_info_handler &handler) = delete;
/**
After creating an object and assembling components, this method is
used to initialize internal structures. Everything that does not
depend on other components (e.g. mutexes) should be placed in the
object's constructor though.
@retval false success,
@retval true otherwise error.
*/
int init_info() { return do_init_info(); }
/**
Checks the repository's status.
@retval REPOSITORY_EXISTS reposistory is ready to
be used.
@retval REPOSITORY_DOES_NOT_EXIST repository needs to be
configured.
@retval ERROR_CHECKING_REPOSITORY error while checking the
reposistory.
*/
enum_return_check check_info() { return do_check_info(); }
/**
Flushes and syncs in-memory information into a stable storage (i.e.
repository). Usually, syncing after flushing depends on other options
such as @c relay-log-info-sync, @c master-info-sync. These options
dictate after how many events or transactions the information
should be synced. We can ignore them and always sync by setting the
parameter @c force, which is by default @c false, to @c true.
So if the number of events is below a threshold, the parameter
@c force is false and we are using a file system as a storage
system, it may happen that the changes will only end up in the
operating system's cache and a crash may lead to inconsistencies.
@retval false No error
@retval true Failure
*/
int flush_info(const bool force) { return do_flush_info(force); }
/**
Deletes any information in it and in some cases the repository.
The decision to remove the repository is delegated to the
developer.
@retval false No error
@retval true Failure
*/
int remove_info() { return do_remove_info(); }
/**
Deletes any information in the repository. In contrast to the
@c remove_info() method, the repository is not removed.
@retval false No error
@retval true Failure
*/
int clean_info() { return do_clean_info(); }
/**
Closes access to the repository.
@retval false No error
@retval true Failure
*/
void end_info() { do_end_info(); }
/**
Enables the storage system to receive reads, i.e.
getters.
@retval false No error
@retval true Failure
*/
int prepare_info_for_read() { return (do_prepare_info_for_read()); }
/**
Enables the storage system to receive writes, i.e.
setters.
@retval false No error
@retval true Failure
*/
int prepare_info_for_write() { return (do_prepare_info_for_write()); }
/**
Gets the type of the repository that is used.
@return Type of repository.
*/
uint get_rpl_info_type() { return (do_get_rpl_info_type()); }
/**
Returns a string corresponding to the type.
*/
const char *get_rpl_info_type_str();
/**
Sets the value of a field to @c value.
Any call must be done in the right order which
is defined by the caller that wants to persist
the information.
@param[in] value Value to be set.
@retval false No error
@retval true Failure
*/
template <class TypeHandler>
bool set_info(TypeHandler const value) {
if (cursor >= ninfo || prv_error) return true;
if (!(prv_error = do_set_info(cursor, value))) cursor++;
return (prv_error);
}
template <class TypeHandler>
bool set_info(TypeHandler const value, const size_t size) {
if (cursor >= ninfo || prv_error) return true;
if (!(prv_error = do_set_info(cursor, value, size))) cursor++;
return (prv_error);
}
/**
set the value of a field pointed at @c pk_cursor to
@ value.
@param[in] pk_cursor cursor for the filed value.
@param[in] value fieled[pk_cursor] would be set
this value.
@retval false ok
@retval true error.
*/
template <class TypeHandler>
bool set_info(int pk_cursor, TypeHandler const value) {
if (pk_cursor >= ninfo) return true;
return (do_set_info(pk_cursor, value));
}
/**
Returns the value of a field.
Any call must be done in the right order which
is defined by the caller that wants to return
the information.
@param[in] value Value to be set.
@param[in] default_value Returns a default value
if the field is empty.
@retval false No error
@retval true Failure
*/
template <class TypeHandlerPointer, class TypeHandler>
enum_field_get_status get_info(TypeHandlerPointer value,
TypeHandler const default_value) {
if (cursor >= ninfo || prv_get_error == enum_field_get_status::FAILURE)
return enum_field_get_status::FAILURE;
if ((prv_get_error = do_get_info(cursor, value, default_value)) !=
enum_field_get_status::FAILURE)
cursor++;
return (prv_get_error);
}
/**
Returns the value of a string field.
Any call must be done in the right order which
is defined by the caller that wants to return
the information.
@param[in] value Value to be returned.
@param[in] size Max size of the string to be
returned.
@param[in] default_value Returns a default value
if the field is empty.
TypeHandler is either char* or uchar*, while
default_value is const char* or const uchar*.
Some type trait magic is required to make
char* / uchar* into const char* / uchar*.
@retval false No error
@retval true Failure
*/
template <class TypeHandler>
enum_field_get_status get_info(
TypeHandler value, const size_t size,
std::add_const_t<std::remove_pointer_t<TypeHandler>> *default_value) {
if (cursor >= ninfo || prv_get_error == enum_field_get_status::FAILURE)
return enum_field_get_status::FAILURE;
if ((prv_get_error = do_get_info(cursor, value, size, default_value)) !=
enum_field_get_status::FAILURE)
cursor++;
return (prv_get_error);
}
/**
Returns the value of a Server_id field.
Any call must be done in the right order which
is defined by the caller that wants to return
the information.
@param[out] value Value to be return.
@param[in] default_value Returns a default value
if the field is empty.
@retval false No error
@retval true Failure
*/
enum_field_get_status get_info(Server_ids *value,
const Server_ids *default_value) {
if (cursor >= ninfo || prv_get_error == enum_field_get_status::FAILURE)
return enum_field_get_status::FAILURE;
if ((prv_get_error = do_get_info(cursor, value, default_value)) !=
enum_field_get_status::FAILURE)
cursor++;
return (prv_get_error);
}
/**
Returns the number of fields handled by this handler.
@return Number of fields handled by the handler.
*/
int get_number_info() { return ninfo; }
/**
Configures the number of events after which the info (e.g.
master info, relay log info) must be synced when flush() is
called.
@param[in] period Number of events.
*/
void set_sync_period(uint period);
/**
Returns a string describing the repository. For instance, if the
repository is a file, the returned string is path where data is
stored.
@return a pointer to a string.
*/
char *get_description_info() { return (do_get_description_info()); }
/**
Any transactional repository may have its updates rolled back in case
of a failure. If this is possible, the repository is classified as
transactional.
@retval true If transactional.
@retval false Otherwise.
*/
bool is_transactional() { return do_is_transactional(); }
/**
Updates the value returned by the member function is_transactional()
because it may be expensive to compute it whenever is_transactional()
is called.
In the current implementation, the type of the repository can only be
changed when replication, i.e. slave, is stopped. For that reason,
this member function, i.e. update_is__transactional(), must be called
when slave is starting.
@retval false No error
@retval true Failure
*/
bool update_is_transactional() { return do_update_is_transactional(); }
/*
Pre-store information before writing it to the repository and if
necessary after reading it from the repository. The decision is
delegated to the sub-classes.
*/
Rpl_info_values *field_values;
virtual ~Rpl_info_handler();
protected:
/* Number of fields to be stored in the repository. */
int ninfo;
/* From/To where we should start reading/writing. */
int cursor;
/* Registers if there was failure while accessing a field/information. */
bool prv_error;
enum_field_get_status prv_get_error;
/*
Keeps track of the number of events before fsyncing. The option
--sync-master-info and --sync-relay-log-info determine how many
events should be processed before fsyncing.
*/
uint sync_counter;
/*
The number of events after which we should fsync.
*/
uint sync_period;
/**
Bitset holding which of the fields are allowed to be `NULL`.
*/
MY_BITMAP nullable_fields;
Rpl_info_handler(const int nparam, MY_BITMAP const *nullable_bitmap);
/**
Checks whether or not the field at position `pos` is allowed to be `NULL`.
@return true if the field is allowed to be `NULL` and false otherwise.
*/
bool is_field_nullable(int pos);
private:
virtual int do_init_info() = 0;
virtual int do_init_info(uint instance) = 0;
virtual enum_return_check do_check_info() = 0;
virtual enum_return_check do_check_info(uint instance) = 0;
virtual int do_flush_info(const bool force) = 0;
virtual int do_remove_info() = 0;
virtual int do_clean_info() = 0;
virtual void do_end_info() = 0;
virtual int do_prepare_info_for_read() = 0;
virtual int do_prepare_info_for_write() = 0;
virtual bool do_set_info(const int pos, const char *value) = 0;
virtual bool do_set_info(const int pos, const uchar *value,
const size_t size) = 0;
virtual bool do_set_info(const int pos, const ulong value) = 0;
virtual bool do_set_info(const int pos, const int value) = 0;
virtual bool do_set_info(const int pos, const float value) = 0;
virtual bool do_set_info(const int pos, const Server_ids *value) = 0;
virtual bool do_set_info(const int pos, const std::nullptr_t value) = 0;
virtual bool do_set_info(const int pos, const std::nullptr_t value,
const size_t size) = 0;
virtual enum_field_get_status do_get_info(const int pos, char *value,
const size_t size,
const char *default_value) = 0;
virtual enum_field_get_status do_get_info(const int pos, uchar *value,
const size_t size,
const uchar *default_value) = 0;
virtual enum_field_get_status do_get_info(const int pos, ulong *value,
const ulong default_value) = 0;
virtual enum_field_get_status do_get_info(const int pos, int *value,
const int default_value) = 0;
virtual enum_field_get_status do_get_info(const int pos, float *value,
const float default_value) = 0;
virtual enum_field_get_status do_get_info(
const int pos, Server_ids *value, const Server_ids *default_value) = 0;
virtual char *do_get_description_info() = 0;
virtual bool do_is_transactional() = 0;
virtual bool do_update_is_transactional() = 0;
virtual uint do_get_rpl_info_type() = 0;
};
bool operator!(Rpl_info_handler::enum_field_get_status status);
#ifndef DBUG_OFF
extern ulong w_rr;
extern uint mts_debug_concurrent_access;
#endif
#endif /* RPL_INFO_HANDLER_H */