#At file:///Users/malff/BZR_TREE/mysql-trunk-bugfixing-58620/ based on revid:nirbhay.choubey@stripped
3401 Marc Alff 2010-12-01
Bug#58620 Performance schema failed assert, pfs_instr_class.cc, line 956
Before this fix, the member PFS_table_share::m_refcount was maintained
with ++ and -- operations.
This is not thread safe, since two threads may open or close table
handles on the same table share, and compete when updating m_refcount.
This fix uses atomic operations to maintain this reference counter,
making the counter safe.
modified:
storage/perfschema/pfs_instr.cc
storage/perfschema/pfs_instr_class.cc
storage/perfschema/pfs_instr_class.h
=== modified file 'storage/perfschema/pfs_instr.cc'
--- a/storage/perfschema/pfs_instr.cc 2010-11-16 06:27:18 +0000
+++ b/storage/perfschema/pfs_instr.cc 2010-12-01 08:33:53 +0000
@@ -1057,7 +1057,7 @@ PFS_table* create_table(PFS_table_share
{
pfs->m_identity= identity;
pfs->m_share= share;
- share->m_refcount++;
+ share->inc_refcount();
pfs->m_wait_stat.m_control_flag=
&flag_events_waits_summary_by_instance;
pfs->m_wait_stat.m_parent= &share->m_wait_stat;
=== modified file 'storage/perfschema/pfs_instr_class.cc'
--- a/storage/perfschema/pfs_instr_class.cc 2010-11-16 06:27:18 +0000
+++ b/storage/perfschema/pfs_instr_class.cc 2010-12-01 08:33:53 +0000
@@ -788,7 +788,7 @@ search:
{
PFS_table_share *pfs;
pfs= *entry;
- pfs->m_refcount++ ;
+ pfs->inc_refcount() ;
lf_hash_search_unpin(pins);
return pfs;
}
@@ -835,7 +835,7 @@ search:
reset_single_stat_link(&pfs->m_wait_stat);
pfs->m_enabled= enabled;
pfs->m_timed= timed;
- pfs->m_refcount= 1;
+ pfs->init_refcount();
int res;
res= lf_hash_insert(&table_share_hash, pins, &pfs);
@@ -879,7 +879,7 @@ search:
*/
void purge_table_share(PFS_thread *thread, PFS_table_share *pfs)
{
- if (pfs->m_refcount == 1)
+ if (pfs->get_refcount() == 1)
{
LF_PINS* pins= get_table_share_hash_pins(thread);
if (likely(pins != NULL))
=== modified file 'storage/perfschema/pfs_instr_class.h'
--- a/storage/perfschema/pfs_instr_class.h 2010-11-16 06:27:18 +0000
+++ b/storage/perfschema/pfs_instr_class.h 2010-12-01 08:33:53 +0000
@@ -146,11 +146,32 @@ struct PFS_table_share_key
/** Instrumentation metadata for a table share. */
struct PFS_table_share
{
+public:
enum_object_type get_object_type()
{
return (enum_object_type) m_key.m_hash_key[0];
}
+ inline void init_refcount(void)
+ {
+ PFS_atomic::store_32(& m_refcount, 1);
+ }
+
+ inline int get_refcount(void)
+ {
+ return PFS_atomic::load_32(& m_refcount);
+ }
+
+ inline void inc_refcount(void)
+ {
+ PFS_atomic::add_32(& m_refcount, 1);
+ }
+
+ inline void dec_refcount(void)
+ {
+ PFS_atomic::add_32(& m_refcount, -1);
+ }
+
/** Internal lock. */
pfs_lock m_lock;
/** Search key. */
@@ -170,8 +191,10 @@ struct PFS_table_share
/** True if this table instrument is timed. */
bool m_timed;
bool m_purge;
+
+private:
/** Number of opened table handles. */
- uint m_refcount;
+ int m_refcount;
};
/**
Attachment: [text/bzr-bundle] bzr/marc.alff@oracle.com-20101201083353-50p3cvvg2sb8gkp7.bundle
| Thread |
|---|
| • bzr commit into mysql-trunk-bugfixing branch (marc.alff:3401) Bug#58620 | Marc Alff | 1 Dec |