1 /* Copyright (c) 2010, 2021, Oracle and/or its affiliates.
2 
3   This program is free software; you can redistribute it and/or modify
4   it under the terms of the GNU General Public License, version 2.0,
5   as published by the Free Software Foundation.
6 
7   This program is also distributed with certain software (including
8   but not limited to OpenSSL) that is licensed under separate terms,
9   as designated in a particular file or component or in included license
10   documentation.  The authors of MySQL hereby grant you an additional
11   permission to link the program and your derivative works with the
12   separately licensed software that they have included with MySQL.
13 
14   This program is distributed in the hope that it will be useful,
15   but WITHOUT ANY WARRANTY; without even the implied warranty of
16   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17   GNU General Public License, version 2.0, for more details.
18 
19   You should have received a copy of the GNU General Public License
20   along with this program; if not, write to the Free Software
21   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA */
22 
23 /**
24   @file storage/perfschema/table_esms_by_digest.cc
25   Table EVENTS_STATEMENTS_SUMMARY_GLOBAL_BY_DIGEST (implementation).
26 */
27 
28 #include "my_global.h"
29 #include "my_thread.h"
30 #include "pfs_instr_class.h"
31 #include "pfs_column_types.h"
32 #include "pfs_column_values.h"
33 #include "table_esms_by_digest.h"
34 #include "pfs_global.h"
35 #include "pfs_instr.h"
36 #include "pfs_timer.h"
37 #include "pfs_visitor.h"
38 #include "table_esms_by_digest.h"
39 #include "pfs_digest.h"
40 #include "field.h"
41 
42 THR_LOCK table_esms_by_digest::m_table_lock;
43 
44 static const TABLE_FIELD_TYPE field_types[]=
45 {
46   {
47     { C_STRING_WITH_LEN("SCHEMA_NAME") },
48     { C_STRING_WITH_LEN("varchar(64)") },
49     { NULL, 0}
50   },
51   {
52     { C_STRING_WITH_LEN("DIGEST") },
53     { C_STRING_WITH_LEN("varchar(32)") },
54     { NULL, 0}
55   },
56   {
57     { C_STRING_WITH_LEN("DIGEST_TEXT") },
58     { C_STRING_WITH_LEN("longtext") },
59     { NULL, 0}
60   },
61   {
62     { C_STRING_WITH_LEN("COUNT_STAR") },
63     { C_STRING_WITH_LEN("bigint(20)") },
64     { NULL, 0}
65   },
66   {
67     { C_STRING_WITH_LEN("SUM_TIMER_WAIT") },
68     { C_STRING_WITH_LEN("bigint(20)") },
69     { NULL, 0}
70   },
71   {
72     { C_STRING_WITH_LEN("MIN_TIMER_WAIT") },
73     { C_STRING_WITH_LEN("bigint(20)") },
74     { NULL, 0}
75   },
76   {
77     { C_STRING_WITH_LEN("AVG_TIMER_WAIT") },
78     { C_STRING_WITH_LEN("bigint(20)") },
79     { NULL, 0}
80   },
81   {
82     { C_STRING_WITH_LEN("MAX_TIMER_WAIT") },
83     { C_STRING_WITH_LEN("bigint(20)") },
84     { NULL, 0}
85   },
86   {
87     { C_STRING_WITH_LEN("SUM_LOCK_TIME") },
88     { C_STRING_WITH_LEN("bigint(20)") },
89     { NULL, 0}
90   },
91   {
92     { C_STRING_WITH_LEN("SUM_ERRORS") },
93     { C_STRING_WITH_LEN("bigint(20)") },
94     { NULL, 0}
95   },
96   {
97     { C_STRING_WITH_LEN("SUM_WARNINGS") },
98     { C_STRING_WITH_LEN("bigint(20)") },
99     { NULL, 0}
100   },
101   {
102     { C_STRING_WITH_LEN("SUM_ROWS_AFFECTED") },
103     { C_STRING_WITH_LEN("bigint(20)") },
104     { NULL, 0}
105   },
106   {
107     { C_STRING_WITH_LEN("SUM_ROWS_SENT") },
108     { C_STRING_WITH_LEN("bigint(20)") },
109     { NULL, 0}
110   },
111   {
112     { C_STRING_WITH_LEN("SUM_ROWS_EXAMINED") },
113     { C_STRING_WITH_LEN("bigint(20)") },
114     { NULL, 0}
115   },
116   {
117     { C_STRING_WITH_LEN("SUM_CREATED_TMP_DISK_TABLES") },
118     { C_STRING_WITH_LEN("bigint(20)") },
119     { NULL, 0}
120   },
121   {
122     { C_STRING_WITH_LEN("SUM_CREATED_TMP_TABLES") },
123     { C_STRING_WITH_LEN("bigint(20)") },
124     { NULL, 0}
125   },
126   {
127     { C_STRING_WITH_LEN("SUM_SELECT_FULL_JOIN") },
128     { C_STRING_WITH_LEN("bigint(20)") },
129     { NULL, 0}
130   },
131   {
132     { C_STRING_WITH_LEN("SUM_SELECT_FULL_RANGE_JOIN") },
133     { C_STRING_WITH_LEN("bigint(20)") },
134     { NULL, 0}
135   },
136   {
137     { C_STRING_WITH_LEN("SUM_SELECT_RANGE") },
138     { C_STRING_WITH_LEN("bigint(20)") },
139     { NULL, 0}
140   },
141   {
142     { C_STRING_WITH_LEN("SUM_SELECT_RANGE_CHECK") },
143     { C_STRING_WITH_LEN("bigint(20)") },
144     { NULL, 0}
145   },
146   {
147     { C_STRING_WITH_LEN("SUM_SELECT_SCAN") },
148     { C_STRING_WITH_LEN("bigint(20)") },
149     { NULL, 0}
150   },
151   {
152     { C_STRING_WITH_LEN("SUM_SORT_MERGE_PASSES") },
153     { C_STRING_WITH_LEN("bigint(20)") },
154     { NULL, 0}
155   },
156   {
157     { C_STRING_WITH_LEN("SUM_SORT_RANGE") },
158     { C_STRING_WITH_LEN("bigint(20)") },
159     { NULL, 0}
160   },
161   {
162     { C_STRING_WITH_LEN("SUM_SORT_ROWS") },
163     { C_STRING_WITH_LEN("bigint(20)") },
164     { NULL, 0}
165   },
166   {
167     { C_STRING_WITH_LEN("SUM_SORT_SCAN") },
168     { C_STRING_WITH_LEN("bigint(20)") },
169     { NULL, 0}
170   },
171   {
172     { C_STRING_WITH_LEN("SUM_NO_INDEX_USED") },
173     { C_STRING_WITH_LEN("bigint(20)") },
174     { NULL, 0}
175   },
176   {
177     { C_STRING_WITH_LEN("SUM_NO_GOOD_INDEX_USED") },
178     { C_STRING_WITH_LEN("bigint(20)") },
179     { NULL, 0}
180   },
181   {
182     { C_STRING_WITH_LEN("FIRST_SEEN") },
183     { C_STRING_WITH_LEN("timestamp") },
184     { NULL, 0}
185   },
186   {
187     { C_STRING_WITH_LEN("LAST_SEEN") },
188     { C_STRING_WITH_LEN("timestamp") },
189     { NULL, 0}
190   }
191 };
192 
193 TABLE_FIELD_DEF
194 table_esms_by_digest::m_field_def=
195 { 29, field_types };
196 
197 PFS_engine_table_share
198 table_esms_by_digest::m_share=
199 {
200   { C_STRING_WITH_LEN("events_statements_summary_by_digest") },
201   &pfs_truncatable_acl,
202   table_esms_by_digest::create,
203   NULL, /* write_row */
204   table_esms_by_digest::delete_all_rows,
205   table_esms_by_digest::get_row_count,
206   sizeof(PFS_simple_index),
207   &m_table_lock,
208   &m_field_def,
209   false, /* checked */
210   false  /* perpetual */
211 };
212 
213 PFS_engine_table*
create(void)214 table_esms_by_digest::create(void)
215 {
216   return new table_esms_by_digest();
217 }
218 
219 int
delete_all_rows(void)220 table_esms_by_digest::delete_all_rows(void)
221 {
222   reset_esms_by_digest();
223   return 0;
224 }
225 
226 ha_rows
get_row_count(void)227 table_esms_by_digest::get_row_count(void)
228 {
229   return digest_max;
230 }
231 
table_esms_by_digest()232 table_esms_by_digest::table_esms_by_digest()
233   : PFS_engine_table(&m_share, &m_pos),
234     m_row_exists(false), m_pos(0), m_next_pos(0)
235 {}
236 
reset_position(void)237 void table_esms_by_digest::reset_position(void)
238 {
239   m_pos= 0;
240   m_next_pos= 0;
241 }
242 
rnd_next(void)243 int table_esms_by_digest::rnd_next(void)
244 {
245   PFS_statements_digest_stat* digest_stat;
246 
247   if (statements_digest_stat_array == NULL)
248     return HA_ERR_END_OF_FILE;
249 
250   for (m_pos.set_at(&m_next_pos);
251        m_pos.m_index < digest_max;
252        m_pos.next())
253   {
254     digest_stat= &statements_digest_stat_array[m_pos.m_index];
255     if (digest_stat->m_lock.is_populated())
256     {
257       if (digest_stat->m_first_seen != 0)
258       {
259         make_row(digest_stat);
260         m_next_pos.set_after(&m_pos);
261         return 0;
262       }
263     }
264   }
265 
266   return HA_ERR_END_OF_FILE;
267 }
268 
269 int
rnd_pos(const void * pos)270 table_esms_by_digest::rnd_pos(const void *pos)
271 {
272   PFS_statements_digest_stat* digest_stat;
273 
274   if (statements_digest_stat_array == NULL)
275     return HA_ERR_END_OF_FILE;
276 
277   set_position(pos);
278   digest_stat= &statements_digest_stat_array[m_pos.m_index];
279 
280   if (digest_stat->m_lock.is_populated())
281   {
282     if (digest_stat->m_first_seen != 0)
283     {
284       make_row(digest_stat);
285       return 0;
286     }
287   }
288 
289   return HA_ERR_RECORD_DELETED;
290 }
291 
292 
make_row(PFS_statements_digest_stat * digest_stat)293 void table_esms_by_digest::make_row(PFS_statements_digest_stat* digest_stat)
294 {
295   m_row_exists= false;
296   m_row.m_first_seen= digest_stat->m_first_seen;
297   m_row.m_last_seen= digest_stat->m_last_seen;
298   m_row.m_digest.make_row(digest_stat);
299 
300   /*
301     Get statements stats.
302   */
303   time_normalizer *normalizer= time_normalizer::get(statement_timer);
304   m_row.m_stat.set(normalizer, & digest_stat->m_stat);
305 
306   m_row_exists= true;
307 }
308 
309 int table_esms_by_digest
read_row_values(TABLE * table,unsigned char * buf,Field ** fields,bool read_all)310 ::read_row_values(TABLE *table, unsigned char *buf, Field **fields,
311                   bool read_all)
312 {
313   Field *f;
314 
315   if (unlikely(! m_row_exists))
316     return HA_ERR_RECORD_DELETED;
317 
318   /*
319     Set the null bits. It indicates how many fields could be null
320     in the table.
321   */
322   assert(table->s->null_bytes == 1);
323   buf[0]= 0;
324 
325   for (; (f= *fields) ; fields++)
326   {
327     if (read_all || bitmap_is_set(table->read_set, f->field_index))
328     {
329       switch(f->field_index)
330       {
331       case 0: /* SCHEMA_NAME */
332       case 1: /* DIGEST */
333       case 2: /* DIGEST_TEXT */
334         m_row.m_digest.set_field(f->field_index, f);
335         break;
336       case 27: /* FIRST_SEEN */
337         set_field_timestamp(f, m_row.m_first_seen);
338         break;
339       case 28: /* LAST_SEEN */
340         set_field_timestamp(f, m_row.m_last_seen);
341         break;
342       default: /* 3, ... COUNT/SUM/MIN/AVG/MAX */
343         m_row.m_stat.set_field(f->field_index - 3, f);
344         break;
345       }
346     }
347   }
348 
349   return 0;
350 }
351 
352