Commit e69becf1 authored by monty@narttu.mysql.fi's avatar monty@narttu.mysql.fi

changed to use IO_CACHE instead of FILE

parent 7a013339
monty@tik.mysql.com
monty@narttu.mysql.fi
......@@ -3610,10 +3610,13 @@ similar system. In the worst case, we may require access to your system
to be able to create a binary distribution.
@item
If you can provide accommodations and pay for traveler fares, you can even
get a @strong{MySQL} developer to visit you and offer you help with your
troubles. Extended login support entitles you to one personal
encounter per year, but we are always very flexible towards our customers!
If you can provide accommodations and pay for traveler fares, you can
even get a @strong{MySQL} developer to visit you and offer you help with
your troubles. Extended login support entitles you to one personal
encounter per year, but we are always very flexible towards our
customers! If the visit takes 16 hours or more, the first 8 hours is
without charge. For the hours above 8 hours, you will be charged with a
rate that is at least 20 % less than our standard rates.
@end itemize
@node Installing, Compatibility, Licensing and Support, Top
......@@ -38367,6 +38370,9 @@ though, so 3.23 is not released as a stable version yet.
@appendixsubsec Changes in release 3.23.28
@itemize @bullet
@item
Changed all log files to use our own IO_CACHE mechanism instead of
FILE:s to avoid OS problems when there is many files open.
@item
Added options @code{--open-files} and @code{--timezone} to @code{safe_mysqld}.
@item
Fixed fatal bug in @code{CREATE TEMPORARY TABLE ...SELECT ...}.
......@@ -25,7 +25,7 @@
** * *
** *************************
*/
#define IMPORT_VERSION "2.5"
#define IMPORT_VERSION "2.6"
#include <global.h>
#include <my_sys.h>
......@@ -125,7 +125,7 @@ file. The SQL command 'LOAD DATA INFILE' is used to import the rows.\n");
Give the column names in a comma separated list.\n\
This is same as giving columns to LOAD DATA INFILE.\n\
-C, --compress Use compression in server/client protocol\n\
-d, --delete Deletes first all rows from table.\n\
-d, --delete First delete all rows from table.\n\
-f, --force Continue even if we get an sql-error.\n\
-h, --host=... Connect to host.\n\
-i, --ignore If duplicate unique key was found, keep old row.\n\
......
......@@ -95,17 +95,6 @@ bool String::realloc(uint32 alloc_length)
return FALSE;
}
#ifdef NOT_NEEDED
bool String::set(long num)
{
if (alloc(14))
return TRUE;
str_length=(uint32) (int10_to_str(num,Ptr,-10)-Ptr);
return FALSE;
}
#endif
bool String::set(longlong num)
{
if (alloc(21))
......@@ -274,6 +263,7 @@ bool String::append(const char *s,uint32 arg_length)
return FALSE;
}
#ifdef TO_BE_REMOVED
bool String::append(FILE* file, uint32 arg_length, myf my_flags)
{
if (realloc(str_length+arg_length))
......@@ -286,6 +276,20 @@ bool String::append(FILE* file, uint32 arg_length, myf my_flags)
str_length+=arg_length;
return FALSE;
}
#endif
bool String::append(IO_CACHE* file, uint32 arg_length)
{
if (realloc(str_length+arg_length))
return TRUE;
if (my_b_read(file, (byte*) Ptr + str_length, arg_length))
{
shrink(str_length);
return TRUE;
}
str_length+=arg_length;
return FALSE;
}
uint32 String::numchars()
{
......
......@@ -107,9 +107,9 @@ public:
Alloced_length=0;
my_free(Ptr,MYF(0));
Ptr=0;
str_length=0; /* Safety */
}
}
inline bool alloc(uint32 arg_length)
{
if (arg_length < Alloced_length)
......@@ -152,7 +152,7 @@ public:
bool copy(const char *s,uint32 arg_length); // Allocate new string
bool append(const String &s);
bool append(const char *s,uint32 arg_length=0);
bool append(FILE* file, uint32 arg_length, myf my_flags);
bool append(IO_CACHE* file, uint32 arg_length);
int strstr(const String &search,uint32 offset=0); // Returns offset to substring or -1
int strrstr(const String &search,uint32 offset=0); // Returns offset to substring or -1
bool replace(uint32 offset,uint32 arg_length,const String &to);
......
......@@ -59,6 +59,7 @@ extern int NEAR my_errno; /* Last error in mysys */
#define MY_WME 16 /* Write message on error */
#define MY_WAIT_IF_FULL 32 /* Wait and try again if disk full error */
#define MY_RAID 64 /* Support for RAID (not the "Johnson&Johnson"-s one ;) */
#define MY_DONT_CHECK_FILESIZE 128 /* Option to init_io_cache() */
#define MY_LINK_WARNING 32 /* my_redel() gives warning if links */
#define MY_COPYTIME 64 /* my_redel() copys time */
#define MY_HOLD_ORIGINAL_MODES 128 /* my_copy() holds to file modes */
......@@ -505,6 +506,10 @@ extern int my_block_write(IO_CACHE *info, const byte *Buffer,
uint Count, my_off_t pos);
extern int flush_io_cache(IO_CACHE *info);
extern int end_io_cache(IO_CACHE *info);
extern uint my_b_fill(IO_CACHE *info);
extern void my_b_seek(IO_CACHE *info,my_off_t pos);
extern uint my_b_gets(IO_CACHE *info, char *to, uint max_length);
extern uint my_b_printf(IO_CACHE *info, const char* fmt, ...);
extern my_bool open_cached_file(IO_CACHE *cache,const char *dir,
const char *prefix, uint cache_size,
myf cache_myflags);
......
No preview for this file type
......@@ -26,7 +26,7 @@ libmysys_a_SOURCES = my_init.c my_getwd.c mf_getdate.c\
mf_path.c mf_loadpath.c\
my_open.c my_create.c my_seek.c my_read.c \
my_pread.c my_write.c \
mf_reccache.c mf_keycache.c \
mf_keycache.c \
mf_iocache.c mf_cache.c mf_tempfile.c \
my_lock.c mf_brkhant.c my_alarm.c \
my_malloc.c my_realloc.c my_once.c mulalloc.c \
......
......@@ -74,7 +74,7 @@ my_bool open_cached_file(IO_CACHE *cache, const char* dir, const char *prefix,
}
my_free(cache->dir, MYF(MY_ALLOW_ZERO_PTR));
my_free(cache->prefix,MYF(MY_ALLOW_ZERO_PTR));
DBUG_RETURN(0);
DBUG_RETURN(1);
}
/* Create the temporary file */
......@@ -101,10 +101,12 @@ void close_cached_file(IO_CACHE *cache)
DBUG_ENTER("close_cached_file");
if (my_b_inited(cache))
{
File file=cache->file;
cache->file= -1; /* Don't flush data */
(void) end_io_cache(cache);
if (cache->file >= 0)
if (file >= 0)
{
(void) my_close(cache->file,MYF(0));
(void) my_close(file,MYF(0));
#ifdef CANT_DELETE_OPEN_FILES
if (cache->file_name)
{
......
......@@ -22,10 +22,13 @@
(and get a EOF-error).
Possibly use of asyncronic io.
macros for read and writes for faster io.
Used instead of FILE when reading or writing hole files.
This shall make mf_rec_cache obsolite.
One can change info->pos_in_file to a higer value to skipp bytes in file if
Used instead of FILE when reading or writing whole files.
This will make mf_rec_cache obsolete.
One can change info->pos_in_file to a higher value to skip bytes in file if
also info->rc_pos is set to info->rc_end.
If called through open_cached_file(), then the temporary file will
only be created if a write exeeds the file buffer or if one calls
flush_io_cache().
*/
#define MAP_TO_USE_RAID
......@@ -40,7 +43,7 @@ static void my_aiowait(my_aio_result *result);
/*
** if cachesize == 0 then use default cachesize (from s-file)
** if file == -1 then real_open_cached_file() will be called to
** if file == -1 then real_open_cached_file() will be called.
** returns 0 if ok
*/
......@@ -59,6 +62,12 @@ int init_io_cache(IO_CACHE *info, File file, uint cachesize,
min_cache=use_async_io ? IO_SIZE*4 : IO_SIZE*2;
if (type == READ_CACHE)
{ /* Assume file isn't growing */
if (cache_myflags & MY_DONT_CHECK_FILESIZE)
{
cache_myflags &= ~MY_DONT_CHECK_FILESIZE;
}
else
{
my_off_t file_pos,end_of_file;
if ((file_pos=my_tell(file,MYF(0)) == MY_FILEPOS_ERROR))
DBUG_RETURN(1);
......@@ -72,6 +81,7 @@ int init_io_cache(IO_CACHE *info, File file, uint cachesize,
use_async_io=0; /* No nead to use async */
}
}
}
for (;;)
{
......@@ -545,7 +555,6 @@ int my_block_write(register IO_CACHE *info, const byte *Buffer, uint Count,
return error;
}
/* Flush write cache */
int flush_io_cache(IO_CACHE *info)
......@@ -565,7 +574,9 @@ int flush_io_cache(IO_CACHE *info)
length=(uint) (info->rc_pos - info->buffer);
if (info->seek_not_done)
{ /* File touched, do seek */
VOID(my_seek(info->file,info->pos_in_file,MY_SEEK_SET,MYF(0)));
if (my_seek(info->file,info->pos_in_file,MY_SEEK_SET,MYF(0)) ==
MY_FILEPOS_ERROR)
DBUG_RETURN((info->error= -1));
info->seek_not_done=0;
}
info->rc_pos=info->buffer;
......
......@@ -21,74 +21,49 @@
#include <stdarg.h>
#include <m_ctype.h>
int my_vsnprintf(char* str, size_t n, const char* fmt, va_list ap)
int my_vsnprintf(char *to, size_t n, const char* fmt, va_list ap)
{
uint olen = 0, plen;
const char *tpos;
reg1 char *endpos;
reg2 char * par;
char* ebuff = str;
char *start=to, *end=to+n-1;
endpos=ebuff;
tpos = fmt;
while (*tpos)
for (; *fmt ; fmt++)
{
if (tpos[0] != '%')
if (fmt[0] != '%')
{
if(olen + 1 >= n)
if (to == end) /* End of buffer */
break;
*endpos++= *tpos++; /* Copy ordinary char */
olen++;
*to++= *fmt; /* Copy ordinary char */
continue;
}
if (*++tpos == '%') /* test if %% */
{
olen--;
}
else
{
/* Skipp if max size is used (to be compatible with printf) */
while (isdigit(*tpos) || *tpos == '.' || *tpos == '-')
tpos++;
if (*tpos == 's') /* String parameter */
while (isdigit(*fmt) || *fmt == '.' || *fmt == '-')
fmt++;
if (*fmt == 's') /* String parameter */
{
par = va_arg(ap, char *);
plen = (uint) strlen(par);
if (olen + plen < n) /* Replace if possible */
reg2 char *par = va_arg(ap, char *);
uint plen = (uint) strlen(par);
if ((uint) (end-to) > plen) /* Replace if possible */
{
endpos=strmov(endpos,par);
tpos++;
olen+=plen;
to=strmov(to,par);
continue;
}
}
else if (*tpos == 'd' || *tpos == 'u') /* Integer parameter */
else if (*fmt == 'd' || *fmt == 'u') /* Integer parameter */
{
register int iarg;
if ((uint) (end-to) < 16)
break;
iarg = va_arg(ap, int);
if(olen + 16 >= n) break;
if (*tpos == 'd')
plen= (uint) (int2str((long) iarg,endpos, -10) - endpos);
if (*fmt == 'd')
to=int10_to_str((long) iarg,to, -10);
else
plen= (uint) (int2str((long) (uint) iarg,endpos,10)- endpos);
if (olen + plen < n) /* Replace parameter if possible */
{
endpos+=plen;
tpos++;
olen+=plen;
to=int10_to_str((long) (uint) iarg,to,10);
continue;
}
/* We come here on '%%', unknown code or too long parameter */
if (to == end)
break;
*to++='%'; /* % used as % or unknown code */
}
}
*endpos++='%'; /* % used as % or unknown code */
}
*endpos='\0';
/* End of errmessage */
return olen;
*to='\0'; /* End of errmessage */
return (uint) (to - start);
}
This diff is collapsed.
This diff is collapsed.
......@@ -65,9 +65,9 @@ public:
int valid_exec_time; // if false, the exec time setting is bogus
uint32 server_id;
int write(FILE* file);
int write_header(FILE* file);
virtual int write_data(FILE* file __attribute__((unused))) { return 0; }
int write(IO_CACHE* file);
int write_header(IO_CACHE* file);
virtual int write_data(IO_CACHE* file __attribute__((unused))) { return 0; }
virtual Log_event_type get_type_code() = 0;
Log_event(time_t when_arg, ulong exec_time_arg = 0,
int valid_exec_time_arg = 0, uint32 server_id = 0): when(when_arg),
......@@ -92,11 +92,11 @@ public:
void print_header(FILE* file);
// if mutex is 0, the read will proceed without mutex
static Log_event* read_log_event(FILE* file, pthread_mutex_t* log_lock);
static Log_event* read_log_event(IO_CACHE* file, pthread_mutex_t* log_lock);
static Log_event* read_log_event(const char* buf, int max_buf);
#ifndef MYSQL_CLIENT
static int read_log_event(FILE* file, String* packet,
static int read_log_event(IO_CACHE* file, String* packet,
pthread_mutex_t* log_lock);
#endif
......@@ -132,18 +132,18 @@ public:
}
#endif
Query_log_event(FILE* file, time_t when, uint32 server_id);
Query_log_event(IO_CACHE* file, time_t when, uint32 server_id);
Query_log_event(const char* buf, int max_buf);
~Query_log_event()
{
if (data_buf)
{
my_free((gptr)data_buf, MYF(0));
my_free((gptr) data_buf, MYF(0));
}
}
Log_event_type get_type_code() { return QUERY_EVENT; }
int write(FILE* file);
int write_data(FILE* file); // returns 0 on success, -1 on error
int write(IO_CACHE* file);
int write_data(IO_CACHE* file); // returns 0 on success, -1 on error
int get_data_size()
{
return q_len + db_len + 2 +
......@@ -183,6 +183,8 @@ class Load_log_event: public Log_event
{
protected:
char* data_buf;
void Load_log_event::copy_log_event(const char *buf, ulong data_len);
public:
int thread_id;
uint32 table_name_len;
......@@ -272,17 +274,17 @@ public:
void set_fields(List<Item> &fields);
#endif
Load_log_event(FILE* file, time_t when, uint32 server_id);
Load_log_event(IO_CACHE * file, time_t when, uint32 server_id);
Load_log_event(const char* buf, int max_buf);
~Load_log_event()
{
if (data_buf)
{
my_free((gptr)data_buf, MYF(0));
my_free((gptr) data_buf, MYF(0));
}
}
Log_event_type get_type_code() { return LOAD_EVENT; }
int write_data(FILE* file); // returns 0 on success, -1 on error
int write_data(IO_CACHE* file); // returns 0 on success, -1 on error
int get_data_size()
{
return table_name_len + 2 + db_len + 2 + fname_len
......@@ -311,30 +313,26 @@ public:
created = (uint32) when;
memcpy(server_version, ::server_version, sizeof(server_version));
}
Start_log_event(FILE* file, time_t when_arg, uint32 server_id) :
Start_log_event(IO_CACHE* file, time_t when_arg, uint32 server_id) :
Log_event(when_arg, 0, 0, server_id)
{
char buf[sizeof(server_version) + sizeof(binlog_version) +
sizeof(created)];
my_fseek(file, 4L, MY_SEEK_CUR, MYF(MY_WME)); // skip the event length
if (my_fread(file, (byte*) buf, sizeof(buf), MYF(MY_NABP | MY_WME)))
sizeof(created)+4];
if (my_b_read(file, (byte*) buf, sizeof(buf)))
return;
binlog_version = uint2korr(buf);
memcpy(server_version, buf + 2, sizeof(server_version));
created = uint4korr(buf + 2 + sizeof(server_version));
binlog_version = uint2korr(buf+4);
memcpy(server_version, buf + 6, sizeof(server_version));
created = uint4korr(buf + 6 + sizeof(server_version));
}
Start_log_event(const char* buf);
~Start_log_event() {}
Log_event_type get_type_code() { return START_EVENT;}
int write_data(FILE* file)
int write_data(IO_CACHE* file)
{
if(my_fwrite(file, (byte*) &binlog_version, sizeof(binlog_version),
MYF(MY_NABP | MY_WME)) ||
my_fwrite(file, (byte*) server_version, sizeof(server_version),
MYF(MY_NABP | MY_WME)) ||
my_fwrite(file, (byte*) &created, sizeof(created),
MYF(MY_NABP | MY_WME)))
if (my_b_write(file, (byte*) &binlog_version, sizeof(binlog_version)) ||
my_b_write(file, (byte*) server_version, sizeof(server_version)) ||
my_b_write(file, (byte*) &created, sizeof(created)))
return -1;
return 0;
}
......@@ -354,12 +352,12 @@ public:
Intvar_log_event(uchar type_arg, ulonglong val_arg)
:Log_event(time(NULL)),val(val_arg),type(type_arg)
{}
Intvar_log_event(FILE* file, time_t when, uint32 server_id);
Intvar_log_event(IO_CACHE* file, time_t when, uint32 server_id);
Intvar_log_event(const char* buf);
~Intvar_log_event() {}
Log_event_type get_type_code() { return INTVAR_EVENT;}
int get_data_size() { return sizeof(type) + sizeof(val);}
int write_data(FILE* file);
int write_data(IO_CACHE* file);
void print(FILE* file, bool short_form = 0);
......@@ -370,10 +368,11 @@ class Stop_log_event: public Log_event
public:
Stop_log_event() :Log_event(time(NULL))
{}
Stop_log_event(FILE* file, time_t when_arg, uint32 server_id):
Stop_log_event(IO_CACHE* file, time_t when_arg, uint32 server_id):
Log_event(when_arg,0,0,server_id)
{
my_fseek(file, 4L, MY_SEEK_CUR, MYF(MY_WME)); // skip the event length
char skip[4];
my_b_read(file, skip, sizeof(skip)); // skip the event length
}
Stop_log_event(const char* buf):Log_event(buf)
{
......@@ -397,7 +396,7 @@ public:
alloced(0)
{}
Rotate_log_event(FILE* file, time_t when, uint32 server_id) ;
Rotate_log_event(IO_CACHE* file, time_t when, uint32 server_id) ;
Rotate_log_event(const char* buf, int max_buf);
~Rotate_log_event()
{
......@@ -406,7 +405,7 @@ public:
}
Log_event_type get_type_code() { return ROTATE_EVENT;}
int get_data_size() { return ident_len;}
int write_data(FILE* file);
int write_data(IO_CACHE* file);
void print(FILE* file, bool short_form = 0);
};
......
......@@ -32,17 +32,19 @@
#define MAP_TO_USE_RAID
#include "mysql_priv.h"
#include <mysys_err.h>
#ifdef HAVE_AIOWAIT
#include <mysys_err.h>
#include <errno.h>
static void my_aiowait(my_aio_result *result);
#endif
/* if cachesize == 0 then use default cachesize (from s-file) */
/* returns 0 if we have enough memory */
extern "C" {
/*
** if cachesize == 0 then use default cachesize (from s-file)
** if file == -1 then real_open_cached_file() will be called.
** returns 0 if ok
*/
int init_io_cache(IO_CACHE *info, File file, uint cachesize,
enum cache_type type, my_off_t seek_offset,
......@@ -60,6 +62,12 @@ int init_io_cache(IO_CACHE *info, File file, uint cachesize,
min_cache=use_async_io ? IO_SIZE*4 : IO_SIZE*2;
if (type == READ_CACHE)
{ /* Assume file isn't growing */
if (cache_myflags & MY_DONT_CHECK_FILESIZE)
{
cache_myflags &= ~MY_DONT_CHECK_FILESIZE;
}
else
{
my_off_t file_pos,end_of_file;
if ((file_pos=my_tell(file,MYF(0)) == MY_FILEPOS_ERROR))
DBUG_RETURN(1);
......@@ -73,7 +81,7 @@ int init_io_cache(IO_CACHE *info, File file, uint cachesize,
use_async_io=0; /* No nead to use async */
}
}
}
if ((int) type < (int) READ_NET)
{
for (;;)
......@@ -167,7 +175,8 @@ my_bool reinit_io_cache(IO_CACHE *info, enum cache_type type,
DBUG_ENTER("reinit_io_cache");
info->seek_not_done= test(info->file >= 0); /* Seek not done */
if (!clear_cache && seek_offset >= info->pos_in_file &&
if (! clear_cache &&
seek_offset >= info->pos_in_file &&
seek_offset <= info->pos_in_file +
(uint) (info->rc_end - info->rc_request_pos))
{ /* use current buffer */
......@@ -231,6 +240,7 @@ int _my_b_read(register IO_CACHE *info, byte *Buffer, uint Count)
{
uint length,diff_length,left_length;
my_off_t max_length, pos_in_file;
memcpy(Buffer,info->rc_pos,
(size_t) (left_length=(uint) (info->rc_end-info->rc_pos)));
Buffer+=left_length;
......@@ -607,7 +617,9 @@ int flush_io_cache(IO_CACHE *info)
length=(uint) (info->rc_pos - info->buffer);
if (info->seek_not_done)
{ /* File touched, do seek */
VOID(my_seek(info->file,info->pos_in_file,MY_SEEK_SET,MYF(0)));
if (my_seek(info->file,info->pos_in_file,MY_SEEK_SET,MYF(0)) ==
MY_FILEPOS_ERROR)
DBUG_RETURN((info->error= -1));
info->seek_not_done=0;
}
info->rc_pos=info->buffer;
......@@ -644,4 +656,4 @@ int end_io_cache(IO_CACHE *info)
DBUG_RETURN(error);
} /* end_io_cache */
}
} /* extern "C" */
......@@ -55,7 +55,7 @@ static struct option long_options[] =
{"password", required_argument,0, 'p'},
{"position", required_argument,0, 'j'},
#ifndef DBUG_OFF
{"debug", required_argument, 0, '#'}
{"debug", optional_argument, 0, '#'}
#endif
};
......@@ -151,7 +151,7 @@ static int parse_args(int *argc, char*** argv)
{
int c, opt_index = 0;
while((c = getopt_long(*argc, *argv, "so:#:h:j:u:p:P:t:?", long_options,
while((c = getopt_long(*argc, *argv, "so:#::h:j:u:p:P:t:?", long_options,
&opt_index)) != EOF)
{
switch(c)
......@@ -310,24 +310,43 @@ Unfortunately, no sweepstakes today, adjusted position to 4\n");
static void dump_local_log_entries(const char* logname)
{
FILE* file;
File fd;
IO_CACHE cache,*file= &cache;
int rec_count = 0;
if(logname && logname[0] != '-')
file = my_fopen(logname, O_RDONLY|O_BINARY, MYF(MY_WME));
if (logname && logname[0] != '-')
{
if ((fd = my_open(logname, O_RDONLY | O_BINARY, MYF(MY_WME))) < 0)
exit(1);
if (init_io_cache(file, fd, 0, READ_CACHE, (my_off_t) position, 0,
MYF(MY_WME | MY_NABP)))
exit(1);
}
else
file = stdin;
if(!file)
die("Could not open log file %s", logname);
if(my_fseek(file, position, MY_SEEK_SET, MYF(MY_WME)))
die("failed on my_fseek()");
{
if (init_io_cache(file, fileno(stdout), 0, READ_CACHE, (my_off_t) 0,
0, MYF(MY_WME | MY_NABP | MY_DONT_CHECK_FILESIZE)))
exit(1);
if (position)
{
/* skip 'position' characters from stdout */
char buff[IO_SIZE];
my_off_t length,tmp;
for (length=position ; length > 0 ; length-=tmp)
{
tmp=min(length,sizeof(buff));
if (my_b_read(file,buff,tmp))
exit(1);
}
}
file->pos_in_file=position;
file->seek_not_done=0;
}
if(!position)
if (!position)
{
char magic[4];
if (my_fread(file, (byte*) magic, sizeof(magic), MYF(MY_NABP|MY_WME)))
if (my_b_read(file, (byte*) magic, sizeof(magic)))
die("I/O error reading binlog magic number");
if(memcmp(magic, BINLOG_MAGIC, 4))
die("Bad magic number");
......@@ -336,23 +355,24 @@ static void dump_local_log_entries(const char* logname)
while(1)
{
Log_event* ev = Log_event::read_log_event(file, 0);
if(!ev)
if(!feof(file))
if (!ev)
{
if (file->error)
die("Could not read entry at offset %ld : Error in log format or \
read error",
my_ftell(file, MYF(MY_WME)));
else
my_b_tell(file));
break;
if(rec_count >= offset)
}
if (rec_count >= offset)
ev->print(stdout, short_form);
rec_count++;
delete ev;
}
my_fclose(file, MYF(MY_WME));
my_close(fd, MYF(MY_WME));
end_io_cache(file);
}
int main(int argc, char** argv)
{
MY_INIT(argv[0]);
......@@ -370,7 +390,7 @@ int main(int argc, char** argv)
mysql = safe_connect();
}
if(table)
if (table)
{
if(!use_remote)
die("You must specify connection parameter to get table dump");
......@@ -382,14 +402,14 @@ int main(int argc, char** argv)
dump_remote_table(&mysql->net, db, tbl);
}
else
{
while(--argc >= 0)
{
dump_log_entries(*(argv++));
}
if(use_remote)
}
if (use_remote)
mc_mysql_close(mysql);
return 0;
}
......
......@@ -113,11 +113,17 @@ THD::THD()
ull=0;
system_thread=0;
bzero((char*) &mem_root,sizeof(mem_root));
#if defined(HAVE_BDB) || defined(HAVE_INNOBASE) || defined(HAVE_GEMENI)
if (open_cached_file(&transactions.trans_log,
mysql_tempdir,LOG_PREFIX,0,MYF(MY_WME)))
killed=1;
transaction.bdb_lock_count=0;
#endif
transaction.bdb_tid=0;
#ifdef __WIN__
real_id = 0 ;
#endif
transaction.bdb_lock_count=0;
transaction.bdb_tid=0;
}
THD::~THD()
......@@ -136,6 +142,9 @@ THD::~THD()
close_thread_tables(this);
}
close_temporary_tables(this);
#if defined(HAVE_BDB) || defined(HAVE_INNOBASE) || defined(HAVE_GEMENI)
close_cached_file(transactions.trans_log);
#endif
if (global_read_lock)
{
pthread_mutex_lock(&LOCK_open);
......
......@@ -82,16 +82,16 @@ typedef struct st_master_info
} MASTER_INFO;
class MYSQL_LOG {
public:
private:
pthread_mutex_t LOCK_log, LOCK_index;
File file, index_file;
time_t last_time,query_start;
IO_CACHE log_file;
File index_file;
char *name;
enum_log_type log_type;
volatile enum_log_type log_type;
char time_buff[20],db[NAME_LEN+1];
char log_file_name[FN_REFLEN],index_file_name[FN_REFLEN];
bool write_error,inited;
bool write_error,inited,opened;
bool no_rotate; // for binlog - if log name can never change
// we should not try to rotate it or write any rotation events
// the user should use FLUSH MASTER instead of FLUSH LOGS for
......@@ -114,7 +114,7 @@ public:
int generate_new_name(char *new_name,const char *old_name);
void make_log_name(char* buf, const char* log_ident);
bool is_active(const char* log_file_name);
void flush(void);
// void flush(void);
void close(bool exiting = 0); // if we are exiting, we also want to close the
// index file
......@@ -270,6 +270,7 @@ public:
thr_lock_type update_lock_default;
delayed_insert *di;
struct st_transactions {
IO_CACHE trans_log;
void *bdb_tid;
uint bdb_lock_count;
} transaction;
......
......@@ -2439,7 +2439,7 @@ bool reload_acl_and_cache(THD *thd, uint options, TABLE_LIST *tables)
bool result=0;
select_errors=0; /* Write if more errors */
mysql_log.flush(); // Flush log
// mysql_log.flush(); // Flush log
if (options & REFRESH_GRANT)
{
acl_reload();
......
......@@ -93,54 +93,74 @@ static int send_file(THD *thd)
DBUG_RETURN(error);
}
static File open_log(IO_CACHE *log, const char *log_file_name,
const char **errmsg)
{
File file;
char magic[4];
if ((file = my_open(log_file_name, O_RDONLY | O_BINARY, MYF(MY_WME))) < 0 ||
init_io_cache(log, file, IO_SIZE*2, READ_CACHE, 0, 0,
MYF(MY_WME)))
{
*errmsg = "Could not open log file"; // This will not be sent
goto err;
}
if (my_b_read(log, (byte*) magic, sizeof(magic)))
{
*errmsg = "I/O error reading binlog magic number";
goto err;
}
if (memcmp(magic, BINLOG_MAGIC, 4))
{
*errmsg = "Binlog has bad magic number, fire your magician";
goto err;
}
return file;
err:
if (file > 0)
my_close(file,MYF(0));
end_io_cache(log);
return -1;
}
void mysql_binlog_send(THD* thd, char* log_ident, ulong pos, ushort flags)
{
LOG_INFO linfo;
char *log_file_name = linfo.log_file_name;
char search_file_name[FN_REFLEN];
char magic[4];
FILE* log = NULL;
IO_CACHE log;
File file = -1;
String* packet = &thd->packet;
int error;
const char *errmsg = "Unknown error";
NET* net = &thd->net;
DBUG_ENTER("mysql_binlog_send");
bzero((char*) &log,sizeof(log));
if(!mysql_bin_log.is_open())
{
errmsg = "Binary log is not open";
goto err;
}
if(log_ident[0])
if (log_ident[0])
mysql_bin_log.make_log_name(search_file_name, log_ident);
else
search_file_name[0] = 0;
if(mysql_bin_log.find_first_log(&linfo, search_file_name))
if (mysql_bin_log.find_first_log(&linfo, search_file_name))
{
errmsg = "Could not find first log";
goto err;
}
log = my_fopen(log_file_name, O_RDONLY|O_BINARY, MYF(MY_WME));
if(!log)
{
errmsg = "Could not open log file";
goto err;
}
if(my_fread(log, (byte*) magic, sizeof(magic), MYF(MY_NABP|MY_WME)))
{
errmsg = "I/O error reading binlog magic number";
goto err;
}
if(memcmp(magic, BINLOG_MAGIC, 4))
{
errmsg = "Binlog has bad magic number, fire your magician";
if ((file=open_log(&log, log_file_name, &errmsg)) < 0)
goto err;
}
if(pos < 4)
{
......@@ -149,13 +169,7 @@ sweepstakes if you report the bug";
goto err;
}
if(my_fseek(log, pos, MY_SEEK_SET, MYF(MY_WME)) == MY_FILEPOS_ERROR )
{
errmsg = "Error on fseek()";
goto err;
}
my_b_seek(&log, pos); // Seek will done on next read
packet->length(0);
packet->append("\0", 1);
// we need to start a packet with something other than 255
......@@ -165,7 +179,7 @@ sweepstakes if you report the bug";
{
pthread_mutex_t *log_lock = mysql_bin_log.get_log_lock();
while(!(error = Log_event::read_log_event(log, packet, log_lock)))
while (!(error = Log_event::read_log_event(&log, packet, log_lock)))
{
if(my_net_write(net, (char*)packet->ptr(), packet->length()) )
{
......@@ -221,7 +235,7 @@ sweepstakes if you report the bug";
// if we did not miss anything, we just wait for other threads
// to signal us
{
clearerr(log);
log.error=0;
// tell the kill thread how to wake us up
pthread_mutex_lock(&thd->mysys_var->mutex);
......@@ -235,7 +249,7 @@ sweepstakes if you report the bug";
// no one will update the log while we are reading
// now, but we'll be quick and just read one record
switch(Log_event::read_log_event(log, packet, log_lock))
switch(Log_event::read_log_event(&log, packet, log_lock))
{
case 0:
read_packet = 1;
......@@ -288,8 +302,7 @@ sweepstakes if you report the bug";
errmsg = "error reading log entry";
goto err;
}
clearerr(log);
log.error=0;
}
}
else
......@@ -312,25 +325,10 @@ sweepstakes if you report the bug";
if(loop_breaker)
break;
(void) my_fclose(log, MYF(MY_WME));
log = my_fopen(log_file_name, O_RDONLY|O_BINARY, MYF(MY_WME));
if(!log)
{
errmsg = "Could not open next log";
end_io_cache(&log);
(void) my_close(file, MYF(MY_WME));
if ((file=open_log(&log, log_file_name, &errmsg)) < 0)
goto err;
}
//check the magic
if(my_fread(log, (byte*) magic, sizeof(magic), MYF(MY_NABP|MY_WME)))
{
errmsg = "I/O error reading binlog magic number";
goto err;
}
if(memcmp(magic, BINLOG_MAGIC, 4))
{
errmsg = "Binlog has bad magic number, fire your magician";
goto err;
}
// fake Rotate_log event just in case it did not make it to the log
// otherwise the slave make get confused about the offset
......@@ -362,15 +360,17 @@ sweepstakes if you report the bug";
}
}
(void)my_fclose(log, MYF(MY_WME));
end_io_cache(&log);
(void)my_close(file, MYF(MY_WME));
send_eof(&thd->net);
thd->proc_info = "waiting to finalize termination";
DBUG_VOID_RETURN;
err:
thd->proc_info = "waiting to finalize termination";
if(log)
(void) my_fclose(log, MYF(MY_WME));
end_io_cache(&log);
if (file >= 0)
(void) my_close(file, MYF(MY_WME));
send_error(&thd->net, 0, errmsg);
DBUG_VOID_RETURN;
}
......
......@@ -95,17 +95,6 @@ bool String::realloc(uint32 alloc_length)
return FALSE;
}
#ifdef NOT_NEEDED
bool String::set(long num)
{
if (alloc(14))
return TRUE;
str_length=(uint32) (int10_to_str(num,Ptr,-10)-Ptr);
return FALSE;
}
#endif
bool String::set(longlong num)
{
if (alloc(21))
......@@ -274,6 +263,7 @@ bool String::append(const char *s,uint32 arg_length)
return FALSE;
}
#ifdef TO_BE_REMOVED
bool String::append(FILE* file, uint32 arg_length, myf my_flags)
{
if (realloc(str_length+arg_length))
......@@ -286,6 +276,20 @@ bool String::append(FILE* file, uint32 arg_length, myf my_flags)
str_length+=arg_length;
return FALSE;
}
#endif
bool String::append(IO_CACHE* file, uint32 arg_length)
{
if (realloc(str_length+arg_length))
return TRUE;
if (my_b_read(file, (byte*) Ptr + str_length, arg_length))
{
shrink(str_length);
return TRUE;
}
str_length+=arg_length;
return FALSE;
}
uint32 String::numchars()
{
......
......@@ -152,7 +152,7 @@ public:
bool copy(const char *s,uint32 arg_length); // Allocate new string
bool append(const String &s);
bool append(const char *s,uint32 arg_length=0);
bool append(FILE* file, uint32 arg_length, myf my_flags);
bool append(IO_CACHE* file, uint32 arg_length);
int strstr(const String &search,uint32 offset=0); // Returns offset to substring or -1
int strrstr(const String &search,uint32 offset=0); // Returns offset to substring or -1
bool replace(uint32 offset,uint32 arg_length,const String &to);
......
......@@ -413,16 +413,6 @@ ulong convert_month_to_period(ulong month)
return year*100+month%12+1;
}
#ifdef NOT_NEEDED
ulong add_to_period(ulong period,int months)
{
if (period == 0L)
return 0L;
return convert_month_to_period(convert_period_to_month(period)+months);
}
#endif
/*****************************************************************************
** convert a timestamp string to a TIME value.
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment