Skip to content

Commit

Permalink
Add ATTRIBUTE_NORETURN and ATTRIBUTE_COLD
Browse files Browse the repository at this point in the history
ATTRIBUTE_NORETURN is supported on all platforms (MSVS and GCC-like).
It declares that a function will not return; instead, the thread or
the whole process will terminate.

ATTRIBUTE_COLD is supported starting with GCC 4.3. It declares that
a function is supposed to be executed rarely. Rarely used error-handling
functions and functions that emit messages to the error log should be
tagged such.
  • Loading branch information
dr-m committed Aug 31, 2017
1 parent 03a8eaa commit 4386ee8
Show file tree
Hide file tree
Showing 21 changed files with 70 additions and 50 deletions.
14 changes: 8 additions & 6 deletions client/mysqltest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -574,15 +574,17 @@ struct st_replace *glob_replace= 0;
void replace_strings_append(struct st_replace *rep, DYNAMIC_STRING* ds,
const char *from, int len);

static void cleanup_and_exit(int exit_code) __attribute__((noreturn));
ATTRIBUTE_NORETURN
static void cleanup_and_exit(int exit_code);

void really_die(const char *msg) __attribute__((noreturn));
ATTRIBUTE_NORETURN
void really_die(const char *msg);
void report_or_die(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
void die(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2)
__attribute__((noreturn));
ATTRIBUTE_NORETURN ATTRIBUTE_FORMAT(printf, 1, 2)
void die(const char *fmt, ...);
static void make_error_message(char *buf, size_t len, const char *fmt, va_list args);
void abort_not_supported_test(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2)
__attribute__((noreturn));
ATTRIBUTE_NORETURN ATTRIBUTE_FORMAT(printf, 1, 2)
void abort_not_supported_test(const char *fmt, ...);
void verbose_msg(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);
void log_msg(const char *fmt, ...) ATTRIBUTE_FORMAT(printf, 1, 2);

Expand Down
23 changes: 23 additions & 0 deletions include/my_compiler.h
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,29 @@ struct my_aligned_storage
#define MY_ALIGNED(size)
#endif

#ifdef __GNUC__
# define ATTRIBUTE_NORETURN __attribute__((noreturn))
# if MY_GNUC_PREREQ(4,3)
/** Starting with GCC 4.3, the "cold" attribute is used to inform the
compiler that a function is unlikely executed. The function is
optimized for size rather than speed and on many targets it is placed
into special subsection of the text section so all cold functions
appears close together improving code locality of non-cold parts of
program. The paths leading to call of cold functions within code are
marked as unlikely by the branch prediction mechanism. optimize a
rarely invoked function for size instead for speed. */
# define ATTRIBUTE_COLD __attribute__((cold))
# endif
#elif defined _WIN32
# define ATTRIBUTE_NORETURN __declspec(noreturn)
#else
# define ATTRIBUTE_NORETURN /* empty */
#endif

#ifndef ATTRIBUTE_COLD
# define ATTRIBUTE_COLD /* empty */
#endif

#include <my_attribute.h>

#endif /* MY_COMPILER_INCLUDED */
2 changes: 1 addition & 1 deletion sql/init.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,6 @@
#include "my_global.h" /* ulong */

void unireg_init(ulong options);
void unireg_end(void) __attribute__((noreturn));
ATTRIBUTE_NORETURN void unireg_end(void);

#endif /* INIT_INCLUDED */
2 changes: 1 addition & 1 deletion sql/mysqld.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1570,7 +1570,7 @@ static void close_server_sock();
static void clean_up_mutexes(void);
static void wait_for_signal_thread_to_end(void);
static void create_pid_file();
static void mysqld_exit(int exit_code) __attribute__((noreturn));
ATTRIBUTE_NORETURN static void mysqld_exit(int exit_code);
#endif
static void delete_pid_file(myf flags);
static void end_ssl();
Expand Down
2 changes: 1 addition & 1 deletion sql/mysqld.h
Original file line number Diff line number Diff line change
Expand Up @@ -708,7 +708,7 @@ enum enum_query_type
/* query_id */
extern query_id_t global_query_id;

void unireg_end(void) __attribute__((noreturn));
ATTRIBUTE_NORETURN void unireg_end(void);

/* increment query_id and return it. */
inline __attribute__((warn_unused_result)) query_id_t next_query_id()
Expand Down
2 changes: 1 addition & 1 deletion storage/innobase/fil/fil0fil.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1005,7 +1005,7 @@ fil_flush_low(fil_space_t* space)
@param[in] size desired size in number of pages
@param[out] success whether the operation succeeded
@return whether the operation should be retried */
static UNIV_COLD __attribute__((warn_unused_result, nonnull))
static ATTRIBUTE_COLD __attribute__((warn_unused_result, nonnull))
bool
fil_space_extend_must_retry(
fil_space_t* space,
Expand Down
6 changes: 3 additions & 3 deletions storage/innobase/fsp/fsp0fsp.cc
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ then we will not allocate more extents
@param[in,out] space tablespace
@param[in,out] header tablespace header
@param[in,out] mtr mini-transaction */
static UNIV_COLD
static ATTRIBUTE_COLD
void
fsp_fill_free_list(
bool init_space,
Expand Down Expand Up @@ -899,7 +899,7 @@ data file.
@param[in,out] header tablespace header
@param[in,out] mtr mini-transaction
@return true if success */
static UNIV_COLD MY_ATTRIBUTE((warn_unused_result))
static ATTRIBUTE_COLD __attribute__((warn_unused_result))
bool
fsp_try_extend_data_file_with_pages(
fil_space_t* space,
Expand Down Expand Up @@ -932,7 +932,7 @@ fsp_try_extend_data_file_with_pages(
@param[in,out] mtr mini-transaction
@return number of pages added
@retval 0 if the tablespace was not extended */
UNIV_COLD MY_ATTRIBUTE((nonnull))
ATTRIBUTE_COLD __attribute__((nonnull))
static
ulint
fsp_try_extend_data_file(fil_space_t* space, fsp_header_t* header, mtr_t* mtr)
Expand Down
2 changes: 1 addition & 1 deletion storage/innobase/handler/handler0alter.cc
Original file line number Diff line number Diff line change
Expand Up @@ -271,7 +271,7 @@ innobase_get_int_col_max_value(
const Field* field); /*!< in: MySQL field */

/* Report an InnoDB error to the client by invoking my_error(). */
static UNIV_COLD MY_ATTRIBUTE((nonnull))
static ATTRIBUTE_COLD __attribute__((nonnull))
void
my_error_innodb(
/*============*/
Expand Down
2 changes: 1 addition & 1 deletion storage/innobase/include/btr0btr.h
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ btr_corruption_report(
/*==================*/
const buf_block_t* block, /*!< in: corrupted block */
const dict_index_t* index) /*!< in: index tree */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));

/** Assert that a B-tree page is not corrupted.
@param block buffer block containing a B-tree page
Expand Down
2 changes: 1 addition & 1 deletion storage/innobase/include/dict0dict.h
Original file line number Diff line number Diff line change
Expand Up @@ -1867,7 +1867,7 @@ dict_set_corrupted(
dict_index_t* index, /*!< in/out: index */
trx_t* trx, /*!< in/out: transaction */
const char* ctx) /*!< in: context */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));

/** Flags an index corrupted in the data dictionary cache only. This
is used mostly to mark a corrupted index when index's own dictionary
Expand Down
6 changes: 2 additions & 4 deletions storage/innobase/include/os0thread.h
Original file line number Diff line number Diff line change
Expand Up @@ -128,10 +128,8 @@ os_thread_join(
/** Exits the current thread.
@param[in] detach if true, the thread will be detached right before
exiting. If false, another thread is responsible for joining this thread */
void
os_thread_exit(
bool detach = true)
UNIV_COLD MY_ATTRIBUTE((noreturn));
ATTRIBUTE_NORETURN ATTRIBUTE_COLD
void os_thread_exit(bool detach = true);

/*****************************************************************//**
Returns the thread identifier of current thread.
Expand Down
10 changes: 5 additions & 5 deletions storage/innobase/include/row0log.h
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ row_log_online_op(
const dtuple_t* tuple, /*!< in: index tuple */
trx_id_t trx_id) /*!< in: transaction ID for insert,
or 0 for delete */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));

