// Copyright 2010 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package runtime

import "unsafe"

type mOS struct {
	waitsema      int32 // semaphore for parking on locks
	waitsemacount int32
	waitsemalock  int32
}

func nacl_exception_stack(p uintptr, size int32) int32
func nacl_exception_handler(fn uintptr, arg unsafe.Pointer) int32
func nacl_sem_create(flag int32) int32
func nacl_sem_wait(sem int32) int32
func nacl_sem_post(sem int32) int32
func nacl_mutex_create(flag int32) int32
func nacl_mutex_lock(mutex int32) int32
func nacl_mutex_trylock(mutex int32) int32
func nacl_mutex_unlock(mutex int32) int32
func nacl_cond_create(flag int32) int32
func nacl_cond_wait(cond, n int32) int32
func nacl_cond_signal(cond int32) int32
func nacl_cond_broadcast(cond int32) int32

//go:noescape
func nacl_cond_timed_wait_abs(cond, lock int32, ts *timespec) int32
func nacl_thread_create(fn uintptr, stk, tls, xx unsafe.Pointer) int32

//go:noescape
func nacl_nanosleep(ts, extra *timespec) int32
func nanotime() int64
func mmap(addr unsafe.Pointer, n uintptr, prot, flags, fd int32, off uint32) (p unsafe.Pointer, err int)
func exit(code int32)
func osyield()

//go:noescape
func write(fd uintptr, p unsafe.Pointer, n int32) int32

//go:linkname os_sigpipe os.sigpipe
func os_sigpipe() {
	throw("too many writes on closed pipe")
}

func dieFromSignal(sig uint32) {
	exit(2)
}

func sigpanic() {
	g := getg()
	if !canpanic(g) {
		throw("unexpected signal during runtime execution")
	}

	// Native Client only invokes the exception handler for memory faults.
	g.sig = _SIGSEGV
	panicmem()
}

func raiseproc(sig uint32) {
}

// Stubs so tests can link correctly. These should never be called.
func open(name *byte, mode, perm int32) int32
func closefd(fd int32) int32
func read(fd int32, p unsafe.Pointer, n int32) int32

type sigset struct{}

// Called to initialize a new m (including the bootstrap m).
// Called on the parent thread (main thread in case of bootstrap), can allocate memory.
func mpreinit(mp *m) {
	mp.gsignal = malg(32 * 1024)
	mp.gsignal.m = mp
}

func sigtramp()

//go:nosplit
func msigsave(mp *m) {
}

//go:nosplit
func msigrestore(sigmask sigset) {
}

//go:nosplit
//go:nowritebarrierrec
func clearSignalHandlers() {
}

//go:nosplit
func sigblock() {
}

// Called to initialize a new m (including the bootstrap m).
// Called on the new thread, cannot allocate memory.
func minit() {
	_g_ := getg()

	// Initialize signal handling
	ret := nacl_exception_stack(_g_.m.gsignal.stack.lo, 32*1024)
	if ret < 0 {
		print("runtime: nacl_exception_stack: error ", -ret, "\n")
	}

	ret = nacl_exception_handler(funcPC(sigtramp), nil)
	if ret < 0 {
		print("runtime: nacl_exception_handler: error ", -ret, "\n")
	}
}

// Called from dropm to undo the effect of an minit.
func unminit() {
}

func osinit() {
	ncpu = 1
	getg().m.procid = 2
	//nacl_exception_handler(funcPC(sigtramp), nil);
	physPageSize = 65536
}

func signame(sig uint32) string {
	if sig >= uint32(len(sigtable)) {
		return ""
	}
	return sigtable[sig].name
}

func crash() {
	*(*int32)(nil) = 0
}

//go:noescape
func getRandomData([]byte)

func goenvs() {
	goenvs_unix()
}

func initsig(preinit bool) {
}

//go:nosplit
func usleep(us uint32) {
	var ts timespec

	ts.tv_sec = int64(us / 1e6)
	ts.tv_nsec = int32(us%1e6) * 1e3
	nacl_nanosleep(&ts, nil)
}

func mstart_nacl()

// May run with m.p==nil, so write barriers are not allowed.
//go:nowritebarrier
func newosproc(mp *m, stk unsafe.Pointer) {
	mp.tls[0] = uintptr(unsafe.Pointer(mp.g0))
	mp.tls[1] = uintptr(unsafe.Pointer(mp))
	ret := nacl_thread_create(funcPC(mstart_nacl), stk, unsafe.Pointer(&mp.tls[2]), nil)
	if ret < 0 {
		print("nacl_thread_create: error ", -ret, "\n")
		throw("newosproc")
	}
}

