[PATCH 04/11] sapi: Add SMP lock profiling app. level data

Gedare Bloom gedare at rtems.org
Mon Mar 10 15:52:23 UTC 2014


On Mon, Mar 10, 2014 at 9:28 AM, Sebastian Huber
<sebastian.huber at embedded-brains.de> wrote:
> ---
>  cpukit/sapi/include/rtems/profiling.h |   88 ++++++++++++++++++++++++++++++++-
>  cpukit/sapi/src/profilingreportxml.c  |   70 ++++++++++++++++++++++++++
>  2 files changed, 157 insertions(+), 1 deletions(-)
>
> diff --git a/cpukit/sapi/include/rtems/profiling.h b/cpukit/sapi/include/rtems/profiling.h
> index ecb3ff7..2a66015 100644
> --- a/cpukit/sapi/include/rtems/profiling.h
> +++ b/cpukit/sapi/include/rtems/profiling.h
> @@ -66,7 +66,14 @@ typedef enum {
>     *
>     * @see rtems_profiling_per_cpu.
>     */
> -  RTEMS_PROFILING_PER_CPU
> +  RTEMS_PROFILING_PER_CPU,
> +
> +  /**
> +   * @brief Type of SMP lock profiling data.
> +   *
> +   * @see rtems_profiling_smp_lock.
> +   */
> +  RTEMS_PROFILING_SMP_LOCK
>  } rtems_profiling_type;
>
>  /**
> @@ -152,6 +159,80 @@ typedef struct {
>  } rtems_profiling_per_cpu;
>
>  /**
> + * @brief Count of lock contention counters for SMP lock profiling.
> + */
> +#define RTEMS_PROFILING_SMP_LOCK_CONTENTION_COUNTS 4
> +
> +/**
> + * @brief SMP lock profiling data.
> + *
> + * The lock acquire attempt instant is the point in time right after the
> + * interrupt disable action in the lock acquire sequence.
> + *
> + * The lock acquire instant is the point in time right after the lock
> + * acquisition.  This is the begin of the critical section code execution.
> + *
> + * The lock release instant is the point in time right before the interrupt
> + * enable action in the lock release sequence.
> + *
> + * The lock section time is the time elapsed between the lock acquire instant
> + * and the lock release instant.
> + *
> + * The lock acquire time is the time elapsed between the lock acquire attempt
> + * instant and the lock acquire instant.
Move this last point up to where you define lock acquire attempt
instant and lock acquire instant.

> + */
> +typedef struct {
> +  /**
> +   * @brief The profiling data header.
> +   */
> +  rtems_profiling_header header;
> +
> +  /**
> +   * @brief The lock name.
> +   */
> +  const char *name;
> +
> +  /**
> +   * @brief The maximum lock section time in nanoseconds.
> +   */
> +  uint32_t max_section_time;
> +
> +  /**
> +   * @brief The maximum lock acquire time in nanoseconds.
> +   */
> +  uint32_t max_acquire_time;
> +
Any possible issues with 32-bit values here?

> +  /**
> +   * @brief The count of lock uses.
> +   *
> +   * This value may overflow.
> +   */
> +  uint64_t usage_count;
> +
> +  /**
> +   * @brief Total lock section time in nanoseconds.
> +   *
> +   * The average lock section time is the total section time divided by the
> +   * lock usage count.
> +   *
> +   * This value may overflow.
> +   */
> +  uint64_t total_section_time;
> +
> +  /**
> +   * @brief The counts of lock acquire operations by contention.
> +   *
> +   * The contention count for index N corresponds to a lock acquire attempt
> +   * with an initial queue length of N.  The last index corresponds to all
> +   * lock acquire attempts with an initial queue length greater than or equal
> +   * to RTEMS_PROFILING_SMP_LOCK_CONTENTION_COUNTS minus one.
> +   *
> +   * The values may overflow.
> +   */
> +  uint64_t contention_counts[RTEMS_PROFILING_SMP_LOCK_CONTENTION_COUNTS];
contention_counts[0] is when there is no contention hence negligible
acquire_time?

Is total_acquire_time not feasible or interesting to profile?

> +} rtems_profiling_smp_lock;
> +
> +/**
>   * @brief Collection of profiling data.
>   */
>  typedef union {
> @@ -164,6 +245,11 @@ typedef union {
>     * @brief Per-CPU profiling data if indicated by the header.
>     */
>    rtems_profiling_per_cpu per_cpu;
> +
> +  /**
> +   * @brief SMP lock profiling data if indicated by the header.
> +   */
> +  rtems_profiling_smp_lock smp_lock;
>  } rtems_profiling_data;
>
>  /**
> diff --git a/cpukit/sapi/src/profilingreportxml.c b/cpukit/sapi/src/profilingreportxml.c
> index f0a6fd6..5aa1282 100644
> --- a/cpukit/sapi/src/profilingreportxml.c
> +++ b/cpukit/sapi/src/profilingreportxml.c
> @@ -18,6 +18,7 @@
>
>  #include <rtems/profiling.h>
>
> +#include <stddef.h>
>  #include <inttypes.h>
>
>  typedef struct {
> @@ -128,6 +129,72 @@ static void report_per_cpu(context *ctx, const rtems_profiling_per_cpu *per_cpu)
>    update_retval(ctx, rv);
>  }
>
> +static void report_smp_lock(context *ctx, const rtems_profiling_smp_lock *smp_lock)
> +{
> +  rtems_profiling_printf printf_func = ctx->printf_func;
> +  void *printf_arg = ctx->printf_arg;
> +  int rv;
> +  size_t i;
> +
> +  indent(ctx, 1);
> +  rv = (*printf_func)(
> +    printf_arg,
> +    "<SMPLockProfilingReport name=\"%s\">\n",
> +    smp_lock->name
> +  );
> +  update_retval(ctx, rv);
> +
> +  indent(ctx, 2);
> +  rv = (*printf_func)(
> +    printf_arg,
> +    "<MaxSectionTime unit=\"ns\">%" PRIu32 "</MaxSectionTime>\n",
> +    smp_lock->max_section_time
> +  );
> +  update_retval(ctx, rv);
> +
> +  indent(ctx, 2);
> +  rv = (*printf_func)(
> +    printf_arg,
> +    "<MaxAcquireTime unit=\"ns\">%" PRIu32 "</MaxAcquireTime>\n",
> +    smp_lock->max_acquire_time
> +  );
> +  update_retval(ctx, rv);
> +
> +  indent(ctx, 2);
> +  rv = (*printf_func)(
> +    printf_arg,
> +    "<UsageCount>%" PRIu64 "</UsageCount>\n",
> +    smp_lock->usage_count
> +  );
> +  update_retval(ctx, rv);
> +
> +  indent(ctx, 2);
> +  rv = (*printf_func)(
> +    printf_arg,
> +    "<TotalSectionTime unit=\"ns\">%" PRIu64 "</TotalSectionTime>\n",
> +    smp_lock->total_section_time
> +  );
> +  update_retval(ctx, rv);
> +
> +  for (i = 0; i < RTEMS_PROFILING_SMP_LOCK_CONTENTION_COUNTS; ++i) {
> +    indent(ctx, 2);
> +    rv = (*printf_func)(
> +      printf_arg,
> +      "<ContentionCount initialQueueLength=\"%zu\">%" PRIu64 "</ContentionCount>\n",
> +      i,
> +      smp_lock->contention_counts[i]
> +    );
> +    update_retval(ctx, rv);
> +  }
> +
> +  indent(ctx, 1);
> +  rv = (*printf_func)(
> +    printf_arg,
> +    "</SMPLockProfilingReport>\n"
> +  );
> +  update_retval(ctx, rv);
> +}
> +
>  static void report(void *arg, const rtems_profiling_data *data)
>  {
>    context *ctx = arg;
> @@ -136,6 +203,9 @@ static void report(void *arg, const rtems_profiling_data *data)
>      case RTEMS_PROFILING_PER_CPU:
>        report_per_cpu(ctx, &data->per_cpu);
>        break;
> +    case RTEMS_PROFILING_SMP_LOCK:
> +      report_smp_lock(ctx, &data->smp_lock);
> +      break;
>    }
>  }
>
> --
> 1.7.7
>
> _______________________________________________
> rtems-devel mailing list
> rtems-devel at rtems.org
> http://www.rtems.org/mailman/listinfo/rtems-devel



More information about the devel mailing list