/******************************************************//**
Gets the error status of the online index rebuild log.
Expand Down Expand Up @@ -137,7 +137,7 @@ row_log_table_delete(
const ulint* offsets,/*!< in: rec_get_offsets(rec,index) */
const byte* sys) /*!< in: DB_TRX_ID,DB_ROLL_PTR that should
be logged, or NULL to use those in rec */
UNIV_COLD MY_ATTRIBUTE((nonnull(1,2,3)));
ATTRIBUTE_COLD __attribute__((nonnull(1,2,3)));

/******************************************************//**
Logs an update operation to a table that is being rebuilt.
Expand Down Expand Up @@ -174,7 +174,7 @@ row_log_table_get_pk(
byte* sys, /*!< out: DB_TRX_ID,DB_ROLL_PTR for
row_log_table_delete(), or NULL */
mem_heap_t** heap) /*!< in/out: memory heap where allocated */
UNIV_COLD MY_ATTRIBUTE((nonnull(1,2,5), warn_unused_result));
ATTRIBUTE_COLD __attribute__((nonnull(1,2,5), warn_unused_result));

/******************************************************//**
Logs an insert to a table that is being rebuilt.
Expand All @@ -195,15 +195,15 @@ row_log_table_blob_free(
/*====================*/
dict_index_t* index, /*!< in/out: clustered index, X-latched */
ulint page_no)/*!< in: starting page number of the BLOB */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));
/******************************************************//**
Notes that a BLOB is being allocated during online ALTER TABLE. */
void
row_log_table_blob_alloc(
/*=====================*/
dict_index_t* index, /*!< in/out: clustered index, X-latched */
ulint page_no)/*!< in: starting page number of the BLOB */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));

