Rebased to version 1.0.4
This commit is contained in:
parent
531d750853
commit
bb88e4e36f
1
.gitignore
vendored
1
.gitignore
vendored
@ -4,3 +4,4 @@ irqbalance-0.56.tbz2
|
||||
/irqbalance-1.0.1.tar.gz
|
||||
/irqbalance-1.0.2.tar.gz
|
||||
/irqbalance-1.0.3.tar.gz
|
||||
/irqbalance-1.0.4.tar.bz2
|
||||
|
@ -1,74 +0,0 @@
|
||||
From 626dded557de1e7b90cb847df9e900d40be5af1a Mon Sep 17 00:00:00 2001
|
||||
From: Neil Horman <nhorman@tuxdriver.com>
|
||||
Date: Wed, 14 Dec 2011 07:09:07 -0500
|
||||
Subject: [PATCH 1/8] Add sample irqbalance environment file
|
||||
|
||||
It was pointed out that the example systemd unit file pointed to a corresponding
|
||||
environment file that had no sample. Fix that up, and modify the unit file to
|
||||
pass available option via environment variables rather than command line options
|
||||
since that looks a little cleaner.
|
||||
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
|
||||
add irqbalance args variable to env file
|
||||
|
||||
Allow users to pass general arguments to irqbalance through systemd
|
||||
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
misc/irqbalance.env | 26 ++++++++++++++++++++++++++
|
||||
misc/irqbalance.service | 5 ++---
|
||||
2 files changed, 28 insertions(+), 3 deletions(-)
|
||||
create mode 100644 misc/irqbalance.env
|
||||
|
||||
diff --git a/misc/irqbalance.env b/misc/irqbalance.env
|
||||
new file mode 100644
|
||||
index 0000000..bd87e3d
|
||||
--- /dev/null
|
||||
+++ b/misc/irqbalance.env
|
||||
@@ -0,0 +1,26 @@
|
||||
+# irqbalance is a daemon process that distributes interrupts across
|
||||
+# CPUS on SMP systems. The default is to rebalance once every 10
|
||||
+# seconds. This is the environment file that is specified to systemd via the
|
||||
+# EnvironmentFile key in the service unit file (or via whatever method the init
|
||||
+# system you're using has.
|
||||
+#
|
||||
+# ONESHOT=yes
|
||||
+# after starting, wait for a minute, then look at the interrupt
|
||||
+# load and balance it once; after balancing exit and do not change
|
||||
+# it again.
|
||||
+#IRQBALANCE_ONESHOT=
|
||||
+
|
||||
+#
|
||||
+# IRQBALANCE_BANNED_CPUS
|
||||
+# 64 bit bitmask which allows you to indicate which cpu's should
|
||||
+# be skipped when reblancing irqs. Cpu numbers which have their
|
||||
+# corresponding bits set to one in this mask will not have any
|
||||
+# irq's assigned to them on rebalance
|
||||
+#
|
||||
+#IRQBALANCE_BANNED_CPUS=
|
||||
+
|
||||
+#
|
||||
+# IRQBALANCE_ARGS
|
||||
+# append any args here to the irqbalance daemon as documented in the man page
|
||||
+#
|
||||
+#IRQBALANCE_ARGS=
|
||||
diff --git a/misc/irqbalance.service b/misc/irqbalance.service
|
||||
index f349616..aae2b03 100644
|
||||
--- a/misc/irqbalance.service
|
||||
+++ b/misc/irqbalance.service
|
||||
@@ -3,9 +3,8 @@ Description=irqbalance daemon
|
||||
After=syslog.target
|
||||
|
||||
[Service]
|
||||
-EnvironmentFile=/etc/sysconfig/irqbalance
|
||||
-Type=forking
|
||||
-ExecStart=/usr/sbin/irqbalance $ONESHOT
|
||||
+EnvironmentFile=/path/to/irqbalance.env
|
||||
+ExecStart=/usr/sbin/irqbalance $IRQBALANCE_ARGS
|
||||
|
||||
[Install]
|
||||
WantedBy=multi-user.target
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,172 +0,0 @@
|
||||
From 4da232bbf763e535ec2512087aa9ac8a96fba3d9 Mon Sep 17 00:00:00 2001
|
||||
From: Neil Horman <nhorman@tuxdriver.com>
|
||||
Date: Fri, 17 Feb 2012 14:27:11 -0500
|
||||
Subject: [PATCH 2/8] introduce banirq option
|
||||
|
||||
Fixing bug http://code.google.com/p/irqbalance/issues/detail?id=25
|
||||
|
||||
It was pointed out that during the rewrite of irqbalance I inadvertently removed
|
||||
the support for the IRQBALANCE_BANNED_IRQS environment variable. While going to
|
||||
return it to the build, it occured to me that, given the availability of msi[x]
|
||||
irqs, a single system can literally have thousands of interrupt sources, making
|
||||
the environment variable a non-scalable solution. Instead I'm adding a new
|
||||
option, banirqs, which takes its place. It lets you build a list of irqs that
|
||||
you want irqbalance to leave alone.
|
||||
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
classify.c | 32 ++++++++++++++++++++++++++++++++
|
||||
irqbalance.1 | 11 +++++++----
|
||||
irqbalance.c | 15 ++++++++++++---
|
||||
irqbalance.h | 1 +
|
||||
4 files changed, 52 insertions(+), 7 deletions(-)
|
||||
|
||||
diff --git a/classify.c b/classify.c
|
||||
index 124dab0..d59da7f 100644
|
||||
--- a/classify.c
|
||||
+++ b/classify.c
|
||||
@@ -52,6 +52,7 @@ static short class_codes[MAX_CLASS] = {
|
||||
};
|
||||
|
||||
static GList *interrupts_db;
|
||||
+static GList *banned_irqs;
|
||||
|
||||
#define SYSDEV_DIR "/sys/bus/pci/devices"
|
||||
|
||||
@@ -63,6 +64,30 @@ static gint compare_ints(gconstpointer a, gconstpointer b)
|
||||
return ai->irq - bi->irq;
|
||||
}
|
||||
|
||||
+void add_banned_irq(int irq)
|
||||
+{
|
||||
+ struct irq_info find, *new;
|
||||
+ GList *entry;
|
||||
+
|
||||
+ find.irq = irq;
|
||||
+ entry = g_list_find_custom(banned_irqs, &find, compare_ints);
|
||||
+ if (entry)
|
||||
+ return;
|
||||
+
|
||||
+ new = calloc(sizeof(struct irq_info), 1);
|
||||
+ if (!new) {
|
||||
+ if (debug_mode)
|
||||
+ printf("No memory to ban irq %d\n", irq);
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ new->irq = irq;
|
||||
+
|
||||
+ banned_irqs = g_list_append(banned_irqs, new);
|
||||
+ return;
|
||||
+}
|
||||
+
|
||||
+
|
||||
/*
|
||||
* Inserts an irq_info struct into the intterupts_db list
|
||||
* devpath points to the device directory in sysfs for the
|
||||
@@ -90,6 +115,13 @@ static struct irq_info *add_one_irq_to_db(const char *devpath, int irq)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
+ entry = g_list_find_custom(banned_irqs, &find, compare_ints);
|
||||
+ if (entry) {
|
||||
+ if (debug_mode)
|
||||
+ printf("SKIPPING BANNED IRQ %d\n", irq);
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
new = calloc(sizeof(struct irq_info), 1);
|
||||
if (!new)
|
||||
return NULL;
|
||||
diff --git a/irqbalance.1 b/irqbalance.1
|
||||
index 55fc15f..978c7c1 100644
|
||||
--- a/irqbalance.1
|
||||
+++ b/irqbalance.1
|
||||
@@ -62,6 +62,13 @@ average cpu softirq workload, and no cpus are more than 1 standard deviation
|
||||
above (and have more than 1 irq assigned to them), attempt to place 1 cpu in
|
||||
powersave mode. In powersave mode, a cpu will not have any irqs balanced to it,
|
||||
in an effort to prevent that cpu from waking up without need.
|
||||
+
|
||||
+.TP
|
||||
+.B --banirq=<irqnum>
|
||||
+Add the specified irq list to the set of banned irqs. irqbalance will not affect
|
||||
+the affinity of any irqs on the banned list, allowing them to be specified
|
||||
+manually. This option is addative and can be specified multiple times
|
||||
+
|
||||
.SH "ENVIRONMENT VARIABLES"
|
||||
.TP
|
||||
.B IRQBALANCE_ONESHOT
|
||||
@@ -75,10 +82,6 @@ Same as --debug
|
||||
.B IRQBALANCE_BANNED_CPUS
|
||||
Provides a mask of cpus which irqbalance should ignore and never assign interrupts to
|
||||
|
||||
-.TP
|
||||
-.B IRQBALANCE_BANNED_INTERRUPTS
|
||||
-A list of space delimited IRQ numbers that irqbalance should not touch
|
||||
-
|
||||
.SH "Homepage"
|
||||
http://code.google.com/p/irqbalance
|
||||
|
||||
diff --git a/irqbalance.c b/irqbalance.c
|
||||
index 99c5db7..c613e2b 100644
|
||||
--- a/irqbalance.c
|
||||
+++ b/irqbalance.c
|
||||
@@ -72,7 +72,7 @@ struct option lopts[] = {
|
||||
static void usage(void)
|
||||
{
|
||||
printf("irqbalance [--oneshot | -o] [--debug | -d] [--hintpolicy= | -h [exact|subset|ignore]]\n");
|
||||
- printf(" [--powerthresh= | -p <off> | <n>]\n");
|
||||
+ printf(" [--powerthresh= | -p <off> | <n>] [--banirq= | -i <n>]\n");
|
||||
}
|
||||
|
||||
static void parse_command_line(int argc, char **argv)
|
||||
@@ -81,7 +81,7 @@ static void parse_command_line(int argc, char **argv)
|
||||
int longind;
|
||||
|
||||
while ((opt = getopt_long(argc, argv,
|
||||
- "odh:p:",
|
||||
+ "odh:p:b:",
|
||||
lopts, &longind)) != -1) {
|
||||
|
||||
switch(opt) {
|
||||
@@ -103,6 +103,14 @@ static void parse_command_line(int argc, char **argv)
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
+ case 'i':
|
||||
+ val = strtoull(optarg, NULL, 10);
|
||||
+ if (val == ULONG_MAX) {
|
||||
+ usage();
|
||||
+ exit(1);
|
||||
+ }
|
||||
+ add_banned_irq((int)val);
|
||||
+ break;
|
||||
case 'p':
|
||||
if (!strncmp(optarg, "off", strlen(optarg)))
|
||||
power_thresh = ULONG_MAX;
|
||||
@@ -179,8 +187,9 @@ int main(int argc, char** argv)
|
||||
#ifdef HAVE_GETOPT_LONG
|
||||
parse_command_line(argc, argv);
|
||||
#else
|
||||
- if (argc>1 && strstr(argv[1],"--debug"))
|
||||
+ if (argc>1 && strstr(argv[1],"--debug")) {
|
||||
debug_mode=1;
|
||||
+ }
|
||||
if (argc>1 && strstr(argv[1],"--oneshot"))
|
||||
one_shot_mode=1;
|
||||
#endif
|
||||
diff --git a/irqbalance.h b/irqbalance.h
|
||||
index 4e85325..956aa8c 100644
|
||||
--- a/irqbalance.h
|
||||
+++ b/irqbalance.h
|
||||
@@ -103,6 +103,7 @@ extern int get_cpu_count(void);
|
||||
*/
|
||||
extern void rebuild_irq_db(void);
|
||||
extern void free_irq_db(void);
|
||||
+extern void add_banned_irq(int irq);
|
||||
extern void for_each_irq(GList *list, void (*cb)(struct irq_info *info, void *data), void *data);
|
||||
extern struct irq_info *get_irq_info(int irq);
|
||||
extern void migrate_irq(GList **from, GList **to, struct irq_info *info);
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,44 +0,0 @@
|
||||
From 718561bc79c095909f0c9d3fb2f0c1c163478b1e Mon Sep 17 00:00:00 2001
|
||||
From: Petr Holasek <pholasek@redhat.com>
|
||||
Date: Mon, 20 Feb 2012 16:59:05 +0100
|
||||
Subject: [PATCH 3/8] When IRQBALANCE_BANNED_CPUS is set, /proc/stat is not
|
||||
parsed properly.
|
||||
|
||||
proc stats counts all the cpus in /proc/stat, but compares that number to the
|
||||
value in get_cpu_count(), which returns the number of cpus actively being
|
||||
balanced. Since that value doesn't include banned cpus, its incorrect. Since
|
||||
we don't want to measure the load on banned cpus anyway, just skip those lines
|
||||
so cpucount doesn't increment and the count remains equal.
|
||||
|
||||
Signed-off-by: Petr Holasek <pholasek@redhat.com>
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
procinterrupts.c | 5 +++++
|
||||
1 file changed, 5 insertions(+)
|
||||
|
||||
diff --git a/procinterrupts.c b/procinterrupts.c
|
||||
index 4d3b07b..c032caf 100644
|
||||
--- a/procinterrupts.c
|
||||
+++ b/procinterrupts.c
|
||||
@@ -32,6 +32,8 @@
|
||||
|
||||
#define LINESIZE 4096
|
||||
|
||||
+extern cpumask_t banned_cpus;
|
||||
+
|
||||
static int proc_int_has_msi = 0;
|
||||
static int msi_found_in_sysfs = 0;
|
||||
|
||||
@@ -217,6 +219,9 @@ void parse_proc_stat(void)
|
||||
|
||||
cpunr = strtoul(&line[3], NULL, 10);
|
||||
|
||||
+ if (cpu_isset(cpunr, banned_cpus))
|
||||
+ continue;
|
||||
+
|
||||
rc = sscanf(line, "%*s %*d %*d %*d %*d %*d %d %d", &irq_load, &softirq_load);
|
||||
if (rc < 2)
|
||||
break;
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,91 +0,0 @@
|
||||
From 0edc531b0a2ebb41eb5cf49168e2897640cba0ec Mon Sep 17 00:00:00 2001
|
||||
From: Neil Horman <nhorman@tuxdriver.com>
|
||||
Date: Mon, 2 Jul 2012 13:27:14 -0400
|
||||
Subject: [PATCH 4/8] Make irqbalance scan for new irqs when it detects new
|
||||
irqs
|
||||
|
||||
Like cpu hotplug, irqbalance needs to rebuild its topo map and irq db when it
|
||||
detects new irqs in the system. This patch adds that ability
|
||||
|
||||
Resolves: http://code.google.com/p/irqbalance/issues/detail?id=32
|
||||
|
||||
Singed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
irqbalance.c | 6 +++---
|
||||
irqbalance.h | 2 +-
|
||||
procinterrupts.c | 14 ++++++++++++--
|
||||
3 files changed, 16 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/irqbalance.c b/irqbalance.c
|
||||
index c613e2b..5d40321 100644
|
||||
--- a/irqbalance.c
|
||||
+++ b/irqbalance.c
|
||||
@@ -40,7 +40,7 @@ volatile int keep_going = 1;
|
||||
int one_shot_mode;
|
||||
int debug_mode;
|
||||
int numa_avail;
|
||||
-int need_cpu_rescan;
|
||||
+int need_rescan;
|
||||
extern cpumask_t banned_cpus;
|
||||
enum hp_e hint_policy = HINT_POLICY_SUBSET;
|
||||
unsigned long power_thresh = ULONG_MAX;
|
||||
@@ -256,8 +256,8 @@ int main(int argc, char** argv)
|
||||
parse_proc_stat();
|
||||
|
||||
/* cope with cpu hotplug -- detected during /proc/interrupts parsing */
|
||||
- if (need_cpu_rescan) {
|
||||
- need_cpu_rescan = 0;
|
||||
+ if (need_rescan) {
|
||||
+ need_rescan = 0;
|
||||
/* if there's a hotplug event we better turn off power mode for a bit until things settle */
|
||||
power_mode = 0;
|
||||
if (debug_mode)
|
||||
diff --git a/irqbalance.h b/irqbalance.h
|
||||
index 956aa8c..043bfe6 100644
|
||||
--- a/irqbalance.h
|
||||
+++ b/irqbalance.h
|
||||
@@ -64,7 +64,7 @@ enum hp_e {
|
||||
extern int debug_mode;
|
||||
extern int one_shot_mode;
|
||||
extern int power_mode;
|
||||
-extern int need_cpu_rescan;
|
||||
+extern int need_rescan;
|
||||
extern enum hp_e hint_policy;
|
||||
extern unsigned long long cycle_count;
|
||||
extern unsigned long power_thresh;
|
||||
diff --git a/procinterrupts.c b/procinterrupts.c
|
||||
index c032caf..4559b16 100644
|
||||
--- a/procinterrupts.c
|
||||
+++ b/procinterrupts.c
|
||||
@@ -82,8 +82,18 @@ void parse_proc_interrupts(void)
|
||||
c++;
|
||||
number = strtoul(line, NULL, 10);
|
||||
info = get_irq_info(number);
|
||||
- if (!info)
|
||||
+ if (!info) {
|
||||
+ /*
|
||||
+ * If this is our 0th pass through this routine
|
||||
+ * this is an irq that wasn't reported in sysfs
|
||||
+ * and we should just add it. If we've been running
|
||||
+ * a while then this irq just appeared and its time
|
||||
+ * to rescan our irqs
|
||||
+ */
|
||||
+ if (cycle_count)
|
||||
+ need_rescan = 1;
|
||||
info = add_misc_irq(number);
|
||||
+ }
|
||||
|
||||
count = 0;
|
||||
cpunr = 0;
|
||||
@@ -99,7 +109,7 @@ void parse_proc_interrupts(void)
|
||||
cpunr++;
|
||||
}
|
||||
if (cpunr != core_count)
|
||||
- need_cpu_rescan = 1;
|
||||
+ need_rescan = 1;
|
||||
|
||||
info->last_irq_count = info->irq_count;
|
||||
info->irq_count = count;
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,218 +0,0 @@
|
||||
From b18eb8f6b28cc9b0816be0fb8fe3468c9f64f345 Mon Sep 17 00:00:00 2001
|
||||
From: Neil Horman <nhorman@tuxdriver.com>
|
||||
Date: Thu, 5 Jul 2012 14:54:35 -0400
|
||||
Subject: [PATCH 5/8] Add banscript option
|
||||
|
||||
Its been requested in several different ways, that irqbalance have a more robust
|
||||
mechanism for setting balancing policy at run time. While I don't feel its
|
||||
apropriate to have irqbalance be able to implement arbitrary balance policy
|
||||
(having a flexible mechanism to define which irqs should be placed where can
|
||||
become exceedingly complex), I do think we need some mechanism that easily
|
||||
allows users to dynamically exclude irqs from the irqbalance policy at run time.
|
||||
The banscript option does exactly this. It allows the user to point irqbalance
|
||||
toward an exacutable file that is run one for each irq deiscovered passing the
|
||||
sysfs path of the device and an irq vector as arguments. A zero exit code tells
|
||||
irqbalance to manage the irq as it normally would, while a non-zero exit tells
|
||||
irqbalance to ignore the interrupt entirely. This provides adminstrators a code
|
||||
point with which to exclude irqs dynamically based on any programatic
|
||||
informatino available, and to manage those irqs independently, etither via
|
||||
another irqbalance like program, or via static affinity setting.
|
||||
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
|
||||
Reesolves: http://code.google.com/p/irqbalance/issues/detail?id=33
|
||||
---
|
||||
classify.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
|
||||
irqbalance.1 | 11 +++++++++++
|
||||
irqbalance.c | 25 +++++++++++++++++++++----
|
||||
irqbalance.h | 1 +
|
||||
4 files changed, 79 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/classify.c b/classify.c
|
||||
index d59da7f..750d946 100644
|
||||
--- a/classify.c
|
||||
+++ b/classify.c
|
||||
@@ -207,6 +207,43 @@ out:
|
||||
return new;
|
||||
}
|
||||
|
||||
+static int check_for_irq_ban(char *path, int irq)
|
||||
+{
|
||||
+ char *cmd;
|
||||
+ int rc;
|
||||
+
|
||||
+ if (!banscript)
|
||||
+ return 0;
|
||||
+
|
||||
+ cmd = alloca(strlen(path)+strlen(banscript)+32);
|
||||
+ if (!cmd)
|
||||
+ return 0;
|
||||
+
|
||||
+ sprintf(cmd, "%s %s %d",banscript, path, irq);
|
||||
+ rc = system(cmd);
|
||||
+
|
||||
+ /*
|
||||
+ * The system command itself failed
|
||||
+ */
|
||||
+ if (rc == -1) {
|
||||
+ if (debug_mode)
|
||||
+ printf("%s failed, please check the --banscript option\n", cmd);
|
||||
+ else
|
||||
+ syslog(LOG_INFO, "%s failed, please check the --banscript option\n", cmd);
|
||||
+ return 0;
|
||||
+ }
|
||||
+
|
||||
+ if (WEXITSTATUS(rc)) {
|
||||
+ if (debug_mode)
|
||||
+ printf("irq %d is baned by %s\n", irq, banscript);
|
||||
+ else
|
||||
+ syslog(LOG_INFO, "irq %d is baned by %s\n", irq, banscript);
|
||||
+ return 1;
|
||||
+ }
|
||||
+ return 0;
|
||||
+
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* Figures out which interrupt(s) relate to the device we're looking at in dirname
|
||||
*/
|
||||
@@ -231,6 +268,10 @@ static void build_one_dev_entry(const char *dirname)
|
||||
irqnum = strtol(entry->d_name, NULL, 10);
|
||||
if (irqnum) {
|
||||
sprintf(path, "%s/%s", SYSDEV_DIR, dirname);
|
||||
+ if (check_for_irq_ban(path, irqnum)) {
|
||||
+ add_banned_irq(irqnum);
|
||||
+ continue;
|
||||
+ }
|
||||
new = add_one_irq_to_db(path, irqnum);
|
||||
if (!new)
|
||||
continue;
|
||||
@@ -253,6 +294,11 @@ static void build_one_dev_entry(const char *dirname)
|
||||
*/
|
||||
if (irqnum) {
|
||||
sprintf(path, "%s/%s", SYSDEV_DIR, dirname);
|
||||
+ if (check_for_irq_ban(path, irqnum)) {
|
||||
+ add_banned_irq(irqnum);
|
||||
+ goto done;
|
||||
+ }
|
||||
+
|
||||
new = add_one_irq_to_db(path, irqnum);
|
||||
if (!new)
|
||||
goto done;
|
||||
diff --git a/irqbalance.1 b/irqbalance.1
|
||||
index 978c7c1..63b0e26 100644
|
||||
--- a/irqbalance.1
|
||||
+++ b/irqbalance.1
|
||||
@@ -69,6 +69,17 @@ Add the specified irq list to the set of banned irqs. irqbalance will not affect
|
||||
the affinity of any irqs on the banned list, allowing them to be specified
|
||||
manually. This option is addative and can be specified multiple times
|
||||
|
||||
+.TP
|
||||
+.B --banscript=<script>
|
||||
+Execute the specified script for each irq that is discovered, passing the sysfs
|
||||
+path to the associated device as the first argument, and the irq vector as the
|
||||
+second. An exit value of 0 tells irqbalance that this interrupt should balanced
|
||||
+and managed as a normal irq, while a non-zero exit code indicates this irq
|
||||
+should be ignored by irqbalance completely (see --banirq above). Use of this
|
||||
+script provides users the ability to dynamically select which irqs get exluded
|
||||
+from balancing, and provides an opportunity for manual affinity setting in one
|
||||
+single code point.
|
||||
+
|
||||
.SH "ENVIRONMENT VARIABLES"
|
||||
.TP
|
||||
.B IRQBALANCE_ONESHOT
|
||||
diff --git a/irqbalance.c b/irqbalance.c
|
||||
index 5d40321..0184f0f 100644
|
||||
--- a/irqbalance.c
|
||||
+++ b/irqbalance.c
|
||||
@@ -1,5 +1,6 @@
|
||||
/*
|
||||
* Copyright (C) 2006, Intel Corporation
|
||||
+ * Copyright (C) 2012, Neil Horman <nhorman@tuxdriver.com>
|
||||
*
|
||||
* This file is part of irqbalance
|
||||
*
|
||||
@@ -45,6 +46,7 @@ extern cpumask_t banned_cpus;
|
||||
enum hp_e hint_policy = HINT_POLICY_SUBSET;
|
||||
unsigned long power_thresh = ULONG_MAX;
|
||||
unsigned long long cycle_count = 0;
|
||||
+char *banscript = NULL;
|
||||
|
||||
void sleep_approx(int seconds)
|
||||
{
|
||||
@@ -66,6 +68,8 @@ struct option lopts[] = {
|
||||
{"debug", 0, NULL, 'd'},
|
||||
{"hintpolicy", 1, NULL, 'h'},
|
||||
{"powerthresh", 1, NULL, 'p'},
|
||||
+ {"banirq", 1 , NULL, 'i'},
|
||||
+ {"banscript", 1, NULL, 'b'},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
@@ -79,9 +83,10 @@ static void parse_command_line(int argc, char **argv)
|
||||
{
|
||||
int opt;
|
||||
int longind;
|
||||
+ unsigned long val;
|
||||
|
||||
while ((opt = getopt_long(argc, argv,
|
||||
- "odh:p:b:",
|
||||
+ "odh:i:p:b:",
|
||||
lopts, &longind)) != -1) {
|
||||
|
||||
switch(opt) {
|
||||
@@ -193,6 +198,12 @@ int main(int argc, char** argv)
|
||||
if (argc>1 && strstr(argv[1],"--oneshot"))
|
||||
one_shot_mode=1;
|
||||
#endif
|
||||
+
|
||||
+ /*
|
||||
+ * Open the syslog connection
|
||||
+ */
|
||||
+ openlog(argv[0], 0, LOG_DAEMON);
|
||||
+
|
||||
if (getenv("IRQBALANCE_BANNED_CPUS")) {
|
||||
cpumask_parse_user(getenv("IRQBALANCE_BANNED_CPUS"), strlen(getenv("IRQBALANCE_BANNED_CPUS")), banned_cpus);
|
||||
}
|
||||
@@ -221,8 +232,16 @@ int main(int argc, char** argv)
|
||||
|
||||
|
||||
/* On single core UP systems irqbalance obviously has no work to do */
|
||||
- if (core_count<2)
|
||||
+ if (core_count<2) {
|
||||
+ char *msg = "Balancing is ineffective on systems with a "
|
||||
+ "single cache domain. Shutting down\n";
|
||||
+
|
||||
+ if (debug_mode)
|
||||
+ printf("%s", msg);
|
||||
+ else
|
||||
+ syslog(LOG_INFO, "%s", msg);
|
||||
exit(EXIT_SUCCESS);
|
||||
+ }
|
||||
/* On dual core/hyperthreading shared cache systems just do a one shot setup */
|
||||
if (cache_domain_count==1)
|
||||
one_shot_mode = 1;
|
||||
@@ -231,8 +250,6 @@ int main(int argc, char** argv)
|
||||
if (daemon(0,0))
|
||||
exit(EXIT_FAILURE);
|
||||
|
||||
- openlog(argv[0], 0, LOG_DAEMON);
|
||||
-
|
||||
#ifdef HAVE_LIBCAP_NG
|
||||
// Drop capabilities
|
||||
capng_clear(CAPNG_SELECT_BOTH);
|
||||
diff --git a/irqbalance.h b/irqbalance.h
|
||||
index 043bfe6..425e0dd 100644
|
||||
--- a/irqbalance.h
|
||||
+++ b/irqbalance.h
|
||||
@@ -68,6 +68,7 @@ extern int need_rescan;
|
||||
extern enum hp_e hint_policy;
|
||||
extern unsigned long long cycle_count;
|
||||
extern unsigned long power_thresh;
|
||||
+extern char *banscript;
|
||||
|
||||
/*
|
||||
* Numa node access routines
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,41 +0,0 @@
|
||||
From ab5ee2928b75f12a2340afe6778a106886509b4c Mon Sep 17 00:00:00 2001
|
||||
From: Petr Holasek <pholasek@redhat.com>
|
||||
Date: Thu, 12 Jul 2012 14:54:16 +0200
|
||||
Subject: [PATCH 6/8] irqbalance: cpu powersave code disabled when
|
||||
power_thresh is not set
|
||||
|
||||
When user doesn't set power_thresh argument no cpu can enter powersave
|
||||
mode. This patch should remove syslog clogging with pointless message
|
||||
about re-enabling all cpus for irq balancing.
|
||||
|
||||
Signed-off-by: Petr Holasek <pholasek@redhat.com>
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
irqlist.c | 4 ++--
|
||||
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/irqlist.c b/irqlist.c
|
||||
index c29ee84..e03aa7b 100644
|
||||
--- a/irqlist.c
|
||||
+++ b/irqlist.c
|
||||
@@ -112,7 +112,7 @@ static void migrate_overloaded_irqs(struct topo_obj *obj, void *data)
|
||||
if (obj->load <= info->avg_load) {
|
||||
if ((obj->load + info->std_deviation) <= info->avg_load) {
|
||||
info->num_under++;
|
||||
- if (!info->powersave)
|
||||
+ if (power_thresh != ULONG_MAX && !info->powersave)
|
||||
if (!obj->powersave_mode)
|
||||
info->powersave = obj;
|
||||
} else
|
||||
@@ -172,7 +172,7 @@ void update_migration_status(void)
|
||||
{
|
||||
struct load_balance_info info;
|
||||
find_overloaded_objs(cpus, info);
|
||||
- if (cycle_count > 5) {
|
||||
+ if (power_thresh != ULONG_MAX && cycle_count > 5) {
|
||||
if (!info.num_over && (info.num_under >= power_thresh) && info.powersave) {
|
||||
syslog(LOG_INFO, "cpu %d entering powersave mode\n", info.powersave->number);
|
||||
info.powersave->powersave_mode = 1;
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,103 +0,0 @@
|
||||
From 7475c3e26d14bb210eb3524396adef77021e696f Mon Sep 17 00:00:00 2001
|
||||
From: Paolo Bonzini <pbonzini@redhat.com>
|
||||
Date: Tue, 7 Aug 2012 02:54:34 -0400
|
||||
Subject: [PATCH 7/8] apply affinity hint also if the current policy is subset
|
||||
|
||||
--hintpolicy=subset chooses an object that has a non-empty intersection
|
||||
with the affinity hint, but it never restricts the object's CPU mask
|
||||
with the hint itself. As a result, there is no guarantee that the
|
||||
object's CPU mask is a subset of the hint.
|
||||
|
||||
This is visible for interrupts whose balancing policy is not BALANCE_CORE.
|
||||
For example, if there is only one cache domain and the interrupt's policy
|
||||
is BALANCE_CACHE, the chosen object will correspond to "all CPUs" and
|
||||
the affinity hint will be effectively ignored.
|
||||
|
||||
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
activate.c | 45 ++++++++++++++++++++++++++++++++++++++-------
|
||||
1 file changed, 38 insertions(+), 7 deletions(-)
|
||||
|
||||
diff --git a/activate.c b/activate.c
|
||||
index 292c44a..97d84a8 100644
|
||||
--- a/activate.c
|
||||
+++ b/activate.c
|
||||
@@ -1,5 +1,6 @@
|
||||
/*
|
||||
* Copyright (C) 2006, Intel Corporation
|
||||
+ * Copyright (C) 2012, Neil Horman <nhorman@tuxdriver.com>
|
||||
*
|
||||
* This file is part of irqbalance
|
||||
*
|
||||
@@ -31,17 +32,53 @@
|
||||
|
||||
#include "irqbalance.h"
|
||||
|
||||
+static int check_affinity(struct irq_info *info, cpumask_t applied_mask)
|
||||
+{
|
||||
+ cpumask_t current_mask;
|
||||
+ char buf[PATH_MAX];
|
||||
+ char *line = NULL;
|
||||
+ size_t size = 0;
|
||||
+ FILE *file;
|
||||
+
|
||||
+ sprintf(buf, "/proc/irq/%i/smp_affinity", info->irq);
|
||||
+ file = fopen(buf, "r");
|
||||
+ if (!file)
|
||||
+ return 1;
|
||||
+ if (getline(&line, &size, file)==0) {
|
||||
+ free(line);
|
||||
+ fclose(file);
|
||||
+ return 1;
|
||||
+ }
|
||||
+ cpumask_parse_user(line, strlen(line), current_mask);
|
||||
+ fclose(file);
|
||||
+ free(line);
|
||||
+
|
||||
+ return cpus_equal(applied_mask, current_mask);
|
||||
+}
|
||||
|
||||
static void activate_mapping(struct irq_info *info, void *data __attribute__((unused)))
|
||||
{
|
||||
char buf[PATH_MAX];
|
||||
FILE *file;
|
||||
cpumask_t applied_mask;
|
||||
+ int valid_mask = 0;
|
||||
+
|
||||
+ if ((hint_policy == HINT_POLICY_EXACT) &&
|
||||
+ (!cpus_empty(info->affinity_hint))) {
|
||||
+ applied_mask = info->affinity_hint;
|
||||
+ valid_mask = 1;
|
||||
+ } else if (info->assigned_obj) {
|
||||
+ applied_mask = info->assigned_obj->mask;
|
||||
+ valid_mask = 1;
|
||||
+ if ((hint_policy == HINT_POLICY_SUBSET) &&
|
||||
+ (!cpus_empty(info->affinity_hint)))
|
||||
+ cpus_and(applied_mask, applied_mask, info->affinity_hint);
|
||||
+ }
|
||||
|
||||
/*
|
||||
* only activate mappings for irqs that have moved
|
||||
*/
|
||||
- if (!info->moved)
|
||||
+ if (!info->moved && (!valid_mask || check_affinity(info, applied_mask)))
|
||||
return;
|
||||
|
||||
if (!info->assigned_obj)
|
||||
@@ -53,12 +90,6 @@ static void activate_mapping(struct irq_info *info, void *data __attribute__((un
|
||||
if (!file)
|
||||
return;
|
||||
|
||||
- if ((hint_policy == HINT_POLICY_EXACT) &&
|
||||
- (!cpus_empty(info->affinity_hint)))
|
||||
- applied_mask = info->affinity_hint;
|
||||
- else
|
||||
- applied_mask = info->assigned_obj->mask;
|
||||
-
|
||||
cpumask_scnprintf(buf, PATH_MAX, applied_mask);
|
||||
fprintf(file, "%s", buf);
|
||||
fclose(file);
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,31 +0,0 @@
|
||||
From 8285d9a1cac9cf74130ae71df0ddb4ed14122544 Mon Sep 17 00:00:00 2001
|
||||
From: Petr Holasek <pholasek@redhat.com>
|
||||
Date: Tue, 21 Aug 2012 14:45:57 +0200
|
||||
Subject: [PATCH 8/8] irqlist: added check for avoidance of division by zero
|
||||
|
||||
When counting load_sources, its occasionally possible to have one of our object
|
||||
lists be zero (if you exlude all the cpus from balancing for instance). In
|
||||
these cases load_sources can be zero, and that will cause a SIGFPE. Avoid that
|
||||
by making sure that load_sources is always at least 1.
|
||||
|
||||
Signed-off-by: Petr Holasek <pholasek@redhat.com>
|
||||
Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
irqlist.c | 1 +
|
||||
1 file changed, 1 insertion(+)
|
||||
|
||||
diff --git a/irqlist.c b/irqlist.c
|
||||
index e03aa7b..c0e0d2b 100644
|
||||
--- a/irqlist.c
|
||||
+++ b/irqlist.c
|
||||
@@ -160,6 +160,7 @@ static void clear_powersave_mode(struct topo_obj *obj, void *data __attribute__(
|
||||
int ___load_sources;\
|
||||
memset(&(info), 0, sizeof(struct load_balance_info));\
|
||||
for_each_object((name), gather_load_stats, &(info));\
|
||||
+ (info).load_sources = ((info).load_sources == 0) ? 1 : ((info).load_sources);\
|
||||
(info).avg_load = (info).total_load / (info).load_sources;\
|
||||
for_each_object((name), compute_deviations, &(info));\
|
||||
___load_sources = ((info).load_sources == 1) ? 1 : ((info).load_sources - 1);\
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,90 +0,0 @@
|
||||
From 1523a7830cb2670cb531a5fdea86885eaa648eaf Mon Sep 17 00:00:00 2001
|
||||
From: Neil Horman <nhorman@tuxdriver.com>
|
||||
Date: Mon, 2 Jul 2012 13:27:14 -0400
|
||||
Subject: [PATCH] Make irqbalance scan for new irqs when it detects new irqs
|
||||
|
||||
Like cpu hotplug, irqbalance needs to rebuild its topo map and irq db when it
|
||||
detects new irqs in the system. This patch adds that ability
|
||||
|
||||
Resolves: http://code.google.com/p/irqbalance/issues/detail?id=32
|
||||
|
||||
Singed-off-by: Neil Horman <nhorman@tuxdriver.com>
|
||||
---
|
||||
irqbalance.c | 6 +++---
|
||||
irqbalance.h | 2 +-
|
||||
procinterrupts.c | 14 ++++++++++++--
|
||||
3 files changed, 16 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/irqbalance.c b/irqbalance.c
|
||||
index 1fcc367..7ef72af 100644
|
||||
--- a/irqbalance.c
|
||||
+++ b/irqbalance.c
|
||||
@@ -46,7 +46,7 @@ int one_shot_mode;
|
||||
int debug_mode;
|
||||
int foreground_mode;
|
||||
int numa_avail;
|
||||
-int need_cpu_rescan;
|
||||
+int need_rescan;
|
||||
extern cpumask_t banned_cpus;
|
||||
enum hp_e hint_policy = HINT_POLICY_SUBSET;
|
||||
unsigned long power_thresh = ULONG_MAX;
|
||||
@@ -301,8 +301,8 @@ int main(int argc, char** argv)
|
||||
parse_proc_stat();
|
||||
|
||||
/* cope with cpu hotplug -- detected during /proc/interrupts parsing */
|
||||
- if (need_cpu_rescan) {
|
||||
- need_cpu_rescan = 0;
|
||||
+ if (need_rescan) {
|
||||
+ need_rescan = 0;
|
||||
/* if there's a hotplug event we better turn off power mode for a bit until things settle */
|
||||
power_mode = 0;
|
||||
if (debug_mode)
|
||||
diff --git a/irqbalance.h b/irqbalance.h
|
||||
index b9b1f06..8ec7c23 100644
|
||||
--- a/irqbalance.h
|
||||
+++ b/irqbalance.h
|
||||
@@ -64,7 +64,7 @@ enum hp_e {
|
||||
extern int debug_mode;
|
||||
extern int one_shot_mode;
|
||||
extern int power_mode;
|
||||
-extern int need_cpu_rescan;
|
||||
+extern int need_rescan;
|
||||
extern enum hp_e hint_policy;
|
||||
extern unsigned long long cycle_count;
|
||||
extern unsigned long power_thresh;
|
||||
diff --git a/procinterrupts.c b/procinterrupts.c
|
||||
index 8ffe30c..f1d6745 100644
|
||||
--- a/procinterrupts.c
|
||||
+++ b/procinterrupts.c
|
||||
@@ -83,8 +83,18 @@ void parse_proc_interrupts(void)
|
||||
c++;
|
||||
number = strtoul(line, NULL, 10);
|
||||
info = get_irq_info(number);
|
||||
- if (!info)
|
||||
+ if (!info) {
|
||||
+ /*
|
||||
+ * If this is our 0th pass through this routine
|
||||
+ * this is an irq that wasn't reported in sysfs
|
||||
+ * and we should just add it. If we've been running
|
||||
+ * a while then this irq just appeared and its time
|
||||
+ * to rescan our irqs
|
||||
+ */
|
||||
+ if (cycle_count)
|
||||
+ need_rescan = 1;
|
||||
info = add_misc_irq(number);
|
||||
+ }
|
||||
|
||||
count = 0;
|
||||
cpunr = 0;
|
||||
@@ -100,7 +110,7 @@ void parse_proc_interrupts(void)
|
||||
cpunr++;
|
||||
}
|
||||
if (cpunr != core_count)
|
||||
- need_cpu_rescan = 1;
|
||||
+ need_rescan = 1;
|
||||
|
||||
info->last_irq_count = info->irq_count;
|
||||
info->irq_count = count;
|
||||
--
|
||||
1.7.11.4
|
||||
|
@ -1,13 +1,13 @@
|
||||
Name: irqbalance
|
||||
Version: 1.0.3
|
||||
Release: 5%{?dist}
|
||||
Version: 1.0.4
|
||||
Release: 1%{?dist}
|
||||
Epoch: 2
|
||||
Summary: IRQ balancing daemon
|
||||
|
||||
Group: System Environment/Base
|
||||
License: GPLv2
|
||||
Url: http://irqbalance.org/
|
||||
Source0: http://irqbalance.googlecode.com/files/irqbalance-%{version}.tar.gz
|
||||
Source0: http://irqbalance.googlecode.com/files/irqbalance-%{version}.tar.bz2
|
||||
Source1: irqbalance.sysconfig
|
||||
|
||||
BuildRequires: autoconf automake libtool libcap-ng
|
||||
@ -23,29 +23,12 @@ Requires(preun):systemd-units
|
||||
|
||||
ExclusiveArch: %{ix86} x86_64 ia64 ppc ppc64 %{arm}
|
||||
|
||||
Patch1: 0001-Add-sample-irqbalance-environment-file.patch
|
||||
Patch2: 0002-introduce-banirq-option.patch
|
||||
Patch3: 0003-When-IRQBALANCE_BANNED_CPUS-is-set-proc-stat-is-not-.patch
|
||||
Patch4: 0004-Make-irqbalance-scan-for-new-irqs-when-it-detects-ne.patch
|
||||
Patch5: 0005-Add-banscript-option.patch
|
||||
Patch6: 0006-irqbalance-cpu-powersave-code-disabled-when-power_th.patch
|
||||
Patch7: 0007-apply-affinity-hint-also-if-the-current-policy-is-su.patch
|
||||
Patch8: 0008-irqlist-added-check-for-avoidance-of-division-by-zer.patch
|
||||
|
||||
%description
|
||||
irqbalance is a daemon that evenly distributes IRQ load across
|
||||
multiple CPUs for enhanced performance.
|
||||
|
||||
%prep
|
||||
%setup -q
|
||||
%patch1 -p1
|
||||
%patch2 -p1
|
||||
%patch3 -p1
|
||||
%patch4 -p1
|
||||
%patch5 -p1
|
||||
%patch6 -p1
|
||||
%patch7 -p1
|
||||
%patch8 -p1
|
||||
|
||||
%build
|
||||
%{configure}
|
||||
@ -83,6 +66,9 @@ fi
|
||||
/sbin/chkconfig --del irqbalance >/dev/null 2>&1 || :
|
||||
|
||||
%changelog
|
||||
* Mon Aug 27 2012 Petr Holasek <pholasek@redhat.com> - 2:1.0.4-1
|
||||
- Rebased to version 1.0.4
|
||||
|
||||
* Wed Aug 22 2012 Petr Holasek <pholasek@redhat.com> - 2:1.0.3-5
|
||||
- Make irqbalance scan for new irqs when it detects new irqs (bz832815)
|
||||
- Fixes SIGFPE crash for some banning configuration (bz849792)
|
||||
|
Loading…
Reference in New Issue
Block a user