Date: Thu, 14 Apr 2005 02:41:23 GMT From: David Xu <davidxu@FreeBSD.org> To: Perforce Change Reviews <perforce@freebsd.org> Subject: PERFORCE change 75121 for review Message-ID: <200504140241.j3E2fNTK010965@repoman.freebsd.org>
index | next in thread | raw e-mail
http://perforce.freebsd.org/chv.cgi?CH=75121 Change 75121 by davidxu@davidxu_celeron on 2005/04/14 02:41:07 Implement thr_create2, not tested. Affected files ... .. //depot/projects/davidxu_thread/src/sys/kern/kern_thr.c#12 edit Differences ... ==== //depot/projects/davidxu_thread/src/sys/kern/kern_thr.c#12 (text+ko) ==== @@ -182,6 +182,130 @@ } int +thr_create2(struct thread *td, struct thr_create2_args *uap) +{ + struct thr_param param; + struct thread *newtd; + long id; + int error; + struct ksegrp *kg, *newkg; + struct proc *p; + int scope_sys, linkkg; + stack_t stack; + + p = td->td_proc; + kg = td->td_ksegrp; + if (uap->param_size != sizeof(param)) + return (EINVAL); + if ((error = copyin(uap->param, ¶m, sizeof(param)))) + return (error); + + /* Have race condition but it is cheap. */ + if ((p->p_numksegrps >= max_groups_per_proc) || + (p->p_numthreads >= max_threads_per_proc)) { + return (EPROCLIM); + } + scope_sys = (param.flags & THR_SYSTEM_SCOPE) != 0; + if (thr_scope == 1) + scope_sys = 0; + else if (thr_scope == 2) + scope_sys = 1; + + /* Initialize our td and new ksegrp.. */ + newtd = thread_alloc(); + + /* + * Try the copyout as soon as we allocate the td so we don't have to + * tear things down in a failure case below. + */ + id = newtd->td_tid; + if ((error = copyout(&id, param.child_tid, sizeof(long))) || + (error = copyout(&id, ¶m.parent_tid, sizeof(long)))) { + thread_free(newtd); + return (error); + } + bzero(&newtd->td_startzero, + __rangeof(struct thread, td_startzero, td_endzero)); + bcopy(&td->td_startcopy, &newtd->td_startcopy, + __rangeof(struct thread, td_startcopy, td_endcopy)); + newtd->td_proc = td->td_proc; + newtd->td_ucred = crhold(td->td_ucred); + + /* Set up our machine context. */ + stack.ss_sp = param.stack_base; + stack.ss_size = param.stack_size; + /* fork context from current thread. */ + cpu_set_upcall(newtd, td); + /* set upcall address to user thread entry function. */ + cpu_set_upcall_kse(newtd, param.start_func, param.arg, &stack); + /* setup user TLS address and TLS pointer register. */ + cpu_set_user_tls(newtd, param.tls_base, param.tls_size, param.tls_seg); + if ((td->td_proc->p_flag & P_HADTHREADS) == 0) { + p->p_procscopegrp = kg; + mtx_lock_spin(&sched_lock); + sched_set_concurrency(kg, + thr_concurrency ? thr_concurrency : (2*mp_ncpus)); + mtx_unlock_spin(&sched_lock); + } + + linkkg = 0; + if (scope_sys) { + linkkg = 1; + newkg = ksegrp_alloc(); + bzero(&newkg->kg_startzero, + __rangeof(struct ksegrp, kg_startzero, kg_endzero)); + bcopy(&kg->kg_startcopy, &newkg->kg_startcopy, + __rangeof(struct ksegrp, kg_startcopy, kg_endcopy)); + sched_init_concurrency(newkg); + PROC_LOCK(td->td_proc); + } else { +retry: + PROC_LOCK(td->td_proc); + if ((newkg = p->p_procscopegrp) == NULL) { + PROC_UNLOCK(p); + newkg = ksegrp_alloc(); + bzero(&newkg->kg_startzero, + __rangeof(struct ksegrp, kg_startzero, kg_endzero)); + bcopy(&kg->kg_startcopy, &newkg->kg_startcopy, + __rangeof(struct ksegrp, kg_startcopy, kg_endcopy)); + PROC_LOCK(p); + if (p->p_procscopegrp == NULL) { + p->p_procscopegrp = newkg; + sched_init_concurrency(newkg); + sched_set_concurrency(newkg, + thr_concurrency ? thr_concurrency : (2*mp_ncpus)); + linkkg = 1; + } else { + PROC_UNLOCK(p); + ksegrp_free(newkg); + goto retry; + } + } + } + + td->td_proc->p_flag |= P_HADTHREADS; + newtd->td_sigmask = td->td_sigmask; + mtx_lock_spin(&sched_lock); + if (linkkg) + ksegrp_link(newkg, p); + thread_link(newtd, newkg); + PROC_UNLOCK(p); + + /* let the scheduler know about these things. */ + if (linkkg) + sched_fork_ksegrp(td, newkg); + sched_fork_thread(td, newtd); + TD_SET_CAN_RUN(newtd); + if ((uap->flags & THR_SUSPENDED) == 0) + setrunqueue(newtd, SRQ_BORING); + mtx_unlock_spin(&sched_lock); + +out: + return (error); + +} + +int thr_self(struct thread *td, struct thr_self_args *uap) /* long *id */ {help
Want to link to this message? Use this
URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200504140241.j3E2fNTK010965>
