Fix Solaris thread dependency by using pthreads
[zfs.git] / lib / libzpool / include / sys / zfs_context.h
index a50e4b0..55b117c 100644 (file)
@@ -19,8 +19,7 @@
  * CDDL HEADER END
  */
 /*
- * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
- * Use is subject to license terms.
+ * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
  */
 
 #ifndef _SYS_ZFS_CONTEXT_H
@@ -50,8 +49,7 @@ extern "C" {
 #include <errno.h>
 #include <string.h>
 #include <strings.h>
-#include <synch.h>
-#include <thread.h>
+#include <pthread.h>
 #include <assert.h>
 #include <alloca.h>
 #include <umem.h>
@@ -59,6 +57,7 @@ extern "C" {
 #include <atomic.h>
 #include <dirent.h>
 #include <time.h>
+#include <libsysevent.h>
 #include <sys/note.h>
 #include <sys/types.h>
 #include <sys/cred.h>
@@ -73,6 +72,8 @@ extern "C" {
 #include <sys/kstat.h>
 #include <sys/u8_textprep.h>
 #include <sys/sysevent/eventdefs.h>
+#include <sys/sysevent/dev.h>
+#include <sys/sunddi.h>
 
 /*
  * Debugging
@@ -88,6 +89,8 @@ extern "C" {
 #define        CE_PANIC        3       /* panic                */
 #define        CE_IGNORE       4       /* print nothing        */
 
+extern int aok;
+
 /*
  * ZFS debugging
  */
@@ -103,21 +106,27 @@ extern void vpanic(const char *, __va_list);
 
 #define        fm_panic        panic
 
+extern int aok;
+
 /* This definition is copied from assert.h. */
 #if defined(__STDC__)
 #if __STDC_VERSION__ - 0 >= 199901L
-#define        verify(EX) (void)((EX) || \
+#define        zverify(EX) (void)((EX) || (aok) || \
        (__assert_c99(#EX, __FILE__, __LINE__, __func__), 0))
 #else
-#define        verify(EX) (void)((EX) || (__assert(#EX, __FILE__, __LINE__), 0))
+#define        zverify(EX) (void)((EX) || (aok) || \
+       (__assert(#EX, __FILE__, __LINE__), 0))
 #endif /* __STDC_VERSION__ - 0 >= 199901L */
 #else
-#define        verify(EX) (void)((EX) || (_assert("EX", __FILE__, __LINE__), 0))
+#define        zverify(EX) (void)((EX) || (aok) || \
+       (_assert("EX", __FILE__, __LINE__), 0))
 #endif /* __STDC__ */
 
 
-#define        VERIFY  verify
-#define        ASSERT  assert
+#define        VERIFY  zverify
+#define        ASSERT  zverify
+#undef assert
+#define        assert  zverify
 
 extern void __assert(const char *, const char *, int);
 
@@ -128,7 +137,7 @@ extern void __assert(const char *, const char *, int);
 #define        VERIFY3_IMPL(LEFT, OP, RIGHT, TYPE) do { \
        const TYPE __left = (TYPE)(LEFT); \
        const TYPE __right = (TYPE)(RIGHT); \
-       if (!(__left OP __right)) { \
+       if (!(__left OP __right) && (!aok)) { \
                char *__buf = alloca(256); \
                (void) snprintf(__buf, 256, "%s %s %s (0x%llx %s 0x%llx)", \
                        #LEFT, #OP, #RIGHT, \
@@ -187,15 +196,55 @@ _NOTE(CONSTCOND) } while (0)
 /*
  * Threads
  */
-#define        curthread       ((void *)(uintptr_t)thr_self())
+#define        TS_MAGIC                0x72f158ab4261e538ull
+#define        TS_RUN                  0x00000002
+#ifdef __linux__
+#define        STACK_SIZE              8192    /* Linux x86 and amd64 */
+#else
+#define        STACK_SIZE              24576   /* Solaris */
+#endif
+
+#ifdef NPTL_GUARD_WITHIN_STACK
+#define        EXTRA_GUARD_BYTES       PAGESIZE
+#else
+#define        EXTRA_GUARD_BYTES       0
+#endif
+
+/* in libzpool, p0 exists only to have its address taken */
+typedef struct proc {
+       uintptr_t       this_is_never_used_dont_dereference_it;
+} proc_t;
+
+extern struct proc p0;
 
-typedef struct kthread kthread_t;
+typedef void (*thread_func_t)(void *);
+typedef void (*thread_func_arg_t)(void *);
+typedef pthread_t kt_did_t;
 
+typedef struct kthread {
+       kt_did_t        t_tid;
+       thread_func_t   t_func;
+       void *          t_arg;
+} kthread_t;
+
+#define        tsd_get(key)                    pthread_getspecific(key)
+#define        tsd_set(key, val)               pthread_setspecific(key, val)
+#define        curthread                       zk_thread_current()
+#define        thread_exit                     zk_thread_exit
 #define        thread_create(stk, stksize, func, arg, len, pp, state, pri)     \
-       zk_thread_create(func, arg)
-#define        thread_exit() thr_exit(NULL)
+       zk_thread_create(stk, stksize, (thread_func_t)func, arg,        \
+                        len, NULL, state, pri)
+#define        thread_join(t)                  zk_thread_join(t)
+#define        newproc(f,a,cid,pri,ctp,pid)    (ENOSYS)
+
+extern kthread_t *zk_thread_current(void);
+extern void zk_thread_exit(void);
+extern kthread_t *zk_thread_create(caddr_t stk, size_t  stksize,
+       thread_func_t func, void *arg, size_t len,
+       proc_t *pp, int state, pri_t pri);
+extern void zk_thread_join(kt_did_t tid);
 
-extern kthread_t *zk_thread_create(void (*func)(), void *arg);
+#define        PS_NONE         -1
 
 #define        issig(why)      (FALSE)
 #define        ISSIG(thr, why) (FALSE)
@@ -203,53 +252,52 @@ extern kthread_t *zk_thread_create(void (*func)(), void *arg);
 /*
  * Mutexes
  */
+#define        MTX_MAGIC       0x9522f51362a6e326ull
+#define        MTX_INIT        ((void *)NULL)
+#define        MTX_DEST        ((void *)-1UL)
+
 typedef struct kmutex {
        void            *m_owner;
-       boolean_t       initialized;
-       mutex_t         m_lock;
+       uint64_t        m_magic;
+       pthread_mutex_t m_lock;
 } kmutex_t;
 
-#define        MUTEX_DEFAULT   USYNC_THREAD
-#undef MUTEX_HELD
-#define        MUTEX_HELD(m) _mutex_held(&(m)->m_lock)
+#define        MUTEX_DEFAULT   0
+#define MUTEX_HELD(m)  ((m)->m_owner == curthread)
+#define        MUTEX_NOT_HELD(m) (!MUTEX_HELD(m))
 
-/*
- * Argh -- we have to get cheesy here because the kernel and userland
- * have different signatures for the same routine.
- */
-extern int _mutex_init(mutex_t *mp, int type, void *arg);
-extern int _mutex_destroy(mutex_t *mp);
-
-#define        mutex_init(mp, b, c, d)         zmutex_init((kmutex_t *)(mp))
-#define        mutex_destroy(mp)               zmutex_destroy((kmutex_t *)(mp))
-
-extern void zmutex_init(kmutex_t *mp);
-extern void zmutex_destroy(kmutex_t *mp);
+extern void mutex_init(kmutex_t *mp, char *name, int type, void *cookie);
+extern void mutex_destroy(kmutex_t *mp);
 extern void mutex_enter(kmutex_t *mp);
 extern void mutex_exit(kmutex_t *mp);
 extern int mutex_tryenter(kmutex_t *mp);
 extern void *mutex_owner(kmutex_t *mp);
+extern int mutex_held(kmutex_t *mp);
 
 /*
  * RW locks
  */
+#define        RW_MAGIC        0x4d31fb123648e78aull
+#define        RW_INIT         ((void *)NULL)
+#define        RW_DEST         ((void *)-1UL)
+
 typedef struct krwlock {
-       void            *rw_owner;
-       boolean_t       initialized;
-       rwlock_t        rw_lock;
+       void                    *rw_owner;
+       void                    *rw_wr_owner;
+       uint64_t                rw_magic;
+       pthread_rwlock_t        rw_lock;
+       uint_t                  rw_readers;
 } krwlock_t;
 
 typedef int krw_t;
 
 #define        RW_READER       0
 #define        RW_WRITER       1
-#define        RW_DEFAULT      USYNC_THREAD
-
-#undef RW_READ_HELD
-#define        RW_READ_HELD(x)         _rw_read_held(&(x)->rw_lock)
+#define RW_DEFAULT     RW_READER
 
-#undef RW_WRITE_HELD
-#define        RW_WRITE_HELD(x)        _rw_write_held(&(x)->rw_lock)
+#define        RW_READ_HELD(x)         ((x)->rw_readers > 0)
+#define        RW_WRITE_HELD(x)        ((x)->rw_wr_owner == curthread)
+#define        RW_LOCK_HELD(x)         (RW_READ_HELD(x) || RW_WRITE_HELD(x))
 
 extern void rw_init(krwlock_t *rwlp, char *name, int type, void *arg);
 extern void rw_destroy(krwlock_t *rwlp);
@@ -267,9 +315,14 @@ extern gid_t *crgetgroups(cred_t *cr);
 /*
  * Condition variables
  */
-typedef cond_t kcondvar_t;
+#define CV_MAGIC       0xd31ea9a83b1b30c4ull
 
-#define        CV_DEFAULT      USYNC_THREAD
+typedef struct kcondvar {
+       uint64_t                cv_magic;
+       pthread_cond_t          cv;
+} kcondvar_t;
+
+#define        CV_DEFAULT      0
 
 extern void cv_init(kcondvar_t *cv, char *name, int type, void *arg);
 extern void cv_destroy(kcondvar_t *cv);
@@ -302,10 +355,21 @@ extern void kstat_delete(kstat_t *);
 #define        kmem_cache_alloc(_c, _f) umem_cache_alloc(_c, _f)
 #define        kmem_cache_free(_c, _b) umem_cache_free(_c, _b)
 #define        kmem_debugging()        0
-#define        kmem_cache_reap_now(c)
+#define        kmem_cache_reap_now(_c)         /* nothing */
+#define        kmem_cache_set_move(_c, _cb)    /* nothing */
+#define        POINTER_INVALIDATE(_pp)         /* nothing */
+#define        POINTER_IS_VALID(_p)    0
 
 typedef umem_cache_t kmem_cache_t;
 
+typedef enum kmem_cbrc {
+       KMEM_CBRC_YES,
+       KMEM_CBRC_NO,
+       KMEM_CBRC_LATER,
+       KMEM_CBRC_DONT_NEED,
+       KMEM_CBRC_DONT_KNOW
+} kmem_cbrc_t;
+
 /*
  * Task queues
  */
@@ -316,19 +380,27 @@ typedef void (task_func_t)(void *);
 #define        TASKQ_PREPOPULATE       0x0001
 #define        TASKQ_CPR_SAFE          0x0002  /* Use CPR safe protocol */
 #define        TASKQ_DYNAMIC           0x0004  /* Use dynamic thread scheduling */
+#define        TASKQ_THREADS_CPU_PCT   0x0008  /* Scale # threads by # cpus */
+#define        TASKQ_DC_BATCH          0x0010  /* Mark threads as batch */
 
 #define        TQ_SLEEP        KM_SLEEP        /* Can block for memory */
 #define        TQ_NOSLEEP      KM_NOSLEEP      /* cannot block for memory; may fail */
-#define        TQ_NOQUEUE      0x02    /* Do not enqueue if can't dispatch */
+#define        TQ_NOQUEUE      0x02            /* Do not enqueue if can't dispatch */
+#define        TQ_FRONT        0x08            /* Queue in front */
 
 extern taskq_t *system_taskq;
 
 extern taskq_t *taskq_create(const char *, int, pri_t, int, int, uint_t);
+#define        taskq_create_proc(a, b, c, d, e, p, f) \
+           (taskq_create(a, b, c, d, e, f))
+#define        taskq_create_sysdc(a, b, d, e, p, dc, f) \
+           (taskq_create(a, b, maxclsyspri, d, e, f))
 extern taskqid_t taskq_dispatch(taskq_t *, task_func_t, void *, uint_t);
 extern void    taskq_destroy(taskq_t *);
 extern void    taskq_wait(taskq_t *);
-extern int     taskq_member(taskq_t *, void *);
+extern int     taskq_member(taskq_t *, kthread_t *);
 extern void    system_taskq_init(void);
+extern void    system_taskq_fini(void);
 
 #define        XVA_MAPSIZE     3
 #define        XVA_MAGIC       0x78766174
@@ -342,6 +414,7 @@ typedef struct vnode {
        char            *v_path;
 } vnode_t;
 
+#define        AV_SCANSTAMP_SZ 32              /* length of anti-virus scanstamp */
 
 typedef struct xoptattr {
        timestruc_t     xoa_createtime; /* Create time of file */
@@ -357,6 +430,10 @@ typedef struct xoptattr {
        uint8_t         xoa_opaque;
        uint8_t         xoa_av_quarantined;
        uint8_t         xoa_av_modified;
+       uint8_t         xoa_av_scanstamp[AV_SCANSTAMP_SZ];
+       uint8_t         xoa_reparse;
+       uint8_t         xoa_offline;
+       uint8_t         xoa_sparse;
 } xoptattr_t;
 
 typedef struct vattr {
@@ -403,9 +480,11 @@ typedef struct vsecattr {
 
 #define        CRCREAT         0
 
+extern int fop_getattr(vnode_t *vp, vattr_t *vap);
+
 #define        VOP_CLOSE(vp, f, c, o, cr, ct)  0
 #define        VOP_PUTPAGE(vp, of, sz, fl, cr, ct)     0
-#define        VOP_GETATTR(vp, vap, fl, cr, ct)  ((vap)->va_size = (vp)->v_size, 0)
+#define        VOP_GETATTR(vp, vap, fl, cr, ct)  fop_getattr((vp), (vap));
 
 #define        VOP_FSYNC(vp, f, cr, ct)        fsync((vp)->v_fd)
 
@@ -430,20 +509,25 @@ extern vnode_t *rootdir;
 /*
  * Random stuff
  */
-#define        lbolt   (gethrtime() >> 23)
-#define        lbolt64 (gethrtime() >> 23)
+#define        ddi_get_lbolt()         (gethrtime() >> 23)
+#define        ddi_get_lbolt64()       (gethrtime() >> 23)
 #define        hz      119     /* frequency when using gethrtime() >> 23 for lbolt */
 
 extern void delay(clock_t ticks);
 
 #define        gethrestime_sec() time(NULL)
+#define        gethrestime(t) \
+       do {\
+               (t)->tv_sec = gethrestime_sec();\
+               (t)->tv_nsec = 0;\
+       } while (0);
 
 #define        max_ncpus       64
 
 #define        minclsyspri     60
 #define        maxclsyspri     99
 
-#define        CPU_SEQID       (thr_self() & (max_ncpus - 1))
+#define        CPU_SEQID       (pthread_self() & (max_ncpus - 1))
 
 #define        kcred           NULL
 #define        CRED()          NULL
@@ -487,6 +571,9 @@ typedef struct callb_cpr {
 #define        zone_dataset_visible(x, y)      (1)
 #define        INGLOBALZONE(z)                 (1)
 
+extern char *kmem_asprintf(const char *fmt, ...);
+#define        strfree(str) kmem_free((str), strlen(str)+1)
+
 /*
  * Hostname information
  */
@@ -494,6 +581,9 @@ extern char hw_serial[];    /* for userland-emulated hostid access */
 extern int ddi_strtoul(const char *str, char **nptr, int base,
     unsigned long *result);
 
+extern int ddi_strtoull(const char *str, char **nptr, int base,
+    u_longlong_t *result);
+
 /* ZFS Boot Related stuff. */
 
 struct _buf {
@@ -540,6 +630,10 @@ typedef struct ksiddomain {
 ksiddomain_t *ksid_lookupdomain(const char *);
 void ksiddomain_rele(ksiddomain_t *);
 
+#define        DDI_SLEEP       KM_SLEEP
+#define        ddi_log_sysevent(_a, _b, _c, _d, _e, _f, _g) \
+       sysevent_post_event(_c, _d, _b, "libzpool", _e, _f)
+
 #ifdef __cplusplus
 }
 #endif