Ejemplo n.º 1
0
int socket(int domain, int type, int proto, char *mac_addr)
{
	const char mac_prop_name[] = "local-mac-address";
	type_u phandle;
	uint8_t *prop_addr;
	int prop_len;
	int fd;

	/* search free file descriptor (and skip stdio handlers) */
	for (fd = 3; fd < FILEIO_MAX; ++fd) {
		if (fd_array[fd].type == FILEIO_TYPE_EMPTY) {
			break;
		}
	}
	if (fd == FILEIO_MAX) {
		puts("Can not open socket, file descriptor list is full");
		return -2;
	}

	/* Assume that obp-tftp package is the current one, so
	 * my-parent is the NIC node that we are interested in */
	forth_eval("my-parent ?dup IF ihandle>phandle THEN");
	phandle = forth_pop();
	if (phandle == 0) {
		puts("Can not open socket, no parent instance");
		return -1;
	}
	fd_array[fd].read_xt = find_method(phandle, "read");
	if (!fd_array[fd].read_xt) {
		puts("Can not open socket, no 'read' method");
		return -1;
	}
	fd_array[fd].write_xt = find_method(phandle, "write");
	if (!fd_array[fd].write_xt) {
		puts("Can not open socket, no 'write' method");
		return -1;
	}

	/* Read MAC address from device */
	forth_push((unsigned long)mac_prop_name);
	forth_push(strlen(mac_prop_name));
	forth_push(phandle);
	forth_eval("get-property");
	if (forth_pop())
		return -1;
	prop_len = forth_pop();
	prop_addr = (uint8_t *)forth_pop();
	memcpy(mac_addr, &prop_addr[prop_len - 6], 6);

	fd_array[fd].type = FILEIO_TYPE_SOCKET;

	return fd;
}
Ejemplo n.º 2
0
void SLOF_dma_map_out(long phys, void *virt, long size)
{
	forth_push((long)virt);
	forth_push((long)phys);
	forth_push(size);
	forth_eval("dma-map-out");
}
Ejemplo n.º 3
0
/**
 * Call Forth code to try to claim the memory region
 */
