2019-12-10 15:35:00 +01:00
/* Copyright (c) 2008, 2015, Oracle and/or its affiliates. All rights reserved.
2012-08-01 17:27:34 +03:00
This program is free software ; you can redistribute it and / or modify
2020-01-19 12:52:07 +01:00
it under the terms of the GNU General Public License , version 2.0 ,
as published by the Free Software Foundation .
This program is also distributed with certain software ( including
but not limited to OpenSSL ) that is licensed under separate terms ,
as designated in a particular file or component or in included license
documentation . The authors of MySQL hereby grant you an additional
permission to link the program and your derivative works with the
separately licensed software that they have included with MySQL .
2012-08-01 17:27:34 +03:00
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
2020-01-19 12:52:07 +01:00
GNU General Public License , version 2.0 , for more details .
2012-08-01 17:27:34 +03:00
You should have received a copy of the GNU General Public License
along with this program ; if not , write to the Free Software Foundation ,
2019-05-11 19:25:02 +03:00
51 Franklin Street , Fifth Floor , Boston , MA 02110 - 1335 USA */
2012-08-01 17:27:34 +03:00
/**
@ file storage / perfschema / table_setup_objects . cc
Table SETUP_OBJECTS ( implementation ) .
*/
# include "my_global.h"
2019-12-10 15:35:00 +01:00
# include "my_thread.h"
2012-08-01 17:27:34 +03:00
# include "pfs_instr.h"
# include "pfs_column_types.h"
# include "pfs_column_values.h"
# include "pfs_setup_object.h"
# include "table_setup_objects.h"
# include "table_helper.h"
# include "pfs_global.h"
2019-12-10 15:35:00 +01:00
# include "pfs_buffer_container.h"
# include "field.h"
2012-08-01 17:27:34 +03:00
THR_LOCK table_setup_objects : : m_table_lock ;
PFS_engine_table_share
table_setup_objects : : m_share =
{
{ C_STRING_WITH_LEN ( " setup_objects " ) } ,
& pfs_editable_acl ,
table_setup_objects : : create ,
table_setup_objects : : write_row ,
table_setup_objects : : delete_all_rows ,
table_setup_objects : : get_row_count ,
sizeof ( PFS_simple_index ) ,
& m_table_lock ,
2014-08-19 15:18:18 +04:00
{ C_STRING_WITH_LEN ( " CREATE TABLE setup_objects( "
2021-09-10 17:16:18 +03:00
" OBJECT_TYPE ENUM ('EVENT','FUNCTION','PROCEDURE','TABLE','TRIGGER') not null default 'TABLE' comment 'Type of object to instrument.', "
2021-05-02 15:43:04 -05:00
" OBJECT_SCHEMA VARCHAR(64) default '%' comment 'Schema containing the object, either the literal or % for any schema.', "
" OBJECT_NAME VARCHAR(64) not null default '%' comment 'Name of the instrumented object, either the literal or % for any object.', "
" ENABLED ENUM ('YES', 'NO') not null default 'YES' comment 'Whether the object''s events are instrumented or not. Can be disabled, in which case monitoring is not enabled for those objects.', "
2021-09-10 17:16:18 +03:00
" TIMED ENUM ('YES', 'NO') not null default 'YES' comment 'Whether the object''s events are timed or not. Can be modified.') " ) } ,
2019-12-10 15:35:00 +01:00
false /* perpetual */
2012-08-01 17:27:34 +03:00
} ;
int update_derived_flags ( )
{
PFS_thread * thread = PFS_thread : : get_current_thread ( ) ;
if ( unlikely ( thread = = NULL ) )
return HA_ERR_OUT_OF_MEM ;
update_table_share_derived_flags ( thread ) ;
2019-12-10 15:35:00 +01:00
update_program_share_derived_flags ( thread ) ;
2012-08-01 17:27:34 +03:00
update_table_derived_flags ( ) ;
return 0 ;
}
PFS_engine_table * table_setup_objects : : create ( void )
{
return new table_setup_objects ( ) ;
}
2019-07-04 21:31:35 +03:00
int table_setup_objects : : write_row ( TABLE * table , const unsigned char * buf ,
2012-08-01 17:27:34 +03:00
Field * * fields )
{
int result ;
Field * f ;
enum_object_type object_type = OBJECT_TYPE_TABLE ;
2019-06-28 09:05:12 +04:00
String object_schema_data ( " % " , 1 , & my_charset_utf8mb3_bin ) ;
String object_name_data ( " % " , 1 , & my_charset_utf8mb3_bin ) ;
2012-08-01 17:27:34 +03:00
String * object_schema = & object_schema_data ;
String * object_name = & object_name_data ;
enum_yes_no enabled_value = ENUM_YES ;
enum_yes_no timed_value = ENUM_YES ;
bool enabled = true ;
bool timed = true ;
for ( ; ( f = * fields ) ; fields + + )
{
if ( bitmap_is_set ( table - > write_set , f - > field_index ) )
{
switch ( f - > field_index )
{
case 0 : /* OBJECT_TYPE */
object_type = ( enum_object_type ) get_field_enum ( f ) ;
break ;
case 1 : /* OBJECT_SCHEMA */
object_schema = get_field_varchar_utf8 ( f , & object_schema_data ) ;
break ;
case 2 : /* OBJECT_NAME */
object_name = get_field_varchar_utf8 ( f , & object_name_data ) ;
break ;
case 3 : /* ENABLED */
enabled_value = ( enum_yes_no ) get_field_enum ( f ) ;
break ;
case 4 : /* TIMED */
timed_value = ( enum_yes_no ) get_field_enum ( f ) ;
break ;
default :
DBUG_ASSERT ( false ) ;
}
}
}
/* Reject illegal enum values in OBJECT_TYPE */
2019-12-10 15:35:00 +01:00
if ( object_type < FIRST_OBJECT_TYPE | |
object_type > LAST_OBJECT_TYPE | |
object_type = = OBJECT_TYPE_TEMPORARY_TABLE )
2012-08-01 17:27:34 +03:00
return HA_ERR_NO_REFERENCED_ROW ;
/* Reject illegal enum values in ENABLED */
if ( ( enabled_value ! = ENUM_YES ) & & ( enabled_value ! = ENUM_NO ) )
return HA_ERR_NO_REFERENCED_ROW ;
/* Reject illegal enum values in TIMED */
if ( ( timed_value ! = ENUM_YES ) & & ( timed_value ! = ENUM_NO ) )
return HA_ERR_NO_REFERENCED_ROW ;
enabled = ( enabled_value = = ENUM_YES ) ? true : false ;
timed = ( timed_value = = ENUM_YES ) ? true : false ;
result = insert_setup_object ( object_type , object_schema , object_name ,
enabled , timed ) ;
if ( result = = 0 )
result = update_derived_flags ( ) ;
return result ;
}
int table_setup_objects : : delete_all_rows ( void )
{
int result = reset_setup_object ( ) ;
if ( result = = 0 )
result = update_derived_flags ( ) ;
return result ;
}
ha_rows table_setup_objects : : get_row_count ( void )
{
2019-12-10 15:35:00 +01:00
return global_setup_object_container . get_row_count ( ) ;
2012-08-01 17:27:34 +03:00
}
table_setup_objects : : table_setup_objects ( )
: PFS_engine_table ( & m_share , & m_pos ) ,
m_row_exists ( false ) , m_pos ( 0 ) , m_next_pos ( 0 )
{ }
void table_setup_objects : : reset_position ( void )
{
m_pos . m_index = 0 ;
m_next_pos . m_index = 0 ;
}
int table_setup_objects : : rnd_next ( void )
{
PFS_setup_object * pfs ;
2019-12-10 15:35:00 +01:00
m_pos . set_at ( & m_next_pos ) ;
PFS_setup_object_iterator it = global_setup_object_container . iterate ( m_pos . m_index ) ;
pfs = it . scan_next ( & m_pos . m_index ) ;
if ( pfs ! = NULL )
2012-08-01 17:27:34 +03:00
{
2019-12-10 15:35:00 +01:00
make_row ( pfs ) ;
m_next_pos . set_after ( & m_pos ) ;
return 0 ;
2012-08-01 17:27:34 +03:00
}
return HA_ERR_END_OF_FILE ;
}
int table_setup_objects : : rnd_pos ( const void * pos )
{
PFS_setup_object * pfs ;
set_position ( pos ) ;
2019-12-10 15:35:00 +01:00
pfs = global_setup_object_container . get ( m_pos . m_index ) ;
if ( pfs ! = NULL )
2012-08-01 17:27:34 +03:00
{
make_row ( pfs ) ;
return 0 ;
}
return HA_ERR_RECORD_DELETED ;
}
void table_setup_objects : : make_row ( PFS_setup_object * pfs )
{
2019-12-10 15:35:00 +01:00
pfs_optimistic_state lock ;
2012-08-01 17:27:34 +03:00
m_row_exists = false ;
pfs - > m_lock . begin_optimistic_lock ( & lock ) ;
m_row . m_object_type = pfs - > get_object_type ( ) ;
memcpy ( m_row . m_schema_name , pfs - > m_schema_name , pfs - > m_schema_name_length ) ;
m_row . m_schema_name_length = pfs - > m_schema_name_length ;
memcpy ( m_row . m_object_name , pfs - > m_object_name , pfs - > m_object_name_length ) ;
m_row . m_object_name_length = pfs - > m_object_name_length ;
m_row . m_enabled_ptr = & pfs - > m_enabled ;
m_row . m_timed_ptr = & pfs - > m_timed ;
if ( pfs - > m_lock . end_optimistic_lock ( & lock ) )
m_row_exists = true ;
}
int table_setup_objects : : read_row_values ( TABLE * table ,
unsigned char * buf ,
Field * * fields ,
bool read_all )
{
Field * f ;
if ( unlikely ( ! m_row_exists ) )
return HA_ERR_RECORD_DELETED ;
/* Set the null bits */
DBUG_ASSERT ( table - > s - > null_bytes = = 1 ) ;
buf [ 0 ] = 0 ;
for ( ; ( f = * fields ) ; fields + + )
{
if ( read_all | | bitmap_is_set ( table - > read_set , f - > field_index ) )
{
switch ( f - > field_index )
{
case 0 : /* OBJECT_TYPE */
set_field_enum ( f , m_row . m_object_type ) ;
break ;
case 1 : /* OBJECT_SCHEMA */
if ( m_row . m_schema_name_length )
set_field_varchar_utf8 ( f , m_row . m_schema_name ,
m_row . m_schema_name_length ) ;
else
f - > set_null ( ) ;
break ;
case 2 : /* OBJECT_NAME */
if ( m_row . m_object_name_length )
set_field_varchar_utf8 ( f , m_row . m_object_name ,
m_row . m_object_name_length ) ;
else
f - > set_null ( ) ;
break ;
case 3 : /* ENABLED */
set_field_enum ( f , ( * m_row . m_enabled_ptr ) ? ENUM_YES : ENUM_NO ) ;
break ;
case 4 : /* TIMED */
set_field_enum ( f , ( * m_row . m_timed_ptr ) ? ENUM_YES : ENUM_NO ) ;
break ;
default :
DBUG_ASSERT ( false ) ;
}
}
}
return 0 ;
}
int table_setup_objects : : update_row_values ( TABLE * table ,
const unsigned char * ,
2017-04-16 22:40:39 +03:00
const unsigned char * ,
2012-08-01 17:27:34 +03:00
Field * * fields )
{
int result ;
Field * f ;
enum_yes_no value ;
for ( ; ( f = * fields ) ; fields + + )
{
if ( bitmap_is_set ( table - > write_set , f - > field_index ) )
{
switch ( f - > field_index )
{
case 0 : /* OBJECT_TYPE */
case 1 : /* OBJECT_SCHEMA */
case 2 : /* OBJECT_NAME */
return HA_ERR_WRONG_COMMAND ;
case 3 : /* ENABLED */
value = ( enum_yes_no ) get_field_enum ( f ) ;
/* Reject illegal enum values in ENABLED */
if ( ( value ! = ENUM_YES ) & & ( value ! = ENUM_NO ) )
return HA_ERR_NO_REFERENCED_ROW ;
* m_row . m_enabled_ptr = ( value = = ENUM_YES ) ? true : false ;
break ;
case 4 : /* TIMED */
value = ( enum_yes_no ) get_field_enum ( f ) ;
/* Reject illegal enum values in TIMED */
if ( ( value ! = ENUM_YES ) & & ( value ! = ENUM_NO ) )
return HA_ERR_NO_REFERENCED_ROW ;
* m_row . m_timed_ptr = ( value = = ENUM_YES ) ? true : false ;
break ;
default :
DBUG_ASSERT ( false ) ;
}
}
}
result = update_derived_flags ( ) ;
return result ;
}
int table_setup_objects : : delete_row_values ( TABLE * table ,
const unsigned char * buf ,
Field * * fields )
{
2013-03-26 00:03:13 +02:00
DBUG_ASSERT ( m_row_exists ) ;
2012-08-01 17:27:34 +03:00
2019-06-28 09:05:12 +04:00
CHARSET_INFO * cs = & my_charset_utf8mb3_bin ;
2013-03-26 00:03:13 +02:00
enum_object_type object_type = OBJECT_TYPE_TABLE ;
String object_schema ( m_row . m_schema_name , m_row . m_schema_name_length , cs ) ;
String object_name ( m_row . m_object_name , m_row . m_object_name_length , cs ) ;
2012-08-01 17:27:34 +03:00
2013-03-26 00:03:13 +02:00
int result = delete_setup_object ( object_type , & object_schema , & object_name ) ;
2012-08-01 17:27:34 +03:00
if ( result = = 0 )
result = update_derived_flags ( ) ;
return result ;
}