[m-rev.] for review: Introduce some parallel execution profiling code in the runtime system.

Paul Bone pbone at csse.unimelb.edu.au
Mon Jul 13 15:29:42 AEST 2009


For post-commit review by Zoltan.

Introduce some parallel execution profiling code in the runtime system.

This change adds profiling code that can be enabled with the
MR_PROFILE_PARALLEL_EXECUTION C macro and --profile-parallel-execution runtime
option.  Currently it records some very simple information about the global
scheduling of sparks.

runtime/mercury_context.c:
runtime/mercury_context.h:
	Introduce profiling of parallel execution.
	Record the number of sparks that are executed from the global spark queue.
	Record the number of contexts created in order to execute sparks from the
	global queue.
	Rename the MR_finalize_runqueue function to MR_finalize_thread_stuff and
	have it write out the profiling information when profiling is enabled.

runtime/mercury_wrapper.c:
	Parse the new --profile-parallel-execution runtime option and use it to
	enable profiling of parallel execution when support is compiled-in.
	Call MR_finalize_thread_stuff() when finalizing the runtime system, The
	former function MR_finalize_runqueue was not being called anywhere.

runtime/mercury_bootstrap.h:
	Remove the unused finalize_runqueue() macro.

doc/user_guide.texi:
	Document the --max-contexts-per-thread runtime option.
	Document and comment-out the new --profile-parallel-execution runtime
	option.

Index: doc/user_guide.texi
===================================================================
RCS file: /home/mercury1/repository/mercury/doc/user_guide.texi,v
retrieving revision 1.586
diff -u -p -b -r1.586 user_guide.texi
--- doc/user_guide.texi	7 Jul 2009 01:09:00 -0000	1.586
+++ doc/user_guide.texi	13 Jul 2009 05:14:10 -0000
@@ -9577,6 +9577,24 @@ This only has an effect if the executabl
 Tells the runtime system to use @var{num} threads
 if the program was built in a parallel grade.
 
+ at sp 1
+ at item --max-contexts-per-thread @var{num}
+ at findex --max-contexts-per-thread (runtime option)
+Tells the runtime system to create at most @var{num} contexts per
+POSIX thread.
+Each context created requires a set of stacks, setting this value too high
+can consume excess memory.
+This only has an effect if the executable was built in a low-level C parallel
+grade.
+
+ at c @sp 1
+ at c @item --profile-parallel-execution
+ at c @findex --profile-parallel-execution
+ at c Tells the runtime to collect and write out parallel execution profiling
+ at c information to a file named @file{parallel_execution_profile.txt}.
+ at c This only has an effect if the executable was built in a parallel grade
+ at c with the @samp{MR_PROFILE_PARALLEL_EXECUTION} C macro defined.
+
 @c @item -r @var{num}
 @c @findex -r (runtime option)
 @c Repeats execution of the entry point procedure @var{num} times,
Index: runtime/mercury_bootstrap.h
===================================================================
RCS file: /home/mercury1/repository/mercury/runtime/mercury_bootstrap.h,v
retrieving revision 1.40
diff -u -p -b -r1.40 mercury_bootstrap.h
--- runtime/mercury_bootstrap.h	7 Dec 2006 06:25:43 -0000	1.40
+++ runtime/mercury_bootstrap.h	13 Jul 2009 05:24:18 -0000
@@ -233,7 +233,6 @@ typedef MR_Bool			Bool;
 #define	create_context()		MR_create_context()
 #define	destroy_context(context)	MR_destroy_context(context)
 #define	init_thread_stuff(context)	MR_init_thread_stuff(context)
-#define	finalize_runqueue()		MR_finalize_runqueue()
 #define	flounder()			MR_flounder()
 #define	runnext()			MR_runnext()
 #define	schedule(context)		MR_schedule(context)
Index: runtime/mercury_context.c
===================================================================
RCS file: /home/mercury1/repository/mercury/runtime/mercury_context.c,v
retrieving revision 1.63
diff -u -p -b -r1.63 mercury_context.c
--- runtime/mercury_context.c	17 Jun 2009 03:26:00 -0000	1.63
+++ runtime/mercury_context.c	13 Jul 2009 04:43:19 -0000
@@ -66,6 +66,21 @@ MR_PendingContext       *MR_pending_cont
   MercuryLock           MR_pending_contexts_lock;
 #endif
 
