From a34a9fe036c9c6f06452eb893590a6984949dc95 Mon Sep 17 00:00:00 2001 From: Mark Wielaard Date: Fri, 29 Jul 2011 13:35:06 +0200 Subject: [PATCH] Put common probe and session context state definitions in their own files. translate.cxx contained code to produce the common probe and session context state as C code snippets. Large parts were not dependent on the session state at all, so they really were just static blobs of C code wrapped in c++ io stream operators. These have been put in their own C runtime header files (common_session_state.h, common_probe_context.h and runtime_defines.h) to make it easier to edit and document. --- runtime/common_probe_context.h | 61 ++++++++++++++++ runtime/common_session_state.h | 15 ++++ runtime/regs.h | 4 ++ runtime/runtime_defines.h | 58 ++++++++++++++++ translate.cxx | 123 +++------------------------------ 5 files changed, 149 insertions(+), 112 deletions(-) create mode 100644 runtime/common_probe_context.h create mode 100644 runtime/common_session_state.h create mode 100644 runtime/runtime_defines.h diff --git a/runtime/common_probe_context.h b/runtime/common_probe_context.h new file mode 100644 index 000000000..366cb59fa --- /dev/null +++ b/runtime/common_probe_context.h @@ -0,0 +1,61 @@ +/* Included once by translate.cxx c_unparser::emit_common_header () + Defines all common fields and probe flags for struct context. + Available to C-based probe handlers as fields of the CONTEXT ptr. */ + +atomic_t busy; +const char *probe_point; +const char *probe_name; /* as per 'stap -l' */ +int actionremaining; +int nesting; +string_t error_buffer; + +/* Only used when stap script uses tokenize.stp tapset. */ +#ifdef STAP_NEED_CONTEXT_TOKENIZE +string_t tok_str; +char *tok_start; +char *tok_end; +#endif + +/* NB: last_error is used as a health flag within a probe. + While it's 0, execution continues + When it's "something", probe code unwinds, _stp_error's, sets error state */ +const char *last_error; +const char *last_stmt; + +/* status of pt_regs regs field. _STP_REGS_ flags. */ +int regflags; +struct pt_regs *regs; + +/* unwaddr is caching unwound address in each probe handler on ia64. */ +#if defined __ia64__ +unsigned long *unwaddr; +#endif + +/* non-NULL when this probe was a kretprobe. */ +struct kretprobe_instance *pi; +int pi_longs; /* int64_t count in pi->data, the rest is string_t */ + +/* Only used when stap script uses the i386 or x86_64 register.stp tapset. */ +#ifdef STAP_NEED_REGPARM +int regparm; +#endif + +/* State for mark_derived_probes. */ +va_list *mark_va_list; +const char * marker_name; +const char * marker_format; +void *data; + +/* Only used for overload processing. */ +#ifdef STP_OVERLOAD +cycles_t cycles_base; +cycles_t cycles_sum; +#endif + +/* non-NULL when this probe was a uretprobe. */ +struct uretprobe_instance *ri; + +/* Current state of the unwinder (as used in the unwind.c dwarf unwinder). */ +#if defined(STP_NEED_UNWIND_DATA) +struct unwind_context uwcontext; +#endif diff --git a/runtime/common_session_state.h b/runtime/common_session_state.h new file mode 100644 index 000000000..1cdf5b3ca --- /dev/null +++ b/runtime/common_session_state.h @@ -0,0 +1,15 @@ +// Will be included once by translate.cxx c_unparser::emit_common_header (). + +#define STAP_SESSION_STARTING 0 +#define STAP_SESSION_RUNNING 1 +#define STAP_SESSION_ERROR 2 +#define STAP_SESSION_STOPPING 3 +#define STAP_SESSION_STOPPED 4 +static atomic_t session_state = ATOMIC_INIT (STAP_SESSION_STARTING); + +static atomic_t error_count = ATOMIC_INIT (0); +static atomic_t skipped_count = ATOMIC_INIT (0); +static atomic_t skipped_count_lowstack = ATOMIC_INIT (0); +static atomic_t skipped_count_reentrant = ATOMIC_INIT (0); +static atomic_t skipped_count_uprobe_reg = ATOMIC_INIT (0); +static atomic_t skipped_count_uprobe_unreg = ATOMIC_INIT (0); diff --git a/runtime/regs.h b/runtime/regs.h index 08449aa6a..ca98c3126 100644 --- a/runtime/regs.h +++ b/runtime/regs.h @@ -11,6 +11,10 @@ #ifndef _REGS_H_ /* -*- linux-c -*- */ #define _REGS_H_ +/* Defines for the struct context regsflags field. + _STP_REGS_USER regsflags bit to indicate regs fully from user. */ +#define _STP_REGS_USER_FLAG 1 + #if defined (STAPCONF_X86_UNIREGS) && (defined (__x86_64__) || defined (__i386__)) #define REG_IP(regs) regs->ip diff --git a/runtime/runtime_defines.h b/runtime/runtime_defines.h new file mode 100644 index 000000000..8eccc1e2e --- /dev/null +++ b/runtime/runtime_defines.h @@ -0,0 +1,58 @@ +/* Common runtime defines, not dependend on session variables. + Included once at the top of the generated stap.c file by the translate.cxx + translate_pass (). */ + +/* Strings are used for storing backtraces, they are larger on 64bit + so raise the size on 64bit architectures. PR10486. */ +#include +#ifndef MAXSTRINGLEN +#if BITS_PER_LONG == 32 +#define MAXSTRINGLEN 256 +#else +#define MAXSTRINGLEN 512 +#endif +#endif +typedef char string_t[MAXSTRINGLEN]; + +#ifndef MAXACTION +#define MAXACTION 1000 +#endif +#ifndef MAXACTION_INTERRUPTIBLE +#define MAXACTION_INTERRUPTIBLE (MAXACTION * 10) +#endif +#ifndef TRYLOCKDELAY +#define TRYLOCKDELAY 10 /* microseconds */ +#endif +#ifndef MAXTRYLOCK +#define MAXTRYLOCK 100 /* 1 millisecond total */ +#endif +#ifndef MAXMAPENTRIES +#define MAXMAPENTRIES 2048 +#endif +#ifndef MAXERRORS +#define MAXERRORS 0 +#endif +#ifndef MAXSKIPPED +#define MAXSKIPPED 100 +#endif +#ifndef MINSTACKSPACE +#define MINSTACKSPACE 1024 +#endif +#ifndef INTERRUPTIBLE +#define INTERRUPTIBLE 1 +#endif + +/* Overload processing. */ +#ifndef STP_OVERLOAD_INTERVAL +#define STP_OVERLOAD_INTERVAL 1000000000LL +#endif +#ifndef STP_OVERLOAD_THRESHOLD +#define STP_OVERLOAD_THRESHOLD 500000000LL +#endif + +/* We allow the user to completely turn overload processing off + (as opposed to tuning it by overriding the values above) by + running: stap -DSTP_NO_OVERLOAD {other options}. */ +#if !defined(STP_NO_OVERLOAD) && !defined(STAP_NO_OVERLOAD) +#define STP_OVERLOAD +#endif diff --git a/translate.cxx b/translate.cxx index caf9f32a8..4b5f3d493 100644 --- a/translate.cxx +++ b/translate.cxx @@ -913,69 +913,17 @@ translator_output::line () void c_unparser::emit_common_header () { + // Common (static atomic) state of the stap session. o->newline(); - o->newline() << "typedef char string_t[MAXSTRINGLEN];"; - o->newline(); - o->newline() << "#define STAP_SESSION_STARTING 0"; - o->newline() << "#define STAP_SESSION_RUNNING 1"; - o->newline() << "#define STAP_SESSION_ERROR 2"; - o->newline() << "#define STAP_SESSION_STOPPING 3"; - o->newline() << "#define STAP_SESSION_STOPPED 4"; - o->newline() << "static atomic_t session_state = ATOMIC_INIT (STAP_SESSION_STARTING);"; - o->newline() << "static atomic_t error_count = ATOMIC_INIT (0);"; - o->newline() << "static atomic_t skipped_count = ATOMIC_INIT (0);"; - o->newline() << "static atomic_t skipped_count_lowstack = ATOMIC_INIT (0);"; - o->newline() << "static atomic_t skipped_count_reentrant = ATOMIC_INIT (0);"; - o->newline() << "static atomic_t skipped_count_uprobe_reg = ATOMIC_INIT (0);"; - o->newline() << "static atomic_t skipped_count_uprobe_unreg = ATOMIC_INIT (0);"; - - // Defines for the regsflags field. - // _STP_REGS_USER regsflags bit to indicate regs fully from user. - o->newline(); - o->newline() << "#define _STP_REGS_USER_FLAG 1"; - o->newline(); + o->newline() << "#include \"common_session_state.h\""; + // Per CPU context for probes. Includes common shared state held for + // all probes (defined in common_probe_context), the probe locals (union) + // and the function locals (union). o->newline() << "struct context {"; - o->newline(1) << "atomic_t busy;"; - o->newline() << "const char *probe_point;"; - o->newline() << "const char *probe_name;"; // as per 'stap -l' - o->newline() << "int actionremaining;"; - o->newline() << "int nesting;"; - o->newline() << "string_t error_buffer;"; - o->newline() << "#ifdef STAP_NEED_CONTEXT_TOKENIZE"; - o->newline() << "string_t tok_str;"; - o->newline() << "char *tok_start;"; - o->newline() << "char *tok_end;"; - o->newline() << "#endif"; - o->newline() << "const char *last_error;"; - // NB: last_error is used as a health flag within a probe. - // While it's 0, execution continues - // When it's "something", probe code unwinds, _stp_error's, sets error state - o->newline() << "const char *last_stmt;"; - o->newline() << "struct pt_regs *regs;"; - o->newline() << "#if defined __ia64__"; - o->newline() << "unsigned long *unwaddr;"; - // unwaddr is caching unwound address in each probe handler on ia64. - o->newline() << "#endif"; - o->newline() << "struct kretprobe_instance *pi;"; - o->newline() << "int pi_longs;"; // int64_t count in pi->data, the rest is string_t - o->newline() << "int regflags;"; // status of pt_regs regs field. - o->newline() << "#ifdef STAP_NEED_REGPARM"; // i386 or x86_64 register.stp - o->newline() << "int regparm;"; - o->newline() << "#endif"; - o->newline() << "va_list *mark_va_list;"; - o->newline() << "const char * marker_name;"; - o->newline() << "const char * marker_format;"; - o->newline() << "void *data;"; - o->newline() << "#ifdef STP_OVERLOAD"; - o->newline() << "cycles_t cycles_base;"; - o->newline() << "cycles_t cycles_sum;"; - o->newline() << "#endif"; - o->newline() << "struct uretprobe_instance *ri;"; - o->newline() << "#if defined(STP_NEED_UNWIND_DATA)"; - o->newline() << "struct unwind_context uwcontext;"; - o->newline() << "#endif"; + // Common state held shared by probes. + o->newline(1) << "#include \"common_probe_context.h\""; // PR10516: probe locals o->newline() << "union {"; @@ -5799,65 +5747,16 @@ translate_pass (systemtap_session& s) if (ri.recursive) nesting += 10; // This is at the very top of the file. + // All "static" defines (not dependend on session state). + s.op->newline() << "#include\"runtime_defines.h\""; + if (! s.unprivileged) s.op->newline() << "#define STP_PRIVILEGED 1"; + s.op->newline() << "#ifndef MAXNESTING"; s.op->newline() << "#define MAXNESTING " << nesting; s.op->newline() << "#endif"; - // Strings are used for storing backtraces, they are larger on 64bit - // so raise the size on 64bit architectures. PR10486 - s.op->newline() << "#include "; - s.op->newline() << "#ifndef MAXSTRINGLEN"; - s.op->newline() << "#if BITS_PER_LONG == 32"; - s.op->newline() << "#define MAXSTRINGLEN 256"; - s.op->newline() << "#else"; - s.op->newline() << "#define MAXSTRINGLEN 512"; - s.op->newline() << "#endif"; - s.op->newline() << "#endif"; - - s.op->newline() << "#ifndef MAXACTION"; - s.op->newline() << "#define MAXACTION 1000"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef MAXACTION_INTERRUPTIBLE"; - s.op->newline() << "#define MAXACTION_INTERRUPTIBLE (MAXACTION * 10)"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef TRYLOCKDELAY"; - s.op->newline() << "#define TRYLOCKDELAY 10 /* microseconds */"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef MAXTRYLOCK"; - s.op->newline() << "#define MAXTRYLOCK 100 /* 1 millisecond total */"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef MAXMAPENTRIES"; - s.op->newline() << "#define MAXMAPENTRIES 2048"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef MAXERRORS"; - s.op->newline() << "#define MAXERRORS 0"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef MAXSKIPPED"; - s.op->newline() << "#define MAXSKIPPED 100"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef MINSTACKSPACE"; - s.op->newline() << "#define MINSTACKSPACE 1024"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef INTERRUPTIBLE"; - s.op->newline() << "#define INTERRUPTIBLE 1"; - s.op->newline() << "#endif"; - - // Overload processing - s.op->newline() << "#ifndef STP_OVERLOAD_INTERVAL"; - s.op->newline() << "#define STP_OVERLOAD_INTERVAL 1000000000LL"; - s.op->newline() << "#endif"; - s.op->newline() << "#ifndef STP_OVERLOAD_THRESHOLD"; - s.op->newline() << "#define STP_OVERLOAD_THRESHOLD 500000000LL"; - s.op->newline() << "#endif"; - // We allow the user to completely turn overload processing off - // (as opposed to tuning it by overriding the values above) by - // running: stap -DSTP_NO_OVERLOAD {other options} - s.op->newline() << "#if !defined(STP_NO_OVERLOAD) && !defined(STAP_NO_OVERLOAD)"; - s.op->newline() << "#define STP_OVERLOAD"; - s.op->newline() << "#endif"; - s.op->newline() << "#define STP_SKIP_BADVARS " << (s.skip_badvars ? 1 : 0); if (s.bulk_mode) -- 2.43.5