/** Apply the row_log_table log to a table upon completing rebuild.
@param[in] thr query graph
Expand Down
2 changes: 1 addition & 1 deletion storage/innobase/include/trx0undo.h
Original file line number Diff line number Diff line change
Expand Up @@ -319,7 +319,7 @@ void
trx_undo_free_prepared(
/*===================*/
trx_t* trx) /*!< in/out: PREPARED transaction */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));

/* Forward declaration. */
namespace undo {
Expand Down
17 changes: 0 additions & 17 deletions storage/innobase/include/univ.i
Original file line number Diff line number Diff line change
Expand Up @@ -258,23 +258,6 @@ easy way to get it to work. See http://bugs.mysql.com/bug.php?id=52263. */
#endif
#endif

#if defined(COMPILER_HINTS) \
&& defined __GNUC__ \
&& (__GNUC__ > 4 || __GNUC__ == 4 && __GNUC_MINOR__ >= 3)

/** Starting with GCC 4.3, the "cold" attribute is used to inform the
compiler that a function is unlikely executed. The function is
optimized for size rather than speed and on many targets it is placed
into special subsection of the text section so all cold functions
appears close together improving code locality of non-cold parts of
program. The paths leading to call of cold functions within code are
marked as unlikely by the branch prediction mechanism. optimize a
rarely invoked function for size instead for speed. */
# define UNIV_COLD MY_ATTRIBUTE((cold))
#else
# define UNIV_COLD /* empty */
#endif

#define UNIV_INLINE static inline

#define UNIV_WORD_SIZE SIZEOF_SIZE_T
Expand Down
4 changes: 2 additions & 2 deletions storage/innobase/include/ut0dbg.h
Original file line number Diff line number Diff line change
Expand Up @@ -39,13 +39,13 @@ Created 1/30/1994 Heikki Tuuri

/*************************************************************//**
Report a failed assertion. */
ATTRIBUTE_NORETURN ATTRIBUTE_COLD __attribute__((nonnull(2)))
void
ut_dbg_assertion_failed(
/*====================*/
const char* expr, /*!< in: the failed assertion */
const char* file, /*!< in: source file containing the assertion */
unsigned line) /*!< in: line number of the assertion */
UNIV_COLD MY_ATTRIBUTE((nonnull(2), noreturn));
unsigned line); /*!< in: line number of the assertion */

/** Abort execution if EXPR does not evaluate to nonzero.
@param EXPR assertion expression that should hold */
Expand Down
14 changes: 13 additions & 1 deletion storage/innobase/include/ut0ut.h
Original file line number Diff line number Diff line change
Expand Up @@ -299,7 +299,7 @@ void
ut_print_timestamp(
/*===============*/
FILE* file) /*!< in: file where to print */
UNIV_COLD MY_ATTRIBUTE((nonnull));
ATTRIBUTE_COLD __attribute__((nonnull));

#ifndef UNIV_INNOCHECKSUM