+#if defined(MR_THREAD_SAFE) && defined(MR_PROFILE_PARALLEL_EXECUTION_SUPPORT) 
+MR_bool                 MR_profile_parallel_execution = MR_FALSE;
+
+static MR_Integer       MR_profile_parallel_executed_global_sparks = 0;
+static MR_Integer       MR_profile_parallel_contexts_created_for_sparks = 0;
+
+/*
+** Write out the profiling data that we collect during exceution.
+*/
+static void
+MR_write_out_profiling_parallel_execution(void);
+
+#define MR_PROFILE_PARALLEL_EXECUTION_FILENAME "parallel_execution_profile.txt"
+#endif
+
 /*
 ** free_context_list and free_small_context_list are a global linked lists
 ** of unused context structures, with regular and small stacks respectively.
@@ -126,17 +141,64 @@ MR_init_thread_stuff(void)
 }
 
 void
-MR_finalize_runqueue(void)
+MR_finalize_thread_stuff(void)
 {
 #ifdef  MR_THREAD_SAFE
     pthread_mutex_destroy(&MR_runqueue_lock);
     pthread_cond_destroy(&MR_runqueue_cond);
     pthread_mutex_destroy(&free_context_list_lock);
 #endif
+
 #ifdef  MR_LL_PARALLEL_CONJ
     pthread_mutex_destroy(&MR_sync_term_lock);
 #endif
+
+#if defined(MR_THREAD_SAFE) && defined(MR_PROFILE_PARALLEL_EXECUTION_SUPPORT)
+    if (MR_profile_parallel_execution) {
+        MR_write_out_profiling_parallel_execution();
+    }
+#endif
+}
+
+#if defined(MR_THREAD_SAFE) && defined(MR_PROFILE_PARALLEL_EXECUTION_SUPPORT) 
+/*
+ * Write out the profiling data for parallel execution.
+ *
+ * This writes out a flat text file which may be parsed by a machine or easily
+ * read by a human.  There is no advantage in using a binary format since we
+ * do this once at the end of execution and it's a small amount of data.
+ * Therefore a text file is used since it has the advantage of being human
+ * readable.
+ */
+static void
+MR_write_out_profiling_parallel_execution(void)
+{
+    FILE    *file;
+    int     result;
+
+    file = fopen(MR_PROFILE_PARALLEL_EXECUTION_FILENAME, "w");
+    if (NULL == file) goto Error;
+
+    result = fprintf(file, "Mercury parallel execution profiling data\n\n");
+    if (result < 0) goto Error;
+
+    result = fprintf(file, "Global sparks executed: %d\n",
+        MR_profile_parallel_executed_global_sparks); 
+    if (result < 0) goto Error;
+
+    result = fprintf(file, "Contexts created for global spark execution: %d\n",
+        MR_profile_parallel_contexts_created_for_sparks);
+    if (result < 0) goto Error;
+
+    if (0 != fclose(file)) goto Error;
+
+    return;
+
+    Error: 
+        perror(MR_PROFILE_PARALLEL_EXECUTION_FILENAME);
+        abort();
 }
+#endif
 
 static void 
 MR_init_context_maybe_generator(MR_Context *c, const char *id,
@@ -660,7 +722,17 @@ MR_define_entry(MR_do_runnext);
         MR_ENGINE(MR_eng_this_context) = MR_create_context("from spark",
             MR_CONTEXT_SIZE_SMALL, NULL);
         MR_load_context(MR_ENGINE(MR_eng_this_context));
+#ifdef MR_PROFILE_PARALLEL_EXECUTION_SUPPORT
+        if (MR_profile_parallel_execution) {
+            MR_atomic_inc_int(&MR_profile_parallel_contexts_created_for_sparks);
     }
+#endif
+    }
+#ifdef MR_PROFILE_PARALLEL_EXECUTION_SUPPORT
+    if (MR_profile_parallel_execution) {
+        MR_atomic_inc_int(&MR_profile_parallel_executed_global_sparks);
+    }
+#endif
     MR_parent_sp = spark.MR_spark_parent_sp;
     MR_assert(MR_parent_sp != MR_sp);
     MR_SET_THREAD_LOCAL_MUTABLES(spark.MR_spark_thread_local_mutables);
