mirror of
http://git.haproxy.org/git/haproxy.git/
synced 2025-01-23 14:02:56 +00:00
MEDIUM: threads: detect excessive thread counts vs cpu-map
This detects when there are more threads bound via cpu-map than CPUs enabled in cpu-map, or when there are more total threads than the total number of CPUs available at boot (for unbound threads) and configured for bound threads. In this case, a warning is emitted to explain the problems it will cause, and explaining how to address the situation. Note that some configurations will not be detected as faulty because the algorithmic complexity to resolve all arrangements grows in O(N!). This means that having 3 threads on 2 CPUs and one thread on 2 CPUs will not be detected as it's 4 threads for 4 CPUs. But at least configs such as T0:(1,4) T1:(1,4) T2:(2,4) T3:(3,4) will not trigger a warning since they're valid.
This commit is contained in:
parent
8357f950cb
commit
86854dd032
@ -44,6 +44,7 @@ void ha_tkill(unsigned int thr, int sig);
|
||||
void ha_tkillall(int sig);
|
||||
void ha_thread_relax(void);
|
||||
int thread_detect_binding_discrepancies(void);
|
||||
int thread_detect_more_than_cpus(void);
|
||||
int thread_map_to_groups();
|
||||
int thread_resolve_group_mask(struct thread_set *ts, int defgrp, char **err);
|
||||
int parse_thread_set(const char *arg, struct thread_set *ts, char **err);
|
||||
|
@ -2311,6 +2311,7 @@ static void init(int argc, char **argv)
|
||||
#endif
|
||||
|
||||
thread_detect_binding_discrepancies();
|
||||
thread_detect_more_than_cpus();
|
||||
|
||||
/* Apply server states */
|
||||
apply_server_state();
|
||||
|
56
src/thread.c
56
src/thread.c
@ -1171,6 +1171,62 @@ int thread_detect_binding_discrepancies(void)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Returns non-zero on anomaly (more threads than CPUs), and emits a warning in
|
||||
* this case. It checks against configured cpu-map if any, otherwise against
|
||||
* the number of CPUs at boot if known. It's better to run it only after
|
||||
* thread_detect_binding_discrepancies() so that mixed cases can be eliminated.
|
||||
*/
|
||||
int thread_detect_more_than_cpus(void)
|
||||
{
|
||||
#if defined(USE_CPU_AFFINITY)
|
||||
struct hap_cpuset cpuset_map, cpuset_boot, cpuset_all;
|
||||
uint th, tg, id;
|
||||
int bound;
|
||||
int tot_map, tot_all;
|
||||
|
||||
ha_cpuset_zero(&cpuset_boot);
|
||||
ha_cpuset_zero(&cpuset_map);
|
||||
ha_cpuset_zero(&cpuset_all);
|
||||
bound = 0;
|
||||
for (th = 0; th < global.nbthread; th++) {
|
||||
tg = ha_thread_info[th].tgid;
|
||||
id = ha_thread_info[th].ltid;
|
||||
if (ha_cpuset_count(&cpu_map[tg - 1].thread[id])) {
|
||||
ha_cpuset_or(&cpuset_map, &cpu_map[tg - 1].thread[id]);
|
||||
bound++;
|
||||
}
|
||||
}
|
||||
|
||||
ha_cpuset_assign(&cpuset_all, &cpuset_map);
|
||||
if (bound != global.nbthread) {
|
||||
if (ha_cpuset_detect_bound(&cpuset_boot))
|
||||
ha_cpuset_or(&cpuset_all, &cpuset_boot);
|
||||
}
|
||||
|
||||
tot_map = ha_cpuset_count(&cpuset_map);
|
||||
tot_all = ha_cpuset_count(&cpuset_all);
|
||||
|
||||
if (tot_map && bound > tot_map) {
|
||||
ha_warning("This configuration binds %d threads to a total of %d CPUs via cpu-map "
|
||||
"directives. This means that some threads will compete for the same CPU, "
|
||||
"which will cause severe performance degradation. Please fix either the "
|
||||
"'cpu-map' directives or set the global 'nbthread' value accordingly.\n",
|
||||
bound, tot_map);
|
||||
return 1;
|
||||
}
|
||||
else if (tot_all && global.nbthread > tot_all) {
|
||||
ha_warning("This configuration enables %d threads running on a total of %d CPUs. "
|
||||
"This means that some threads will compete for the same CPU, which will cause "
|
||||
"severe performance degradation. Please either the 'cpu-map' directives to "
|
||||
"adjust the CPUs to use, or fix the global 'nbthread' value.\n",
|
||||
global.nbthread, tot_all);
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* scans the configured thread mapping and establishes the final one. Returns <0
|
||||
* on failure, >=0 on success.
|
||||
*/
|
||||
|
Loading…
Reference in New Issue
Block a user