root/lib/pengine/pe_health.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. pe__unpack_node_health_scores
  2. add_node_health_value
  3. pe__sum_node_health_scores
  4. pe__node_health

   1 /*
   2  * Copyright 2004-2024 the Pacemaker project contributors
   3  *
   4  * The version control history for this file may have further details.
   5  *
   6  * This source code is licensed under the GNU Lesser General Public License
   7  * version 2.1 or later (LGPLv2.1+) WITHOUT ANY WARRANTY.
   8  */
   9 
  10 #include <crm_internal.h>
  11 
  12 #include <crm/pengine/status.h>
  13 #include <crm/pengine/internal.h>
  14 #include "pe_status_private.h"
  15 
  16 /*!
  17  * \internal
  18  * \brief Set the node health values to use for \c PCMK_VALUE_RED,
  19  *        \c PCMK_VALUE_YELLOW, and \c PCMK_VALUE_GREEN
  20  *
  21  * \param[in,out] scheduler  Scheduler data
  22  */
  23 void
  24 pe__unpack_node_health_scores(pcmk_scheduler_t *scheduler)
     /* [previous][next][first][last][top][bottom][index][help] */
  25 {
  26     switch (pe__health_strategy(scheduler)) {
  27         case pcmk__health_strategy_none:
  28             pcmk__score_red = 0;
  29             pcmk__score_yellow = 0;
  30             pcmk__score_green = 0;
  31             break;
  32 
  33         case pcmk__health_strategy_no_red:
  34             pcmk__score_red = -PCMK_SCORE_INFINITY;
  35             pcmk__score_yellow = 0;
  36             pcmk__score_green = 0;
  37             break;
  38 
  39         case pcmk__health_strategy_only_green:
  40             pcmk__score_red = -PCMK_SCORE_INFINITY;
  41             pcmk__score_yellow = -PCMK_SCORE_INFINITY;
  42             pcmk__score_green = 0;
  43             break;
  44 
  45         default: // progressive or custom
  46             pcmk__score_red = pe__health_score(PCMK_OPT_NODE_HEALTH_RED,
  47                                                scheduler);
  48             pcmk__score_green = pe__health_score(PCMK_OPT_NODE_HEALTH_GREEN,
  49                                                  scheduler);
  50             pcmk__score_yellow = pe__health_score(PCMK_OPT_NODE_HEALTH_YELLOW,
  51                                                   scheduler);
  52             break;
  53     }
  54 
  55     if ((pcmk__score_red != 0) || (pcmk__score_yellow != 0)
  56         || (pcmk__score_green != 0)) {
  57         crm_debug("Values of node health scores: "
  58                   PCMK_VALUE_RED "=%d "
  59                   PCMK_VALUE_YELLOW "=%d "
  60                   PCMK_VALUE_GREEN "=%d",
  61                   pcmk__score_red, pcmk__score_yellow, pcmk__score_green);
  62     }
  63 }
  64 
  65 /*!
  66  * \internal
  67  * \brief Add node attribute value to an integer, if it is a health attribute
  68  *
  69  * \param[in]     key        Name of node attribute
  70  * \param[in]     value      String value of node attribute
  71  * \param[in,out] user_data  Address of integer to which \p value should be
  72  *                           added if \p key is a node health attribute
  73  */
  74 static void
  75 add_node_health_value(gpointer key, gpointer value, gpointer user_data)
     /* [previous][next][first][last][top][bottom][index][help] */
  76 {
  77     if (pcmk__starts_with((const char *) key, "#health")) {
  78         int score = char2score((const char *) value);
  79         int *health = (int *) user_data;
  80 
  81         *health = pcmk__add_scores(score, *health);
  82         crm_trace("Combined '%s' into node health score (now %s)",
  83                   (const char *) value, pcmk_readable_score(*health));
  84     }
  85 }
  86 
  87 /*!
  88  * \internal
  89  * \brief Sum a node's health attribute scores
  90  *
  91  * \param[in] node         Node whose health attributes should be added
  92  * \param[in] base_health  Add this number to the total
  93  *
  94  * \return Sum of all health attribute scores of \p node plus \p base_health
  95  */
  96 int
  97 pe__sum_node_health_scores(const pcmk_node_t *node, int base_health)
     /* [previous][next][first][last][top][bottom][index][help] */
  98 {
  99     CRM_ASSERT(node != NULL);
 100     g_hash_table_foreach(node->details->attrs, add_node_health_value,
 101                          &base_health);
 102     return base_health;
 103 }
 104 
 105 /*!
 106  * \internal
 107  * \brief Check the general health status for a node
 108  *
 109  * \param[in,out] node  Node to check
 110  *
 111  * \return  A negative value if any health attribute for \p node is red,
 112  *          otherwise 0 if any attribute is yellow, otherwise a positive value.
 113  */
 114 int
 115 pe__node_health(pcmk_node_t *node)
     /* [previous][next][first][last][top][bottom][index][help] */
 116 {
 117     GHashTableIter iter;
 118     const char *name = NULL;
 119     const char *value = NULL;
 120     enum pcmk__health_strategy strategy;
 121     int score = 0;
 122     int rc = 1;
 123 
 124     CRM_ASSERT(node != NULL);
 125 
 126     strategy = pe__health_strategy(node->details->data_set);
 127     if (strategy == pcmk__health_strategy_none) {
 128         return rc;
 129     }
 130 
 131     g_hash_table_iter_init(&iter, node->details->attrs);
 132     while (g_hash_table_iter_next(&iter, (gpointer *) &name,
 133                                   (gpointer *) &value)) {
 134         if (pcmk__starts_with(name, "#health")) {
 135             /* It's possible that pcmk__score_red equals pcmk__score_yellow,
 136              * or pcmk__score_yellow equals pcmk__score_green, so check the
 137              * textual value first to be able to distinguish those.
 138              */
 139             if (pcmk__str_eq(value, PCMK_VALUE_RED, pcmk__str_casei)) {
 140                 return -1;
 141             } else if (pcmk__str_eq(value, PCMK_VALUE_YELLOW,
 142                                     pcmk__str_casei)) {
 143                 rc = 0;
 144                 continue;
 145             }
 146 
 147             // The value is an integer, so compare numerically
 148             score = char2score(value);
 149             if (score <= pcmk__score_red) {
 150                 return -1;
 151             } else if ((score <= pcmk__score_yellow)
 152                        && (pcmk__score_yellow != pcmk__score_green)) {
 153                 rc = 0;
 154             }
 155         }
 156     }
 157     return rc;
 158 }

/* [previous][next][first][last][top][bottom][index][help] */