1 /* Copyright (c) 2019, Oracle and/or its affiliates. All Rights Reserved.
2
3 This program is free software; you can redistribute it and/or modify it under
4 the terms of the GNU General Public License, version 2.0, as published by the
5 Free Software Foundation.
6
7 This program is also distributed with certain software (including but not
8 limited to OpenSSL) that is licensed under separate terms, as designated in a
9 particular file or component or in included license documentation. The authors
10 of MySQL hereby grant you an additional permission to link the program and
11 your derivative works with the separately licensed software that they have
12 included with MySQL.
13
14 This program is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16 FOR A PARTICULAR PURPOSE. See the GNU General Public License, version 2.0,
17 for more details.
18
19 You should have received a copy of the GNU General Public License along with
20 this program; if not, write to the Free Software Foundation, Inc.,
21 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
22
23 /** @file storage/temptable/src/block.cc */
24
25 #include "my_dbug.h"
26 #include "my_psi_config.h"
27 #include "mysql/psi/mysql_memory.h"
28 #include "mysql/psi/psi_base.h"
29 #include "mysql/psi/psi_memory.h"
30
31 #ifdef HAVE_PSI_MEMORY_INTERFACE
32 #define TEMPTABLE_PFS_MEMORY
33
34 /* Enabling this causes ~ 4% performance drop in sysbench distinct ranges. */
35 //#define TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL
36 #endif /* HAVE_PSI_MEMORY_INTERFACE */
37
38 namespace temptable {
39
40 #ifdef TEMPTABLE_PFS_MEMORY
41 #ifdef TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL
42 /** PFS key to account logical memory allocations and deallocations. Logical
43 * is any request for new memory that arrives to the allocator. */
44 PSI_memory_key mem_key_logical;
45 #endif /* TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL */
46
47 /** PFS key to account physical allocations and deallocations from disk. After
48 * we have allocated more than `temptable_max_ram` we start taking memory from
49 * the OS disk, using mmap()'ed files. */
50 PSI_memory_key mem_key_physical_disk;
51
52 /** PFS key to account physical allocations and deallocations from RAM. Before
53 * we have allocated more than `temptable_max_ram` we take memory from the OS
54 * RAM, using e.g. malloc(). */
55 PSI_memory_key mem_key_physical_ram;
56
57 /** Array of PFS keys. */
58 PSI_memory_info pfs_info[] = {
59 #ifdef TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL
60 {&mem_key_logical, "logical", 0, 0, PSI_DOCUMENT_ME},
61 #endif /* TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL */
62 {&mem_key_physical_disk, "physical_disk", 0, 0, PSI_DOCUMENT_ME},
63 {&mem_key_physical_ram, "physical_ram", PSI_FLAG_ONLY_GLOBAL_STAT, 0,
64 PSI_DOCUMENT_ME},
65 };
66
67 /** Number of elements inside `pfs_info[]`. */
68 const size_t pfs_info_num_elements = sizeof(pfs_info) / sizeof(pfs_info[0]);
69 #endif /* TEMPTABLE_PFS_MEMORY */
70
Block_PSI_init()71 void Block_PSI_init() {
72 #ifdef TEMPTABLE_PFS_MEMORY
73 PSI_MEMORY_CALL(register_memory)
74 ("temptable", pfs_info, pfs_info_num_elements);
75 #endif /* TEMPTABLE_PFS_MEMORY */
76 }
77
Block_PSI_track_logical_allocation(size_t size)78 void Block_PSI_track_logical_allocation(size_t size) {
79 (void)size;
80 #ifdef TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL
81 PSI_thread *owner_thread;
82
83 #ifndef DBUG_OFF
84 PSI_memory_key key =
85 #endif /* DBUG_OFF */
86 PSI_MEMORY_CALL(memory_alloc)(mem_key_logical, size, &owner_thread);
87
88 DBUG_ASSERT(key == mem_key_logical || key == PSI_NOT_INSTRUMENTED);
89 #endif /* TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL */
90 }
91
Block_PSI_track_logical_deallocation(size_t size)92 void Block_PSI_track_logical_deallocation(size_t size) {
93 (void)size;
94 #ifdef TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL
95 PSI_MEMORY_CALL(memory_free)
96 (mem_key_logical, size, nullptr);
97 #endif /* TEMPTABLE_PFS_MEMORY_COUNT_LOGICAL */
98 }
99
Block_PSI_track_physical_ram_allocation(size_t size)100 void Block_PSI_track_physical_ram_allocation(size_t size) {
101 (void)size;
102 #ifdef TEMPTABLE_PFS_MEMORY
103 const PSI_memory_key psi_key = mem_key_physical_ram;
104 PSI_thread *owner_thread;
105 #ifndef DBUG_OFF
106 PSI_memory_key got_key =
107 #endif /* DBUG_OFF */
108 PSI_MEMORY_CALL(memory_alloc)(psi_key, size, &owner_thread);
109 DBUG_ASSERT(got_key == psi_key || got_key == PSI_NOT_INSTRUMENTED);
110 #endif /* TEMPTABLE_PFS_MEMORY */
111 }
112
Block_PSI_track_physical_ram_deallocation(size_t size)113 void Block_PSI_track_physical_ram_deallocation(size_t size) {
114 (void)size;
115 #ifdef TEMPTABLE_PFS_MEMORY
116 PSI_MEMORY_CALL(memory_free)(mem_key_physical_ram, size, nullptr);
117 #endif /* TEMPTABLE_PFS_MEMORY */
118 }
119
Block_PSI_track_physical_disk_allocation(size_t size)120 void Block_PSI_track_physical_disk_allocation(size_t size) {
121 (void)size;
122 #ifdef TEMPTABLE_PFS_MEMORY
123 const PSI_memory_key psi_key = mem_key_physical_disk;
124 PSI_thread *owner_thread;
125 #ifndef DBUG_OFF
126 PSI_memory_key got_key =
127 #endif /* DBUG_OFF */
128 PSI_MEMORY_CALL(memory_alloc)(psi_key, size, &owner_thread);
129 DBUG_ASSERT(got_key == psi_key || got_key == PSI_NOT_INSTRUMENTED);
130 #endif /* TEMPTABLE_PFS_MEMORY */
131 }
132
Block_PSI_track_physical_disk_deallocation(size_t size)133 void Block_PSI_track_physical_disk_deallocation(size_t size) {
134 (void)size;
135 #ifdef TEMPTABLE_PFS_MEMORY
136 PSI_MEMORY_CALL(memory_free)(mem_key_physical_disk, size, nullptr);
137 #endif /* TEMPTABLE_PFS_MEMORY */
138 }
139
140 } /* namespace temptable */
141