2017-02-14 21:42:28 +02:00

214 lines
5.6 KiB
C

/*
* Copyright (c) 2016 MariaDB Corporation Ab
*
* Use of this software is governed by the Business Source License included
* in the LICENSE.TXT file and at www.mariadb.com/bsl11.
*
* Change Date: 2019-07-01
*
* On the date above, in accordance with the Business Source License, use
* of this software will be governed by version 2 or later of the General
* Public License.
*/
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <stdio.h>
#include <unistd.h>
#include <binlog_common.h>
#include <blr_constants.h>
#include <maxscale/log_manager.h>
/**
* @file binlog_common.c - Common binary log code shared between multiple modules
*
* This file contains functions that are common to multiple modules that all
* handle MySQL/MariaDB binlog files.
*
* @verbatim
* Revision History
*
* Date Who Description
* 7/3/16 Markus Makela Initial implementation
*
* @endverbatim
*/
/**
* Get the next binlog file name.
*
* @param router The router instance
* @return 0 on error, >0 as sequence number
*/
int blr_file_get_next_binlogname(const char *binlog_name)
{
char *sptr;
int filenum;
if ((sptr = strrchr(binlog_name, '.')) == NULL)
{
return 0;
}
filenum = atoi(sptr + 1);
if (filenum)
{
filenum++;
}
return filenum;
}
/**
* @brief Check if the next binlog file exists and is readable
* @param binlogdir Directory where the binlogs are
* @param binlog Current binlog name
* @return True if next binlog file exists and is readable
*/
bool binlog_next_file_exists(const char* binlogdir, const char* binlog)
{
bool rval = false;
int filenum = blr_file_get_next_binlogname(binlog);
if (filenum)
{
char *sptr = strrchr(binlog, '.');
if (sptr)
{
char buf[BLRM_BINLOG_NAME_STR_LEN + 1];
char filename[PATH_MAX + 1];
char next_file[BLRM_BINLOG_NAME_STR_LEN + 1];
int offset = sptr - binlog;
memcpy(buf, binlog, offset);
buf[offset] = '\0';
sprintf(next_file, BINLOG_NAMEFMT, buf, filenum);
snprintf(filename, PATH_MAX, "%s/%s", binlogdir, next_file);
filename[PATH_MAX] = '\0';
/* Next file in sequence doesn't exist */
if (access(filename, R_OK) == -1)
{
MXS_DEBUG("File '%s' does not yet exist.", filename);
}
else
{
rval = true;
}
}
}
return rval;
}
/**
* Extract a numeric field from a packet of the specified number of bits
*
* @param src The raw packet source
* @param birs The number of bits to extract (multiple of 8)
*/
uint32_t extract_field(uint8_t *src, int bits)
{
uint32_t rval = 0, shift = 0;
while (bits > 0)
{
rval |= (*src++) << shift;
shift += 8;
bits -= 8;
}
return rval;
}
/**
* Convert binlog event type to string
* @param type Event type
* @return Event type in string format
*/
const char* binlog_event_name(int type)
{
switch (type)
{
case START_EVENT_V3:
return "START_EVENT_V3";
case QUERY_EVENT:
return "QUERY_EVENT";
case STOP_EVENT:
return "STOP_EVENT";
case ROTATE_EVENT:
return "ROTATE_EVENT";
case INTVAR_EVENT:
return "INTVAR_EVENT";
case LOAD_EVENT:
return "LOAD_EVENT";
case SLAVE_EVENT:
return "SLAVE_EVENT";
case CREATE_FILE_EVENT:
return "CREATE_FILE_EVENT";
case APPEND_BLOCK_EVENT:
return "APPEND_BLOCK_EVENT";
case EXEC_LOAD_EVENT:
return "EXEC_LOAD_EVENT";
case DELETE_FILE_EVENT:
return "DELETE_FILE_EVENT";
case NEW_LOAD_EVENT:
return "NEW_LOAD_EVENT";
case RAND_EVENT:
return "RAND_EVENT";
case USER_VAR_EVENT:
return "USER_VAR_EVENT";
case FORMAT_DESCRIPTION_EVENT:
return "FORMAT_DESCRIPTION_EVENT";
case XID_EVENT:
return "XID_EVENT";
case BEGIN_LOAD_QUERY_EVENT:
return "BEGIN_LOAD_QUERY_EVENT";
case EXECUTE_LOAD_QUERY_EVENT:
return "EXECUTE_LOAD_QUERY_EVENT";
case TABLE_MAP_EVENT:
return "TABLE_MAP_EVENT";
case WRITE_ROWS_EVENTv0:
return "WRITE_ROWS_EVENTv0";
case UPDATE_ROWS_EVENTv0:
return "UPDATE_ROWS_EVENTv0";
case DELETE_ROWS_EVENTv0:
return "DELETE_ROWS_EVENTv0";
case WRITE_ROWS_EVENTv1:
return "WRITE_ROWS_EVENTv1";
case UPDATE_ROWS_EVENTv1:
return "UPDATE_ROWS_EVENTv1";
case DELETE_ROWS_EVENTv1:
return "DELETE_ROWS_EVENTv1";
case INCIDENT_EVENT:
return "INCIDENT_EVENT";
case HEARTBEAT_EVENT:
return "HEARTBEAT_EVENT";
case IGNORABLE_EVENT:
return "IGNORABLE_EVENT";
case ROWS_QUERY_EVENT:
return "ROWS_QUERY_EVENT";
case WRITE_ROWS_EVENTv2:
return "WRITE_ROWS_EVENTv2";
case UPDATE_ROWS_EVENTv2:
return "UPDATE_ROWS_EVENTv2";
case DELETE_ROWS_EVENTv2:
return "DELETE_ROWS_EVENTv2";
case GTID_EVENT:
return "GTID_EVENT";
case ANONYMOUS_GTID_EVENT:
return "ANONYMOUS_GTID_EVENT";
case PREVIOUS_GTIDS_EVENT:
return "PREVIOUS_GTIDS_EVENT";
case MARIADB_ANNOTATE_ROWS_EVENT:
return "MARIADB_ANNOTATE_ROWS_EVENT";
case MARIADB10_BINLOG_CHECKPOINT_EVENT:
return "MARIADB10_BINLOG_CHECKPOINT_EVENT";
case MARIADB10_GTID_EVENT:
return "MARIADB10_GTID_EVENT";
case MARIADB10_GTID_GTID_LIST_EVENT:
return "MARIADB10_GTID_GTID_LIST_EVENT";
default:
return "UNKNOWN_EVENT";
}
}