// D import file generated from 'src\core\thread.di'
module core.thread;
public import core.time;

version = StackGrowsDown;
version (Posix)
{
    import core.sys.posix.unistd;
    alias core.sys.posix.unistd.getpid getpid;
}
else
{
    version (Windows)
{
    import core.sys.windows.windows;
    alias core.sys.windows.windows.GetCurrentProcessId getpid;
}
}
class ThreadException : Exception
{
    this(string msg, string file = __FILE__, size_t line = __LINE__, Throwable next = null);
    this(string msg, Throwable next, string file = __FILE__, size_t line = __LINE__);
}
class FiberException : Exception
{
    this(string msg, string file = __FILE__, size_t line = __LINE__, Throwable next = null);
    this(string msg, Throwable next, string file = __FILE__, size_t line = __LINE__);
}
class Thread
{
    this(void function() fn, size_t sz = 0);
    this(void delegate() dg, size_t sz = 0);
    ~this();
    final void start();

    final Throwable join(bool rethrow = true);

    final @property string name();

    final @property void name(string val);

    final @property bool isDaemon();

    final @property void isDaemon(bool val);

    final @property bool isRunning();

    const __gshared int PRIORITY_MIN;

    const __gshared int PRIORITY_MAX;

    final @property int priority();

    final @property void priority(int val);

    static void sleep(Duration val);

    static void sleep(long period);

    static void yield();

    static Thread getThis();

    static Thread[] getAll();

    static int opApply(scope int delegate(ref Thread) dg);

    shared static this();
    deprecated alias thread_findByAddr findThread;

    private 
{
    version (Windows)
{
    alias uint TLSKey;
    alias uint ThreadAddr;
}
else
{
    version (Posix)
{
    import core.sys.posix.pthread;
    alias pthread_key_t TLSKey;
    alias pthread_t ThreadAddr;
}
}
    version (D_LP64)
{
    version (Windows)
{
    enum ThreadSize = 312;
}
else
{
    version (OSX)
{
    enum ThreadSize = 320;
}
else
{
    version (Posix)
{
    enum ThreadSize = 184;
}
else
{
    static assert(0,"Platform not supported.");
}
}
}
}
else
{
    static assert((void*).sizeof == 4);
    version (Windows)
{
    enum ThreadSize = 128;
}
else
{
    version (OSX)
{
    enum ThreadSize = 128;
}
else
{
    version (Posix)
{
    enum ThreadSize = 92;
}
else
{
    static assert(0,"Platform not supported.");
}
}
}
}
    void[ThreadSize - __traits(classInstanceSize,Object)] data = void;
}
}
extern (C) void thread_init();

extern (C) bool thread_isMainThread();

extern (C) Thread thread_attachThis();

version (Windows)
{
    extern (C) Thread thread_attachByAddr(Thread.ThreadAddr addr);

    extern (C) Thread thread_attachByAddrB(Thread.ThreadAddr addr, void* bstack);

    deprecated extern (C) nothrow void thread_setNeedLock(bool need);


    deprecated alias thread_attachByAddr thread_attach;

    deprecated alias thread_detachByAddr thread_detach;

}
extern (C) void thread_detachThis();

extern (C) void thread_detachByAddr(Thread.ThreadAddr addr);

static Thread thread_findByAddr(Thread.ThreadAddr addr);

extern (C) void thread_joinAll();

extern (C) nothrow bool thread_needLock();

extern (C) void thread_suspendAll();

extern (C) void thread_resumeAll();

enum ScanType 
{
stack,
tls,
}
alias void delegate(void*, void*) ScanAllThreadsFn;
alias void delegate(ScanType, void*, void*) ScanAllThreadsTypeFn;
extern (C) void thread_scanAllType(scope ScanAllThreadsTypeFn scan, void* curStackTop = null);

extern (C) void thread_scanAll(scope ScanAllThreadsFn scan, void* curStackTop = null);

enum IsMarked : int
{
no,
yes,
unknown,
}
alias IsMarked delegate(void* addr) IsMarkedDg;
extern (C) void thread_processGCMarks(scope IsMarkedDg isMarked);

extern (C) void* thread_stackBottom();

class ThreadGroup
{
    final Thread create(void function() fn);

    final Thread create(void delegate() dg);

    final void add(Thread t);

    final void remove(Thread t);

    final int opApply(scope int delegate(ref Thread) dg);

    final void joinAll(bool rethrow = true);

    private 
{
    version (D_LP64)
{
    enum ThreadGroupSize = 24;
}
else
{
    static assert((void*).sizeof == 4);
    enum ThreadGroupSize = 12;
}
    void[ThreadGroupSize - __traits(classInstanceSize,Object)] data = void;
}
}
private extern const __gshared size_t PAGESIZE;


shared static this();
class Fiber
{
    this(void function() fn, size_t sz = PAGESIZE * 4);
    this(void delegate() dg, size_t sz = PAGESIZE * 4);
    ~this();
    final Object call(bool rethrow = true);

    final void reset();

    enum State 
{
HOLD,
EXEC,
TERM,
}
    final @property const State state();

    static void yield();

    static void yieldAndThrow(Throwable t);

    static Fiber getThis();

    version (Posix)
{
    static this();
}
    private 
{
    version (D_LP64)
{
    version (Windows)
{
    enum FiberSize = 88;
}
else
{
    version (OSX)
{
    enum FiberSize = 88;
}
else
{
    version (Posix)
{
    enum FiberSize = 88;
}
else
{
    static assert(0,"Platform not supported.");
}
}
}
}
else
{
    static assert((void*).sizeof == 4);
    version (Windows)
{
    enum FiberSize = 44;
}
else
{
    version (OSX)
{
    enum FiberSize = 44;
}
else
{
    version (Posix)
{
    enum FiberSize = 44;
}
else
{
    static assert(0,"Platform not supported.");
}
}
}
}
    void[FiberSize - __traits(classInstanceSize,Object)] data = void;
}
}
version (OSX)
{
    extern (D) void* ___tls_get_addr(void* p);

}
