// 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.

// +build ignore

/*
 * Translate a .goc file into a .c file.  A .goc file is a combination
 * of a limited form of Go with C.
 */

/*
	package PACKAGENAME
	{# line}
	func NAME([NAME TYPE { , NAME TYPE }]) [(NAME TYPE { , NAME TYPE })] \{
	  C code with proper brace nesting
	\}
*/

/*
 * We generate C code which implements the function such that it can
 * be called from Go and executes the C code.
 */

#include <u.h>
#include <stdio.h>
#include <libc.h>

/* Whether we're emitting for gcc */
static int gcc;

/* File and line number */
static const char *file;
static unsigned int lineno = 1;

/* List of names and types.  */
struct params {
	struct params *next;
	char *name;
	char *type;
};

/* index into type_table */
enum {
	Bool,
	Float,
	Int,
	Uint,
	Uintptr,
	String,
	Slice,
	Eface,
};

static struct {
	char *name;
	int size;
} type_table[] = {
	/* variable sized first, for easy replacement */
	/* order matches enum above */
	/* default is 32-bit architecture sizes */
	"bool",		1,
	"float",	4,
	"int",		4,
	"uint",		4,
	"uintptr",	4,
	"String",	8,
	"Slice",	12,
	"Eface",	8,

	/* fixed size */
	"float32",	4,
	"float64",	8,
	"byte",		1,
	"int8",		1,
	"uint8",	1,
	"int16",	2,
	"uint16",	2,
	"int32",	4,
	"uint32",	4,
	"int64",	8,
	"uint64",	8,

	NULL,
};

/* Fixed structure alignment (non-gcc only) */
int structround = 4;

/* Unexpected EOF.  */
static void
bad_eof(void)
{
	sysfatal("%s:%ud: unexpected EOF\n", file, lineno);
}

/* Out of memory.  */
static void
bad_mem(void)
{
	sysfatal("%s:%ud: out of memory\n", file, lineno);
}

/* Allocate memory without fail.  */
static void *
xmalloc(unsigned int size)
{
	void *ret = malloc(size);
	if (ret == NULL)
		bad_mem();
	return ret;
}

/* Reallocate memory without fail.  */
static void*
xrealloc(void *buf, unsigned int size)
{
	void *ret = realloc(buf, size);
	if (ret == NULL)
		bad_mem();
	return ret;
}

/* Free a list of parameters.  */
static void
free_params(struct params *p)
{
	while (p != NULL) {
		struct params *next;

		next = p->next;
		free(p->name);
		free(p->type);
		free(p);
		p = next;
	}
}

/* Read a character, tracking lineno.  */
static int
getchar_update_lineno(void)
{
	int c;

	c = getchar();
	if (c == '\n')
		++lineno;
	return c;
}

/* Read a character, giving an error on EOF, tracking lineno.  */
static int
getchar_no_eof(void)
{
	int c;

	c = getchar_update_lineno();
	if (c == EOF)
		bad_eof();
	return c;
}

/* Read a character, skipping comments.  */
static int
getchar_skipping_comments(void)
{
	int c;

	while (1) {
		c = getchar_update_lineno();
		if (c != '/')
			return c;

		c = getchar();
		if (c == '/') {
			do {
				c = getchar_update_lineno();
			} while (c != EOF && c != '\n');
			return c;
		} else if (c == '*') {
			while (1) {
				c = getchar_update_lineno();
				if (c == EOF)
					return EOF;
				if (c == '*') {
					do {
						c = getchar_update_lineno();
					} while (c == '*');
					if (c == '/')
						break;
				}
			}
		} else {
			ungetc(c, stdin);
			return '/';
		}
	}
}

/*
 * Read and return a token.  Tokens are string or character literals
 * or else delimited by whitespace or by [(),{}].
 * The latter are all returned as single characters.
 */