int
elf_forth_claim(void *addr, long size)
{
	forth_push((long)addr);
	forth_push(size);
	forth_eval("elf-claim-segment");
	return forth_pop();
}
Ejemplo n.º 4
0
long SLOF_dma_map_in(void *virt, long size, int cacheable)
{
	forth_push((long)virt);
	forth_push(size);
	forth_push(cacheable);
	forth_eval("dma-map-in");
	return forth_pop();
}
Ejemplo n.º 5
0
static type_u find_method(type_u phandle, const char *name)
{
	forth_push((type_u)name);
	forth_push(strlen(name));
	forth_push(phandle);
	forth_eval("find-method");
	if (forth_pop())
		return forth_pop();

	return 0;
}
Ejemplo n.º 6
0
void test_colon(void) {
  test_setup();

  printf("\n<<<<<<<<<<<< TEST ':' <<<<<<<<<<<< \n\n");

  printf("ctx->rsp: %p\n", ctx_rsp);
  printf("ctx->psp: %p\n", ctx_psp);
  printf("ctx->vars: %p\n", ctx_vars);
  printf("ctx->regs: %p\n", ctx_regs);

  // Vars
  int i, n;
  fcell_xt* var[50] = {0};

  i = 0; n = 15;
  for (int j = 0; j < n; j++)
    var[j] = forth_alloc_var();

  fword_t *entry_colon = dict_find(1, ":");
  printf("colon: `:` %p \n", entry_colon);
  TEST_CHECK_(entry_colon != NULL, "Expected non-null `:` word, got "CELL_FMT"", entry_colon);
  printf("colon cfa: `:` %p\n", dict_cfa(entry_colon));
  printf("xt_colon: `:` %p -> %p \n", xt_colon, *xt_colon);

  int idx_interpret = i;
  *var[i++] = (fcell_xt) dict_cfa(dict_find(7, "docolon"));
  *var[i++] = (fcell_xt) dict_cfa(dict_find(9, "interpret"));
  *var[i++] = dict_cfa(dict_find(4, "semi"));
  (void)idx_interpret;

  ctx_vars->tib_str = " : a 0x99 ;";
  ctx_vars->tib_len = strlen(ctx_vars->tib_str);
  ctx_vars->tib_idx = 0;

  forth_eval(var[0]);
  forth_flush_tob();

  dict_print();
  // Try running new word!


  fword_t *entry_a = dict_find(1, "a");
  TEST_CHECK_(entry_a != NULL, "Expected non-null `:` word, got %p for %s", entry_a, "entry_a");
  printf("entry_a: %p\n", entry_a);

  fcell_xt * cfa_a = (fcell_xt *) dict_cfa(entry_a);
  TEST_CHECK_(cfa_a != NULL, "Expected non-null `:` word, got "CELL_FMT" for %s", cfa_a, "cfa_a");

  printf("cfa_aa: %p\n", cfa_a);

  fword_t *semicolon = dict_find(1, ";");
  printf("semicolon: %p\n", semicolon);

  fcell_t expi;
  fcell_t expl;
  fcell_t cnt;
  fcell_t x;
  fcell_t err;

  // Good Case
  ctx_vars->tib_str = "a 1 +";
  ctx_vars->tib_len = 5;
  ctx_vars->tib_idx = 0;

  forth_eval(var[0]);
  forth_flush_tob();

  expi = 154;
  expl = 1;

  cnt = forth_count();
  TEST_CHECK_(cnt == expl, "Expected "CELL_FMT", got "CELL_FMT"", expl, cnt);
  x = forth_pop();
  TEST_CHECK_(x == expi, "Expected "CELL_FMT", got "CELL_FMT"", expi, x);

  err = forth_errno();
  TEST_CHECK_(err == FW_OK, "Expected "CELL_FMT", got "CELL_FMT"", FW_OK, err);

  // Bad Case
  ctx_vars->tib_str = "b 1 +";
  ctx_vars->tib_len = 5;
  ctx_vars->tib_idx = 0;

  forth_eval(var[0]);
  forth_flush_tob();

  expi = 0;
  expl = 0;

  cnt = forth_count();
  TEST_CHECK_(cnt == expl, "Expected "CELL_FMT", got "CELL_FMT"", expl, cnt);

  err = forth_errno();
  TEST_CHECK_(err == FW_ERR_NOWORD, "Expected "CELL_FMT", got "CELL_FMT"", FW_ERR_NOWORD, err);

}
Ejemplo n.º 7
0
void test_interpreter(void) {
  test_setup();

  dict_print();
  fcell_t dlen = ctx_vars->tob_idx;
  printf("TOB SZ: %s\n", ctx_vars->tob_str);
  for (fcell_t i = 0; i < dlen; i++) {
    putchar(ctx_vars->tob_str[i]);
  }
  printf("TOB DONE\n");

  printf("ctx->rsp: %p\n", ctx_rsp);
  printf("ctx->psp: %p\n", ctx_psp);
  printf("ctx->vars: %p\n", ctx_vars);
  printf("ctx->regs: %p\n", ctx_regs);

  // Vars
  int i, n;
  fcell_xt* var[50] = {0};

  i = 0; n = 4;
  for (int j = 0; j < n; j++)
    var[j] = forth_alloc_var();

  // Colons
  *var[i++] = (fcell_xt) dict_cfa(dict_find(7, "docolon"));
  *var[i++] = (fcell_xt) dict_cfa(dict_find(9, "interpret"));
  *var[i++] = dict_cfa(dict_find(4, "semi"));

  ctx_vars->tib_str = "7 2 +";
  ctx_vars->tib_len = 5;
  ctx_vars->tib_idx = 0;

  forth_eval(var[0]);
  forth_flush_tob();

  print_psp_info();

  int cnt = forth_count();
  fcell_t x = forth_pop();
  TEST_CHECK_(1 == cnt, "Expected "CELL_FMT", got "CELL_FMT"", 1, cnt);

  print_stack(); printf("... stack done\n");

  TEST_CHECK_(x == 9, "Expected "CELL_FMT", got "CELL_FMT"", 9, x);

  x = forth_pop();
  cnt = forth_count();
  TEST_CHECK_(0 == cnt, "Expected "CELL_FMT", got "CELL_FMT"", 0, cnt);
  TEST_CHECK_(forth_errno() == FW_ERR_STACKUNDERFLOW,
              "Expected "CELL_FMT", got "CELL_FMT"",
              forth_errno(),
              FW_ERR_STACKUNDERFLOW);

  forth_clear();

  TEST_CHECK_(forth_errno() == FW_OK,
              "Expected "CELL_FMT", got "CELL_FMT"",
              forth_errno(),
              FW_OK);

  printf(" >>>>>>>>>>>>>> basic test \n\n\n");
}
Ejemplo n.º 8
0
/**

To keep things simple options are parsed first then arguments like files,
although some options take arguments immediately after them. 

A library for parsing command line options like *getopt* should be used,
this would reduce the portability of the program. It is not recommended 
that arguments are parsed in this manner.
**/
int main(int argc, char **argv)
{
	FILE *in = NULL, *dump = NULL;
	int rval = 0, i = 1;
       	int save = 0,            /* attempt to save core if true */
	    eval = 0,            /* have we evaluated anything? */
	    readterm = 0,        /* read from standard in */
	    use_line_editor = 0, /* use a line editor, *if* one exists */
	    mset = 0;            /* memory size specified */
	enum forth_debug_level verbose = FORTH_DEBUG_OFF; /* verbosity level */
	static const size_t kbpc = 1024 / sizeof(forth_cell_t); /*kilobytes per cell*/
	static const char *dump_name = "forth.core";
	char *optarg = NULL;
	forth_cell_t core_size = DEFAULT_CORE_SIZE;
	forth_t *o = NULL;
	int orig_argc = argc;
	char **orig_argv = argv;

#ifdef _WIN32
	/* unmess up Windows file descriptors: there is a warning about an
	 * implicit declaration of _fileno when compiling under Windows in C99
	 * mode */
	_setmode(_fileno(stdin), _O_BINARY);
	_setmode(_fileno(stdout), _O_BINARY);
	_setmode(_fileno(stderr), _O_BINARY);
#endif
/**
This loop processes any options that may have been passed to the program, it
looks for arguments beginning with '-' and attempts to process that option,
if the argument does not start with '-' the option processing stops. It is
a simple mechanism for processing program arguments and there are better
ways of doing it (such as "getopt" and "getopts"), but by using them we
sacrifice portability.
**/

	for(i = 1; i < argc && argv[i][0] == '-'; i++) {
		if(strlen(argv[i]) > 2) {
			fatal("Only one option allowed at a time (got %s)", argv[i]);
			goto fail;
		}
		switch(argv[i][1]) {
		case '\0': goto done; /* stop processing options */
		case 'h':  usage(argv[0]); 
			   help(); 
			   return -1;
		case 'L':  use_line_editor = 1;
			   /* XXX fall through */
		case 't':  readterm = 1; 
			   if(verbose >= FORTH_DEBUG_NOTE)
				   note("stdin on. line editor %s", use_line_editor ? "on" : "off");
			   break;
		case 'u':
			   return libforth_unit_tests(0, 0, 0);
		case 'e':
			if(i >= (argc - 1))
				goto fail;
			forth_initial_enviroment(&o, core_size, stdin, stdout, verbose, orig_argc, orig_argv);
			optarg = argv[++i];
			if(verbose >= FORTH_DEBUG_NOTE)
				note("evaluating '%s'", optarg);
			if(forth_eval(o, optarg) < 0)
				goto end;
			eval = 1;
			break;
		case 'f':
			if(i >= (argc - 1))
				goto fail;
			forth_initial_enviroment(&o, core_size, stdin, stdout, verbose, orig_argc, orig_argv);
			optarg = argv[++i];
			if(verbose >= FORTH_DEBUG_NOTE)
				note("reading from file '%s'", optarg);
			if(eval_file(o, optarg, verbose) < 0)
				goto end;
			break;
		case 's':
			if(i >= (argc - 1))
				goto fail;
			dump_name = argv[++i];
			/* XXX fall through */
		case 'd':  /*use default name */
			if(verbose >= FORTH_DEBUG_NOTE)
				note("saving core file to '%s' (on exit)", dump_name);
			save = 1;
			break;
		case 'm':
			if(o || (i >= argc - 1) || forth_string_to_cell(10, &core_size, argv[++i]))
				goto fail;
			if((core_size *= kbpc) < MINIMUM_CORE_SIZE) {
				fatal("-m too small (minimum %zu)", MINIMUM_CORE_SIZE / kbpc);
				return -1;
			}
			if(verbose >= FORTH_DEBUG_NOTE)
				note("memory size set to %zu", core_size);
			mset = 1;
			break;
		case 'l':
			if(o || mset || (i >= argc - 1))
				goto fail;
			optarg = argv[++i];
			if(verbose >= FORTH_DEBUG_NOTE)
				note("loading core file '%s'", optarg);
			if(!(o = forth_load_core_file(dump = forth_fopen_or_die(optarg, "rb")))) {
				fatal("%s, core load failed", optarg);
				return -1;
			}
			forth_set_debug_level(o, verbose);
			fclose(dump);
			break;
		case 'v':
			verbose++;
			break;
		case 'V':
			version();
			return EXIT_SUCCESS;
			break;
		default:
		fail:
			fatal("invalid argument '%s'", argv[i]);
			usage(argv[0]);
			return -1;
		}
	}

done:
	/* if no files are given, read stdin */
	readterm = (!eval && i == argc) || readterm;
	forth_initial_enviroment(&o, core_size, stdin, stdout, verbose, orig_argc, orig_argv);

	for(; i < argc; i++) /* process all files on command line */
		if(eval_file(o, argv[i], verbose) < 0)
			goto end;

	if(readterm) { /* if '-t' or no files given, read from stdin */
		if(verbose >= FORTH_DEBUG_NOTE)
			note("reading from stdin (%p)", stdin);

#ifdef USE_LINE_EDITOR
		if(use_line_editor) {
			rval = forth_line_editor(o);
			goto end;
		}
#endif

		forth_set_file_input(o, stdin);
		rval = forth_run(o);
	}

end:	
	fclose_input(&in);

/**
If the save option has been given we only want to save valid core files,
we might want to make an option to force saving of core files for debugging
purposes, but in general we do not want to over write valid previously saved
state with invalid data.
**/

	if(save) { /* save core file */
		if(rval || forth_is_invalid(o)) {
			fatal("refusing to save invalid core, %u/%d", rval, forth_is_invalid(o));
			return -1;
		}
		if(verbose >= FORTH_DEBUG_NOTE)
			note("saving for file to '%s'", dump_name);
		if(forth_save_core_file(o, dump = forth_fopen_or_die(dump_name, "wb"))) {
			fatal("core file save to '%s' failed", dump_name);
			rval = -1;
		}
		fclose(dump);
	}

/** 
Whilst the following **forth_free** is not strictly necessary, there
is often a debate that comes up making short lived programs or programs whose
memory use stays either constant or only goes up, when these programs exit
it is not necessary to clean up the environment and in some case (although
not this one) it can slow down the exit of the program for
no reason.  However not freeing the memory after use does not play nice with
programs that detect memory leaks, like Valgrind. Either way, we free the
memory used here, but only if no other errors have occurred before hand. 
**/

	forth_free(o);
	return rval;
}
Ejemplo n.º 9
0
void SLOF_free_mem(void *addr, long size)
{
	forth_push((long)addr);
	forth_push(size);
	forth_eval("free-mem");
}
Ejemplo n.º 10
0
void *SLOF_alloc_mem(long size)
{
	forth_push(size);
	forth_eval("alloc-mem");
	return (void *)forth_pop();
}
Ejemplo n.º 11
0
void SLOF_dma_free(void *virt, long size)
{
	forth_push((long)virt);
	forth_push(size);
	forth_eval("dma-free");
}
Ejemplo n.º 12
0
void *SLOF_dma_alloc(long size)
{
	forth_push(size);
	forth_eval("dma-alloc");
	return (void *)forth_pop();
}
Ejemplo n.º 13
0
/**
 * get msec-timer value
 * access to HW register
 * overrun will occur if boot exceeds 1.193 hours (49 days)
 *
 * @param   -
 * @return  actual timer value in ms as 32bit
 */
uint32_t SLOF_GetTimer(void)
{
	forth_eval("get-msecs");
	return (uint32_t) forth_pop();
}