summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/threads/thread.c3
-rw-r--r--src/threads/thread.h24
-rw-r--r--src/userprog/process.c24
3 files changed, 45 insertions, 6 deletions
diff --git a/src/threads/thread.c b/src/threads/thread.c
index 43dd8e3..3112a71 100644
--- a/src/threads/thread.c
+++ b/src/threads/thread.c
@@ -436,6 +436,9 @@ init_thread (struct thread *t, const char *name, int priority)
strlcpy (t->name, name, sizeof t->name);
t->stack = (uint8_t *) t + PGSIZE;
t->priority = priority;
+#ifdef USERPROG
+ list_init (&t->children);
+#endif
t->magic = THREAD_MAGIC;
}
diff --git a/src/threads/thread.h b/src/threads/thread.h
index e3c426d..b822b64 100644
--- a/src/threads/thread.h
+++ b/src/threads/thread.h
@@ -4,6 +4,7 @@
#include <debug.h>
#include <list.h>
#include <stdint.h>
+#include "threads/synch.h"
#define MAX_FDS 128 /* Max number of file descriptors per thread */
@@ -21,6 +22,24 @@ enum thread_status
typedef int tid_t;
#define TID_ERROR ((tid_t) -1) /* Error value for tid_t. */
+/* The relationship between a parent and child process.
+ It is setup by the child in
+ The child reports its exit status by setting exit_status
+ and upping exit_sema.
+ The parent places the parent_child element in its list of children.
+*/
+struct parent_child
+ {
+ struct list_elem elem; // owned by the parent
+
+ struct semaphore exit_sema;
+
+ struct lock l;
+ int exit_status;
+ int alive_count;
+
+ };
+
/* Thread priorities. */
#define PRI_MIN 0 /* Lowest priority. */
#define PRI_DEFAULT 31 /* Default priority. */
@@ -98,7 +117,10 @@ struct thread
#ifdef USERPROG
/* Owned by userprog/process.c. */
uint32_t *pagedir; /* Page directory. */
- struct file **fds; /* Pointer to array of file descriptors. */
+ struct file **fds; /* Pointer to array of file descriptors. */
+
+ struct parent_child parent; // one parent
+ struct list children; // multiple children
#endif
/* Owned by thread.c. */
diff --git a/src/userprog/process.c b/src/userprog/process.c
index 5897c84..5f7448b 100644
--- a/src/userprog/process.c
+++ b/src/userprog/process.c
@@ -28,6 +28,7 @@ struct start_process_args
// child -> parent
bool success;
+ struct list_elem *child_elem; // list_elem to insert into list of children
};
static thread_func start_process NO_RETURN;
@@ -41,9 +42,11 @@ tid_t
process_execute (const char *file_name)
{
struct start_process_args args; // stack allocated since we know we wait for thread_create to finish reading
+ struct thread *t;
tid_t tid;
- printf("%s starting %s\n", thread_current ()->name, file_name);
+ t = thread_current ();
+ printf("%s starting %s\n", t->name, file_name);
sema_init (&args.sema, 0);
@@ -64,9 +67,11 @@ process_execute (const char *file_name)
if (tid != TID_ERROR) {
sema_down (&args.sema);
- //TODO push to list of children
- if (!args.success)
+ if (args.success) {
+ list_push_back (&t->children, args.child_elem);
+ } else {
tid = -1;
+ }
}
palloc_free_page (args.file_name);
return tid;
@@ -79,17 +84,26 @@ start_process (void *args_)
{
struct start_process_args *args = args_;
struct intr_frame if_;
+ struct thread *t;
bool success;
+ t = thread_current ();
+
/* Initialize interrupt frame and load executable. */
memset (&if_, 0, sizeof if_);
if_.gs = if_.fs = if_.es = if_.ds = if_.ss = SEL_UDSEG;
if_.cs = SEL_UCSEG;
if_.eflags = FLAG_IF | FLAG_MBS;
- printf("reading\n");
success = load (args->file_name, &if_.eip, &if_.esp);
-
args->success = success;
+
+ if (success) {
+ sema_init (&t->parent.exit_sema, 0);
+ lock_init (&t->parent.l);
+
+ args->child_elem = &t->parent.elem;
+ }
+
sema_up (&args->sema);
/* If load failed, quit. */