// Copyright 2009 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 reflect
#include "runtime.h"
#include "type.h"

static Type*
gettype(void *typ)
{
	// typ is a *runtime.Type (or *runtime.MapType, etc), but the Type
	// defined in type.h includes an interface value header
	// in front of the raw structure.  the -2 below backs up
	// to the interface value header.
	return (Type*)((void**)typ - 2);
}

/*
 * Go wrappers around the C functions near the bottom of hashmap.c
 * There's no recursion here even though it looks like there is:
 * the names after func are in the reflect package name space
 * but the names in the C bodies are in the standard C name space.
 */

func mapaccess(map *byte, key *byte, val *byte) (pres bool) {
	runtime·mapaccess((Hmap*)map, key, val, &pres);
}

func mapassign(map *byte, key *byte, val *byte) {
	runtime·mapassign((Hmap*)map, key, val);
}

func maplen(map *byte) (len int32) {
	// length is first word of map
	len = *(uint32*)map;
}

func mapiterinit(map *byte) (it *byte) {
	it = (byte*)runtime·newmapiterinit((Hmap*)map);
}

func mapiternext(it *byte) {
	runtime·mapiternext((struct hash_iter*)it);
}

func mapiterkey(it *byte, key *byte) (ok bool) {
	ok = runtime·mapiterkey((struct hash_iter*)it, key);
}

func makemap(typ *byte) (map *byte) {
	MapType *t;

	t = (MapType*)gettype(typ);
	map = (byte*)runtime·makemap_c(t->key, t->elem, 0);
}

/*
 * Go wrappers around the C functions in chan.c
 */

func makechan(typ *byte, size uint32) (ch *byte) {
	ChanType *t;

	// typ is a *runtime.ChanType, but the ChanType
	// defined in type.h includes an interface value header
	// in front of the raw ChanType.  the -2 below backs up
	// to the interface value header.
	t = (ChanType*)gettype(typ);
	ch = (byte*)runtime·makechan_c(t->elem, size);
}

func chansend(ch *byte, val *byte, pres *bool) {
	runtime·chansend((Hchan*)ch, val, pres);
}

func chanrecv(ch *byte, val *byte, pres *bool) {
	runtime·chanrecv((Hchan*)ch, val, pres, nil);
}

func chanclose(ch *byte) {
	runtime·chanclose((Hchan*)ch);
}

func chanclosed(ch *byte) (r bool) {
	r = runtime·chanclosed((Hchan*)ch);
}

func chanlen(ch *byte) (r int32) {
	r = runtime·chanlen((Hchan*)ch);
}

func chancap(ch *byte) (r int32) {
	r = runtime·chancap((Hchan*)ch);
}


/*
 * Go wrappers around the functions in iface.c
 */

func setiface(typ *byte, x *byte, ret *byte) {
	InterfaceType *t;

	t = (InterfaceType*)gettype(typ);
	if(t->mhdr.len == 0) {
		// already an empty interface
		*(Eface*)ret = *(Eface*)x;
		return;
	}
	if(((Eface*)x)->type == nil) {
		// can assign nil to any interface
		((Iface*)ret)->tab = nil;
		((Iface*)ret)->data = nil;
		return;
	}
	runtime·ifaceE2I((InterfaceType*)gettype(typ), *(Eface*)x, (Iface*)ret);
}
