Commit f9a321af authored by monty@hundin.mysql.fi's avatar monty@hundin.mysql.fi

merge

parents 9285b745 af2e1348
......@@ -163,7 +163,7 @@ os_fast_mutex_trylock(
#endif
/**************************************************************
Releases ownership of a fast mutex. */
UNIV_INLINE
void
os_fast_mutex_unlock(
/*=================*/
......
......@@ -40,17 +40,3 @@ os_fast_mutex_trylock(
}
#endif
/**************************************************************
Releases ownership of a fast mutex. */
UNIV_INLINE
void
os_fast_mutex_unlock(
/*=================*/
os_fast_mutex_t* fast_mutex) /* in: mutex to release */
{
#ifdef __WIN__
LeaveCriticalSection(fast_mutex);
#else
pthread_mutex_unlock(fast_mutex);
#endif
}
......@@ -66,6 +66,9 @@ extern char* srv_unix_file_flush_method_str;
extern ulint srv_unix_file_flush_method;
extern ulint srv_force_recovery;
extern ulint srv_thread_concurrency;
extern lint srv_conc_n_threads;
extern ibool srv_fast_shutdown;
extern ibool srv_use_doublewrite_buf;
......
......@@ -454,6 +454,21 @@ os_fast_mutex_lock(
#endif
}
/**************************************************************
Releases ownership of a fast mutex. */
void
os_fast_mutex_unlock(
/*=================*/
os_fast_mutex_t* fast_mutex) /* in: mutex to release */
{
#ifdef __WIN__
LeaveCriticalSection(fast_mutex);
#else
pthread_mutex_unlock(fast_mutex);
#endif
}
/**************************************************************
Frees a mutex object. */
......
......@@ -946,11 +946,27 @@ row_create_table_for_mysql(
"InnoDB: mysqld and edit my.cnf so that newraw is replaced\n"
"InnoDB: with raw, and innodb_force_... is removed.\n");
trx_commit_for_mysql(trx);
return(DB_ERROR);
}
trx->op_info = (char *) "creating table";
if (0 == ut_strcmp(table->name, "mysql/host")
|| 0 == ut_strcmp(table->name, "mysql/user")
|| 0 == ut_strcmp(table->name, "mysql/db")) {
fprintf(stderr,
"InnoDB: Error: trying to create a MySQL system table %s of type InnoDB.\n"
"InnoDB: MySQL system tables must be of the MyISAM type!\n",
table->name);
trx_commit_for_mysql(trx);
return(DB_ERROR);
}
trx_start_if_not_started(trx);
namelen = ut_strlen(table->name);
......@@ -1428,6 +1444,8 @@ funct_exit:
que_graph_free(graph);
trx_commit_for_mysql(trx);
trx->op_info = (char *) "";
return((int) err);
......@@ -1513,6 +1531,20 @@ row_rename_table_for_mysql(
"InnoDB: mysqld and edit my.cnf so that newraw is replaced\n"
"InnoDB: with raw, and innodb_force_... is removed.\n");
trx_commit_for_mysql(trx);
return(DB_ERROR);
}
if (0 == ut_strcmp(new_name, "mysql/host")
|| 0 == ut_strcmp(new_name, "mysql/user")
|| 0 == ut_strcmp(new_name, "mysql/db")) {
fprintf(stderr,
"InnoDB: Error: trying to create a MySQL system table %s of type InnoDB.\n"
"InnoDB: MySQL system tables must be of the MyISAM type!\n",
new_name);
trx_commit_for_mysql(trx);
return(DB_ERROR);
}
......@@ -1596,6 +1628,8 @@ funct_exit:
que_graph_free(graph);
trx_commit_for_mysql(trx);
trx->op_info = (char *) "";
return((int) err);
......
......@@ -121,12 +121,17 @@ semaphore contention and convoy problems can occur withput this restriction.
Value 10 should be good if there are less than 4 processors + 4 disks in the
computer. Bigger computers need bigger values. */
ulint srv_thread_concurrency = 4;
ulint srv_thread_concurrency = 8;
os_fast_mutex_t srv_conc_mutex; /* this mutex protects srv_conc data
structures */
ulint srv_conc_n_threads = 0; /* number of OS threads currently
inside InnoDB */
lint srv_conc_n_threads = 0; /* number of OS threads currently
inside InnoDB; it is not an error
if this drops temporarily below zero
because we do not demand that every
thread increments this, but a thread
waiting for a lock decrements this
temporarily */
typedef struct srv_conc_slot_struct srv_conc_slot_t;
struct srv_conc_slot_struct{
......@@ -1646,7 +1651,7 @@ srv_conc_enter_innodb(
os_fast_mutex_lock(&srv_conc_mutex);
if (srv_conc_n_threads < srv_thread_concurrency) {
if (srv_conc_n_threads < (lint)srv_thread_concurrency) {
srv_conc_n_threads++;
os_fast_mutex_unlock(&srv_conc_mutex);
......@@ -1654,7 +1659,7 @@ srv_conc_enter_innodb(
return;
}
/* Too many threads inside: put to the current thread to a queue */
/* Too many threads inside: put the current thread to a queue */
for (i = 0; i < OS_THREAD_MAX_N; i++) {
slot = srv_conc_slots + i;
......@@ -1734,11 +1739,9 @@ srv_conc_exit_innodb(void)
os_fast_mutex_lock(&srv_conc_mutex);
ut_a(srv_conc_n_threads > 0);
srv_conc_n_threads--;
if (srv_conc_n_threads < srv_thread_concurrency) {
if (srv_conc_n_threads < (lint)srv_thread_concurrency) {
/* Look for a slot where a thread is waiting and no other
thread has yet released the thread */
......@@ -1985,16 +1988,18 @@ srv_lock_timeout_and_monitor_thread(
void* arg) /* in: a dummy parameter required by
os_thread_create */
{
srv_slot_t* slot;
double time_elapsed;
time_t current_time;
time_t last_monitor_time;
time_t last_table_monitor_time;
ibool some_waits;
srv_slot_t* slot;
double wait_time;
ulint i;
UT_NOT_USED(arg);
last_monitor_time = time(NULL);
last_table_monitor_time = time(NULL);
loop:
srv_lock_timeout_and_monitor_active = TRUE;
......@@ -2056,7 +2061,7 @@ loop:
"ROW OPERATIONS\n"
"--------------\n");
printf(
"%lu queries inside InnoDB; main thread: %s\n",
"%ld queries inside InnoDB; main thread: %s\n",
srv_conc_n_threads, srv_main_thread_op_info);
printf(
"Number of rows inserted %lu, updated %lu, deleted %lu, read %lu\n",
......@@ -2083,12 +2088,13 @@ loop:
printf("----------------------------\n"
"END OF INNODB MONITOR OUTPUT\n"
"============================\n");
}
if (srv_print_innodb_tablespace_monitor) {
if (srv_print_innodb_tablespace_monitor
&& difftime(current_time, last_table_monitor_time) > 60) {
last_table_monitor_time = time(NULL);
printf("================================================\n");
ut_print_timestamp(stdout);
......@@ -2105,7 +2111,10 @@ loop:
"=======================================\n");
}
if (srv_print_innodb_table_monitor) {
if (srv_print_innodb_table_monitor
&& difftime(current_time, last_table_monitor_time) > 60) {
last_table_monitor_time = time(NULL);
printf("===========================================\n");
......@@ -2208,7 +2217,13 @@ loop:
os_thread_sleep(10000000);
sync_array_print_long_waits();
/* Flush stdout and stderr so that a database user gets their output
to possible MySQL error file */
fflush(stderr);
fflush(stdout);
if (srv_shutdown_state < SRV_SHUTDOWN_LAST_PHASE) {
goto loop;
......
......@@ -1004,6 +1004,13 @@ innobase_shutdown_for_mysql(void)
logs_empty_and_mark_files_at_shutdown();
if (srv_conc_n_threads != 0) {
fprintf(stderr,
"InnoDB: Warning: query counter shows %ld queries still\n"
"InnoDB: inside InnoDB at shutdown\n",
srv_conc_n_threads);
}
ut_free_all_mem();
return((int) DB_SUCCESS);
......
......@@ -305,16 +305,16 @@ MI_INFO *mi_open(const char *name, int mode, uint open_flags)
}
}
}
if (share->keyinfo[i].flag & HA_FULLTEXT) /* SerG */
if (share->keyinfo[i].flag & HA_FULLTEXT)
{
share->keyinfo[i].seg=pos-FT_SEGS; /* SerG */
share->keyinfo[i].seg=pos-FT_SEGS;
share->fulltext_index=1;
}
share->keyinfo[i].end=pos;
pos->type=HA_KEYTYPE_END; /* End */
pos->length=share->base.rec_reflength;
pos->null_bit=0;
pos->flag=0;
pos->flag=0; /* For purify */
pos++;
}
for (i=0 ; i < uniques ; i++)
......@@ -338,6 +338,7 @@ MI_INFO *mi_open(const char *name, int mode, uint open_flags)
share->uniqueinfo[i].end=pos;
pos->type=HA_KEYTYPE_END; /* End */
pos->null_bit=0;
pos->flag=0;
pos++;
}
}
......
......@@ -633,6 +633,7 @@ start_master()
--basedir=$MY_BASEDIR --init-rpl-role=master \
--port=$MASTER_MYPORT \
--exit-info=256 \
--core
--datadir=$MASTER_MYDDIR \
--pid-file=$MASTER_MYPID \
--socket=$MASTER_MYSOCK \
......
......@@ -63,7 +63,7 @@ done
for i in extra/comp_err extra/replace extra/perror extra/resolveip \
extra/my_print_defaults extra/resolve_stack_dump \
isam/isamchk isam/pack_isam myisam/myisamchk \
myisam/myisampack sql/mysqld sql/mysqlbinlog \
myisam/myisampack sql/mysqld client/mysqlbinlog \
client/mysql sql/mysqld client/mysqlshow client/mysqlcheck \
client/mysqladmin client/mysqldump client/mysqlimport client/mysqltest \
client/mysqlmanagerc client/mysqlmanager-pwgen tools/mysqlmanager \
......
......@@ -6,6 +6,7 @@ use Data::Dumper;
use File::Basename;
use File::Path;
use DBI;
use Sys::Hostname;
=head1 NAME
......@@ -36,7 +37,7 @@ WARNING: THIS PROGRAM IS STILL IN BETA. Comments/patches welcome.
# Documentation continued at end of file
my $VERSION = "1.12";
my $VERSION = "1.13";
my $opt_tmpdir = $ENV{TMPDIR} || "/tmp";
......@@ -68,6 +69,7 @@ Usage: $0 db_name[./table_regex/] [new_db_name | directory]
--resetmaster reset the binlog once all tables are locked
--resetslave reset the master.info once all tables are locked
--tmpdir=# temporary directory (instead of $opt_tmpdir)
--record_log_pos=# record slave and master status in specified db.table
Try \'perldoc $0 for more complete documentation\'
_OPTIONS
......@@ -101,6 +103,7 @@ GetOptions( \%opt,
"regexp=s",
"suffix=s",
"checkpoint=s",
"record_log_pos=s",
"flushlog",
"resetmaster",
"resetslave",
......@@ -117,6 +120,7 @@ GetOptions( \%opt,
# 'target' - destination directory of the copy
# 'tables' - array-ref to list of tables in the db
# 'files' - array-ref to list of files to be copied
# 'index' - array-ref to list of indexes to be copied
#
my @db_desc = ();
......@@ -172,6 +176,16 @@ if ( $opt{checkpoint} ) {
if ( $@ );
}
# --- check that log_pos table exists if specified ---
if ( $opt{record_log_pos} ) {
eval { $dbh->do( qq{ select host, time_stamp, log_file, log_pos, master_host, master_log_file, master_log_pos
from $opt{record_log_pos} where 1 != 1} );
};
die "Error accessing log_pos table ($opt{record_log_pos}): $@"
if ( $@ );
}
# --- get variables from database ---
my $sth_vars = $dbh->prepare("show variables like 'datadir'");
$sth_vars->execute;
......@@ -294,8 +308,6 @@ foreach my $rdb ( @db_desc ) {
# --- resolve targets for copies ---
my @targets = ();
if (defined($tgt_name) && length $tgt_name ) {
# explicit destination directory specified
......@@ -382,11 +394,12 @@ foreach my $rdb ( @db_desc ) {
# read lock all the tables we'll be copying
# in order to get a consistent snapshot of the database
if ( $opt{checkpoint} ) {
# convert existing READ lock on checkpoint table into WRITE lock
unless ( $hc_locks =~ s/$opt{checkpoint}\s+READ/$opt{checkpoint} WRITE/ ) {
$hc_locks .= ", $opt{checkpoint} WRITE";
}
if ( $opt{checkpoint} || $opt{record_log_pos} ) {
# convert existing READ lock on checkpoint and/or log_pos table into WRITE lock
foreach my $table ( grep { defined } ( $opt{checkpoint}, $opt{record_log_pos} ) ) {
$hc_locks .= ", $table WRITE"
unless ( $hc_locks =~ s/$table\s+READ/$table WRITE/ );
}
}
my $hc_started = time; # count from time lock is granted
......@@ -411,6 +424,11 @@ else {
$dbh->do( "FLUSH LOGS" ) if ( $opt{flushlog} );
$dbh->do( "RESET MASTER" ) if ( $opt{resetmaster} );
$dbh->do( "RESET SLAVE" ) if ( $opt{resetslave} );
if ( $opt{record_log_pos} ) {
record_log_pos( $dbh, $opt{record_log_pos} );
$dbh->do("FLUSH TABLES /*!32323 $hc_tables */");
}
}
my @failed = ();
......@@ -473,6 +491,12 @@ if ( @failed ) {
# delete any @targets
# rename _old copy back to original
my @targets = ();
foreach my $rdb ( @db_desc ) {
push @targets, $rdb->{target} if ( -d $rdb->{target} );
}
print "Deleting @targets \n" if $opt{debug};
print "Deleting @targets \n" if $opt{debug};
rmtree([@targets]);
if (@existing) {
......@@ -603,7 +627,6 @@ sub safe_system
}
}
sub retire_directory {
my ( @dir ) = @_;
......@@ -625,6 +648,40 @@ sub retire_directory {
}
}
sub record_log_pos {
my ( $dbh, $table_name ) = @_;
eval {
my ($file,$position) = get_row( $dbh, "show master status" );
die "master status is undefined" if !defined $file || !defined $position;
my ($master_host, undef, undef, undef, $log_file, $log_pos )
= get_row( $dbh, "show slave status" );
my $hostname = hostname();
$dbh->do( qq{ replace into $table_name
set host=?, log_file=?, log_pos=?,
master_host=?, master_log_file=?, master_log_pos=? },
undef,
$hostname, $file, $position,
$master_host, $log_file, $log_pos );
};
if ( $@ ) {
warn "Failed to store master position: $@\n";
}
}
sub get_row {
my ( $dbh, $sql ) = @_;
my $sth = $dbh->prepare($sql);
$sth->execute;
return $sth->fetchrow_array();
}
__END__
=head1 DESCRIPTION
......@@ -659,6 +716,38 @@ The checkpoint-table must contain at least the following fields:
=back
=item --record_log_pos log-pos-table
Just before the database files are copied, update the record in the
log-pos-table from the values returned from "show master status" and
"show slave status". The master status values are stored in the
log_file and log_pos columns, and establish the position in the binary
logs that any slaves of this host should adopt if initialised from
this dump. The slave status values are stored in master_host,
master_log_file, and master_log_pos, and these are useful if the host
performing the dump is a slave and other sibling slaves are to be
initialised from this dump.
The name of the log-pos table should be supplied in database.table format.
A sample log-pos table definition:
=over 4
CREATE TABLE log_pos (
host varchar(60) NOT null,
time_stamp timestamp(14) NOT NULL,
log_file varchar(32) default NULL,
log_pos int(11) default NULL,
master_host varchar(60) NULL,
master_log_file varchar(32) NULL,
master_log_pos int NULL,
PRIMARY KEY (host)
);
=back
=item --suffix suffix
Each database is copied back into the originating datadir under
......@@ -784,7 +873,7 @@ Study the code inside this script and only rely on it if I<you> believe
that it does the right thing for you.
Patches adding bug fixes, documentation and new features are welcome.
Please send these to internals@mysql.com.
Please send these to internals@lists.mysql.com.
=head1 TO DO
......@@ -814,6 +903,8 @@ Add support for forthcoming MySQL ``RAID'' table subdirectory layouts.
Tim Bunce
Martin Waite - added checkpoint, flushlog, regexp and dryrun options
Fixed cleanup of targets when hotcopy fails.
Added --record_log_pos.
Ralph Corderoy - added synonyms for commands
......
......@@ -1472,7 +1472,9 @@ ha_innobase::write_row(
The lock is released at each SQL statement's
end. */
srv_conc_enter_innodb(prebuilt->trx);
error = row_lock_table_autoinc_for_mysql(prebuilt);
srv_conc_exit_innodb();
if (error != DB_SUCCESS) {
......@@ -1523,7 +1525,9 @@ ha_innobase::write_row(
auto_inc = table->next_number_field->val_int();
srv_conc_enter_innodb(prebuilt->trx);
error = row_lock_table_autoinc_for_mysql(prebuilt);
srv_conc_exit_innodb();
if (error != DB_SUCCESS) {
......@@ -2803,6 +2807,8 @@ ha_innobase::delete_table(
srv_active_wake_master_thread();
trx_commit_for_mysql(trx);
trx_free_for_mysql(trx);
error = convert_error_code_to_mysql(error);
......@@ -2856,6 +2862,7 @@ innobase_drop_database(
srv_active_wake_master_thread();
trx_commit_for_mysql(trx);
trx_free_for_mysql(trx);
error = convert_error_code_to_mysql(error);
......@@ -2908,6 +2915,7 @@ ha_innobase::rename_table(
srv_active_wake_master_thread();
trx_commit_for_mysql(trx);
trx_free_for_mysql(trx);
error = convert_error_code_to_mysql(error);
......
......@@ -525,7 +525,7 @@ String *Item_func_sec_to_time::val_str(String *str)
seconds= -seconds;
sign= "-";
}
uint sec= (uint) (seconds % 3600);
uint sec= (uint) ((ulonglong) seconds % 3600);
sprintf(buff,"%s%02lu:%02u:%02u",sign,(long) (seconds/3600),
sec/60, sec % 60);
str->copy(buff,(uint) strlen(buff));
......
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