static char *
read_token(void)
{
	int c, q;
	char *buf;
	unsigned int alc, off;
	const char* delims = "(),{}";

	while (1) {
		c = getchar_skipping_comments();
		if (c == EOF)
			return NULL;
		if (!isspace(c))
			break;
	}
	alc = 16;
	buf = xmalloc(alc + 1);
	off = 0;
	if(c == '"' || c == '\'') {
		q = c;
		buf[off] = c;
		++off;
		while (1) {
			if (off+2 >= alc) { // room for c and maybe next char
				alc *= 2;
				buf = xrealloc(buf, alc + 1);
			}
			c = getchar_no_eof();
			buf[off] = c;
			++off;
			if(c == q)
				break;
			if(c == '\\') {
				buf[off] = getchar_no_eof();
				++off;
			}
		}
	} else if (strchr(delims, c) != NULL) {
		buf[off] = c;
		++off;
	} else {
		while (1) {
			if (off >= alc) {
				alc *= 2;
				buf = xrealloc(buf, alc + 1);
			}
			buf[off] = c;
			++off;
			c = getchar_skipping_comments();
			if (c == EOF)
				break;
			if (isspace(c) || strchr(delims, c) != NULL) {
				if (c == '\n')
					lineno--;
				ungetc(c, stdin);
				break;
			}
		}
	}
	buf[off] = '\0';
	return buf;
}

/* Read a token, giving an error on EOF.  */
static char *
read_token_no_eof(void)
{
	char *token = read_token();
	if (token == NULL)
		bad_eof();
	return token;
}

/* Read the package clause, and return the package name.  */
static char *
read_package(void)
{
	char *token;

	token = read_token_no_eof();
	if (token == nil)
		sysfatal("%s:%ud: no token\n", file, lineno);
	if (strcmp(token, "package") != 0) {
		sysfatal("%s:%ud: expected \"package\", got \"%s\"\n",
			file, lineno, token);
	}
	return read_token_no_eof();
}

/* Read and copy preprocessor lines.  */
static void
read_preprocessor_lines(void)
{
	while (1) {
		int c;

		do {
			c = getchar_skipping_comments();
		} while (isspace(c));
		if (c != '#') {
			ungetc(c, stdin);
			break;
		}
		putchar(c);
		do {
			c = getchar_update_lineno();
			putchar(c);
		} while (c != '\n');
	}
}

/*
 * Read a type in Go syntax and return a type in C syntax.  We only
 * permit basic types and pointers.
 */
static char *
read_type(void)
{
	char *p, *op, *q;
	int pointer_count;
	unsigned int len;

	p = read_token_no_eof();
	if (*p != '*')
		return p;
	op = p;
	pointer_count = 0;
	while (*p == '*') {
		++pointer_count;
		++p;
	}
	len = strlen(p);
	q = xmalloc(len + pointer_count + 1);
	memcpy(q, p, len);
	while (pointer_count > 0) {
		q[len] = '*';
		++len;
		--pointer_count;
	}
	q[len] = '\0';
	free(op);
	return q;
}

/* Return the size of the given type. */
static int
type_size(char *p)
{
	int i;

	if(p[strlen(p)-1] == '*')
		return type_table[Uintptr].size;

	for(i=0; type_table[i].name; i++)
		if(strcmp(type_table[i].name, p) == 0)
			return type_table[i].size;
	sysfatal("%s:%ud: unknown type %s\n", file, lineno, p);
	return 0;
}

/*
 * Read a list of parameters.  Each parameter is a name and a type.
 * The list ends with a ')'.  We have already read the '('.
 */
static struct params *
read_params(int *poffset)
{
	char *token;
	struct params *ret, **pp, *p;
	int offset, size, rnd;

	ret = NULL;
	pp = &ret;
	token = read_token_no_eof();
	offset = 0;
	if (strcmp(token, ")") != 0) {
		while (1) {
			p = xmalloc(sizeof(struct params));
			p->name = token;
			p->type = read_type();
			p->next = NULL;
			*pp = p;
			pp = &p->next;

			size = type_size(p->type);
			rnd = size;
			if(rnd > structround)
				rnd = structround;
			if(offset%rnd)
				offset += rnd - offset%rnd;
			offset += size;

			token = read_token_no_eof();
			if (strcmp(token, ",") != 0)
				break;
			token = read_token_no_eof();
		}
	}
	if (strcmp(token, ")") != 0) {
		sysfatal("%s:%ud: expected '('\n",
			file, lineno);
	}
	if (poffset != NULL)
		*poffset = offset;
	return ret;
}