Expand Down Expand Up @@ -505,6 +505,7 @@ use this class directly, instead use one of the derived classes. */
class logger {
public:
template<typename T>
ATTRIBUTE_COLD
logger& operator<<(const T& rhs)
{
m_oss << rhs;
Expand All @@ -515,6 +516,7 @@ class logger {
@param[in] buf the buffer whose contents will be logged.
@param[in] count the length of the buffer buf.
@return the output stream into which buffer was written. */
ATTRIBUTE_COLD
std::ostream&
write(
const char* buf,
Expand All @@ -527,6 +529,7 @@ class logger {
@param[in] buf the buffer whose contents will be logged.
@param[in] count the length of the buffer buf.
@return the output stream into which buffer was written. */
ATTRIBUTE_COLD
std::ostream&
write(
const byte* buf,
Expand All @@ -539,6 +542,7 @@ class logger {
protected:
/* This class must not be used directly, hence making the default
constructor protected. */
ATTRIBUTE_COLD
logger() {}
};

Expand All @@ -555,20 +559,23 @@ statement. If a named object is created, then the log message will be emitted
only when it goes out of scope or destroyed. */
class info : public logger {
public:
ATTRIBUTE_COLD
~info();
};

/** The class warn is used to emit warnings. Refer to the documentation of
class info for further details. */
class warn : public logger {
public:
ATTRIBUTE_COLD
~warn();
};

/** The class error is used to emit error messages. Refer to the
documentation of class info for further details. */
class error : public logger {
public:
ATTRIBUTE_COLD
~error();
};

Expand All @@ -577,17 +584,20 @@ by crashing it. Use this class when MySQL server needs to be stopped
immediately. Refer to the documentation of class info for usage details. */
class fatal : public logger {
public:
ATTRIBUTE_NORETURN
~fatal();
};

/** Emit an error message if the given predicate is true, otherwise emit a
warning message */
class error_or_warn : public logger {
public:
ATTRIBUTE_COLD
error_or_warn(bool pred)
: m_error(pred)
{}

ATTRIBUTE_COLD
~error_or_warn();
private:
const bool m_error;
Expand All @@ -597,10 +607,12 @@ class error_or_warn : public logger {
error message. */
class fatal_or_error : public logger {
public:
ATTRIBUTE_COLD
fatal_or_error(bool pred)
: m_fatal(pred)
{}

ATTRIBUTE_COLD
~fatal_or_error();
private:
const bool m_fatal;
Expand Down
4 changes: 2 additions & 2 deletions storage/innobase/os/os0thread.cc
Original file line number Diff line number Diff line change
Expand Up @@ -174,9 +174,9 @@ os_thread_join(
/** Exits the current thread.
@param[in] detach if true, the thread will be detached right before
exiting. If false, another thread is responsible for joining this thread */
ATTRIBUTE_NORETURN
void
os_thread_exit(
bool detach)
os_thread_exit(bool detach)
{
#ifdef UNIV_DEBUG_THREAD_CREATION
ib::info() << "Thread exits, id "
Expand Down
2 changes: 1 addition & 1 deletion storage/innobase/rem/rem0cmp.cc
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ TODO: Remove this function. Everything should use MYSQL_TYPE_NEWDECIMAL.
@param[in] b_length length of b, in bytes (not UNIV_SQL_NULL)
@return positive, 0, negative, if a is greater, equal, less than b,
respectively */
static UNIV_COLD
static ATTRIBUTE_COLD
int
cmp_decimal(
const byte* a,
Expand Down
1 change: 1 addition & 0 deletions storage/innobase/ut/ut0dbg.cc
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ Created 1/30/1994 Heikki Tuuri

/*************************************************************//**
Report a failed assertion. */
ATTRIBUTE_NORETURN
void
ut_dbg_assertion_failed(
/*====================*/
Expand Down
1 change: 1 addition & 0 deletions storage/innobase/ut/ut0ut.cc
Original file line number Diff line number Diff line change
Expand Up @@ -834,6 +834,7 @@ error::~error()
sql_print_error("InnoDB: %s", m_oss.str().c_str());
}

ATTRIBUTE_NORETURN
fatal::~fatal()
{
sql_print_error("[FATAL] InnoDB: %s", m_oss.str().c_str());
Expand Down
2 changes: 1 addition & 1 deletion storage/maria/maria_chk.c
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,7 @@ static int sort_record_index(MARIA_SORT_PARAM *sort_param, MARIA_PAGE *page,
uint sortkey, File new_file,
my_bool update_index);
static my_bool write_log_record(HA_CHECK *param);
static void my_exit(int exit_code) __attribute__ ((noreturn));
ATTRIBUTE_NORETURN static void my_exit(int exit_code);

HA_CHECK check_param;

Expand Down

0 comments on commit 4386ee8

Please sign in to comment.