summaryrefslogtreecommitdiff
path: root/usr/src/cmd/picl
diff options
context:
space:
mode:
authorMichael Bergknoff <Michael.Bergknoff@Sun.COM>2010-01-12 10:02:48 -0800
committerMichael Bergknoff <Michael.Bergknoff@Sun.COM>2010-01-12 10:02:48 -0800
commit34f1a571c0d0c682a4a70b97b1e62430aa630559 (patch)
tree1e77f3e7cfe9927e741bbeb5d555381b5b8abd77 /usr/src/cmd/picl
parent555c8a42842325f69996b42d0fb5240d1a7561ab (diff)
downloadillumos-joyent-34f1a571c0d0c682a4a70b97b1e62430aa630559.tar.gz
6871957 picl hangs on a LDom guest
Diffstat (limited to 'usr/src/cmd/picl')
-rw-r--r--usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.c33
-rw-r--r--usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.h5
2 files changed, 36 insertions, 2 deletions
diff --git a/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.c b/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.c
index 1a1c0c1d1d..62e97e1a00 100644
--- a/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.c
+++ b/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.c
@@ -20,7 +20,7 @@
*/
/*
- * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2010 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -41,6 +41,7 @@
#include <synch.h>
#include <errno.h>
#include <time.h>
+#include <signal.h>
#include <picldefs.h>
#include <picl.h>
@@ -396,6 +397,9 @@ snmpplugin_fini(void)
(void) cond_signal(&rebuild_tree_cv);
(void) mutex_unlock(&rebuild_tree_lock);
+ /* send SIGUSR1 to get tree_builder out of a blocked system call */
+ (void) thr_kill(tree_builder_thr_id, SIGUSR1);
+
/* reap the thread */
(void) thr_join(tree_builder_thr_id, NULL, NULL);
@@ -412,6 +416,20 @@ snmpplugin_fini(void)
}
/*ARGSUSED*/
+static void
+usr1_handler(int sig, siginfo_t *siginfo, void *sigctx)
+{
+ /*
+ * Nothing to do here.
+ * The act of catching the signal causes any cond_wait() or blocked
+ * system call to return EINTR. This is used to trigger early exit from
+ * the tree builder thread which may be blocked in snmp_init. More work
+ * would be required to allow early exit if the tree builder thread is
+ * already in its main processing loop and not blocked in cond_wait.
+ */
+}
+
+/*ARGSUSED*/
static void *
tree_builder(void *arg)
{
@@ -419,6 +437,19 @@ tree_builder(void *arg)
picl_nodehdl_t root_node;
picl_nodehdl_t physplat_root;
picl_nodehdl_t old_physplat_root;
+ struct sigaction act;
+
+ /*
+ * catch SIGUSR1 to allow early exit from snmp_init which may block
+ * indefinitely in a guest domain.
+ */
+ act.sa_sigaction = usr1_handler;
+ (void) sigemptyset(&act.sa_mask);
+ act.sa_flags = 0;
+ if (sigaction(SIGUSR1, &act, NULL) == -1) {
+ syslog(LOG_ERR, SIGACT_FAILED, strsignal(SIGUSR1),
+ strerror(errno));
+ }
/*
* Initialize SNMP service
diff --git a/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.h b/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.h
index f1a1a1da46..8bd7d87db1 100644
--- a/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.h
+++ b/usr/src/cmd/picl/plugins/sun4v/snmp/snmpplugin.h
@@ -20,7 +20,7 @@
*/
/*
- * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2010 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -193,6 +193,9 @@ void snmpplugin_fini(void);
#define SNMPP_LINK_RESET \
gettext("PICL snmpplugin: snmp ds reset happened, rebuilding tree\n")
+#define SIGACT_FAILED \
+ gettext("PICL snmpplugin: Failed to install signal handler for %s: %s\n")
+
#ifdef SNMPPLUGIN_DEBUG
#define SNMPPLUGIN_DBLOCK_SZ 4096
#define SNMPPLUGIN_DMAX_LINE 80