#include <9pm/windows.h>
#include <9pm/u.h>
#include <9pm/libc.h>
#include <9pm/thread.h>
#include <9pm/ns.h>
#include <9pm/syscall.h>

Rune srv[] = L"Plan 9 Kernel";

void
threadmain(int argc, char **argv)
{
	HWND hwin;
	HANDLE hsrv;
	HANDLE hmem;
	Handles *h;
	int pid;
	void *mem;
	ulong *volatile c;

	threadprint(1, "hello world pong\n");

	hwin = FindWindow(srv, srv);
	if(hwin == 0){
		oserror();
		threadprint(1, "cannot find window: %r\n");
		threadexitsall(nil);
	}

	GetWindowThreadProcessId(hwin, &pid);
	hsrv = OpenProcess(PROCESS_ALL_ACCESS, 0, pid);
	if(hsrv == 0){
		oserror();
		threadprint(1, "cannot access kernel pid %d: %r\n", pid);
		threadexitsall(nil);
	}

	hmem = (void*)SendMessage(hwin, WM_USER, 0, GetCurrentProcessId());
	if(hmem == 0){
		oserror();
		threadprint(1, "cannot get shared memory: %r\n");
		threadexitsall(nil);
	}

	mem = MapViewOfFile(hmem, FILE_MAP_WRITE, 0, 0, 0);
	if(mem == nil){
		oserror();
		threadprint(1, "cannot map shapred memory: %r\n");
		threadexitsall(nil);
	}

	threadprint(1, "found proc %d\n", pid);
	threadprint(1, "calling\n");
	h = (Handles*)mem+1;
	c = (ulong*)&h[1];
	*c = 23456;
	if(!ReleaseSemaphore(h->hserversig, 1, nil)){
		oserror();
		threadprint(1, "ReleaseSemaphore: %r\n");
	}
	/* BUG: wait for server proc too in case it dies */
	if(WaitForSingleObject(h->hclientsig, INFINITE) != WAIT_OBJECT_0){
		oserror();
		threadprint(1, "WaitForSingleObject: %r\n");
	}
	threadprint(1, "response: %d\n", c[1]);
	threadexitsall(nil);
}


syntax highlighted by Code2HTML, v. 0.9.1