diff options
-rw-r--r-- | ChangeLog | 8 | ||||
-rw-r--r-- | runtime/ChangeLog | 4 | ||||
-rw-r--r-- | runtime/staprun/ChangeLog | 7 | ||||
-rw-r--r-- | runtime/staprun/common.c | 19 | ||||
-rw-r--r-- | runtime/staprun/ctl.c | 3 | ||||
-rw-r--r-- | runtime/staprun/relay.c | 6 | ||||
-rw-r--r-- | runtime/staprun/relay_old.c | 12 | ||||
-rw-r--r-- | runtime/staprun/staprun.h | 1 | ||||
-rw-r--r-- | runtime/uprobes/uprobes.c | 51 | ||||
-rw-r--r-- | runtime/user/ChangeLog | 62 | ||||
-rw-r--r-- | runtime/user/README | 3 | ||||
-rw-r--r-- | runtime/user/alloc.c | 52 | ||||
-rw-r--r-- | runtime/user/copy.c | 7 | ||||
-rw-r--r-- | runtime/user/emul.h | 121 | ||||
-rw-r--r-- | runtime/user/io.c | 80 | ||||
-rw-r--r-- | runtime/user/print.c | 96 | ||||
-rwxr-xr-x | runtime/user/recreate_links | 15 | ||||
-rw-r--r-- | runtime/user/runtime.h | 56 | ||||
-rw-r--r-- | runtime/user/test.h | 247 | ||||
-rw-r--r-- | tapset/ChangeLog | 33 | ||||
-rw-r--r-- | tapset/aux_syscalls.stp | 28 | ||||
-rw-r--r-- | tapset/queue_stats.stp | 1 | ||||
-rw-r--r-- | tapset/rpc.stp | 4 | ||||
-rw-r--r-- | tapset/syscalls2.stp | 2 | ||||
-rw-r--r-- | testsuite/systemtap.syscall/ChangeLog | 11 | ||||
-rw-r--r-- | testsuite/systemtap.syscall/rt_signal.c | 17 | ||||
-rw-r--r-- | testsuite/systemtap.syscall/signal.c | 46 |
27 files changed, 202 insertions, 790 deletions
@@ -1,3 +1,11 @@ +2007-10-09 Jim Keniston <jkenisto@us.ibm.com> + + PR 5083 + * runtime/uprobes/uprobes.c: Adjust module ref-count + when creating or removing uprobe_process, so "rmmod + --wait uprobes" waits as needed until uretprobed + functions return. + 2007-10-08 Jim Keniston <jkenisto@us.ibm.com> PR 5079 diff --git a/runtime/ChangeLog b/runtime/ChangeLog index a442eb18..65702a00 100644 --- a/runtime/ChangeLog +++ b/runtime/ChangeLog @@ -1,3 +1,7 @@ +2007-10-09 Martin Hunt <hunt@redhat.com> + + * user/*: Removed obsolete userspace test files. + 2007-10-02 Frank Ch. Eigler <fche@elastic.org> PR 5041 diff --git a/runtime/staprun/ChangeLog b/runtime/staprun/ChangeLog index cebaeb2c..4e23c424 100644 --- a/runtime/staprun/ChangeLog +++ b/runtime/staprun/ChangeLog @@ -1,3 +1,10 @@ +2007-10-09 Martin Hunt <hunt@redhat.com> + + * common.c (set_clexec): New. + * staprun.h: Add prototype for set_clexec. + * relay*.c, ctl.c: Call set_clexec after + file opens. + 2007-09-14 Martin Hunt <hunt@redhat.com> * ctl.c (init_ctl_channel): Return 1 if the ctl file opened diff --git a/runtime/staprun/common.c b/runtime/staprun/common.c index d3f8835a..47778efd 100644 --- a/runtime/staprun/common.c +++ b/runtime/staprun/common.c @@ -315,3 +315,22 @@ int send_request(int type, void *data, int len) memcpy(&buf[4], data, len); return write(control_channel, buf, len+4); } + +/* + * set FD_CLOEXEC for any file descriptor + */ +int set_clexec(int fd) +{ + int val; + if ((val = fcntl(fd, F_GETFD, 0)) < 0) + goto err; + + if ((val = fcntl(fd, F_SETFD, val | FD_CLOEXEC)) < 0) + goto err; + + return 0; +err: + perr("fcntl failed"); + close(fd); + return -1; +} diff --git a/runtime/staprun/ctl.c b/runtime/staprun/ctl.c index d0b07260..7fe57206 100644 --- a/runtime/staprun/ctl.c +++ b/runtime/staprun/ctl.c @@ -36,6 +36,9 @@ int init_ctl_channel(void) perr("Couldn't open control channel '%s'", buf); return -1; } + if (set_clexec(control_channel) < 0) + return -1; + return old_transport; } diff --git a/runtime/staprun/relay.c b/runtime/staprun/relay.c index 30c4ce1e..538d027c 100644 --- a/runtime/staprun/relay.c +++ b/runtime/staprun/relay.c @@ -148,7 +148,7 @@ int init_relayfs(void) return -1; dbug(2, "attempting to open %s\n", buf); relay_fd[i] = open(buf, O_RDONLY | O_NONBLOCK); - if (relay_fd[i] < 0) + if (relay_fd[i] < 0 || set_clexec(relay_fd[i]) < 0) break; } ncpus = i; @@ -184,6 +184,8 @@ int init_relayfs(void) perr("Couldn't open output file %s", buf); return -1; } + if (set_clexec(out_fd[i]) < 0) + return -1; } } else { /* stream mode */ @@ -193,6 +195,8 @@ int init_relayfs(void) perr("Couldn't open output file %s", outfile_name); return -1; } + if (set_clexec(out_fd[i]) < 0) + return -1; } else out_fd[0] = STDOUT_FILENO; diff --git a/runtime/staprun/relay_old.c b/runtime/staprun/relay_old.c index 3f65acbb..f138aee5 100644 --- a/runtime/staprun/relay_old.c +++ b/runtime/staprun/relay_old.c @@ -86,7 +86,7 @@ static int open_relayfs_files(int cpu, const char *relay_filebase, const char *p return -1; dbug(2, "Opening %s.\n", tmp); relay_fd[cpu] = open(tmp, O_RDONLY | O_NONBLOCK); - if (relay_fd[cpu] < 0) { + if (relay_fd[cpu] < 0 || set_clexec(relay_fd[cpu]) < 0) { relay_fd[cpu] = 0; return 0; } @@ -99,6 +99,10 @@ static int open_relayfs_files(int cpu, const char *relay_filebase, const char *p perr("Couldn't open proc file %s", tmp); goto err1; } + if (set_clexec(relay_fd[cpu]) < 0) { + relay_fd[cpu] = 0; + return -1; + } if (outfile_name) { /* special case: for testing we sometimes want to @@ -118,6 +122,10 @@ static int open_relayfs_files(int cpu, const char *relay_filebase, const char *p perr("Couldn't open output file %s", tmp); goto err2; } + if (set_clexec(fileno(percpu_tmpfile[cpu])) < 0) { + perr("Couldn't open output file %s", tmp); + goto err2; + } total_bufsize = subbuf_size * n_subbufs; relay_buffer[cpu] = mmap(NULL, total_bufsize, PROT_READ, @@ -243,7 +251,7 @@ int init_oldrelayfs(void) if (!bulkmode) { if (outfile_name) { out_fd[0] = open (outfile_name, O_CREAT|O_TRUNC|O_WRONLY, 0666); - if (out_fd[0] < 0) { + if (out_fd[0] < 0 || set_clexec(out_fd[0]) < 0) { perr("Couldn't open output file '%s'", outfile_name); return -1; } diff --git a/runtime/staprun/staprun.h b/runtime/staprun/staprun.h index 1b0f3221..685de294 100644 --- a/runtime/staprun/staprun.h +++ b/runtime/staprun/staprun.h @@ -152,6 +152,7 @@ void parse_args(int argc, char **argv); void usage(char *prog); void parse_modpath(const char *); void setup_signals(void); +int set_clexec(int fd); /* * variables diff --git a/runtime/uprobes/uprobes.c b/runtime/uprobes/uprobes.c index 16c5e046..01b40670 100644 --- a/runtime/uprobes/uprobes.c +++ b/runtime/uprobes/uprobes.c @@ -475,10 +475,16 @@ static void uprobe_free_process(struct uprobe_process *uproc) * Decrement uproc's ref count. If it's zero, free uproc and return 1. * Else return 0. If uproc is locked, don't call this; use * uprobe_decref_process(). + * + * If we free uproc, we also decrement the ref-count on the uprobes + * module, if any. If somebody is doing "rmmod --wait uprobes", this + * function could schedule removal of the module. Therefore, don't call + * this function and then sleep in uprobes code, unless you know you'll + * return with the module ref-count > 0. */ static int uprobe_put_process(struct uprobe_process *uproc) { - int ret = 0; + int freed = 0; if (atomic_dec_and_test(&uproc->refcount)) { lock_uproc_table(); down_write(&uproc->rwsem); @@ -491,11 +497,13 @@ static int uprobe_put_process(struct uprobe_process *uproc) up_write(&uproc->rwsem); } else { uprobe_free_process(uproc); - ret = 1; + freed = 1; } unlock_uproc_table(); } - return ret; + if (freed) + module_put(THIS_MODULE); + return freed; } static struct uprobe_kimg *uprobe_mk_kimg(struct uprobe *u) @@ -842,10 +850,18 @@ int register_uprobe(struct uprobe *u) if (uproc) unlock_uproc_table(); else { + /* Creating a new uprobe_process. Ref-count the module. */ + if (!try_module_get(THIS_MODULE)) { + /* uprobes.ko is being removed. */ + ret = -ENOSYS; + unlock_uproc_table(); + goto fail_tsk; + } uproc = uprobe_mk_process(p); if (IS_ERR(uproc)) { ret = (int) PTR_ERR(uproc); unlock_uproc_table(); + module_put(THIS_MODULE); goto fail_tsk; } /* Hold uproc_mutex until we've added uproc to uproc_table. */ @@ -955,6 +971,7 @@ fail_uproc: if (uproc_is_new) { uprobe_free_process(uproc); unlock_uproc_table(); + module_put(THIS_MODULE); } else { up_write(&uproc->rwsem); uprobe_put_process(uproc); @@ -1063,8 +1080,9 @@ static struct task_struct *find_surviving_thread(struct uprobe_process *uproc) /* * Run all the deferred_registrations previously queued by the current utask. - * Runs with no locks or mutexes held. The current utask could disappear - * as the result of unregister_u*probe() called here. + * Runs with no locks or mutexes held. The current utask's uprobe_process + * is ref-counted, so they won't disappear as the result of + * unregister_u*probe() called here. */ static void uprobe_run_def_regs(struct list_head *drlist) { @@ -1577,7 +1595,7 @@ static u32 uprobe_report_signal(struct utrace_attached_engine *engine, u32 ret; unsigned long probept; int hit_uretprobe_trampoline = 0; - LIST_HEAD(def_reg_list); + int registrations_deferred = 0; utask = rcu_dereference((struct uprobe_task *)engine->data); BUG_ON(!utask); @@ -1673,12 +1691,16 @@ bkpt_done: utask->active_probe = NULL; - /* - * The deferred_registrations list accumulates in utask, - * but utask could go away when we uprobe_run_def_regs. - * So switch the list head to a local variable. - */ - list_splice_init(&utask->deferred_registrations, &def_reg_list); + if (!list_empty(&utask->deferred_registrations)) { + /* + * Make sure utask doesn't go away before we run + * the deferred registrations. This also keeps + * the module from getting unloaded before we're + * ready. + */ + registrations_deferred = 1; + uprobe_get_process(uproc); + } ret = UTRACE_ACTION_HIDE | UTRACE_SIGNAL_IGN | UTRACE_ACTION_NEWSTATE; @@ -1698,7 +1720,10 @@ bkpt_done: */ uprobe_put_process(uproc); - uprobe_run_def_regs(&def_reg_list); + if (registrations_deferred) { + uprobe_run_def_regs(&utask->deferred_registrations); + uprobe_put_process(uproc); + } break; default: goto no_interest; diff --git a/runtime/user/ChangeLog b/runtime/user/ChangeLog deleted file mode 100644 index 90041891..00000000 --- a/runtime/user/ChangeLog +++ /dev/null @@ -1,62 +0,0 @@ -2006-09-26 David Smith <dsmith@redhat.com> - - * io.c: Changed 'stpd' references to 'staprun'. - * print.c: Ditto. - -2006-03-30 Martin Hunt <hunt@redhat.com> - - * emul.h (kmalloc_node): New. - -2006-01-25 Martin Hunt <hunt@redhat.com> - - * alloc.c (_stp_alloc_percpu): New function. - (_stp_free_percpu): New function. - -2005-12-14 Martin Hunt <hunt@redhat.com> - - * emul.h: Add fake spinlock funcs. - -2005-12-07 Martin Hunt <hunt@redhat.com> - - * alloc.c: Remove all unused functions. - * io.c: Add vprintf() prototype. - -2005-11-29 Martin Hunt <hunt@redhat.com> - - * recreate_links: Remove links to deleted files. - -2005-11-08 Martin Hunt <hunt@redhat.com> - - * recreate_links: Add link to pmap-gen.c - * print.c (next_fmt): Remove unneeded dbug(). - * alloc.c: Update to reflect changes to runtime/alloc.c. - -2005-10-26 Martin Hunt <hunt@redhat.com> - - * recreate_links: Add link to map-gen.c. - -2005-09-09 Martin Hunt <hunt@redhat.com> - - * runtime.h: Add arith.c - * recreate_links: Add arith.c - * emul.h: Define jiffies so arith.c will compile. - -2005-08-31 Martin Hunt <hunt@redhat.com> - - * emul.h (_stp_kallsyms_lookup): Renamed from kallsyms_lookup. - * runtime.h: Add prototype for exit(); - * copy.c: New file. Just some empty functions. - -2005-08-19 Martin Hunt <hunt@redhat.com> - - * runtime.h: Include io.c. - -2005-07-14 Frank Ch. Eigler <fche@redhat.com> - - * alloc.c (_stp_error): Rename, to avoid name collision with ../io.c. - -2005-06-22 Martin Hunt <hunt@redhat.com> - - * runtime.h: Include config.h first then redefine CONFIG_SMP - and NR_CPUS. - diff --git a/runtime/user/README b/runtime/user/README deleted file mode 100644 index b5f8f81a..00000000 --- a/runtime/user/README +++ /dev/null @@ -1,3 +0,0 @@ -These files are for user-space testing of SystemTap code. - -You need to run ./recreate_links here before running tests. diff --git a/runtime/user/alloc.c b/runtime/user/alloc.c deleted file mode 100644 index 361e7d98..00000000 --- a/runtime/user/alloc.c +++ /dev/null @@ -1,52 +0,0 @@ -#ifndef _ALLOC_C_ -#define _ALLOC_C_ - -/* emulated memory allocation functions */ - -void *malloc(size_t size); -void free(void *ptr); - -enum errorcode { ERR_NONE=0, ERR_NO_MEM }; -enum errorcode _stp_errorcode = ERR_NONE; - -void *__kmalloc(size_t size, gfp_t flags) -{ - return malloc(size); -} - -void *_stp_alloc_percpu(size_t size) -{ - int i; - struct percpu_data *pdata = malloc(sizeof (*pdata)); - if (!pdata) - return NULL; - - for_each_cpu(i) { - pdata->ptrs[i] = malloc(size); - if (!pdata->ptrs[i]) - goto unwind_oom; - memset(pdata->ptrs[i], 0, size); - } - - /* Catch derefs w/o wrappers */ - return (void *) (~(unsigned long) pdata); - -unwind_oom: - while (--i >= 0) { - free(pdata->ptrs[i]); - } - free(pdata); - return NULL; -} - -void _stp_free_percpu(const void *objp) -{ - int i; - struct percpu_data *p = (struct percpu_data *) (~(unsigned long) objp); - - for_each_cpu(i) - free(p->ptrs[i]); - free(p); -} - -#endif /* _ALLOC_C_ */ diff --git a/runtime/user/copy.c b/runtime/user/copy.c deleted file mode 100644 index 2186aa59..00000000 --- a/runtime/user/copy.c +++ /dev/null @@ -1,7 +0,0 @@ -long -_stp_strncpy_from_user(char *dst, const char __user *src, long count) -{ - return 0; -} - -void __get_user_4(void) {}; diff --git a/runtime/user/emul.h b/runtime/user/emul.h deleted file mode 100644 index 63938b08..00000000 --- a/runtime/user/emul.h +++ /dev/null @@ -1,121 +0,0 @@ -#define kmalloc(size,flags) malloc(size) -#define kmalloc(size,flags) malloc(size) -#define kmalloc_node(size,flags,cpu) malloc(size) - -#define kfree(ptr) free(ptr) - -int vscnprintf(char *buf, size_t size, const char *fmt, va_list args) -{ - int i; - i=vsnprintf(buf,size,fmt,args); - return (i >= size) ? (size - 1) : i; -} - -//#define _stp_log printf - -/* cpu emulation */ -#undef smp_processor_id -#undef get_cpu -#undef put_cpu -#undef for_each_cpu -#define for_each_cpu(cpu) \ - for (cpu = 0; cpu < NR_CPUS; cpu++) - -int _processor_number = 0; -#define smp_processor_id() _processor_number -#define get_cpu() _processor_number -#define put_cpu() ; - -#include "alloc.c" -void *__alloc_percpu(size_t size, size_t align) -{ - int i; - struct percpu_data *pdata = malloc(sizeof (*pdata)); - - if (!pdata) - return NULL; - - for (i = 0; i < NR_CPUS; i++) { - pdata->ptrs[i] = malloc(size); - - if (!pdata->ptrs[i]) - return NULL; - - memset(pdata->ptrs[i], 0, size); - } - - /* Catch derefs w/o wrappers */ - return (void *) (~(unsigned long) pdata); -} - -void -free_percpu(const void *objp) -{ - int i; - struct percpu_data *p = (struct percpu_data *) (~(unsigned long) objp); - - for (i = 0; i < NR_CPUS; i++) { - free(p->ptrs[i]); - } - free(p); -} - -#include <stdarg.h> -unsigned long strtoul(const char *nptr, char **endptr, int base); -#define simple_strtoul strtoul - -const char *_stp_kallsyms_lookup (unsigned long addr, - unsigned long *symbolsize, - unsigned long *offset, - char **modname, - char *namebuf) -{ - static char buf[32]; - sprintf (namebuf, "foobar"); - sprintf (buf, "foobar_mod"); - *offset = 1; - modname = (char **)&buf; - return namebuf; -} - -int __lockfunc _spin_trylock(spinlock_t *lock) -{ - return 1; -} - -void __lockfunc _spin_lock(spinlock_t *lock) -{ -} - -void __lockfunc _spin_unlock(spinlock_t *lock) -{ -} - -size_t strlcat(char *dest, const char *src, size_t count) -{ - size_t dsize = strlen(dest); - size_t len = strlen(src); - size_t res = dsize + len; - - /* This would be a bug */ - BUG_ON(dsize >= count); - - dest += dsize; - count -= dsize; - if (len >= count) - len = count-1; - memcpy(dest, src, len); - dest[len] = 0; - return res; -} -size_t strlcpy(char *dest, const char *src, size_t size) -{ - size_t ret = strlen(src); - - if (size) { - size_t len = (ret >= size) ? size - 1 : ret; - memcpy(dest, src, len); - dest[len] = '\0'; - } - return ret; -} diff --git a/runtime/user/io.c b/runtime/user/io.c deleted file mode 100644 index ecc3d050..00000000 --- a/runtime/user/io.c +++ /dev/null @@ -1,80 +0,0 @@ -/* I/O for printing warnings, errors and debug messages - * Copyright (C) 2005 Red Hat Inc. - * - * This file is part of systemtap, and is free software. You can - * redistribute it and/or modify it under the terms of the GNU General - * Public License (GPL); either version 2, or (at your option) any - * later version. - */ - -#ifndef _IO_C_ -#define _IO_C_ -int vprintf(const char *format, va_list ap); - -/** Logs Data. - * This function sends the message immediately to staprun. It - * will also be sent over the bulk transport (relayfs) if it is - * being used. If the last character is not a newline, then one - * is added. This function is not as efficient as _stp_printf() - * and should only be used for urgent messages. You probably want - * dbug(), or _stp_warn(). - * @param fmt A variable number of args. - * @todo Evaluate if this function is necessary. - */ -void _stp_log (const char *fmt, ...) -{ - va_list args; - va_start(args, fmt); - vprintf (fmt, args); - va_end(args); -} - -/** Prints warning. - * This function sends a warning message immediately to staprun. It - * will also be sent over the bulk transport (relayfs) if it is - * being used. If the last character is not a newline, then one - * is added. - * @param fmt A variable number of args. - */ -void _stp_warn (const char *fmt, ...) -{ - va_list args; - va_start(args, fmt); - vprintf (fmt, args); - va_end(args); -} - -/** Exits and unloads the module. - * This function sends a signal to staprun to tell it to - * unload the module and exit. The module will not be - * unloaded until after the current probe returns. - * @note Be careful to not treat this like the Linux exit() - * call. You should probably call return immediately after - * calling _stp_exit(). - */ -void _stp_exit (void) -{ - exit (-1); -} - -/** Prints error message and exits. - * This function sends an error message immediately to staprun. It - * will also be sent over the bulk transport (relayfs) if it is - * being used. If the last character is not a newline, then one - * is added. - * - * After the error message is displayed, the module will be unloaded. - * @param fmt A variable number of args. - * @sa _stp_exit(). - */ -void _stp_error (const char *fmt, ...) -{ - va_list args; - va_start(args, fmt); - vprintf (fmt, args); - va_end(args); - _stp_exit(); -} - -/** @} */ -#endif /* _IO_C_ */ diff --git a/runtime/user/print.c b/runtime/user/print.c deleted file mode 100644 index acc938b9..00000000 --- a/runtime/user/print.c +++ /dev/null @@ -1,96 +0,0 @@ -#ifndef _PRINT_C_ /* -*- linux-c -*- */ -#define _PRINT_C_ - -#include <linux/config.h> -#include <stdio.h> - -/** @file print.c - * @addtogroup print Print Buffer - * Print Buffer Functions. - * The print buffer is for collecting output to send to the user daemon. - * This is a per-cpu static buffer. The buffer is sent when - * _stp_print_flush() is called. - * - * The reason to do this is to allow multiple small prints to be combined then - * timestamped and sent together to staprun. It could flush automatically on newlines, - * but what about stack traces which span many lines? So try this and see how it works for us. - * @{ - */ - -/** Size of buffer, not including terminating NULL */ -#ifndef STP_PRINT_BUF_LEN -#define STP_PRINT_BUF_LEN 8000 -#endif - -#include "string.h" -#include "io.c" - -static int _stp_pbuf_len[NR_CPUS]; - -#define STP_PRINT_BUF_START 0 -static char _stp_pbuf[NR_CPUS][STP_PRINT_BUF_LEN + 1]; - -void _stp_print_flush (void) -{ - int cpu = smp_processor_id(); - char *buf = &_stp_pbuf[cpu][0]; - int len = _stp_pbuf_len[cpu]; - - if (len == 0) - return; - - fwrite (buf, len, 1, stdout); - _stp_pbuf_len[cpu] = 0; -} - -#define _stp_printf(args...) _stp_sprintf(_stp_stdout,args) -#define _stp_vprintf(fmt,args) _stp_vsprintf(_stp_stdout,fmt,args) -#define _stp_print_cstr(str) _stp_string_cat_cstr(_stp_stdout,str) -#define _stp_print_string(str) _stp_string_cat_string(_stp_stdout,str) -/** Write a String or C string into the print buffer. - * This macro selects the proper function to call. - * @param str A String or C string (char *) - * @sa _stp_print_cstr _stp_print_string - */ - - -/* Print stuff until a format specification is found. */ -/* Return pointer to that. */ -static char *next_fmt(char *fmt, int *num) -{ - char *f = fmt; - int in_fmt = 0; - *num = 0; - while (*f) { - if (in_fmt) { - if (*f == '%') { - _stp_string_cat_char(_stp_stdout,'%'); - in_fmt = 0; - } else if (*f > '0' && *f <= '9') { - *num = *f - '0'; - f++; - return f; - } else - return f; - } else if (*f == '%') - in_fmt = 1; - else - _stp_string_cat_char(_stp_stdout,*f); - f++; - } - return f; -} - -#define _stp_print(str) \ - ({ \ - if (__builtin_types_compatible_p (typeof (str), char[])) { \ - char *x = (char *)str; \ - _stp_string_cat_cstr(_stp_stdout,x); \ - } else { \ - String x = (String)str; \ - _stp_string_cat_string(_stp_stdout,x); \ - } \ - }) - -/** @} */ -#endif /* _PRINT_C_ */ diff --git a/runtime/user/recreate_links b/runtime/user/recreate_links deleted file mode 100755 index 5b182480..00000000 --- a/runtime/user/recreate_links +++ /dev/null @@ -1,15 +0,0 @@ -#!/bin/bash - -ln -s ../map.h . -ln -s ../map.c . -ln -s ../map-stat.c . -ln -s ../string.c . -ln -s ../string.h . -ln -s ../sym.c . -ln -s ../counter.c . -ln -s ../stat.c . -ln -s ../stat.h . -ln -s ../stat-common.c . -ln -s ../arith.c . -ln -s ../map-gen.c . -ln -s ../pmap-gen.c . diff --git a/runtime/user/runtime.h b/runtime/user/runtime.h deleted file mode 100644 index 79a9dc22..00000000 --- a/runtime/user/runtime.h +++ /dev/null @@ -1,56 +0,0 @@ -#ifndef _RUNTIME_H_ -#define _RUNTIME_H_ -/** @file runtime.h - * @brief Main include file for runtime functions. - */ - -#define _STP_TEST_ 1 - -#define __KERNEL__ -#include <linux/config.h> -#undef CONFIG_NR_CPUS -#undef CONFIG_SMP -#define CONFIG_NR_CPUS 8 -#define CONFIG_SMP -#include <linux/module.h> -#include <linux/kernel.h> -#include <linux/miscdevice.h> -#include <linux/init.h> -#include <linux/hash.h> -#include <linux/kprobes.h> -#include <linux/proc_fs.h> -#include <linux/vmalloc.h> -#include <linux/time.h> -#include <linux/spinlock.h> -#include <asm/uaccess.h> -#include <linux/kallsyms.h> -#include <linux/percpu.h> - - -#ifdef DEBUG -#define dbug(args...) \ - { \ - printf("%s:%d: ", __FUNCTION__, __LINE__); \ - printf(args); \ - } -#else -#define dbug(args...) ; -#endif - -#include "emul.h" - -#undef memcpy -#define memcpy __builtin_memcpy - -void exit(int status); - -#define NEED_STAT_LOCKS 0 -#define NEED_COUNTER_LOCKS 0 - -#include "io.c" -#include "print.c" -#include "string.c" -#include "arith.c" -#include "alloc.c" - -#endif /* _RUNTIME_H_ */ diff --git a/runtime/user/test.h b/runtime/user/test.h deleted file mode 100644 index 3139cfec..00000000 --- a/runtime/user/test.h +++ /dev/null @@ -1,247 +0,0 @@ -/* include file for testing maps without running in the kernel */ - -#include <stdio.h> -#include <stdarg.h> -#include <stdlib.h> -#include <string.h> -#include <unistd.h> -#include <limits.h> -#include <errno.h> - -#define likely(x) __builtin_expect(!!(x), 1) -#define unlikely(x) __builtin_expect(!!(x), 0) - -static inline unsigned long hash_long(unsigned long val, unsigned int bits) -{ - unsigned long hash = val; - -#if __WORDSIZE == 64 - /* Sigh, gcc can't optimise this alone like it does for 32 bits. */ - unsigned long n = hash; - n <<= 18; - hash -= n; - n <<= 33; - hash -= n; - n <<= 3; - hash += n; - n <<= 3; - hash -= n; - n <<= 4; - hash += n; - n <<= 2; - hash += n; -#else - /* On some cpus multiply is faster, on others gcc will do shifts */ - hash *= 0x9e370001UL; -#endif - - /* High bits are more random, so use them. */ - return hash >> (8*sizeof(long) - bits); -} - - -#define STRINGLEN 128 -#define HASH_ELEM_NUM 5000 -#define HASH_TABLE_BITS 8 -#define HASH_TABLE_SIZE (1<<HASH_TABLE_BITS) -#define BUCKETS 16 /* largest histogram width */ -#define PK 0 /* sprinkle debug printk into probe code */ - -#define LIST_POISON1 ((void *) 0x00100100) -#define LIST_POISON2 ((void *) 0x00200200) - -struct list_head { - struct list_head *next, *prev; -}; - -#define LIST_HEAD_INIT(name) { &(name), &(name) } - -#define LIST_HEAD(name) \ - struct list_head name = LIST_HEAD_INIT(name) - -#define INIT_LIST_HEAD(ptr) do { \ - (ptr)->next = (ptr); (ptr)->prev = (ptr); \ -} while (0) - -/* - * Insert a new entry between two known consecutive entries. - * - * This is only for internal list manipulation where we know - * the prev/next entries already! - */ -static inline void __list_add(struct list_head *new, - struct list_head *prev, - struct list_head *next) -{ - next->prev = new; - new->next = next; - new->prev = prev; - prev->next = new; -} - -static inline void list_add(struct list_head *new, struct list_head *head) -{ - __list_add(new, head, head->next); -} - - -static inline void list_add_tail(struct list_head *new, struct list_head *head) -{ - __list_add(new, head->prev, head); -} -/* - * Delete a list entry by making the prev/next entries - * point to each other. - * - * This is only for internal list manipulation where we know - * the prev/next entries already! - */ -static inline void __list_del(struct list_head * prev, struct list_head * next) -{ - next->prev = prev; - prev->next = next; -} - -static inline void list_del(struct list_head *entry) -{ - __list_del(entry->prev, entry->next); - entry->next = LIST_POISON1; - entry->prev = LIST_POISON2; -} - -static inline int list_empty(const struct list_head *head) -{ - return head->next == head; -} - -static inline void list_move_tail(struct list_head *list, - struct list_head *head) -{ - __list_del(list->prev, list->next); - list_add_tail(list, head); -} - - -struct hlist_head { - struct hlist_node *first; -}; - -struct hlist_node { - struct hlist_node *next, **pprev; -}; -#define HLIST_HEAD_INIT { .first = NULL } -#define HLIST_HEAD(name) struct hlist_head name = { .first = NULL } -#define INIT_HLIST_HEAD(ptr) ((ptr)->first = NULL) -#define INIT_HLIST_NODE(ptr) ((ptr)->next = NULL, (ptr)->pprev = NULL) - -static inline void hlist_add_head(struct hlist_node *n, struct hlist_head *h) -{ - struct hlist_node *first = h->first; - n->next = first; - if (first) - first->pprev = &n->next; - h->first = n; - n->pprev = &h->first; -} - -#define hlist_for_each(pos, head) \ - for (pos = (head)->first; pos; pos = pos->next) - -#define hlist_entry(ptr, type, member) container_of(ptr,type,member) - -#define container_of(ptr, type, member) ({ \ - const typeof( ((type *)0)->member ) *__mptr = (ptr); \ - (type *)( (char *)__mptr - offsetof(type,member) );}) - -#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER) - -static inline void __hlist_del(struct hlist_node *n) -{ - struct hlist_node *next = n->next; - struct hlist_node **pprev = n->pprev; - *pprev = next; - if (next) - next->pprev = pprev; -} - -static inline void hlist_del(struct hlist_node *n) -{ - __hlist_del(n); - n->next = LIST_POISON1; - n->pprev = LIST_POISON2; -} - -static inline void hlist_del_init(struct hlist_node *n) -{ - if (n->pprev) { - __hlist_del(n); - INIT_HLIST_NODE(n); - } -} - -static inline void hlist_add_before(struct hlist_node *n, - struct hlist_node *next) -{ - n->pprev = next->pprev; - n->next = next; - next->pprev = &n->next; - *(n->pprev) = n; -} - -#define GFP_ATOMIC 0 - -void *kmalloc (size_t len, int flags) -{ - return malloc (len); -} - -void *vmalloc (size_t len) -{ - return malloc (len); -} - -#define kfree(x) free(x) -#define vfree(x) free(x) - -/***** END OF KERNEL STUFF ********/ - -#ifdef DEBUG -#define dbug(args...) \ - { \ - printf("%s:%d: ", __FUNCTION__, __LINE__); \ - printf(args); \ - } -#else -#define dbug(args...) ; -#endif - -#define dlog(args...) printf(args); -#define _stp_log(args...) printf(args); - -#define STP_NUM_STRINGS 5 -#define NR_CPUS 2 - -int smp_processor_id(void) -{ - return 0; -} - -#define vscnprintf vsnprintf - -#include "../alloc.c" -#include "../map.h" -#include "../map.c" - -/* handle renamed functions */ -#define map_new _stp_map_new -#define map_key_del _stp_map_key_del -#define map_start _stp_map_start -#define map_iter _stp_map_iter -#define map_get_str _stp_map_get_str -#define map_set_int64 _stp_map_set_int64 -#define map_get_int64 _stp_map_get_int64 -#define map_key_str_str _stp_map_key_str_str -#define map_key_str _stp_map_key_str -#define map_key_long _stp_map_key_long -#define map_key_long_long _stp_map_key_long_long -#define map_set_stat _stp_map_set_stat diff --git a/tapset/ChangeLog b/tapset/ChangeLog index b325a627..287b0823 100644 --- a/tapset/ChangeLog +++ b/tapset/ChangeLog @@ -1,3 +1,36 @@ +2007-10-10 Martin Hunt <hunt@redhat.com> + + * aux_syscalls.stp (_stp_lookup_str): When defaulting + to a numeric value, append, don't overwrite. + +2007-10-10 Zhaolei <zhaolei@cn.fujitsu.com> + + From Lai Jiangshan <laijs@cn.fujitsu.com> + * aux_syscalls.stp (_stp_lookup_or_str) redirect to _stp_lookup_str + if val is 0. + +2007-10-09 Mike Mason <mmlnx@us.ibm.com> + + * rpc.stp: Replaced atomic_read()'s with kread()'s + +2007-10-09 Martin Hunt <hunt@redhat.com> + PR5153 + * aux_syscalls.stp (_sighandler_str): No + sa_restorer field for IA64. + +2007-10-09 Martin Hunt <hunt@redhat.com> + + * syscalls2.stp (sys_signal): Call + _sighandler_str(). + + * aux_syscalls.stp (_stp_sigset_str): Don't + include SIG_0. + (_sighandler_str): New. + +2007-10-09 Zhaolei <zhaolei@cn.fujitsu.com> + + * queue_stats.stp (qsq_start): Add destruction for qs_utime. + 2007-10-09 Zhaolei <zhaolei@cn.fujitsu.com> From Cai Fei <caifei@cn.fujitsu.com> diff --git a/tapset/aux_syscalls.stp b/tapset/aux_syscalls.stp index 3818ae75..05c7dc98 100644 --- a/tapset/aux_syscalls.stp +++ b/tapset/aux_syscalls.stp @@ -1520,7 +1520,7 @@ typedef struct { void _stp_lookup_str(const _stp_val_array * const array, long val, char *ptr, int len) { - int i = 0; + int i = 0, slen; while (array[i].name) { if (array[i].val == val) { strlcat (ptr, array[i].name, len); @@ -1528,11 +1528,18 @@ void _stp_lookup_str(const _stp_val_array * const array, long val, char *ptr, in } i++; } - snprintf(ptr, len, "0x%lx", val); + slen = strlen(ptr); + _stp_snprintf(ptr + slen, len - slen, "0x%lx", val); } void _stp_lookup_or_str(const _stp_val_array * const array, long val, char *ptr, int len) { int i = 0, flag = 0; + + if (val == 0) { + _stp_lookup_str(array, val, ptr, len); + return; + } + while (array[i].name) { if (array[i].val & val) { if (flag) @@ -1587,7 +1594,7 @@ void _stp_sigset_str(sigset_t *mask, char *ptr, int len) const _stp_val_array * const array = _stp_signal_list; int i = 0, flag = 0; while (array[i].name) { - if (sigismember(mask, array[i].val)) { + if (array[i].val && sigismember(mask, array[i].val)) { if (flag) strlcat(ptr, "|", len); strlcat(ptr, array[i].name, len); @@ -1785,6 +1792,17 @@ function get_mmap_args:string (args:long) strlcpy (THIS->__retvalue, "UNKNOWN", MAXSTRINGLEN); %} + +function _sighandler_str:string(uaddr:long) +%{ /* pure */ + static const _stp_val_array const _stp_sa_handler_list[] = { + {0, "SIG_DFL"}, + {1, "SIG_IGN"}, + {0, NULL} + }; + _stp_lookup_str(_stp_sa_handler_list, (long)THIS->uaddr, THIS->__retvalue, MAXSTRINGLEN); +%} + function _struct_sigaction_u:string(uaddr:long) %{ /* pure */ static const _stp_val_array const _stp_sa_handler_list[] = { @@ -1818,8 +1836,12 @@ function _struct_sigaction_u:string(uaddr:long) strlcat (THIS->__retvalue, ", ", MAXSTRINGLEN); _stp_lookup_or_str(_stp_sa_flags_list, act.sa_flags, THIS->__retvalue, MAXSTRINGLEN); strlcat (THIS->__retvalue, ", ", MAXSTRINGLEN); +#if !defined (__ia64__) len = strlen(THIS->__retvalue); _stp_snprintf(THIS->__retvalue + len, MAXSTRINGLEN - len, "0x%lx, [", (long)act.sa_restorer); +#else + strlcat (THIS->__retvalue, "[", MAXSTRINGLEN); +#endif _stp_sigset_str(&act.sa_mask, THIS->__retvalue, MAXSTRINGLEN); strlcat (THIS->__retvalue, "]", MAXSTRINGLEN); } diff --git a/tapset/queue_stats.stp b/tapset/queue_stats.stp index 75407fee..9d89903c 100644 --- a/tapset/queue_stats.stp +++ b/tapset/queue_stats.stp @@ -59,6 +59,7 @@ function qsq_start (qname) { # reset statistics for new baseline delete qs_wtime[qname] delete qs_wlentime[qname] delete qs_dcount[qname] + delete qs_utime[qname] qs_stime[qname] = qs_time () } diff --git a/tapset/rpc.stp b/tapset/rpc.stp index 3d17d221..eecdb796 100644 --- a/tapset/rpc.stp +++ b/tapset/rpc.stp @@ -948,7 +948,7 @@ function clones_from_clnt:long(clnt:long) %{ /* pure */ struct rpc_clnt *clnt = (struct rpc_clnt *)(long)THIS->clnt; #if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22) - THIS->__retvalue = atomic_read(&clnt->cl_count); /* FIXME: deref hazard! */ + THIS->__retvalue = kread(&(clnt->cl_count)); #else THIS->__retvalue = -1; #endif @@ -958,7 +958,7 @@ function tasks_from_clnt:long(clnt:long) %{ /* pure */ struct rpc_clnt *clnt = (struct rpc_clnt *)(long)THIS->clnt; #if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22) - THIS->__retvalue = atomic_read(&clnt->cl_users); /* FIXME: deref hazard! */ + THIS->__retvalue = kread(&(clnt->cl_users)); #else THIS->__retvalue = -1; #endif diff --git a/tapset/syscalls2.stp b/tapset/syscalls2.stp index acb2c137..e702bbcd 100644 --- a/tapset/syscalls2.stp +++ b/tapset/syscalls2.stp @@ -2122,7 +2122,7 @@ probe syscall.signal = kernel.function("sys_signal") ? { name = "signal" sig = $sig handler = $handler - argstr = sprintf("%s, %p", _signal_name($sig), $handler) + argstr = sprintf("%s, %s", _signal_name($sig), _sighandler_str($handler)) } probe syscall.signal.return = kernel.function("sys_signal").return ? { name = "signal" diff --git a/testsuite/systemtap.syscall/ChangeLog b/testsuite/systemtap.syscall/ChangeLog index 9811a707..61c72bc2 100644 --- a/testsuite/systemtap.syscall/ChangeLog +++ b/testsuite/systemtap.syscall/ChangeLog @@ -1,3 +1,14 @@ +2007-10-09 Martin Hunt <hunt@redhat.com> + + * rt_signal.c: Fix expected results for IA64. + +2007-10-09 Martin Hunt <hunt@redhat.com> + + * rt_signal.c: Fix expected patterns to match + recent changes in tapsets. + + * signal.c: Use syscall(). Fix expected patterns. + 2007-10-01 Martin Hunt <hunt@redhat.com> * test.tcl (run_one_test): Append newlines when diff --git a/testsuite/systemtap.syscall/rt_signal.c b/testsuite/systemtap.syscall/rt_signal.c index 32eb9a92..f25633b7 100644 --- a/testsuite/systemtap.syscall/rt_signal.c +++ b/testsuite/systemtap.syscall/rt_signal.c @@ -18,26 +18,33 @@ int main() sigemptyset(&mask); sigaddset(&mask, SIGUSR1); + sigaddset(&mask, SIGUSR2); sigprocmask(SIG_BLOCK, &mask, NULL); - // rt_sigprocmask (SIG_BLOCK, XXXX, 0x[0]+, 8) = 0 + // rt_sigprocmask (SIG_BLOCK, \[SIGUSR1|SIGUSR2\], 0x[0]+, 8) = 0 + sigdelset(&mask, SIGUSR2); sigprocmask(SIG_UNBLOCK, &mask, NULL); - // rt_sigprocmask (SIG_UNBLOCK, XXXX, 0x[0]+, 8) = 0 + // rt_sigprocmask (SIG_UNBLOCK, \[SIGUSR1\], 0x[0]+, 8) = 0 sa.sa_handler = SIG_IGN; sigemptyset(&sa.sa_mask); sigaddset(&sa.sa_mask, SIGALRM); sa.sa_flags = 0; sigaction(SIGUSR1, &sa, NULL); - // rt_sigaction (SIGUSR1, XXXX, 0x[0]+, 8) = 0 + // rt_sigaction (SIGUSR1, {SIG_IGN}, 0x[0]+, 8) = 0 sa.sa_handler = SIG_DFL; sigaction(SIGUSR1, &sa, NULL); - // rt_sigaction (SIGUSR1, XXXX, 0x[0]+, 8) = 0 + // rt_sigaction (SIGUSR1, {SIG_DFL}, 0x[0]+, 8) = 0 sa.sa_handler = sig_act_handler; sigaction(SIGUSR1, &sa, NULL); - // rt_sigaction (SIGUSR1, XXXX, 0x[0]+, 8) = 0 + +#ifdef __ia64__ + // rt_sigaction (SIGUSR1, {XXXX, [^,]+, \[SIGALRM\]}, 0x[0]+, 8) = 0 +#else + // rt_sigaction (SIGUSR1, {XXXX, [^,]+, XXXX, \[SIGALRM\]}, 0x[0]+, 8) = 0 +#endif return 0; } diff --git a/testsuite/systemtap.syscall/signal.c b/testsuite/systemtap.syscall/signal.c index e125e4a1..2c0abe38 100644 --- a/testsuite/systemtap.syscall/signal.c +++ b/testsuite/systemtap.syscall/signal.c @@ -2,56 +2,54 @@ #include <sys/types.h> #include <unistd.h> #include <signal.h> +#include <string.h> #include <sys/syscall.h> -#ifdef SYS_signal static void sig_act_handler(int signo) { } -#endif int main() { -#ifdef SYS_signal sigset_t mask; struct sigaction sa; pid_t pid; +#ifdef SYS_signal syscall(SYS_signal, SIGUSR1, SIG_IGN); - // signal (SIGUSR1, 0x0+1) = 0 + // signal (SIGUSR1, SIG_IGN) - syscall(SYS_signal, SIGUSR1, SIG_DFL); - // signal (SIGUSR1, 0x0+) = 1 + syscall (SYS_signal, SIGUSR1, SIG_DFL); + // signal (SIGUSR1, SIG_DFL) = 1 - syscall(SYS_signal, SIGUSR1, sig_act_handler); + syscall (SYS_signal, SIGUSR1, sig_act_handler); // signal (SIGUSR1, XXXX) = 0 +#endif sigemptyset(&mask); - sigaddset(&mask, SIGUSR1); - syscall(SYS_sigprocmask,SIG_BLOCK, &mask, NULL); + sigaddset(&mask, SIGUSR2); + +#ifdef SYS_sigprocmask + syscall (SYS_sigprocmask, SIG_BLOCK, &mask, NULL); // sigprocmask (SIG_BLOCK, XXXX, 0x0+) = 0 - syscall(SYS_sigprocmask,SIG_UNBLOCK, &mask, NULL); + syscall (SYS_sigprocmask, SIG_UNBLOCK, &mask, NULL); // sigprocmask (SIG_UNBLOCK, XXXX, 0x0+) = 0 +#endif + memset(&sa, 0, sizeof(sa)); + sigfillset(&sa.sa_mask); sa.sa_handler = SIG_IGN; - sigemptyset(&sa.sa_mask); - sigaddset(&sa.sa_mask, SIGALRM); - sa.sa_flags = 0; - syscall(SYS_sigaction,SIGUSR1, &sa, NULL); - // sigaction (SIGUSR1, XXXX, 0x0+) = 0 - - /* syscall(SYS_kill,0,SIGUSR1); - kill (0, SIGUSR1) = 0 - - pid = getpid(); - getpid () = NNNN +#ifdef SYS_sigaction + syscall (SYS_sigaction, SIGUSR1, &sa, NULL); + // sigaction (SIGUSR1, {SIG_IGN}, 0x0+) = 0 + #endif - syscall(SYS_tgkill,pid,pid,SIGUSR1); - tgkill (NNNN, NNNN, SIGUSR1) = 0 - */ +#ifdef SYS_tgkill + syscall(SYS_tgkill, 1234, 5678, 0); + // tgkill (1234, 5678, SIG_0) #endif return 0; |