1 /* Copyright (c) 2008, 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 Foundation,
21   51 Franklin Street, Fifth Floor, Boston, MA 02110-1335 USA */
22 
23 #ifndef MYSQL_FILE_H
24 #define MYSQL_FILE_H
25 
26 /* For strlen() */
27 #include <string.h>
28 /* For MY_STAT */
29 #include <my_dir.h>
30 /* For my_chsize */
31 #include <my_sys.h>
32 
33 /**
34   @file mysql/psi/mysql_file.h
35   Instrumentation helpers for mysys file io.
36   This header file provides the necessary declarations
37   to use the mysys file API with the performance schema instrumentation.
38   In some compilers (SunStudio), 'static inline' functions, when declared
39   but not used, are not optimized away (because they are unused) by default,
40   so that including a static inline function from a header file does
41   create unwanted dependencies, causing unresolved symbols at link time.
42   Other compilers, like gcc, optimize these dependencies by default.
43 
44   Since the instrumented APIs declared here are wrapper on top
45   of mysys file io APIs, including mysql/psi/mysql_file.h assumes that
46   the dependency on my_sys already exists.
47 */
48 
49 #include "mysql/psi/psi.h"
50 
51 #ifndef PSI_FILE_CALL
52 #define PSI_FILE_CALL(M) PSI_DYNAMIC_CALL(M)
53 #endif
54 
55 /**
56   @defgroup File_instrumentation File Instrumentation
57   @ingroup Instrumentation_interface
58   @{
59 */
60 
61 /**
62   @def mysql_file_register(P1, P2, P3)
63   File registration.
64 */
65 #define mysql_file_register(P1, P2, P3) \
66   inline_mysql_file_register(P1, P2, P3)
67 
68 /**
69   @def mysql_file_fgets(P1, P2, F)
70   Instrumented fgets.
71   @c mysql_file_fgets is a replacement for @c fgets.
72 */
73 #ifdef HAVE_PSI_FILE_INTERFACE
74   #define mysql_file_fgets(P1, P2, F) \
75     inline_mysql_file_fgets(__FILE__, __LINE__, P1, P2, F)
76 #else
77   #define mysql_file_fgets(P1, P2, F) \
78     inline_mysql_file_fgets(P1, P2, F)
79 #endif
80 
81 /**
82   @def mysql_file_fgetc(F)
83   Instrumented fgetc.
84   @c mysql_file_fgetc is a replacement for @c fgetc.
85 */
86 #ifdef HAVE_PSI_FILE_INTERFACE
87   #define mysql_file_fgetc(F) inline_mysql_file_fgetc(__FILE__, __LINE__, F)
88 #else
89   #define mysql_file_fgetc(F) inline_mysql_file_fgetc(F)
90 #endif
91 
92 /**
93   @def mysql_file_fputs(P1, F)
94   Instrumented fputs.
95   @c mysql_file_fputs is a replacement for @c fputs.
96 */
97 #ifdef HAVE_PSI_FILE_INTERFACE
98   #define mysql_file_fputs(P1, F) \
99     inline_mysql_file_fputs(__FILE__, __LINE__, P1, F)
100 #else
101   #define mysql_file_fputs(P1, F)\
102     inline_mysql_file_fputs(P1, F)
103 #endif
104 
105 /**
106   @def mysql_file_fputc(P1, F)
107   Instrumented fputc.
108   @c mysql_file_fputc is a replacement for @c fputc.
109 */
110 #ifdef HAVE_PSI_FILE_INTERFACE
111   #define mysql_file_fputc(P1, F) \
112     inline_mysql_file_fputc(__FILE__, __LINE__, P1, F)
113 #else
114   #define mysql_file_fputc(P1, F) \
115     inline_mysql_file_fputc(P1, F)
116 #endif
117 
118 /**
119   @def mysql_file_fprintf
120   Instrumented fprintf.
121   @c mysql_file_fprintf is a replacement for @c fprintf.
122 */
123 #define mysql_file_fprintf inline_mysql_file_fprintf
124 
125 /**
126   @def mysql_file_vfprintf(F, P1, P2)
127   Instrumented vfprintf.
128   @c mysql_file_vfprintf is a replacement for @c vfprintf.
129 */
130 #ifdef HAVE_PSI_FILE_INTERFACE
131   #define mysql_file_vfprintf(F, P1, P2) \
132     inline_mysql_file_vfprintf(__FILE__, __LINE__, F, P1, P2)
133 #else
134   #define mysql_file_vfprintf(F, P1, P2) \
135     inline_mysql_file_vfprintf(F, P1, P2)
136 #endif
137 
138 /**
139   @def mysql_file_fflush(F, P1, P2)
140   Instrumented fflush.
141   @c mysql_file_fflush is a replacement for @c fflush.
142 */
143 #ifdef HAVE_PSI_FILE_INTERFACE
144   #define mysql_file_fflush(F) \
145     inline_mysql_file_fflush(__FILE__, __LINE__, F)
146 #else
147   #define mysql_file_fflush(F) \
148     inline_mysql_file_fflush(F)
149 #endif
150 
151 /**
152   @def mysql_file_feof(F)
153   Instrumented feof.
154   @c mysql_file_feof is a replacement for @c feof.
155 */
156 #define mysql_file_feof(F) inline_mysql_file_feof(F)
157 
158 /**
159   @def mysql_file_fstat(FN, S, FL)
160   Instrumented fstat.
161   @c mysql_file_fstat is a replacement for @c my_fstat.
162 */
163 #ifdef HAVE_PSI_FILE_INTERFACE
164   #define mysql_file_fstat(FN, S, FL) \
165     inline_mysql_file_fstat(__FILE__, __LINE__, FN, S, FL)
166 #else
167   #define mysql_file_fstat(FN, S, FL) \
168     inline_mysql_file_fstat(FN, S, FL)
169 #endif
170 
171 /**
172   @def mysql_file_stat(K, FN, S, FL)
173   Instrumented stat.
174   @c mysql_file_stat is a replacement for @c my_stat.
175 */
176 #ifdef HAVE_PSI_FILE_INTERFACE
177   #define mysql_file_stat(K, FN, S, FL) \
178     inline_mysql_file_stat(K, __FILE__, __LINE__, FN, S, FL)
179 #else
180   #define mysql_file_stat(K, FN, S, FL) \
181     inline_mysql_file_stat(FN, S, FL)
182 #endif
183 
184 /**
185   @def mysql_file_chsize(F, P1, P2, P3)
186   Instrumented chsize.
187   @c mysql_file_chsize is a replacement for @c my_chsize.
188 */
189 #ifdef HAVE_PSI_FILE_INTERFACE
190   #define mysql_file_chsize(F, P1, P2, P3) \
191     inline_mysql_file_chsize(__FILE__, __LINE__, F, P1, P2, P3)
192 #else
193   #define mysql_file_chsize(F, P1, P2, P3) \
194     inline_mysql_file_chsize(F, P1, P2, P3)
195 #endif
196 
197 /**
198   @def mysql_file_fopen(K, N, F1, F2)
199   Instrumented fopen.
200   @c mysql_file_fopen is a replacement for @c my_fopen.
201 */
202 #ifdef HAVE_PSI_FILE_INTERFACE
203   #define mysql_file_fopen(K, N, F1, F2) \
204     inline_mysql_file_fopen(K, __FILE__, __LINE__, N, F1, F2)
205 #else
206   #define mysql_file_fopen(K, N, F1, F2) \
207     inline_mysql_file_fopen(N, F1, F2)
208 #endif
209 
210 /**
211   @def mysql_file_fclose(FD, FL)
212   Instrumented fclose.
213   @c mysql_file_fclose is a replacement for @c my_fclose.
214   Without the instrumentation, this call will have the same behavior as the
215   undocumented and possibly platform specific my_fclose(NULL, ...) behavior.
216   With the instrumentation, mysql_fclose(NULL, ...) will safely return 0,
217   which is an extension compared to my_fclose and is therefore compliant.
218   mysql_fclose is on purpose *not* implementing
219   @code assert(file != NULL) @endcode,
220   since doing so could introduce regressions.
221 */
222 #ifdef HAVE_PSI_FILE_INTERFACE
223   #define mysql_file_fclose(FD, FL) \
224     inline_mysql_file_fclose(__FILE__, __LINE__, FD, FL)
225 #else
226   #define mysql_file_fclose(FD, FL) \
227     inline_mysql_file_fclose(FD, FL)
228 #endif
229 
230 /**
231   @def mysql_file_fread(FD, P1, P2, P3)
232   Instrumented fread.
233   @c mysql_file_fread is a replacement for @c my_fread.
234 */
235 #ifdef HAVE_PSI_FILE_INTERFACE
236   #define mysql_file_fread(FD, P1, P2, P3) \
237     inline_mysql_file_fread(__FILE__, __LINE__, FD, P1, P2, P3)
238 #else
239   #define mysql_file_fread(FD, P1, P2, P3) \
240     inline_mysql_file_fread(FD, P1, P2, P3)
241 #endif
242 
243 /**
244   @def mysql_file_fwrite(FD, P1, P2, P3)
245   Instrumented fwrite.
246   @c mysql_file_fwrite is a replacement for @c my_fwrite.
247 */
248 #ifdef HAVE_PSI_FILE_INTERFACE
249   #define mysql_file_fwrite(FD, P1, P2, P3) \
250     inline_mysql_file_fwrite(__FILE__, __LINE__, FD, P1, P2, P3)
251 #else
252   #define mysql_file_fwrite(FD, P1, P2, P3) \
253     inline_mysql_file_fwrite(FD, P1, P2, P3)
254 #endif
255 
256 /**
257   @def mysql_file_fseek(FD, P, W, F)
258   Instrumented fseek.
259   @c mysql_file_fseek is a replacement for @c my_fseek.
260 */
261 #ifdef HAVE_PSI_FILE_INTERFACE
262   #define mysql_file_fseek(FD, P, W, F) \
263     inline_mysql_file_fseek(__FILE__, __LINE__, FD, P, W, F)
264 #else
265   #define mysql_file_fseek(FD, P, W, F) \
266     inline_mysql_file_fseek(FD, P, W, F)
267 #endif
268 
269 /**
270   @def mysql_file_ftell(FD, F)
271   Instrumented ftell.
272   @c mysql_file_ftell is a replacement for @c my_ftell.
273 */
274 #ifdef HAVE_PSI_FILE_INTERFACE
275   #define mysql_file_ftell(FD, F) \
276     inline_mysql_file_ftell(__FILE__, __LINE__, FD, F)
277 #else
278   #define mysql_file_ftell(FD, F) \
279     inline_mysql_file_ftell(FD, F)
280 #endif
281 
282 /**
283   @def mysql_file_create(K, N, F1, F2, F3)
284   Instrumented create.
285   @c mysql_file_create is a replacement for @c my_create.
286 */
287 #ifdef HAVE_PSI_FILE_INTERFACE
288   #define mysql_file_create(K, N, F1, F2, F3) \
289   inline_mysql_file_create(K, __FILE__, __LINE__, N, F1, F2, F3)
290 #else
291   #define mysql_file_create(K, N, F1, F2, F3) \
292     inline_mysql_file_create(N, F1, F2, F3)
293 #endif
294 
295 /**
296   @def mysql_file_create_temp(K, T, D, P, M, F)
297   Instrumented create_temp_file.
298   @c mysql_file_create_temp is a replacement for @c create_temp_file.
299 */
300 #ifdef HAVE_PSI_FILE_INTERFACE
301   #define mysql_file_create_temp(K, T, D, P, M, F) \
302     inline_mysql_file_create_temp(K, __FILE__, __LINE__, T, D, P, M, F)
303 #else
304   #define mysql_file_create_temp(K, T, D, P, M, F) \
305     inline_mysql_file_create_temp(T, D, P, M, F)
306 #endif
307 
308 /**
309   @def mysql_file_open(K, N, F1, F2)
310   Instrumented open.
311   @c mysql_file_open is a replacement for @c my_open.
312 */
313 #ifdef HAVE_PSI_FILE_INTERFACE
314   #define mysql_file_open(K, N, F1, F2) \
315     inline_mysql_file_open(K, __FILE__, __LINE__, N, F1, F2)
316 #else
317   #define mysql_file_open(K, N, F1, F2) \
318     inline_mysql_file_open(N, F1, F2)
319 #endif
320 
321 /**
322   @def mysql_file_close(FD, F)
323   Instrumented close.
324   @c mysql_file_close is a replacement for @c my_close.
325 */
326 #ifdef HAVE_PSI_FILE_INTERFACE
327   #define mysql_file_close(FD, F) \
328     inline_mysql_file_close(__FILE__, __LINE__, FD, F)
329 #else
330   #define mysql_file_close(FD, F) \
331     inline_mysql_file_close(FD, F)
332 #endif
333 
334 /**
335   @def mysql_file_read(FD, B, S, F)
336   Instrumented read.
337   @c mysql_read is a replacement for @c my_read.
338 */
339 #ifdef HAVE_PSI_FILE_INTERFACE
340   #define mysql_file_read(FD, B, S, F) \
341     inline_mysql_file_read(__FILE__, __LINE__, FD, B, S, F)
342 #else
343   #define mysql_file_read(FD, B, S, F) \
344     inline_mysql_file_read(FD, B, S, F)
345 #endif
346 
347 /**
348   @def mysql_file_write(FD, B, S, F)
349   Instrumented write.
350   @c mysql_file_write is a replacement for @c my_write.
351 */
352 #ifdef HAVE_PSI_FILE_INTERFACE
353   #define mysql_file_write(FD, B, S, F) \
354     inline_mysql_file_write(__FILE__, __LINE__, FD, B, S, F)
355 #else
356   #define mysql_file_write(FD, B, S, F) \
357     inline_mysql_file_write(FD, B, S, F)
358 #endif
359 
360 /**
361   @def mysql_file_pread(FD, B, S, O, F)
362   Instrumented pread.
363   @c mysql_pread is a replacement for @c my_pread.
364 */
365 #ifdef HAVE_PSI_FILE_INTERFACE
366   #define mysql_file_pread(FD, B, S, O, F) \
367     inline_mysql_file_pread(__FILE__, __LINE__, FD, B, S, O, F)
368 #else
369   #define mysql_file_pread(FD, B, S, O, F) \
370     inline_mysql_file_pread(FD, B, S, O, F)
371 #endif
372 
373 /**
374   @def mysql_file_pwrite(FD, B, S, O, F)
375   Instrumented pwrite.
376   @c mysql_file_pwrite is a replacement for @c my_pwrite.
377 */
378 #ifdef HAVE_PSI_FILE_INTERFACE
379   #define mysql_file_pwrite(FD, B, S, O, F) \
380     inline_mysql_file_pwrite(__FILE__, __LINE__, FD, B, S, O, F)
381 #else
382   #define mysql_file_pwrite(FD, B, S, O, F) \
383     inline_mysql_file_pwrite(FD, B, S, O, F)
384 #endif
385 
386 /**
387   @def mysql_file_seek(FD, P, W, F)
388   Instrumented seek.
389   @c mysql_file_seek is a replacement for @c my_seek.
390 */
391 #ifdef HAVE_PSI_FILE_INTERFACE
392   #define mysql_file_seek(FD, P, W, F) \
393     inline_mysql_file_seek(__FILE__, __LINE__, FD, P, W, F)
394 #else
395   #define mysql_file_seek(FD, P, W, F) \
396     inline_mysql_file_seek(FD, P, W, F)
397 #endif
398 
399 /**
400   @def mysql_file_tell(FD, F)
401   Instrumented tell.
402   @c mysql_file_tell is a replacement for @c my_tell.
403 */
404 #ifdef HAVE_PSI_FILE_INTERFACE
405   #define mysql_file_tell(FD, F) \
406     inline_mysql_file_tell(__FILE__, __LINE__, FD, F)
407 #else
408   #define mysql_file_tell(FD, F) \
409     inline_mysql_file_tell(FD, F)
410 #endif
411 
412 /**
413   @def mysql_file_delete(K, P1, P2)
414   Instrumented delete.
415   @c mysql_file_delete is a replacement for @c my_delete.
416 */
417 #ifdef HAVE_PSI_FILE_INTERFACE
418   #define mysql_file_delete(K, P1, P2) \
419     inline_mysql_file_delete(K, __FILE__, __LINE__, P1, P2)
420 #else
421   #define mysql_file_delete(K, P1, P2) \
422     inline_mysql_file_delete(P1, P2)
423 #endif
424 
425 /**
426   @def mysql_file_rename(K, P1, P2, P3)
427   Instrumented rename.
428   @c mysql_file_rename is a replacement for @c my_rename.
429 */
430 #ifdef HAVE_PSI_FILE_INTERFACE
431   #define mysql_file_rename(K, P1, P2, P3) \
432     inline_mysql_file_rename(K, __FILE__, __LINE__, P1, P2, P3)
433 #else
434   #define mysql_file_rename(K, P1, P2, P3) \
435     inline_mysql_file_rename(P1, P2, P3)
436 #endif
437 
438 /**
439   @def mysql_file_create_with_symlink(K, P1, P2, P3, P4, P5)
440   Instrumented create with symbolic link.
441   @c mysql_file_create_with_symlink is a replacement
442   for @c my_create_with_symlink.
443 */
444 #ifdef HAVE_PSI_FILE_INTERFACE
445   #define mysql_file_create_with_symlink(K, P1, P2, P3, P4, P5) \
446   inline_mysql_file_create_with_symlink(K, __FILE__, __LINE__, \
447                                         P1, P2, P3, P4, P5)
448 #else
449   #define mysql_file_create_with_symlink(K, P1, P2, P3, P4, P5) \
450   inline_mysql_file_create_with_symlink(P1, P2, P3, P4, P5)
451 #endif
452 
453 /**
454   @def mysql_file_delete_with_symlink(K, P1, P2, P3)
455   Instrumented delete with symbolic link.
456   @c mysql_file_delete_with_symlink is a replacement
457   for @c my_handler_delete_with_symlink.
458 */
459 #ifdef HAVE_PSI_FILE_INTERFACE
460   #define mysql_file_delete_with_symlink(K, P1, P2, P3) \
461   inline_mysql_file_delete_with_symlink(K, __FILE__, __LINE__, P1, P2, P3)
462 #else
463   #define mysql_file_delete_with_symlink(K, P1, P2, P3) \
464   inline_mysql_file_delete_with_symlink(P1, P2, P3)
465 #endif
466 
467 /**
468   @def mysql_file_rename_with_symlink(K, P1, P2, P3)
469   Instrumented rename with symbolic link.
470   @c mysql_file_rename_with_symlink is a replacement
471   for @c my_rename_with_symlink.
472 */
473 #ifdef HAVE_PSI_FILE_INTERFACE
474   #define mysql_file_rename_with_symlink(K, P1, P2, P3) \
475   inline_mysql_file_rename_with_symlink(K, __FILE__, __LINE__, P1, P2, P3)
476 #else
477   #define mysql_file_rename_with_symlink(K, P1, P2, P3) \
478   inline_mysql_file_rename_with_symlink(P1, P2, P3)
479 #endif
480 
481 /**
482   @def mysql_file_sync(P1, P2)
483   Instrumented file sync.
484   @c mysql_file_sync is a replacement for @c my_sync.
485 */
486 #ifdef HAVE_PSI_FILE_INTERFACE
487   #define mysql_file_sync(P1, P2) \
488     inline_mysql_file_sync(__FILE__, __LINE__, P1, P2)
489 #else
490   #define mysql_file_sync(P1, P2) \
491     inline_mysql_file_sync(P1, P2)
492 #endif
493 
494 /**
495   An instrumented FILE structure.
496   @sa MYSQL_FILE
497 */
498 struct st_mysql_file
499 {
500   /** The real file. */
501   FILE *m_file;
502   /**
503     The instrumentation hook.
504     Note that this hook is not conditionally defined,
505     for binary compatibility of the @c MYSQL_FILE interface.
506   */
507   struct PSI_file *m_psi;
508 };
509 
510 /**
511   Type of an instrumented file.
512   @c MYSQL_FILE is a drop-in replacement for @c FILE.
513   @sa mysql_file_open
514 */
515 typedef struct st_mysql_file MYSQL_FILE;
516 
inline_mysql_file_register(const char * category,PSI_file_info * info,int count)517 static inline void inline_mysql_file_register(
518 #ifdef HAVE_PSI_FILE_INTERFACE
519   const char *category,
520   PSI_file_info *info,
521   int count
522 #else
523   const char *category __attribute__ ((unused)),
524   void *info __attribute__ ((unused)),
525   int count __attribute__ ((unused))
526 #endif
527 )
528 {
529 #ifdef HAVE_PSI_FILE_INTERFACE
530   PSI_FILE_CALL(register_file)(category, info, count);
531 #endif
532 }
533 
534 static inline char *
inline_mysql_file_fgets(const char * src_file,uint src_line,char * str,int size,MYSQL_FILE * file)535 inline_mysql_file_fgets(
536 #ifdef HAVE_PSI_FILE_INTERFACE
537   const char *src_file, uint src_line,
538 #endif
539   char *str, int size, MYSQL_FILE *file)
540 {
541   char *result;
542 #ifdef HAVE_PSI_FILE_INTERFACE
543   if (psi_likely(file->m_psi))
544   {
545     struct PSI_file_locker *locker;
546     PSI_file_locker_state state;
547     locker= PSI_FILE_CALL(get_thread_file_stream_locker) (&state, file->m_psi, PSI_FILE_READ);
548     if (likely(locker != NULL))
549     {
550       PSI_FILE_CALL(start_file_wait)(locker, (size_t) size, src_file, src_line);
551       result= fgets(str, size, file->m_file);
552       PSI_FILE_CALL(end_file_wait)(locker, result ? strlen(result) : 0);
553       return result;
554     }
555   }
556 #endif
557 
558   result= fgets(str, size, file->m_file);
559   return result;
560 }
561 
562 static inline int
inline_mysql_file_fgetc(const char * src_file,uint src_line,MYSQL_FILE * file)563 inline_mysql_file_fgetc(
564 #ifdef HAVE_PSI_FILE_INTERFACE
565   const char *src_file, uint src_line,
566 #endif
567   MYSQL_FILE *file)
568 {
569   int result;
570 #ifdef HAVE_PSI_FILE_INTERFACE
571   if (psi_likely(file->m_psi))
572   {
573     struct PSI_file_locker *locker;
574     PSI_file_locker_state state;
575     locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi, PSI_FILE_READ);
576     if (likely(locker != NULL))
577     {
578       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 1, src_file, src_line);
579       result= fgetc(file->m_file);
580       PSI_FILE_CALL(end_file_wait)(locker, (size_t) 1);
581       return result;
582     }
583   }
584 #endif
585 
586   result= fgetc(file->m_file);
587   return result;
588 }
589 
590 static inline int
inline_mysql_file_fputs(const char * src_file,uint src_line,const char * str,MYSQL_FILE * file)591 inline_mysql_file_fputs(
592 #ifdef HAVE_PSI_FILE_INTERFACE
593   const char *src_file, uint src_line,
594 #endif
595   const char *str, MYSQL_FILE *file)
596 {
597   int result;
598 #ifdef HAVE_PSI_FILE_INTERFACE
599   if (psi_likely(file->m_psi))
600   {
601     struct PSI_file_locker *locker;
602     PSI_file_locker_state state;
603     size_t bytes;
604     locker= PSI_FILE_CALL(get_thread_file_stream_locker) (&state, file->m_psi, PSI_FILE_WRITE);
605     if (likely(locker != NULL))
606     {
607       bytes= str ? strlen(str) : 0;
608       PSI_FILE_CALL(start_file_wait)(locker, bytes, src_file, src_line);
609       result= fputs(str, file->m_file);
610       PSI_FILE_CALL(end_file_wait)(locker, bytes);
611       return result;
612     }
613   }
614 #endif
615 
616   result= fputs(str, file->m_file);
617   return result;
618 }
619 
620 static inline int
inline_mysql_file_fputc(const char * src_file,uint src_line,char c,MYSQL_FILE * file)621 inline_mysql_file_fputc(
622 #ifdef HAVE_PSI_FILE_INTERFACE
623   const char *src_file, uint src_line,
624 #endif
625   char c, MYSQL_FILE *file)
626 {
627   int result;
628 #ifdef HAVE_PSI_FILE_INTERFACE
629   if (psi_likely(file->m_psi))
630   {
631     struct PSI_file_locker *locker;
632     PSI_file_locker_state state;
633     locker= PSI_FILE_CALL(get_thread_file_stream_locker) (&state, file->m_psi, PSI_FILE_WRITE);
634     if (likely(locker != NULL))
635     {
636       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 1, src_file, src_line);
637       result= fputc(c, file->m_file);
638       PSI_FILE_CALL(end_file_wait)(locker, (size_t) 1);
639       return result;
640     }
641   }
642 #endif
643 
644   result= fputc(c, file->m_file);
645   return result;
646 }
647 
648 static inline int
inline_mysql_file_fprintf(MYSQL_FILE * file,const char * format,...)649 inline_mysql_file_fprintf(MYSQL_FILE *file, const char *format, ...)
650 {
651   /*
652     TODO: figure out how to pass src_file and src_line from the caller.
653   */
654   int result;
655   va_list args;
656 #ifdef HAVE_PSI_FILE_INTERFACE
657   if (psi_likely(file->m_psi))
658   {
659     struct PSI_file_locker *locker;
660     PSI_file_locker_state state;
661     locker= PSI_FILE_CALL(get_thread_file_stream_locker) (&state, file->m_psi, PSI_FILE_WRITE);
662     if (likely(locker != NULL))
663     {
664       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, __FILE__, __LINE__);
665       va_start(args, format);
666       result= vfprintf(file->m_file, format, args);
667       va_end(args);
668       PSI_FILE_CALL(end_file_wait)(locker, (size_t) result);
669       return result;
670     }
671   }
672 #endif
673 
674   va_start(args, format);
675   result= vfprintf(file->m_file, format, args);
676   va_end(args);
677   return result;
678 }
679 
680 static inline int
inline_mysql_file_vfprintf(const char * src_file,uint src_line,MYSQL_FILE * file,const char * format,va_list args)681 inline_mysql_file_vfprintf(
682 #ifdef HAVE_PSI_FILE_INTERFACE
683   const char *src_file, uint src_line,
684 #endif
685   MYSQL_FILE *file, const char *format, va_list args)
686 {
687   int result;
688 #ifdef HAVE_PSI_FILE_INTERFACE
689   if (psi_likely(file->m_psi))
690   {
691     struct PSI_file_locker *locker;
692     PSI_file_locker_state state;
693     locker= PSI_FILE_CALL(get_thread_file_stream_locker) (&state, file->m_psi, PSI_FILE_WRITE);
694     if (likely(locker != NULL))
695     {
696       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
697       result= vfprintf(file->m_file, format, args);
698       PSI_FILE_CALL(end_file_wait)(locker, (size_t) result);
699       return result;
700     }
701   }
702 #endif
703 
704   result= vfprintf(file->m_file, format, args);
705   return result;
706 }
707 
708 static inline int
inline_mysql_file_fflush(const char * src_file,uint src_line,MYSQL_FILE * file)709 inline_mysql_file_fflush(
710 #ifdef HAVE_PSI_FILE_INTERFACE
711   const char *src_file, uint src_line,
712 #endif
713   MYSQL_FILE *file)
714 {
715   int result;
716 #ifdef HAVE_PSI_FILE_INTERFACE
717   if (psi_likely(file->m_psi))
718   {
719     struct PSI_file_locker *locker;
720     PSI_file_locker_state state;
721     locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi, PSI_FILE_FLUSH);
722     if (likely(locker != NULL))
723     {
724       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
725       result= fflush(file->m_file);
726       PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
727       return result;
728     }
729   }
730 #endif
731 
732   result= fflush(file->m_file);
733   return result;
734 }
735 
inline_mysql_file_feof(MYSQL_FILE * file)736 static inline int inline_mysql_file_feof(MYSQL_FILE *file)
737 {
738   /* Not instrumented, there is no wait involved */
739   return feof(file->m_file);
740 }
741 
742 static inline int
inline_mysql_file_fstat(const char * src_file,uint src_line,int filenr,MY_STAT * stat_area,myf flags)743 inline_mysql_file_fstat(
744 #ifdef HAVE_PSI_FILE_INTERFACE
745   const char *src_file, uint src_line,
746 #endif
747   int filenr, MY_STAT *stat_area, myf flags)
748 {
749   int result;
750 #ifdef HAVE_PSI_FILE_INTERFACE
751   struct PSI_file_locker *locker;
752   PSI_file_locker_state state;
753   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, filenr, PSI_FILE_FSTAT);
754   if (psi_likely(locker != NULL))
755   {
756     PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
757     result= my_fstat(filenr, stat_area, flags);
758     PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
759     return result;
760   }
761 #endif
762 
763   result= my_fstat(filenr, stat_area, flags);
764   return result;
765 }
766 
767 static inline MY_STAT *
inline_mysql_file_stat(PSI_file_key key,const char * src_file,uint src_line,const char * path,MY_STAT * stat_area,myf flags)768 inline_mysql_file_stat(
769 #ifdef HAVE_PSI_FILE_INTERFACE
770   PSI_file_key key, const char *src_file, uint src_line,
771 #endif
772   const char *path, MY_STAT *stat_area, myf flags)
773 {
774   MY_STAT *result;
775 #ifdef HAVE_PSI_FILE_INTERFACE
776   struct PSI_file_locker *locker;
777   PSI_file_locker_state state;
778   locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_STAT, path, &locker);
779   if (psi_likely(locker != NULL))
780   {
781     PSI_FILE_CALL(start_file_open_wait)(locker, src_file, src_line);
782     result= my_stat(path, stat_area, flags);
783     PSI_FILE_CALL(end_file_open_wait)(locker, result);
784     return result;
785   }
786 #endif
787 
788   result= my_stat(path, stat_area, flags);
789   return result;
790 }
791 
792 static inline int
inline_mysql_file_chsize(const char * src_file,uint src_line,File file,my_off_t newlength,int filler,myf flags)793 inline_mysql_file_chsize(
794 #ifdef HAVE_PSI_FILE_INTERFACE
795   const char *src_file, uint src_line,
796 #endif
797   File file, my_off_t newlength, int filler, myf flags)
798 {
799   int result;
800 #ifdef HAVE_PSI_FILE_INTERFACE
801   struct PSI_file_locker *locker;
802   PSI_file_locker_state state;
803   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_CHSIZE);
804   if (psi_likely(locker != NULL))
805   {
806     PSI_FILE_CALL(start_file_wait)(locker, (size_t) newlength, src_file,
807                                    src_line);
808     result= my_chsize(file, newlength, filler, flags);
809     PSI_FILE_CALL(end_file_wait)(locker, (size_t) newlength);
810     return result;
811   }
812 #endif
813 
814   result= my_chsize(file, newlength, filler, flags);
815   return result;
816 }
817 
818 static inline MYSQL_FILE*
inline_mysql_file_fopen(PSI_file_key key,const char * src_file,uint src_line,const char * filename,int flags,myf myFlags)819 inline_mysql_file_fopen(
820 #ifdef HAVE_PSI_FILE_INTERFACE
821   PSI_file_key key, const char *src_file, uint src_line,
822 #endif
823   const char *filename, int flags, myf myFlags)
824 {
825   MYSQL_FILE *that;
826   that= (MYSQL_FILE*) my_malloc(PSI_NOT_INSTRUMENTED,
827                                 sizeof(MYSQL_FILE), MYF(MY_WME));
828   if (likely(that != NULL))
829   {
830 #ifdef HAVE_PSI_FILE_INTERFACE
831     struct PSI_file_locker *locker;
832     PSI_file_locker_state state;
833     locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_STREAM_OPEN,
834                                                        filename, that);
835     if (psi_likely(locker != NULL))
836     {
837       PSI_FILE_CALL(start_file_open_wait)(locker, src_file, src_line);
838       that->m_file= my_fopen(filename, flags, myFlags);
839       that->m_psi= PSI_FILE_CALL(end_file_open_wait)(locker, that->m_file);
840       if (unlikely(that->m_file == NULL))
841       {
842         my_free(that);
843         return NULL;
844       }
845       return that;
846     }
847 #endif
848 
849     that->m_psi= NULL;
850     that->m_file= my_fopen(filename, flags, myFlags);
851     if (unlikely(that->m_file == NULL))
852     {
853       my_free(that);
854       return NULL;
855     }
856   }
857   return that;
858 }
859 
860 static inline int
inline_mysql_file_fclose(const char * src_file,uint src_line,MYSQL_FILE * file,myf flags)861 inline_mysql_file_fclose(
862 #ifdef HAVE_PSI_FILE_INTERFACE
863   const char *src_file, uint src_line,
864 #endif
865   MYSQL_FILE *file, myf flags)
866 {
867   int result= 0;
868   if (likely(file != NULL))
869   {
870 #ifdef HAVE_PSI_FILE_INTERFACE
871     if (psi_likely(file->m_psi))
872     {
873       struct PSI_file_locker *locker;
874       PSI_file_locker_state state;
875       locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi,
876                                                            PSI_FILE_STREAM_CLOSE);
877       if (likely(locker != NULL))
878       {
879         PSI_FILE_CALL(start_file_close_wait)(locker, src_file, src_line);
880         result= my_fclose(file->m_file, flags);
881         PSI_FILE_CALL(end_file_close_wait)(locker, result);
882         my_free(file);
883         return result;
884       }
885     }
886 #endif
887 
888     result= my_fclose(file->m_file, flags);
889     my_free(file);
890   }
891   return result;
892 }
893 
894 static inline size_t
inline_mysql_file_fread(const char * src_file,uint src_line,MYSQL_FILE * file,uchar * buffer,size_t count,myf flags)895 inline_mysql_file_fread(
896 #ifdef HAVE_PSI_FILE_INTERFACE
897   const char *src_file, uint src_line,
898 #endif
899   MYSQL_FILE *file, uchar *buffer, size_t count, myf flags)
900 {
901   size_t result;
902 #ifdef HAVE_PSI_FILE_INTERFACE
903   if (psi_likely(file->m_psi))
904   {
905     struct PSI_file_locker *locker;
906     PSI_file_locker_state state;
907     size_t bytes_read;
908     locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi, PSI_FILE_READ);
909     if (likely(locker != NULL))
910     {
911       PSI_FILE_CALL(start_file_wait)(locker, count, src_file, src_line);
912       result= my_fread(file->m_file, buffer, count, flags);
913       if (flags & (MY_NABP | MY_FNABP))
914         bytes_read= (result == 0) ? count : 0;
915       else
916         bytes_read= (result != MY_FILE_ERROR) ? result : 0;
917       PSI_FILE_CALL(end_file_wait)(locker, bytes_read);
918       return result;
919     }
920   }
921 #endif
922 
923   result= my_fread(file->m_file, buffer, count, flags);
924   return result;
925 }
926 
927 static inline size_t
inline_mysql_file_fwrite(const char * src_file,uint src_line,MYSQL_FILE * file,const uchar * buffer,size_t count,myf flags)928 inline_mysql_file_fwrite(
929 #ifdef HAVE_PSI_FILE_INTERFACE
930   const char *src_file, uint src_line,
931 #endif
932   MYSQL_FILE *file, const uchar *buffer, size_t count, myf flags)
933 {
934   size_t result;
935 #ifdef HAVE_PSI_FILE_INTERFACE
936   if (psi_likely(file->m_psi))
937   {
938     struct PSI_file_locker *locker;
939     PSI_file_locker_state state;
940     size_t bytes_written;
941     locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi, PSI_FILE_WRITE);
942     if (likely(locker != NULL))
943     {
944       PSI_FILE_CALL(start_file_wait)(locker, count, src_file, src_line);
945       result= my_fwrite(file->m_file, buffer, count, flags);
946       if (flags & (MY_NABP | MY_FNABP))
947         bytes_written= (result == 0) ? count : 0;
948       else
949         bytes_written= (result != MY_FILE_ERROR) ? result : 0;
950       PSI_FILE_CALL(end_file_wait)(locker, bytes_written);
951       return result;
952     }
953   }
954 #endif
955 
956   result= my_fwrite(file->m_file, buffer, count, flags);
957   return result;
958 }
959 
960 static inline my_off_t
inline_mysql_file_fseek(const char * src_file,uint src_line,MYSQL_FILE * file,my_off_t pos,int whence,myf flags)961 inline_mysql_file_fseek(
962 #ifdef HAVE_PSI_FILE_INTERFACE
963   const char *src_file, uint src_line,
964 #endif
965   MYSQL_FILE *file, my_off_t pos, int whence, myf flags)
966 {
967   my_off_t result;
968 #ifdef HAVE_PSI_FILE_INTERFACE
969   if (psi_likely(file->m_psi))
970   {
971     struct PSI_file_locker *locker;
972     PSI_file_locker_state state;
973     locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi, PSI_FILE_SEEK);
974     if (likely(locker != NULL))
975     {
976       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
977       result= my_fseek(file->m_file, pos, whence, flags);
978       PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
979       return result;
980     }
981   }
982 #endif
983 
984   result= my_fseek(file->m_file, pos, whence, flags);
985   return result;
986 }
987 
988 static inline my_off_t
inline_mysql_file_ftell(const char * src_file,uint src_line,MYSQL_FILE * file,myf flags)989 inline_mysql_file_ftell(
990 #ifdef HAVE_PSI_FILE_INTERFACE
991   const char *src_file, uint src_line,
992 #endif
993   MYSQL_FILE *file, myf flags)
994 {
995   my_off_t result;
996 #ifdef HAVE_PSI_FILE_INTERFACE
997   if (psi_likely(file->m_psi))
998   {
999     struct PSI_file_locker *locker;
1000     PSI_file_locker_state state;
1001     locker= PSI_FILE_CALL(get_thread_file_stream_locker)(&state, file->m_psi, PSI_FILE_TELL);
1002     if (likely(locker != NULL))
1003     {
1004       PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
1005       result= my_ftell(file->m_file, flags);
1006       PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
1007       return result;
1008     }
1009   }
1010 #endif
1011 
1012   result= my_ftell(file->m_file, flags);
1013   return result;
1014 }
1015 
1016 static inline File
inline_mysql_file_create(PSI_file_key key,const char * src_file,uint src_line,const char * filename,int create_flags,int access_flags,myf myFlags)1017 inline_mysql_file_create(
1018 #ifdef HAVE_PSI_FILE_INTERFACE
1019   PSI_file_key key, const char *src_file, uint src_line,
1020 #endif
1021   const char *filename, int create_flags, int access_flags, myf myFlags)
1022 {
1023   File file;
1024 #ifdef HAVE_PSI_FILE_INTERFACE
1025   struct PSI_file_locker *locker;
1026   PSI_file_locker_state state;
1027   locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_CREATE, filename,
1028                                                      &locker);
1029   if (psi_likely(locker != NULL))
1030   {
1031     PSI_FILE_CALL(start_file_open_wait)(locker, src_file, src_line);
1032     file= my_create(filename, create_flags, access_flags, myFlags);
1033     PSI_FILE_CALL(end_file_open_wait_and_bind_to_descriptor)(locker, file);
1034     return file;
1035   }
1036 #endif
1037 
1038   file= my_create(filename, create_flags, access_flags, myFlags);
1039   return file;
1040 }
1041 
1042 static inline File
inline_mysql_file_create_temp(PSI_file_key key,const char * src_file,uint src_line,char * to,const char * dir,const char * pfx,int mode,myf myFlags)1043 inline_mysql_file_create_temp(
1044 #ifdef HAVE_PSI_FILE_INTERFACE
1045   PSI_file_key key, const char *src_file, uint src_line,
1046 #endif
1047   char *to, const char *dir, const char *pfx, int mode, myf myFlags)
1048 {
1049   File file;
1050 #ifdef HAVE_PSI_FILE_INTERFACE
1051   struct PSI_file_locker *locker;
1052   PSI_file_locker_state state;
1053   locker= PSI_FILE_CALL(get_thread_file_name_locker)
1054     (&state, key, PSI_FILE_CREATE, NULL, &locker);
1055   if (psi_likely(locker != NULL))
1056   {
1057     PSI_FILE_CALL(start_file_open_wait)(locker, src_file, src_line);
1058     /* The file name is generated by create_temp_file(). */
1059     file= create_temp_file(to, dir, pfx, mode, myFlags);
1060     PSI_FILE_CALL(end_temp_file_open_wait_and_bind_to_descriptor)(locker, file, (const char*)to);
1061     return file;
1062   }
1063 #endif
1064 
1065   file= create_temp_file(to, dir, pfx, mode, myFlags);
1066   return file;
1067 }
1068 
1069 static inline File
inline_mysql_file_open(PSI_file_key key,const char * src_file,uint src_line,const char * filename,int flags,myf myFlags)1070 inline_mysql_file_open(
1071 #ifdef HAVE_PSI_FILE_INTERFACE
1072   PSI_file_key key, const char *src_file, uint src_line,
1073 #endif
1074   const char *filename, int flags, myf myFlags)
1075 {
1076   File file;
1077 #ifdef HAVE_PSI_FILE_INTERFACE
1078   struct PSI_file_locker *locker;
1079   PSI_file_locker_state state;
1080   locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_OPEN, filename,
1081                                                      &locker);
1082   if (psi_likely(locker != NULL))
1083   {
1084     PSI_FILE_CALL(start_file_open_wait)(locker, src_file, src_line);
1085     file= my_open(filename, flags, myFlags);
1086     PSI_FILE_CALL(end_file_open_wait_and_bind_to_descriptor)(locker, file);
1087     return file;
1088   }
1089 #endif
1090 
1091   file= my_open(filename, flags, myFlags);
1092   return file;
1093 }
1094 
1095 static inline int
inline_mysql_file_close(const char * src_file,uint src_line,File file,myf flags)1096 inline_mysql_file_close(
1097 #ifdef HAVE_PSI_FILE_INTERFACE
1098   const char *src_file, uint src_line,
1099 #endif
1100   File file, myf flags)
1101 {
1102   int result;
1103 #ifdef HAVE_PSI_FILE_INTERFACE
1104   struct PSI_file_locker *locker;
1105   PSI_file_locker_state state;
1106   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_CLOSE);
1107   if (psi_likely(locker != NULL))
1108   {
1109     PSI_FILE_CALL(start_file_close_wait)(locker, src_file, src_line);
1110     result= my_close(file, flags);
1111     PSI_FILE_CALL(end_file_close_wait)(locker, result);
1112     return result;
1113   }
1114 #endif
1115 
1116   result= my_close(file, flags);
1117   return result;
1118 }
1119 
1120 static inline size_t
inline_mysql_file_read(const char * src_file,uint src_line,File file,uchar * buffer,size_t count,myf flags)1121 inline_mysql_file_read(
1122 #ifdef HAVE_PSI_FILE_INTERFACE
1123   const char *src_file, uint src_line,
1124 #endif
1125   File file, uchar *buffer, size_t count, myf flags)
1126 {
1127   size_t result;
1128 #ifdef HAVE_PSI_FILE_INTERFACE
1129   struct PSI_file_locker *locker;
1130   PSI_file_locker_state state;
1131   size_t bytes_read;
1132   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_READ);
1133   if (psi_likely(locker != NULL))
1134   {
1135     PSI_FILE_CALL(start_file_wait)(locker, count, src_file, src_line);
1136     result= my_read(file, buffer, count, flags);
1137     if (flags & (MY_NABP | MY_FNABP))
1138       bytes_read= (result == 0) ? count : 0;
1139     else
1140       bytes_read= (result != MY_FILE_ERROR) ? result : 0;
1141     PSI_FILE_CALL(end_file_wait)(locker, bytes_read);
1142     return result;
1143   }
1144 #endif
1145 
1146   result= my_read(file, buffer, count, flags);
1147   return result;
1148 }
1149 
1150 static inline size_t
inline_mysql_file_write(const char * src_file,uint src_line,File file,const uchar * buffer,size_t count,myf flags)1151 inline_mysql_file_write(
1152 #ifdef HAVE_PSI_FILE_INTERFACE
1153   const char *src_file, uint src_line,
1154 #endif
1155   File file, const uchar *buffer, size_t count, myf flags)
1156 {
1157   size_t result;
1158 #ifdef HAVE_PSI_FILE_INTERFACE
1159   struct PSI_file_locker *locker;
1160   PSI_file_locker_state state;
1161   size_t bytes_written;
1162   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_WRITE);
1163   if (psi_likely(locker != NULL))
1164   {
1165     PSI_FILE_CALL(start_file_wait)(locker, count, src_file, src_line);
1166     result= my_write(file, buffer, count, flags);
1167     if (flags & (MY_NABP | MY_FNABP))
1168       bytes_written= (result == 0) ? count : 0;
1169     else
1170       bytes_written= (result != MY_FILE_ERROR) ? result : 0;
1171     PSI_FILE_CALL(end_file_wait)(locker, bytes_written);
1172     return result;
1173   }
1174 #endif
1175 
1176   result= my_write(file, buffer, count, flags);
1177   return result;
1178 }
1179 
1180 static inline size_t
inline_mysql_file_pread(const char * src_file,uint src_line,File file,uchar * buffer,size_t count,my_off_t offset,myf flags)1181 inline_mysql_file_pread(
1182 #ifdef HAVE_PSI_FILE_INTERFACE
1183   const char *src_file, uint src_line,
1184 #endif
1185   File file, uchar *buffer, size_t count, my_off_t offset, myf flags)
1186 {
1187   size_t result;
1188 #ifdef HAVE_PSI_FILE_INTERFACE
1189   struct PSI_file_locker *locker;
1190   PSI_file_locker_state state;
1191   size_t bytes_read;
1192   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_READ);
1193   if (psi_likely(locker != NULL))
1194   {
1195     PSI_FILE_CALL(start_file_wait)(locker, count, src_file, src_line);
1196     result= my_pread(file, buffer, count, offset, flags);
1197     if (flags & (MY_NABP | MY_FNABP))
1198       bytes_read= (result == 0) ? count : 0;
1199     else
1200       bytes_read= (result != MY_FILE_ERROR) ? result : 0;
1201     PSI_FILE_CALL(end_file_wait)(locker, bytes_read);
1202     return result;
1203   }
1204 #endif
1205 
1206   result= my_pread(file, buffer, count, offset, flags);
1207   return result;
1208 }
1209 
1210 static inline size_t
inline_mysql_file_pwrite(const char * src_file,uint src_line,File file,const uchar * buffer,size_t count,my_off_t offset,myf flags)1211 inline_mysql_file_pwrite(
1212 #ifdef HAVE_PSI_FILE_INTERFACE
1213   const char *src_file, uint src_line,
1214 #endif
1215   File file, const uchar *buffer, size_t count, my_off_t offset, myf flags)
1216 {
1217   size_t result;
1218 #ifdef HAVE_PSI_FILE_INTERFACE
1219   struct PSI_file_locker *locker;
1220   PSI_file_locker_state state;
1221   size_t bytes_written;
1222   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_WRITE);
1223   if (psi_likely(locker != NULL))
1224   {
1225     PSI_FILE_CALL(start_file_wait)(locker, count, src_file, src_line);
1226     result= my_pwrite(file, buffer, count, offset, flags);
1227     if (flags & (MY_NABP | MY_FNABP))
1228       bytes_written= (result == 0) ? count : 0;
1229     else
1230       bytes_written= (result != MY_FILE_ERROR) ? result : 0;
1231     PSI_FILE_CALL(end_file_wait)(locker, bytes_written);
1232     return result;
1233   }
1234 #endif
1235 
1236   result= my_pwrite(file, buffer, count, offset, flags);
1237   return result;
1238 }
1239 
1240 static inline my_off_t
inline_mysql_file_seek(const char * src_file,uint src_line,File file,my_off_t pos,int whence,myf flags)1241 inline_mysql_file_seek(
1242 #ifdef HAVE_PSI_FILE_INTERFACE
1243   const char *src_file, uint src_line,
1244 #endif
1245   File file, my_off_t pos, int whence, myf flags)
1246 {
1247   my_off_t result;
1248 #ifdef HAVE_PSI_FILE_INTERFACE
1249   struct PSI_file_locker *locker;
1250   PSI_file_locker_state state;
1251   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_SEEK);
1252   if (psi_likely(locker != NULL))
1253   {
1254     PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
1255     result= my_seek(file, pos, whence, flags);
1256     PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
1257     return result;
1258   }
1259 #endif
1260 
1261   result= my_seek(file, pos, whence, flags);
1262   return result;
1263 }
1264 
1265 static inline my_off_t
inline_mysql_file_tell(const char * src_file,uint src_line,File file,myf flags)1266 inline_mysql_file_tell(
1267 #ifdef HAVE_PSI_FILE_INTERFACE
1268   const char *src_file, uint src_line,
1269 #endif
1270   File file, myf flags)
1271 {
1272   my_off_t result;
1273 #ifdef HAVE_PSI_FILE_INTERFACE
1274   struct PSI_file_locker *locker;
1275   PSI_file_locker_state state;
1276   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, file, PSI_FILE_TELL);
1277   if (psi_likely(locker != NULL))
1278   {
1279     PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
1280     result= my_tell(file, flags);
1281     PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
1282     return result;
1283   }
1284 #endif
1285 
1286   result= my_tell(file, flags);
1287   return result;
1288 }
1289 
1290 static inline int
inline_mysql_file_delete(PSI_file_key key,const char * src_file,uint src_line,const char * name,myf flags)1291 inline_mysql_file_delete(
1292 #ifdef HAVE_PSI_FILE_INTERFACE
1293   PSI_file_key key, const char *src_file, uint src_line,
1294 #endif
1295   const char *name, myf flags)
1296 {
1297   int result;
1298 #ifdef HAVE_PSI_FILE_INTERFACE
1299   struct PSI_file_locker *locker;
1300   PSI_file_locker_state state;
1301   locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_DELETE, name, &locker);
1302   if (psi_likely(locker != NULL))
1303   {
1304     PSI_FILE_CALL(start_file_close_wait)(locker, src_file, src_line);
1305     result= my_delete(name, flags);
1306     PSI_FILE_CALL(end_file_close_wait)(locker, result);
1307     return result;
1308   }
1309 #endif
1310 
1311   result= my_delete(name, flags);
1312   return result;
1313 }
1314 
1315 static inline int
inline_mysql_file_rename(PSI_file_key key,const char * src_file,uint src_line,const char * from,const char * to,myf flags)1316 inline_mysql_file_rename(
1317 #ifdef HAVE_PSI_FILE_INTERFACE
1318   PSI_file_key key, const char *src_file, uint src_line,
1319 #endif
1320   const char *from, const char *to, myf flags)
1321 {
1322   int result;
1323 #ifdef HAVE_PSI_FILE_INTERFACE
1324   struct PSI_file_locker *locker;
1325   PSI_file_locker_state state;
1326   locker= PSI_FILE_CALL(get_thread_file_name_locker)
1327     (&state, key, PSI_FILE_RENAME, from, &locker);
1328   if (psi_likely(locker != NULL))
1329   {
1330     PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
1331     result= my_rename(from, to, flags);
1332     PSI_FILE_CALL(end_file_rename_wait)(locker, from, to, result);
1333     return result;
1334   }
1335 #endif
1336 
1337   result= my_rename(from, to, flags);
1338   return result;
1339 }
1340 
1341 
1342 static inline File
inline_mysql_file_create_with_symlink(PSI_file_key key,const char * src_file,uint src_line,const char * linkname,const char * filename,int create_flags,int access_flags,myf flags)1343 inline_mysql_file_create_with_symlink(
1344 #ifdef HAVE_PSI_FILE_INTERFACE
1345   PSI_file_key key, const char *src_file, uint src_line,
1346 #endif
1347   const char *linkname, const char *filename, int create_flags,
1348   int access_flags, myf flags)
1349 {
1350   File file;
1351 #ifdef HAVE_PSI_FILE_INTERFACE
1352   struct PSI_file_locker *locker;
1353   PSI_file_locker_state state;
1354   locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_CREATE, filename,
1355                                                      &locker);
1356   if (psi_likely(locker != NULL))
1357   {
1358     PSI_FILE_CALL(start_file_open_wait)(locker, src_file, src_line);
1359     file= my_create_with_symlink(linkname, filename, create_flags, access_flags,
1360                                  flags);
1361     PSI_FILE_CALL(end_file_open_wait_and_bind_to_descriptor)(locker, file);
1362     return file;
1363   }
1364 #endif
1365 
1366   file= my_create_with_symlink(linkname, filename, create_flags, access_flags,
1367                                flags);
1368   return file;
1369 }
1370 
1371 
1372 static inline int
inline_mysql_file_delete_with_symlink(PSI_file_key key,const char * src_file,uint src_line,const char * name,const char * ext,myf flags)1373 inline_mysql_file_delete_with_symlink(
1374 #ifdef HAVE_PSI_FILE_INTERFACE
1375   PSI_file_key key, const char *src_file, uint src_line,
1376 #endif
1377   const char *name, const char *ext, myf flags)
1378 {
1379   int result;
1380   char buf[FN_REFLEN];
1381   char *fullname= fn_format(buf, name, "", ext, MY_UNPACK_FILENAME | MY_APPEND_EXT);
1382 #ifdef HAVE_PSI_FILE_INTERFACE
1383   struct PSI_file_locker *locker;
1384   PSI_file_locker_state state;
1385   locker= PSI_FILE_CALL(get_thread_file_name_locker)(&state, key, PSI_FILE_DELETE, fullname,
1386                                                      &locker);
1387   if (psi_likely(locker != NULL))
1388   {
1389     PSI_FILE_CALL(start_file_close_wait)(locker, src_file, src_line);
1390     result= my_handler_delete_with_symlink(fullname, flags);
1391     PSI_FILE_CALL(end_file_close_wait)(locker, result);
1392     return result;
1393   }
1394 #endif
1395 
1396   result= my_handler_delete_with_symlink(fullname, flags);
1397   return result;
1398 }
1399 
1400 
1401 static inline int
inline_mysql_file_rename_with_symlink(PSI_file_key key,const char * src_file,uint src_line,const char * from,const char * to,myf flags)1402 inline_mysql_file_rename_with_symlink(
1403 #ifdef HAVE_PSI_FILE_INTERFACE
1404   PSI_file_key key, const char *src_file, uint src_line,
1405 #endif
1406   const char *from, const char *to, myf flags)
1407 {
1408   int result;
1409 #ifdef HAVE_PSI_FILE_INTERFACE
1410   struct PSI_file_locker *locker;
1411   PSI_file_locker_state state;
1412   locker= PSI_FILE_CALL(get_thread_file_name_locker)
1413     (&state, key, PSI_FILE_RENAME, from, &locker);
1414   if (psi_likely(locker != NULL))
1415   {
1416     PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
1417     result= my_rename_with_symlink(from, to, flags);
1418     PSI_FILE_CALL(end_file_rename_wait)(locker, from, to, result);
1419     return result;
1420   }
1421 #endif
1422 
1423   result= my_rename_with_symlink(from, to, flags);
1424   return result;
1425 }
1426 
1427 static inline int
inline_mysql_file_sync(const char * src_file,uint src_line,File fd,myf flags)1428 inline_mysql_file_sync(
1429 #ifdef HAVE_PSI_FILE_INTERFACE
1430   const char *src_file, uint src_line,
1431 #endif
1432   File fd, myf flags)
1433 {
1434   int result= 0;
1435 #ifdef HAVE_PSI_FILE_INTERFACE
1436   struct PSI_file_locker *locker;
1437   PSI_file_locker_state state;
1438   locker= PSI_FILE_CALL(get_thread_file_descriptor_locker)(&state, fd, PSI_FILE_SYNC);
1439   if (psi_likely(locker != NULL))
1440   {
1441     PSI_FILE_CALL(start_file_wait)(locker, (size_t) 0, src_file, src_line);
1442     result= my_sync(fd, flags);
1443     PSI_FILE_CALL(end_file_wait)(locker, (size_t) 0);
1444     return result;
1445   }
1446 #endif
1447 
1448   result= my_sync(fd, flags);
1449   return result;
1450 }
1451 
1452 /** @} (end of group File_instrumentation) */
1453 
1454 #endif
1455