1 /*
   2  * This file and its contents are supplied under the terms of the
   3  * Common Development and Distribution License ("CDDL"), version 1.0.
   4  * You may only use this file in accordance with the terms of version
   5  * 1.0 of the CDDL.
   6  *
   7  * A full copy of the text of the CDDL should have accompanied this
   8  * source.  A copy of the CDDL is also available via the Internet at
   9  * http://www.illumos.org/license/CDDL.
  10  */
  11 
  12 /*
  13  * Copyright 2013 Nexenta Systems, Inc.  All rights reserved.
  14  * Copyright 2017 RackTop Systems.
  15  */
  16 
  17 #include <sys/cmn_err.h>
  18 #include <sys/thread.h>
  19 #include <sys/zone.h>
  20 #include <sys/proc.h>
  21 
  22 #define _SYNCH_H        /* keep out <synch.h> */
  23 #include <thread.h>
  24 
  25 /*
  26  * Get the current kthread_t pointer.
  27  */
  28 kthread_t *
  29 _curthread(void)
  30 {
  31         thread_t tid;
  32 
  33         tid = thr_self();
  34         return ((kthread_t *)(uintptr_t)tid);
  35 }
  36 
  37 /*
  38  * Create a thread.
  39  *
  40  * thread_create() blocks for memory if necessary.  It never fails.
  41  */
  42 /* ARGSUSED */
  43 kthread_t *
  44 thread_create(
  45         caddr_t stk,
  46         size_t  stksize,
  47         void    (*func)(),
  48         void    *arg,
  49         size_t  len,
  50         struct proc *pp,
  51         int     state,
  52         pri_t   pri)
  53 {
  54         void * (*thr_func)(void *);
  55         thread_t newtid;
  56         int thr_flags = 0;
  57         int rc;
  58 
  59         thr_flags = THR_BOUND;
  60 
  61         switch (state) {
  62         case TS_RUN:
  63         case TS_ONPROC:
  64                 break;
  65         case TS_STOPPED:
  66                 thr_flags |= THR_SUSPENDED;
  67                 break;
  68         default:
  69                 cmn_err(CE_PANIC, "thread_create: invalid state");
  70                 break;
  71         }
  72 
  73         thr_func = (void *(*)(void *))func;
  74         rc = thr_create(NULL, 0, thr_func, arg, thr_flags, &newtid);
  75         if (rc != 0)
  76                 cmn_err(CE_PANIC, "thread_create failed, rc=%d", rc);
  77 
  78         return ((void *)(uintptr_t)newtid);
  79 }
  80 
  81 void
  82 thread_exit(void)
  83 {
  84         thr_exit(NULL);
  85 }
  86 
  87 void
  88 thread_join(kt_did_t id)
  89 {
  90         thread_t thr_id;
  91 
  92         thr_id = (thread_t)id;
  93         (void) thr_join(thr_id, NULL, NULL);
  94 }
  95 
  96 void
  97 tsignal(kthread_t *kt, int sig)
  98 {
  99         thread_t tid = (thread_t)(uintptr_t)kt;
 100 
 101         (void) thr_kill(tid, sig);
 102 }
 103 
 104 
 105 /*ARGSUSED*/
 106 kthread_t *
 107 zthread_create(
 108     caddr_t stk,
 109     size_t stksize,
 110     void (*func)(),
 111     void *arg,
 112     size_t len,
 113     pri_t pri)
 114 {
 115         kthread_t *t;
 116 
 117         t = thread_create(stk, stksize, func, arg, len, NULL, TS_RUN, pri);
 118 
 119         return (t);
 120 }
 121 
 122 void
 123 zthread_exit(void)
 124 {
 125         thread_exit();
 126         /* NOTREACHED */
 127 }
 128 
 129 void
 130 tsd_create(uint_t *keyp, void (*destructor)(void *))
 131 {
 132         VERIFY0(thr_keycreate(keyp, destructor));
 133 }
 134 
 135 /*ARGSUSED*/
 136 void
 137 tsd_destroy(uint_t *keyp)
 138 {}
 139 
 140 void *
 141 tsd_get(uint_t key)
 142 {
 143         void *value;
 144 
 145         return (thr_getspecific(key, &value) ? NULL : value);
 146 }
 147 
 148 int
 149 tsd_set(uint_t key, void *value)
 150 {
 151         return (thr_setspecific(key, value));
 152 }