diff options
author | Matthew D Fleming <mdf@FreeBSD.org> | 2011-07-08 20:41:12 +0000 |
---|---|---|
committer | Matthew D Fleming <mdf@FreeBSD.org> | 2011-07-08 20:41:12 +0000 |
commit | b5bd50ae40085c9fa935b1e89f5c70eb0558bbf7 (patch) | |
tree | bd0780db425378e454850c756d18521fb1d5bc31 /sys/kern/kern_fail.c | |
parent | 0894a9bca6ac7c9a06d0c33daee62ff5db47ef19 (diff) | |
download | src-b5bd50ae40085c9fa935b1e89f5c70eb0558bbf7.tar.gz src-b5bd50ae40085c9fa935b1e89f5c70eb0558bbf7.zip |
Add an option to have a fail point term only execute when run by a
specified pid. This is helpful for automated testing involving a global
knob that would otherwise be executed by many other threads.
MFC after: 1 week
Notes
Notes:
svn path=/head/; revision=223876
Diffstat (limited to 'sys/kern/kern_fail.c')
-rw-r--r-- | sys/kern/kern_fail.c | 20 |
1 files changed, 19 insertions, 1 deletions
diff --git a/sys/kern/kern_fail.c b/sys/kern/kern_fail.c index 6a96534244d5..f1924718ef55 100644 --- a/sys/kern/kern_fail.c +++ b/sys/kern/kern_fail.c @@ -60,6 +60,7 @@ __FBSDID("$FreeBSD$"); #include <sys/lock.h> #include <sys/malloc.h> #include <sys/mutex.h> +#include <sys/proc.h> #include <sys/sbuf.h> #include <machine/stdarg.h> @@ -114,7 +115,7 @@ struct fail_point_entry { int fe_arg; /**< argument to type (e.g. return value) */ int fe_prob; /**< likelihood of firing in millionths */ int fe_count; /**< number of times to fire, 0 means always */ - + pid_t fe_pid; /**< only fail for this process */ TAILQ_ENTRY(fail_point_entry) fe_entries; /**< next entry in fail point */ }; @@ -227,6 +228,8 @@ fail_point_eval_nontrivial(struct fail_point *fp, int *return_value) if (ent->fe_prob < PROB_MAX && ent->fe_prob < random() % PROB_MAX) continue; + if (ent->fe_pid != NO_PID && ent->fe_pid != curproc->p_pid) + continue; switch (ent->fe_type) { case FAIL_POINT_PANIC: @@ -315,6 +318,8 @@ fail_point_get(struct fail_point *fp, struct sbuf *sb) sbuf_printf(sb, "%s", fail_type_strings[ent->fe_type].name); if (ent->fe_arg) sbuf_printf(sb, "(%d)", ent->fe_arg); + if (ent->fe_pid != NO_PID) + sbuf_printf(sb, "[pid %d]", ent->fe_pid); if (TAILQ_NEXT(ent, fe_entries)) sbuf_printf(sb, "->"); } @@ -451,6 +456,7 @@ parse_term(struct fail_point_entries *ents, char *p) ent = fp_malloc(sizeof *ent, M_WAITOK | M_ZERO); ent->fe_prob = PROB_MAX; + ent->fe_pid = NO_PID; TAILQ_INSERT_TAIL(ents, ent, fe_entries); /* @@ -458,6 +464,7 @@ parse_term(struct fail_point_entries *ents, char *p) * ( (<float> "%") | (<integer> "*" ) )* * <type> * [ "(" <integer> ")" ] + * [ "[pid " <integer> "]" ] */ /* ( (<float> "%") | (<integer> "*" ) )* */ @@ -500,6 +507,17 @@ parse_term(struct fail_point_entries *ents, char *p) if (*p++ != ')') return (NULL); + /* [ "[pid " <integer> "]" ] */ +#define PID_STRING "[pid " + if (strncmp(p, PID_STRING, sizeof(PID_STRING) - 1) != 0) + return (p); + p += sizeof(PID_STRING) - 1; + if (!isdigit(*p)) + return (NULL); + ent->fe_pid = strtol(p, &p, 0); + if (*p++ != ']') + return (NULL); + return (p); } |