From 19c71cc6583c054bc820eb23585b519e116362e4 Mon Sep 17 00:00:00 2001 From: Bahadir Balban Date: Tue, 26 May 2009 17:29:10 +0300 Subject: [PATCH] Cleaned up thread_control functions --- src/api/thread.c | 117 +++++++++++------------------------------------ 1 file changed, 27 insertions(+), 90 deletions(-) diff --git a/src/api/thread.c b/src/api/thread.c index a81842e..4cee760 100644 --- a/src/api/thread.c +++ b/src/api/thread.c @@ -229,9 +229,8 @@ int arch_setup_new_thread(struct ktcb *new, struct ktcb *orig, int thread_setup_new_ids(struct task_ids *ids, unsigned int flags, struct ktcb *new, struct ktcb *orig) { - /* For tid, allocate requested id if it's available, else a new one */ - if ((ids->tid = id_get(thread_id_pool, ids->tid)) < 0) - ids->tid = id_new(thread_id_pool); + /* Allocate a new id */ + ids->tid = id_new(thread_id_pool); /* * If thread space is new or copied, @@ -279,7 +278,8 @@ int thread_setup_space(struct ktcb *tcb, struct task_ids *ids, unsigned int flag ret = (int)new; goto out; } - ids->spid = new->spid; /* Returned back to caller */ + /* New space id to be returned back to caller */ + ids->spid = new->spid; address_space_attach(tcb, new); address_space_add(new); } @@ -288,7 +288,8 @@ int thread_setup_space(struct ktcb *tcb, struct task_ids *ids, unsigned int flag ret = (int)new; goto out; } - ids->spid = new->spid; /* Returned back to caller */ + /* New space id to be returned back to caller */ + ids->spid = new->spid; address_space_attach(tcb, new); address_space_add(new); } @@ -300,107 +301,43 @@ out: int thread_create(struct task_ids *ids, unsigned int flags) { - struct ktcb *new, *orig_task = 0; + struct ktcb *new; + struct ktcb *parent; int err; flags &= THREAD_CREATE_MASK; + parent = 0; if (!(new = tcb_alloc_init())) return -ENOMEM; - if (flags == THREAD_SAME_SPACE || flags == THREAD_COPY_SPACE) { - if (!(orig_task = tcb_find(ids->tid))) { - /* Pre-mature tcb needs freeing by free_page */ - free_page(new); - return -EINVAL; + /* Set up new thread space by using space id and flags */ + if ((err = thread_setup_space(new, ids, flags)) < 0) + goto out_err; + + /* Obtain parent thread if there is one */ + if (flags == THREAD_SAME_SPACE || + flags == THREAD_COPY_SPACE) { + if (!(parent = tcb_find(ids->tid))) { + err = -EINVAL; + goto out_err; } } - if ((err = thread_setup_space(new, ids, flags)) < 0) { - /* Pre-mature tcb needs freeing by free_page */ - free_page(new); - return err; - } - - /* Set up ids and context using original tcb or from scratch */ - thread_setup_new_ids(ids, flags, new, orig_task); - arch_setup_new_thread(new, orig_task, flags); + /* Set up new thread context by using parent ids and flags */ + thread_setup_new_ids(ids, flags, new, parent); + arch_setup_new_thread(new, parent, flags); tcb_add(new); return 0; + +out_err: + /* Pre-mature tcb needs freeing by free_page */ + free_page(new); + return err; } -#if 0 -/* - * Creates a thread, with a new thread id, and depending on the flags, - * either creates a new space, uses the same space as another thread, - * or creates a new space copying the space of another thread. These - * are respectively used when creating a brand new task, creating a - * new thread in an existing address space, or forking a task. - */ -int thread_create_old(struct task_ids *ids, unsigned int flags) -{ - struct ktcb *task = 0; - struct ktcb *new = (struct ktcb *)zalloc_page(); - unsigned int create_flags = flags & THREAD_CREATE_MASK; - int err; - - if (!new) - return -ENOMEM; - - /* Determine space allocation */ - if (create_flags == THREAD_NEW_SPACE) { - /* Allocate new pgd and copy all kernel areas */ - if (!(TASK_PGD(new) = alloc_pgd())) { - free_page(new); - return -ENOMEM; - } - - copy_pgd_kern_all(TASK_PGD(new)); - } else { - /* Existing space will be used, find it from all tasks */ - list_for_each_entry(task, &global_task_list, task_list) { - /* Space ids match, can use existing space */ - if (task->spid == ids->spid) { - if (flags == THREAD_SAME_SPACE) { - TASK_PGD(new) = TASK_PGD(task); - } else { - TASK_PGD(new) = copy_page_tables(TASK_PGD(task)); - if (IS_ERR(TASK_PGD(new))) { - err = (int)TASK_PGD(new); - free_page(new); - return err; - } - } - goto out; - } - } - printk("Could not find given space, is " - "SAMESPC/COPYSPC the right flag?\n"); - BUG(); - } -out: - /* Set up new thread's tid, spid, tgid according to flags */ - thread_setup_new_ids(ids, create_flags, new, task); - - /* Initialise task's scheduling state and parameters. */ - sched_init_task(new, TASK_PRIO_NORMAL); - - /* Initialise ipc waitqueues */ - waitqueue_head_init(&new->wqh_send); - waitqueue_head_init(&new->wqh_recv); - waitqueue_head_init(&new->wqh_pager); - - arch_setup_new_thread(new, task, flags); - - /* Add task to global hlist of tasks */ - add_task_global(new); - - return 0; -} -#endif - /* * Creates, destroys and modifies threads. Also implicitly creates an address * space for a thread that doesn't already have one, or destroys it if the last