/*
 * Read a function header.  This reads up to and including the initial
 * '{' character.  Returns 1 if it read a header, 0 at EOF.
 */
static int
read_func_header(char **name, struct params **params, int *paramwid, struct params **rets)
{
	int lastline;
	char *token;

	lastline = -1;
	while (1) {
		token = read_token();
		if (token == NULL)
			return 0;
		if (strcmp(token, "func") == 0) {
			if(lastline != -1)
				printf("\n");
			break;
		}
		if (lastline != lineno) {
			if (lastline == lineno-1)
				printf("\n");
			else
				printf("\n#line %d \"%s\"\n", lineno, file);
			lastline = lineno;
		}
		printf("%s ", token);
	}

	*name = read_token_no_eof();

	token = read_token();
	if (token == NULL || strcmp(token, "(") != 0) {
		sysfatal("%s:%ud: expected \"(\"\n",
			file, lineno);
	}
	*params = read_params(paramwid);

	token = read_token();
	if (token == NULL || strcmp(token, "(") != 0)
		*rets = NULL;
	else {
		*rets = read_params(NULL);
		token = read_token();
	}
	if (token == NULL || strcmp(token, "{") != 0) {
		sysfatal("%s:%ud: expected \"{\"\n",
			file, lineno);
	}
	return 1;
}

/* Write out parameters.  */
static void
write_params(struct params *params, int *first)
{
	struct params *p;

	for (p = params; p != NULL; p = p->next) {
		if (*first)
			*first = 0;
		else
			printf(", ");
		printf("%s %s", p->type, p->name);
	}
}

/* Write a 6g function header.  */
static void
write_6g_func_header(char *package, char *name, struct params *params,
		     int paramwid, struct params *rets)
{
	int first, n;

	printf("void\n%s·%s(", package, name);
	first = 1;
	write_params(params, &first);

	/* insert padding to align output struct */
	if(rets != NULL && paramwid%structround != 0) {
		n = structround - paramwid%structround;
		if(n & 1)
			printf(", uint8");
		if(n & 2)
			printf(", uint16");
		if(n & 4)
			printf(", uint32");
	}

	write_params(rets, &first);
	printf(")\n{\n");
}

/* Write a 6g function trailer.  */
static void
write_6g_func_trailer(struct params *rets)
{
	struct params *p;

	for (p = rets; p != NULL; p = p->next)
		printf("\tFLUSH(&%s);\n", p->name);
	printf("}\n");
}

/* Define the gcc function return type if necessary.  */
static void
define_gcc_return_type(char *package, char *name, struct params *rets)
{
	struct params *p;

	if (rets == NULL || rets->next == NULL)
		return;
	printf("struct %s_%s_ret {\n", package, name);
	for (p = rets; p != NULL; p = p->next)
		printf("  %s %s;\n", p->type, p->name);
	printf("};\n");
}

/* Write out the gcc function return type.  */
static void
write_gcc_return_type(char *package, char *name, struct params *rets)
{
	if (rets == NULL)
		printf("void");
	else if (rets->next == NULL)
		printf("%s", rets->type);
	else
		printf("struct %s_%s_ret", package, name);
}

/* Write out a gcc function header.  */
static void
write_gcc_func_header(char *package, char *name, struct params *params,
		      struct params *rets)
{
	int first;
	struct params *p;

	define_gcc_return_type(package, name, rets);
	write_gcc_return_type(package, name, rets);
	printf(" %s_%s(", package, name);
	first = 1;
	write_params(params, &first);
	printf(") asm (\"%s.%s\");\n", package, name);
	write_gcc_return_type(package, name, rets);
	printf(" %s_%s(", package, name);
	first = 1;
	write_params(params, &first);
	printf(")\n{\n");
	for (p = rets; p != NULL; p = p->next)
		printf("  %s %s;\n", p->type, p->name);
}

