> -----Original Message-----
> From: Martin Sebor [mailto:[EMAIL PROTECTED]
> Sent: Friday, July 07, 2006 3:46 AM
> To: [email protected]
> Subject: Re: string methods thread safety
>
> Martin Sebor wrote:
[...]
> This last part would be best implemented in the test driver
> under some generic interface similar to rw_thread_create()
> (e.g., rw_process_create()).

Martin, I implemented the functions rw_process_create() and rw_process_join():

--------------------------------------
typedef long rw_pid_t;

// returns pid of the created process
// returns -1 if failed
// note: argv[0] should be equal to path
_TEST_EXPORT rw_pid_t
rw_process_create (const char* path, char* const argv []);

// returns pid of the specified process
// returns -1 if failed
// result is a pointer to a buffer where the result code
// of the specified process will be stored, or NULL
_TEST_EXPORT rw_pid_t
rw_process_join (rw_pid_t pid, int* result);
--------------------------------------

  The diff files is attached. What do you think about this?

Farid.
Index: rwthread.cpp
===================================================================
--- rwthread.cpp        (revision 423417)
+++ rwthread.cpp        (working copy)
@@ -425,3 +425,70 @@
 }
 
 }   // extern "C"
+
+/**************************************************************************/
+
+#if defined (_WIN32) || defined (_WIN64)
+
+#include <process.h>      // for spawnp(), cwait()
+
+#else
+
+#include <sys/types.h>
+#include <sys/wait.h>   // for waitpid()
+#include <unistd.h>     // for fork(), execv()
+
+#include <stdlib.h>     // for exit()
+
+#include <driver.h>     // for rw_fatal()
+
+#ifndef P_NOWAIT
+#define P_NOWAIT 1
+#endif
+
+#ifndef WAIT_CHILD
+#define WAIT_CHILD 0
+#endif
+
+static rw_pid_t spawnv(int, const char* path, char* const argv [])
+{
+    if (rw_pid_t child_pid = fork ())
+        // the parent process
+        return child_pid;
+
+    // the child process
+    execv (path, argv);
+
+    // the execvp returns only if an error occurs
+    rw_fatal (0, __FILE__, __LINE__, "execvp failed: : errno = %{#m} (%{m})");
+
+    exit (1);
+}
+
+static rw_pid_t cwait(int* status, rw_pid_t pid, int)
+{
+    const rw_pid_t res = waitpid (pid, status, 0);
+
+    if (res == pid && status)
+        *status = WEXITSTATUS (*status);
+
+    return res;
+}
+
+#endif
+
+extern "C" {
+
+_TEST_EXPORT rw_pid_t
+rw_process_create (const char* path, char* const argv[])
+{
+    return spawnv (P_NOWAIT, path, argv);
+}
+
+_TEST_EXPORT rw_pid_t
+rw_process_join (rw_pid_t pid, int* result)
+{
+    return cwait (result, pid, WAIT_CHILD);
+}
+
+}   // extern "C"
Index: rwthread.h
===================================================================
--- rwthread.h  (revision 423417)
+++ rwthread.h  (working copy)
@@ -29,6 +29,8 @@
 
 struct rw_thread_attr_t;
 
+typedef long rw_pid_t;
+
 struct rw_thread_t
 {
     long  threadno;
@@ -54,6 +56,19 @@
                 void* (*)(void*),
                 void**);
 
+// returns pid of the created process
+// returns -1 if failed
+// note: argv[0] should be equal to path
+_TEST_EXPORT rw_pid_t
+rw_process_create (const char*, char* const []);
+
+// returns pid of the specified process
+// returns -1 if failed
+// result is a pointer to a buffer where the result code
+// of the specified process will be stored, or NULL
+_TEST_EXPORT rw_pid_t
+rw_process_join (rw_pid_t, int*);
+
 }   // extern "C"
 
 #endif   // RW_RWTHREAD_H_INCLUDED

Reply via email to