#include "forth.h"
/* String handling. */

/* What we want is a primitive that goes in front of the counted
 * string in the dictionary; when encountered, this primitive
 * pushes the address and the count onto the stack.
 */

PRIMITIVE ("gnirts", Fgnirts, Sgnirts, NON_IMMEDIATE, ( -- ) )
{
  /* When we enter this function, the PC is pointing at a CF which
   * contains the address of gnirts.  The next byte is the length of a
   * string, followed by the string itself.
   *
   * We want to push the string's address and length, and advance PC
   * past it.
   */
  char count;
  char *straddr;

  /* Get past this CFA. */
  pc++;

  /* First byte is count, the rest is string. */
  count = *((char *) pc)++;
  straddr = (char *) (pc);

  PUSH ((long) straddr);
  PUSH ((long) count);

  /* The "- 1" compensates for address_interpreter's "pc++". */
  pc = (funcptr **) ALIGN_STRING (pc, *((long *) (pc - 1))) - 1;
}


/* For now, we will define this stuff in C. */


PRIMITIVE ("string", Fstring, Sstring, NON_IMMEDIATE, ( c -- ) )
{
  /* Compile the input characters delimited by c into the
   * dictionary.
   */

  char count;
  char *from_addr;

  Fword ();      /* ( c -- a )   */
  Fcount ();     /* ( a -- a n ) */

  count = (char) POP;
  from_addr = (char *) POP;

  *((char *) dp)++ = count;
  memcpy ((char *) dp, (char *) from_addr, count);

  /* Make sure that dp is aligned. */
  dp = (long *) ALIGN_STRING (dp, count);
}


PRIMITIVE ("type", Ftype, Stype, NON_IMMEDIATE, ( a n -- ) )
{
  /* Output n characters, starting at address a. */
  size_t bytes = (size_t) POP;
  char *addr   = (char *) POP;
  fwrite (addr, sizeof (char), bytes, outfile);
}