/* Write out a gcc function trailer.  */
static void
write_gcc_func_trailer(char *package, char *name, struct params *rets)
{
	if (rets == NULL)
		;
	else if (rets->next == NULL)
		printf("return %s;\n", rets->name);
	else {
		struct params *p;

		printf("  {\n    struct %s_%s_ret __ret;\n", package, name);
		for (p = rets; p != NULL; p = p->next)
			printf("    __ret.%s = %s;\n", p->name, p->name);
		printf("    return __ret;\n  }\n");
	}
	printf("}\n");
}

/* Write out a function header.  */
static void
write_func_header(char *package, char *name,
		  struct params *params, int paramwid,
		  struct params *rets)
{
	if (gcc)
		write_gcc_func_header(package, name, params, rets);
	else
		write_6g_func_header(package, name, params, paramwid, rets);
	printf("#line %d \"%s\"\n", lineno, file);
}

/* Write out a function trailer.  */
static void
write_func_trailer(char *package, char *name,
		   struct params *rets)
{
	if (gcc)
		write_gcc_func_trailer(package, name, rets);
	else
		write_6g_func_trailer(rets);
}

/*
 * Read and write the body of the function, ending in an unnested }
 * (which is read but not written).
 */
static void
copy_body(void)
{
	int nesting = 0;
	while (1) {
		int c;

		c = getchar_no_eof();
		if (c == '}' && nesting == 0)
			return;
		putchar(c);
		switch (c) {
		default:
			break;
		case '{':
			++nesting;
			break;
		case '}':
			--nesting;
			break;
		case '/':
			c = getchar_update_lineno();
			putchar(c);
			if (c == '/') {
				do {
					c = getchar_no_eof();
					putchar(c);
				} while (c != '\n');
			} else if (c == '*') {
				while (1) {
					c = getchar_no_eof();
					putchar(c);
					if (c == '*') {
						do {
							c = getchar_no_eof();
							putchar(c);
						} while (c == '*');
						if (c == '/')
							break;
					}
				}
			}
			break;
		case '"':
		case '\'':
			{
				int delim = c;
				do {
					c = getchar_no_eof();
					putchar(c);
					if (c == '\\') {
						c = getchar_no_eof();
						putchar(c);
						c = '\0';
					}
				} while (c != delim);
			}
			break;
		}
	}
}

/* Process the entire file.  */
static void
process_file(void)
{
	char *package, *name;
	struct params *params, *rets;
	int paramwid;

	package = read_package();
	read_preprocessor_lines();
	while (read_func_header(&name, &params, &paramwid, &rets)) {
		write_func_header(package, name, params, paramwid, rets);
		copy_body();
		write_func_trailer(package, name, rets);
		free(name);
		free_params(params);
		free_params(rets);
	}
	free(package);
}

static void
usage(void)
{
	sysfatal("Usage: goc2c [--6g | --gc] [file]\n");
}

void
main(int argc, char **argv)
{
	char *goarch;

	argv0 = argv[0];
	while(argc > 1 && argv[1][0] == '-') {
		if(strcmp(argv[1], "-") == 0)
			break;
		if(strcmp(argv[1], "--6g") == 0)
			gcc = 0;
		else if(strcmp(argv[1], "--gcc") == 0)
			gcc = 1;
		else
			usage();
		argc--;
		argv++;
	}

	if(argc <= 1 || strcmp(argv[1], "-") == 0) {
		file = "<stdin>";
		process_file();
		exits(0);
	}

	if(argc > 2)
		usage();

	file = argv[1];
	if(freopen(file, "r", stdin) == 0) {
		sysfatal("open %s: %r\n", file);
	}

	if(!gcc) {
		// 6g etc; update size table
		goarch = getenv("GOARCH");
		if(goarch != NULL && strcmp(goarch, "amd64") == 0) {
			type_table[Uintptr].size = 8;
			type_table[String].size = 16;
			type_table[Slice].size = 8+4+4;
			type_table[Eface].size = 8+8;
			structround = 8;
		}
	}

	printf("// AUTO-GENERATED by autogen.sh; DO NOT EDIT\n\n");
	process_file();
	exits(0);
}