Index: runtime/mercury_context.h
===================================================================
RCS file: /home/mercury1/repository/mercury/runtime/mercury_context.h,v
retrieving revision 1.49
diff -u -p -b -r1.49 mercury_context.h
--- runtime/mercury_context.h	17 Jun 2009 03:26:00 -0000	1.49
+++ runtime/mercury_context.h	13 Jul 2009 03:33:27 -0000
@@ -346,6 +346,10 @@ extern      MR_Context  *MR_runqueue_tai
   extern    MercuryLock     MR_sync_term_lock;
 #endif
 
+#if defined(MR_THREAD_SAFE) && defined(MR_PROFILE_PARALLEL_EXECUTION_SUPPORT) 
+extern MR_bool  MR_profile_parallel_execution;
+#endif
+
 /*
 ** As well as the runqueue, we maintain a linked list of contexts
 ** and associated file descriptors that are suspended blocked for
@@ -447,9 +451,10 @@ extern  void        MR_destroy_context(M
 extern  void        MR_init_thread_stuff(void);
 
 /*
-** MR_finalize_runqueue() finalizes the lock structures for the runqueue.
+** MR_finalize_thread_stuff() finalizes the lock structures for the runqueue
+** amoung other things setup by MR_init_thread_stuff().
 */
-extern  void        MR_finalize_runqueue(void);
+extern  void        MR_finalize_thread_stuff(void);
 
 /*
 ** MR_flounder() aborts with a runtime error message. It is called if
Index: runtime/mercury_wrapper.c
===================================================================
RCS file: /home/mercury1/repository/mercury/runtime/mercury_wrapper.c,v
retrieving revision 1.196
diff -u -p -b -r1.196 mercury_wrapper.c
--- runtime/mercury_wrapper.c	17 Jun 2009 03:26:00 -0000	1.196
+++ runtime/mercury_wrapper.c	13 Jul 2009 03:33:45 -0000
@@ -1198,6 +1198,7 @@ enum MR_long_option {
     MR_GEN_NONDETSTACK_REDZONE_SIZE,
     MR_GEN_NONDETSTACK_REDZONE_SIZE_KWORDS,
     MR_MAX_CONTEXTS_PER_THREAD,
+    MR_PROFILE_PARALLEL_EXECUTION,
     MR_MDB_TTY,
     MR_MDB_IN,
     MR_MDB_OUT,
@@ -1294,6 +1295,7 @@ struct MR_option MR_long_opts[] = {
     { "gen-nondetstack-zone-size-kwords",
         1, 0, MR_GEN_NONDETSTACK_REDZONE_SIZE_KWORDS },
     { "max-contexts-per-thread",        1, 0, MR_MAX_CONTEXTS_PER_THREAD },
+    { "profile-parallel-execution",     0, 0, MR_PROFILE_PARALLEL_EXECUTION },
     { "mdb-tty",                        1, 0, MR_MDB_TTY },
     { "mdb-in",                         1, 0, MR_MDB_IN },
     { "mdb-out",                        1, 0, MR_MDB_OUT },
@@ -1706,6 +1708,12 @@ MR_process_options(int argc, char **argv
                 MR_max_contexts_per_thread = size;
                 break;
 
+            case MR_PROFILE_PARALLEL_EXECUTION:
+#if defined(MR_THREAD_SAFE) && defined(MR_PROFILE_PARALLEL_EXECUTION_SUPPORT) 
+                MR_profile_parallel_execution = MR_TRUE;
+#endif
+                break;
+
             case 'i':
             case MR_MDB_IN:
                 MR_mdb_in_filename = MR_copy_string(MR_optarg);
@@ -2890,6 +2898,8 @@ mercury_runtime_terminate(void)
 
     assert(MR_primordial_thread == pthread_self());
     MR_primordial_thread = (MercuryThread) 0;
+    
+    MR_finalize_thread_stuff();
 #endif
 
 #ifdef MR_HAVE_SYS_STAT_H
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 481 bytes
Desc: Digital signature
URL: <http://lists.mercurylang.org/archives/reviews/attachments/20090713/b5fecb96/attachment.sig>


More information about the reviews mailing list