forked from percona/percona-server
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[plugin] PS-269: Initial Percona Server 8.0.12 tree
PS-5741: Incorrect use of memset_s in keyring_vault. Fixed the usage of memset_s. The arguments should be: void memset_s(void *dest, size_t dest_max, int c, size_t n) where the 2nd argument is size of buffer and the 3rd is argument is character to fill. --------------------------------------------------------------------------- PS-7769 - Fix use-after-return error in audit_log_exclude_accounts_validate --- *Problem:* `st_mysql_value::val_str` might return a pointer to `buf` which after the function called is deleted. Therefore the value in `save`, after reuturnin from the function, is invalid. In this particular case, the error is not manifesting as val_str` returns memory allocated with `thd_strmake` and it does not use `buf`. *Solution:* Allocate memory with `thd_strmake` so the memory in `save` is not local. --------------------------------------------------------------------------- Fix test main.bug12969156 when WITH_ASAN=ON *Problem:* ASAN complains about stack-buffer-overflow on function `mysql_heartbeat`: ``` ==90890==ERROR: AddressSanitizer: stack-buffer-overflow on address 0x7fe746d06d14 at pc 0x7fe760f5b017 bp 0x7fe746d06cd0 sp 0x7fe746d06478 WRITE of size 24 at 0x7fe746d06d14 thread T16777215 Address 0x7fe746d06d14 is located in stack of thread T26 at offset 340 in frame #0 0x7fe746d0a55c in mysql_heartbeat(void*) /home/yura/ws/percona-server/plugin/daemon_example/daemon_example.cc:62 This frame has 4 object(s): [48, 56) 'result' (line 66) [80, 112) '_db_stack_frame_' (line 63) [144, 200) 'tm_tmp' (line 67) [240, 340) 'buffer' (line 65) <== Memory access at offset 340 overflows this variable HINT: this may be a false positive if your program uses some custom stack unwind mechanism, swapcontext or vfork (longjmp and C++ exceptions *are* supported) Thread T26 created by T25 here: #0 0x7fe760f5f6d5 in __interceptor_pthread_create ../../../../src/libsanitizer/asan/asan_interceptors.cpp:216 #1 0x557ccbbcb857 in my_thread_create /home/yura/ws/percona-server/mysys/my_thread.c:104 #2 0x7fe746d0b21a in daemon_example_plugin_init /home/yura/ws/percona-server/plugin/daemon_example/daemon_example.cc:148 #3 0x557ccb4c69c7 in plugin_initialize /home/yura/ws/percona-server/sql/sql_plugin.cc:1279 #4 0x557ccb4d19cd in mysql_install_plugin /home/yura/ws/percona-server/sql/sql_plugin.cc:2279 percona#5 0x557ccb4d218f in Sql_cmd_install_plugin::execute(THD*) /home/yura/ws/percona-server/sql/sql_plugin.cc:4664 percona#6 0x557ccb47695e in mysql_execute_command(THD*, bool) /home/yura/ws/percona-server/sql/sql_parse.cc:5160 percona#7 0x557ccb47977c in mysql_parse(THD*, Parser_state*, bool) /home/yura/ws/percona-server/sql/sql_parse.cc:5952 percona#8 0x557ccb47b6c2 in dispatch_command(THD*, COM_DATA const*, enum_server_command) /home/yura/ws/percona-server/sql/sql_parse.cc:1544 percona#9 0x557ccb47de1d in do_command(THD*) /home/yura/ws/percona-server/sql/sql_parse.cc:1065 percona#10 0x557ccb6ac294 in handle_connection /home/yura/ws/percona-server/sql/conn_handler/connection_handler_per_thread.cc:325 percona#11 0x557ccbbfabb0 in pfs_spawn_thread /home/yura/ws/percona-server/storage/perfschema/pfs.cc:2198 percona#12 0x7fe760ab544f in start_thread nptl/pthread_create.c:473 ``` The reason is that `my_thread_cancel` is used to finish the daemon thread. This is not and orderly way of finishing the thread. ASAN does not register the stack variables are not used anymore which generates the error above. This is a benign error as all the variables are on the stack. *Solution*: Finish the thread in orderly way by using a signalling variable. --------------------------------------------------------------------------- PS-8204: Fix XML escape rules for audit plugin https://jira.percona.com/browse/PS-8204 There was a wrong length specified for some XML escape rules. As a result of this terminating null symbol from replacement rule was copied into resulting string. This lead to quer text truncation in audit log file. In addition added empty replacement rules for '\b' and 'f' symbols which just remove them from resulting string. These symboles are not supported in XML 1.0. --------------------------------------------------------------------------- PS-8854: Add main.percona_udf MTR test Add a test to check FNV1A_64, FNV_64, and MURMUR_HASH user-defined functions.
- Loading branch information
Showing
126 changed files
with
11,316 additions
and
1,576 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
*** checking if UDF works without creating the function | ||
SELECT MURMUR_HASH('hello', 'world'); | ||
ERROR 42000: FUNCTION test.MURMUR_HASH does not exist | ||
|
||
*** creating UDF functions | ||
CREATE FUNCTION fnv1a_64 RETURNS INTEGER SONAME 'libfnv1a_udf.so'; | ||
CREATE FUNCTION fnv_64 RETURNS INTEGER SONAME 'libfnv_udf.so'; | ||
CREATE FUNCTION murmur_hash RETURNS INTEGER SONAME 'libmurmur_udf.so'; | ||
|
||
*** checking UDF functions | ||
include/assert.inc [checking hash value for FNV1A_64()] | ||
include/assert.inc [checking hash value for FNV_64()] | ||
include/assert.inc [checking hash value for MURMUR_HASH()] | ||
|
||
*** creating t1 table | ||
CREATE TABLE t1 ( | ||
id BIGINT UNSIGNED NOT NULL AUTO_INCREMENT, | ||
col1 INT, | ||
col2 VARCHAR(16), | ||
col3 TEXT, | ||
PRIMARY KEY(id) | ||
) ENGINE=InnoDB DEFAULT CHARSET=latin1; | ||
INSERT INTO t1(col1, col2, col3) VALUES (1, "b", "c"); | ||
INSERT INTO t1(col1, col2, col3) VALUES (2, "3240", "4000"); | ||
INSERT INTO t1(col1, col2, col3) VALUES (3, "short", "words"); | ||
|
||
*** checking UDF functions with t1 table | ||
include/assert.inc [checking hash value for BIT_XOR(FNV1A_64())] | ||
include/assert.inc [checking hash value for BIT_XOR(FNV_64())] | ||
include/assert.inc [checking hash value for BIT_XOR(MURMUR_HASH())] | ||
include/assert.inc [checking hash value for FNV1A_64(col1, col2, col3)] | ||
|
||
*** cleaning up | ||
DROP FUNCTION fnv1a_64; | ||
DROP FUNCTION fnv_64; | ||
DROP FUNCTION murmur_hash; | ||
DROP TABLE t1; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
--echo *** checking if UDF works without creating the function | ||
--error ER_SP_DOES_NOT_EXIST | ||
SELECT MURMUR_HASH('hello', 'world'); | ||
|
||
--echo | ||
--echo *** creating UDF functions | ||
CREATE FUNCTION fnv1a_64 RETURNS INTEGER SONAME 'libfnv1a_udf.so'; | ||
CREATE FUNCTION fnv_64 RETURNS INTEGER SONAME 'libfnv_udf.so'; | ||
CREATE FUNCTION murmur_hash RETURNS INTEGER SONAME 'libmurmur_udf.so'; | ||
|
||
--echo | ||
--echo *** checking UDF functions | ||
|
||
--let $assert_text = checking hash value for FNV1A_64() | ||
--let $assert_cond = `SELECT FNV1A_64('hello', 'world') = 1214055856804091265` | ||
--source include/assert.inc | ||
|
||
--let $assert_text = checking hash value for FNV_64() | ||
--let $assert_cond = `SELECT FNV_64('hello', 'world') = 2924375256774005480` | ||
--source include/assert.inc | ||
|
||
--let $assert_text = checking hash value for MURMUR_HASH() | ||
--let $assert_cond = `SELECT MURMUR_HASH('hello', 'world') = -7857203399167365490` | ||
--source include/assert.inc | ||
|
||
--echo | ||
--echo *** creating t1 table | ||
CREATE TABLE t1 ( | ||
id BIGINT UNSIGNED NOT NULL AUTO_INCREMENT, | ||
col1 INT, | ||
col2 VARCHAR(16), | ||
col3 TEXT, | ||
PRIMARY KEY(id) | ||
) ENGINE=InnoDB DEFAULT CHARSET=latin1; | ||
|
||
INSERT INTO t1(col1, col2, col3) VALUES (1, "b", "c"); | ||
INSERT INTO t1(col1, col2, col3) VALUES (2, "3240", "4000"); | ||
INSERT INTO t1(col1, col2, col3) VALUES (3, "short", "words"); | ||
|
||
--echo | ||
--echo *** checking UDF functions with t1 table | ||
|
||
--let $assert_text = checking hash value for BIT_XOR(FNV1A_64()) | ||
--let $assert_cond = [SELECT BIT_XOR(CAST(FNV1A_64(col1, col2, col3) AS UNSIGNED)) FROM t1] = 9092447622868433808 | ||
--source include/assert.inc | ||
|
||
--let $assert_text = checking hash value for BIT_XOR(FNV_64()) | ||
--let $assert_cond = [SELECT BIT_XOR(CAST(FNV_64(col1, col2, col3) AS UNSIGNED)) FROM t1] = 3813096360487945067 | ||
--source include/assert.inc | ||
|
||
--let $assert_text = checking hash value for BIT_XOR(MURMUR_HASH()) | ||
--let $assert_cond = [SELECT BIT_XOR(CAST(MURMUR_HASH(col1, col2, col3) AS UNSIGNED)) FROM t1] = 9393970666296144275 | ||
--source include/assert.inc | ||
|
||
--let $assert_text = checking hash value for FNV1A_64(col1, col2, col3) | ||
--let $assert_cond = ["SELECT FNV1A_64(col1, col2, col3) AS Hash_Val FROM t1", Hash_Val, 1] = 5882002141665055715 | ||
--source include/assert.inc | ||
|
||
--echo | ||
--echo *** cleaning up | ||
DROP FUNCTION fnv1a_64; | ||
DROP FUNCTION fnv_64; | ||
DROP FUNCTION murmur_hash; | ||
|
||
DROP TABLE t1; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
# Copyright (c) 2014 Percona LLC 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 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 | ||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
|
||
MYSQL_ADD_PLUGIN(audit_log audit_log.cc file_logger.cc buffer.cc audit_file.cc | ||
audit_syslog.cc filter.cc | ||
MODULE_ONLY MODULE_OUTPUT_NAME "audit_log") | ||
|
||
IF(UNIX) | ||
IF(INSTALL_MYSQLTESTDIR) | ||
INSTALL(DIRECTORY tests/mtr/ DESTINATION ${INSTALL_MYSQLTESTDIR}/suite/audit_log COMPONENT Test) | ||
ENDIF() | ||
ENDIF() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,183 @@ | ||
/* Copyright (c) 2014 Percona LLC 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 | ||
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 | ||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ | ||
|
||
#include "audit_handler.h" | ||
#include "audit_log.h" | ||
#include "buffer.h" | ||
#include "my_dbug.h" | ||
#include "my_sys.h" | ||
#include "mysql/service_mysql_alloc.h" | ||
|
||
struct audit_handler_file_data_t { | ||
size_t struct_size; | ||
LOGGER_HANDLE *logger; | ||
logger_prolog_func_t header; | ||
logger_epilog_func_t footer; | ||
bool sync_on_write; | ||
bool use_buffer; | ||
audit_log_buffer_t *buffer; | ||
}; | ||
|
||
static int audit_handler_file_write(audit_handler_t *handler, const char *buf, | ||
size_t len); | ||
static int audit_handler_file_flush(audit_handler_t *handler) noexcept; | ||
static int audit_handler_file_close(audit_handler_t *handler) noexcept; | ||
static int audit_handler_file_write_nobuf(LOGGER_HANDLE *logger, | ||
const char *buf, size_t len, | ||
log_record_state_t state) noexcept; | ||
static int audit_handler_file_write_buf(audit_log_buffer_t *buffer, | ||
const char *buf, size_t len); | ||
static void audit_handler_file_set_option(audit_handler_t *handler, | ||
audit_handler_option_t opt, | ||
void *val) noexcept; | ||
|
||
static int write_callback(void *data, const char *buf, size_t len, | ||
log_record_state_t state) noexcept { | ||
audit_handler_t *handler = (audit_handler_t *)data; | ||
audit_handler_file_data_t *hdata = (audit_handler_file_data_t *)handler->data; | ||
|
||
assert(hdata->struct_size == sizeof(audit_handler_file_data_t)); | ||
|
||
return audit_handler_file_write_nobuf(hdata->logger, buf, len, state); | ||
} | ||
|
||
audit_handler_t *audit_handler_file_open( | ||
audit_handler_file_config_t *opts) noexcept { | ||
audit_handler_t *handler = (audit_handler_t *)my_malloc( | ||
key_memory_audit_log_handler, | ||
sizeof(audit_handler_t) + sizeof(audit_handler_file_data_t), MY_ZEROFILL); | ||
if (handler != nullptr) { | ||
audit_handler_file_data_t *data = | ||
(audit_handler_file_data_t *)(handler + 1); | ||
data->struct_size = sizeof(audit_handler_file_data_t); | ||
data->footer = opts->footer; | ||
data->header = opts->header; | ||
data->sync_on_write = opts->sync_on_write; | ||
data->use_buffer = opts->use_buffer; | ||
if (data->use_buffer) { | ||
data->buffer = audit_log_buffer_init( | ||
opts->buffer_size, opts->can_drop_data, write_callback, handler); | ||
if (data->buffer == nullptr) goto error; | ||
} | ||
data->logger = logger_open(opts->name, opts->rotate_on_size, | ||
opts->rotate_on_size ? opts->rotations : 0, | ||
!opts->use_buffer, opts->header); | ||
if (data->logger == nullptr) { | ||
goto error; | ||
} | ||
handler->data = data; | ||
handler->write = audit_handler_file_write; | ||
handler->flush = audit_handler_file_flush; | ||
handler->close = audit_handler_file_close; | ||
handler->set_option = audit_handler_file_set_option; | ||
goto success; | ||
error: | ||
if (data->buffer) { | ||
audit_log_buffer_shutdown(data->buffer); | ||
} | ||
my_free(handler); | ||
handler = nullptr; | ||
} | ||
success: | ||
return handler; | ||
} | ||
|
||
static int audit_handler_file_write_nobuf(LOGGER_HANDLE *logger, | ||
const char *buf, size_t len, | ||
log_record_state_t state) noexcept { | ||
return logger_write(logger, buf, len, state); | ||
} | ||
|
||
static int audit_handler_file_write_buf(audit_log_buffer_t *buffer, | ||
const char *buf, size_t len) { | ||
return audit_log_buffer_write(buffer, buf, len); | ||
} | ||
|
||
static int audit_handler_file_write(audit_handler_t *handler, const char *buf, | ||
size_t len) { | ||
audit_handler_file_data_t *data = (audit_handler_file_data_t *)handler->data; | ||
int res; | ||
|
||
assert(data->struct_size == sizeof(audit_handler_file_data_t)); | ||
|
||
if (data->use_buffer) { | ||
assert(data->buffer); | ||
res = audit_handler_file_write_buf(data->buffer, buf, len); | ||
} else { | ||
assert(data->logger); | ||
res = audit_handler_file_write_nobuf(data->logger, buf, len, | ||
log_record_state_t::COMPLETE); | ||
|
||
if (data->sync_on_write) { | ||
logger_sync(data->logger); | ||
} | ||
} | ||
|
||
return res; | ||
} | ||
|
||
static int audit_handler_file_flush(audit_handler_t *handler) noexcept { | ||
audit_handler_file_data_t *data = (audit_handler_file_data_t *)handler->data; | ||
LOGGER_HANDLE *logger; | ||
int res; | ||
|
||
assert(data->struct_size == sizeof(audit_handler_file_data_t)); | ||
|
||
logger = data->logger; | ||
|
||
if (data->use_buffer) audit_log_buffer_pause(data->buffer); | ||
|
||
res = logger_reopen(logger, data->header, data->footer); | ||
|
||
if (data->use_buffer) audit_log_buffer_resume(data->buffer); | ||
|
||
return res; | ||
} | ||
|
||
static int audit_handler_file_close(audit_handler_t *handler) noexcept { | ||
audit_handler_file_data_t *data = (audit_handler_file_data_t *)handler->data; | ||
int res; | ||
LOGGER_HANDLE *logger; | ||
|
||
assert(data->struct_size == sizeof(audit_handler_file_data_t)); | ||
|
||
logger = data->logger; | ||
|
||
if (data->use_buffer) { | ||
audit_log_buffer_shutdown(data->buffer); | ||
} | ||
|
||
res = logger_close(logger, data->footer); | ||
|
||
my_free(handler); | ||
|
||
return res; | ||
} | ||
|
||
static void audit_handler_file_set_option(audit_handler_t *handler, | ||
audit_handler_option_t opt, | ||
void *val) noexcept { | ||
audit_handler_file_data_t *data = (audit_handler_file_data_t *)handler->data; | ||
|
||
switch (opt) { | ||
case audit_handler_option_t::ROTATE_ON_SIZE: | ||
logger_set_size_limit(data->logger, *(ulonglong *)(val)); | ||
break; | ||
case audit_handler_option_t::ROTATIONS: | ||
logger_set_rotations(data->logger, *(ulonglong *)(val)); | ||
break; | ||
} | ||
} |
Oops, something went wrong.