//go:noescape
func exitThread(wait *uint32)

//go:nosplit
func semacreate(mp *m) {
	if mp.waitsema != 0 {
		return
	}
	systemstack(func() {
		mu := nacl_mutex_create(0)
		if mu < 0 {
			print("nacl_mutex_create: error ", -mu, "\n")
			throw("semacreate")
		}
		c := nacl_cond_create(0)
		if c < 0 {
			print("nacl_cond_create: error ", -c, "\n")
			throw("semacreate")
		}
		mp.waitsema = c
		mp.waitsemalock = mu
	})
}

//go:nosplit
func semasleep(ns int64) int32 {
	var ret int32

	systemstack(func() {
		_g_ := getg()
		if nacl_mutex_lock(_g_.m.waitsemalock) < 0 {
			throw("semasleep")
		}

		for _g_.m.waitsemacount == 0 {
			if ns < 0 {
				if nacl_cond_wait(_g_.m.waitsema, _g_.m.waitsemalock) < 0 {
					throw("semasleep")
				}
			} else {
				var ts timespec
				end := ns + nanotime()
				ts.tv_sec = end / 1e9
				ts.tv_nsec = int32(end % 1e9)
				r := nacl_cond_timed_wait_abs(_g_.m.waitsema, _g_.m.waitsemalock, &ts)
				if r == -_ETIMEDOUT {
					nacl_mutex_unlock(_g_.m.waitsemalock)
					ret = -1
					return
				}
				if r < 0 {
					throw("semasleep")
				}
			}
		}

		_g_.m.waitsemacount = 0
		nacl_mutex_unlock(_g_.m.waitsemalock)
		ret = 0
	})
	return ret
}

//go:nosplit
func semawakeup(mp *m) {
	systemstack(func() {
		if nacl_mutex_lock(mp.waitsemalock) < 0 {
			throw("semawakeup")
		}
		if mp.waitsemacount != 0 {
			throw("semawakeup")
		}
		mp.waitsemacount = 1
		nacl_cond_signal(mp.waitsema)
		nacl_mutex_unlock(mp.waitsemalock)
	})
}

func memlimit() uintptr {
	return 0
}

// This runs on a foreign stack, without an m or a g. No stack split.
//go:nosplit
//go:norace
//go:nowritebarrierrec
func badsignal(sig uintptr) {
	cgocallback(unsafe.Pointer(funcPC(badsignalgo)), noescape(unsafe.Pointer(&sig)), unsafe.Sizeof(sig), 0)
}

func badsignalgo(sig uintptr) {
	if !sigsend(uint32(sig)) {
		// A foreign thread received the signal sig, and the
		// Go code does not want to handle it.
		raisebadsignal(uint32(sig))
	}
}

// This runs on a foreign stack, without an m or a g. No stack split.
//go:nosplit
func badsignal2() {
	write(2, unsafe.Pointer(&badsignal1[0]), int32(len(badsignal1)))
	exit(2)
}

var badsignal1 = []byte("runtime: signal received on thread not created by Go.\n")

func raisebadsignal(sig uint32) {
	badsignal2()
}

func madvise(addr unsafe.Pointer, n uintptr, flags int32) {}
func munmap(addr unsafe.Pointer, n uintptr)               {}
func setProcessCPUProfiler(hz int32)                      {}
func setThreadCPUProfiler(hz int32)                       {}
func sigdisable(uint32)                                   {}
func sigenable(uint32)                                    {}
func sigignore(uint32)                                    {}
func closeonexec(int32)                                   {}

// gsignalStack is unused on nacl.
type gsignalStack struct{}

var writelock uint32 // test-and-set spin lock for write

/*
An attempt at IRT. Doesn't work. See end of sys_nacl_amd64.s.

void (*nacl_irt_query)(void);

int8 nacl_irt_basic_v0_1_str[] = "nacl-irt-basic-0.1";
void *nacl_irt_basic_v0_1[6]; // exit, gettod, clock, nanosleep, sched_yield, sysconf
int32 nacl_irt_basic_v0_1_size = sizeof(nacl_irt_basic_v0_1);

int8 nacl_irt_memory_v0_3_str[] = "nacl-irt-memory-0.3";
void *nacl_irt_memory_v0_3[3]; // mmap, munmap, mprotect
int32 nacl_irt_memory_v0_3_size = sizeof(nacl_irt_memory_v0_3);

int8 nacl_irt_thread_v0_1_str[] = "nacl-irt-thread-0.1";
void *nacl_irt_thread_v0_1[3]; // thread_create, thread_exit, thread_nice
int32 nacl_irt_thread_v0_1_size = sizeof(nacl_irt_thread_v0_1);
*/
