2017-04-18 20:43:20 +02:00
|
|
|
/******************************************************
|
|
|
|
Copyright (c) 2011-2013 Percona LLC and/or its affiliates.
|
|
|
|
|
|
|
|
Common declarations for XtraBackup.
|
|
|
|
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
|
|
it under the terms of the GNU General Public License as published by
|
|
|
|
the Free Software Foundation; version 2 of the License.
|
|
|
|
|
|
|
|
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 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
|
2019-05-11 21:19:05 +02:00
|
|
|
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335 USA
|
2017-04-18 20:43:20 +02:00
|
|
|
|
|
|
|
*******************************************************/
|
|
|
|
|
|
|
|
#ifndef XB_COMMON_H
|
|
|
|
#define XB_COMMON_H
|
|
|
|
|
|
|
|
#include <my_global.h>
|
|
|
|
#include <mysql_version.h>
|
|
|
|
#include <stdarg.h>
|
2017-11-24 11:57:44 +01:00
|
|
|
#include <my_sys.h>
|
2017-04-18 20:43:20 +02:00
|
|
|
|
2017-04-18 21:05:57 +02:00
|
|
|
|
2018-03-22 09:49:16 +01:00
|
|
|
/** Determine if (i) is a user tablespace id or not. */
|
|
|
|
# define fil_is_user_tablespace_id(i) (i != 0 \
|
|
|
|
&& !srv_is_undo_tablespace(i))
|
2017-04-18 21:05:57 +02:00
|
|
|
|
|
|
|
#ifdef _MSC_VER
|
|
|
|
#define stat _stati64
|
|
|
|
#define PATH_MAX MAX_PATH
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#ifndef HAVE_VASPRINTF
|
|
|
|
static inline int vasprintf(char **strp, const char *fmt, va_list args)
|
|
|
|
{
|
|
|
|
int len;
|
|
|
|
#ifdef _MSC_VER
|
|
|
|
len = _vscprintf(fmt, args);
|
|
|
|
#else
|
|
|
|
len = vsnprintf(NULL, 0, fmt, args);
|
|
|
|
#endif
|
|
|
|
if (len < 0)
|
|
|
|
{
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
*strp = (char *)malloc(len + 1);
|
|
|
|
if (!*strp)
|
|
|
|
{
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
vsprintf(*strp, fmt, args);
|
|
|
|
return len;
|
|
|
|
}
|
|
|
|
|
|
|
|
static inline int asprintf(char **strp, const char *fmt,...)
|
|
|
|
{
|
|
|
|
va_list args;
|
|
|
|
va_start(args, fmt);
|
|
|
|
int len = vasprintf(strp, fmt, args);
|
|
|
|
va_end(args);
|
|
|
|
return len;
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2017-04-18 20:43:20 +02:00
|
|
|
#define xb_a(expr) \
|
|
|
|
do { \
|
|
|
|
if (!(expr)) { \
|
2019-01-14 22:28:23 +01:00
|
|
|
fprintf(stderr,"Assertion \"%s\" failed at %s:%lu\n", \
|
2017-04-18 20:43:20 +02:00
|
|
|
#expr, __FILE__, (ulong) __LINE__); \
|
|
|
|
abort(); \
|
|
|
|
} \
|
|
|
|
} while (0);
|
|
|
|
|
|
|
|
#ifdef XB_DEBUG
|
|
|
|
#define xb_ad(expr) xb_a(expr)
|
|
|
|
#else
|
|
|
|
#define xb_ad(expr)
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define XB_DELTA_INFO_SUFFIX ".meta"
|
|
|
|
|
2019-01-15 22:47:54 +01:00
|
|
|
static inline int msg1(uint thread_num, const char *prefix, const char *fmt, va_list args)
|
2019-01-14 22:28:23 +01:00
|
|
|
{
|
|
|
|
int result;
|
|
|
|
time_t t = time(NULL);
|
|
|
|
char date[100];
|
|
|
|
char *line;
|
|
|
|
strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&t));
|
|
|
|
result = vasprintf(&line, fmt, args);
|
|
|
|
if (result != -1) {
|
|
|
|
if (fmt && fmt[strlen(fmt)] != '\n')
|
2019-01-15 22:47:54 +01:00
|
|
|
result = fprintf(stderr, "[%02u] %s%s %s\n", thread_num, prefix, date, line);
|
2019-01-14 22:28:23 +01:00
|
|
|
else
|
2019-01-15 22:47:54 +01:00
|
|
|
result = fprintf(stderr, "[%02u] %s%s %s", thread_num, prefix, date, line);
|
2019-01-14 22:28:23 +01:00
|
|
|
free(line);
|
|
|
|
}
|
|
|
|
return result;
|
2017-04-18 20:43:20 +02:00
|
|
|
}
|
2019-01-15 22:47:54 +01:00
|
|
|
|
|
|
|
static inline ATTRIBUTE_FORMAT(printf, 2, 3) int msg(unsigned int thread_num, const char *fmt, ...)
|
2017-04-18 20:43:20 +02:00
|
|
|
{
|
2019-01-14 22:28:23 +01:00
|
|
|
int result;
|
|
|
|
va_list args;
|
|
|
|
va_start(args, fmt);
|
2019-01-15 22:47:54 +01:00
|
|
|
result = msg1(thread_num,"", fmt, args);
|
2019-01-14 22:28:23 +01:00
|
|
|
va_end(args);
|
|
|
|
return result;
|
|
|
|
}
|
2017-04-18 20:43:20 +02:00
|
|
|
|
2019-01-15 22:47:54 +01:00
|
|
|
static inline ATTRIBUTE_FORMAT(printf, 1, 2) int msg(const char *fmt, ...)
|
2019-01-14 22:28:23 +01:00
|
|
|
{
|
|
|
|
int result;
|
|
|
|
va_list args;
|
|
|
|
va_start(args, fmt);
|
2019-01-15 22:47:54 +01:00
|
|
|
result = msg1(0, "", fmt, args);
|
2019-01-14 22:28:23 +01:00
|
|
|
va_end(args);
|
|
|
|
return result;
|
2017-04-18 20:43:20 +02:00
|
|
|
}
|
|
|
|
|
2019-01-15 22:47:54 +01:00
|
|
|
static inline ATTRIBUTE_FORMAT(printf, 1,2) ATTRIBUTE_NORETURN void die(const char *fmt, ...)
|
|
|
|
{
|
|
|
|
va_list args;
|
|
|
|
va_start(args, fmt);
|
|
|
|
msg1(0, "FATAL ERROR: ", fmt, args);
|
|
|
|
va_end(args);
|
|
|
|
fflush(stderr);
|
|
|
|
_exit(EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
|
2019-01-14 22:28:23 +01:00
|
|
|
|
2017-04-18 20:43:20 +02:00
|
|
|
/* Use POSIX_FADV_NORMAL when available */
|
|
|
|
|
|
|
|
#ifdef POSIX_FADV_NORMAL
|
|
|
|
# define USE_POSIX_FADVISE
|
|
|
|
#else
|
|
|
|
# define POSIX_FADV_NORMAL
|
|
|
|
# define POSIX_FADV_SEQUENTIAL
|
|
|
|
# define POSIX_FADV_DONTNEED
|
2023-12-21 05:29:57 +01:00
|
|
|
# define posix_fadvise(fd, offset, len, advice) do { (void)offset; } while(0)
|
2017-04-18 20:43:20 +02:00
|
|
|
#endif
|
|
|
|
|
|
|
|
/***********************************************************************
|
|
|
|
Computes bit shift for a given value. If the argument is not a power
|
|
|
|
of 2, returns 0.*/
|
2021-07-22 10:22:47 +02:00
|
|
|
static inline unsigned get_bit_shift(size_t value)
|
2017-04-18 20:43:20 +02:00
|
|
|
{
|
2021-07-22 10:22:47 +02:00
|
|
|
unsigned shift;
|
2017-04-18 20:43:20 +02:00
|
|
|
|
|
|
|
if (value == 0)
|
|
|
|
return 0;
|
|
|
|
|
2017-04-18 21:05:57 +02:00
|
|
|
for (shift = 0; !(value & 1); shift++) {
|
2017-04-18 20:43:20 +02:00
|
|
|
value >>= 1;
|
|
|
|
}
|
|
|
|
return (value >> 1) ? 0 : shift;
|
|
|
|
}
|
|
|
|
|
|
|
|
/****************************************************************************
|
|
|
|
Read 'len' bytes from 'fd'. It is identical to my_read(..., MYF(MY_FULL_IO)),
|
|
|
|
i.e. tries to combine partial reads into a single block of size 'len', except
|
|
|
|
that it bails out on EOF or error, and returns the number of successfully read
|
|
|
|
bytes instead. */
|
|
|
|
static inline size_t
|
|
|
|
xb_read_full(File fd, uchar *buf, size_t len)
|
|
|
|
{
|
|
|
|
size_t tlen = 0;
|
|
|
|
size_t tbytes;
|
|
|
|
|
|
|
|
while (tlen < len) {
|
|
|
|
tbytes = my_read(fd, buf, len - tlen, MYF(MY_WME));
|
|
|
|
if (tbytes == 0 || tbytes == MY_FILE_ERROR) {
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
buf += tbytes;
|
|
|
|
tlen += tbytes;
|
|
|
|
}
|
|
|
|
|
|
|
|
return tlen;
|
|
|
|
}
|
|
|
|
|
|
|
|
#endif
|