shithub: neoventi

ref: 4b60d3dd32efd00a1d07cb08662926ba9836719f
dir: /neoventi.c/

View raw version
#include <u.h>
#include <libc.h>
#include <bio.h>
#include <thread.h>
#include "neoventi.h"

int mainstacksize = 128*1024;
char *configpath = "/dev/kaladin/arenas";

char *arenapath;
char *isectpath;
char *tcpaddr;

void
parseargs(int argc, char **argv)
{
	ARGBEGIN {
	case 'c':
		configpath = ARGF();
		if(configpath == nil)
			sysfatal("must specify a config path");
		break;
	default:
		sysfatal("unsupported flag '%c'", ARGC());
		break;
	} ARGEND;
}

static void
configvalidate(char *buf)
{
	if(memcmp(buf, "venti config\n", 13) != 0)
		sysfatal("invalid config");
}

static void
configparse(char *buf)
{
	char *lines[16];
	char *fields[2];
	int nlines = getfields(buf+13, lines, 16, 0, "\n");
	for(int i = 0; i < nlines; i += 1){
		if(strlen(lines[i]) == 0)
			continue;
		if(tokenize(lines[i], fields, 2) != 2)
			sysfatal("invalid config, bad tokenize on line %d", i);
		if(strcmp(fields[0], "arenas") == 0)
			arenapath = strdup(fields[1]);
		else if(strcmp(fields[0], "isect") == 0)
			isectpath = strdup(fields[1]);
		else if(strcmp(fields[0], "bcmem") == 0 || strcmp(fields[0], "mem") == 0 || strcmp(fields[0], "icmem") == 0)
			// ignore cache sizing
			;
		else if(strcmp(fields[0], "addr") == 0)
			tcpaddr = strdup(fields[1]);
		else if(strcmp(fields[0], "httpaddr") == 0)
			// no http server, fuck that
			;
		else if(strcmp(fields[0], "index") == 0)
			// apparently no effect????
			;
		else
			fprint(2, "ignoring config directive '%s'\n", fields[0]);
	}
}

static void
loadconfig(void)
{
	// Config is either a flat file, or is the last 8K of a 256K block
	int fd = open(configpath, OREAD);
	Dir *dir = dirfstat(fd);
	// NOTE venti technically allows for 8K bytes of config. Fuck that.
	// 8191 bytes is enough for anybody.
	char buf[8192];
	if(fd < 0 || dir == nil)
		sysfatal("unable to open config '%s'", configpath);
	if(dir->length > 256*1024){
		// Config partition
		vlong w = pread(fd, buf, 8192, 248*1024);
		if(w < 0)
			sysfatal("unable to read configpart '%s'", configpath);
		else if(w == 0)
			sysfatal("configpart empty!");
	} else if(pread(fd, buf, 8192, 0) <= 0)
		sysfatal("unable to read config file '%s'", configpath);
	// Just in case.
	buf[8191] = 0;
	configvalidate(buf);
	configparse(buf);
}

static void
init(void)
{
	loadconfig();
	initarenas();
	initindex();
	cacheinit();
}

static void
validate(void)
{
	fprint(2, "TODO: validate initial state");
}

void
threadmain(int argc, char **argv)
{
	parseargs(argc, argv);
	print("Initializing neoventi build 5... ");
	init();
	validate();
	print("initialized, launching server...");
	print("overridding tcp address for simultaneous testing! tcp!*!14011...\n");
	tcpaddr = "tcp!*!14011";
	serve(tcpaddr);
}