/* Support for connecting Guile's stdio to GDB's.
   as well as r/w memory via ports.

   Copyright (C) 2014-2020 Free Software Foundation, Inc.

   This file is part of GDB.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */

/* See README file in this directory for implementation notes, coding
   conventions, et.al.  */

#include "defs.h"
#include "gdbsupport/gdb_select.h"
#include "top.h"
#include "target.h"
#include "guile-internal.h"
#include "gdbsupport/gdb_optional.h"

#ifdef HAVE_POLL
#if defined (HAVE_POLL_H)
#include <poll.h>
#elif defined (HAVE_SYS_POLL_H)
#include <sys/poll.h>
#endif
#endif

/* Whether we're using Guile < 2.2 and its clumsy port API.  */

#define USING_GUILE_BEFORE_2_2				\
  (SCM_MAJOR_VERSION == 2 && SCM_MINOR_VERSION == 0)


/* A ui-file for sending output to Guile.  */

class ioscm_file_port : public ui_file
{
public:
  /* Return a ui_file that writes to PORT.  */
  explicit ioscm_file_port (SCM port);

  void flush () override;
  void write (const char *buf, long length_buf) override;

private:
  SCM m_port;
};

/* Data for a memory port.  */

typedef struct
{
  /* Bounds of memory range this port is allowed to access: [start, end).
     This means that 0xff..ff is not accessible.  I can live with that.  */
  CORE_ADDR start, end;

  /* (end - start), recorded for convenience.  */
  ULONGEST size;

  /* Think of this as the lseek value maintained by the kernel.
     This value is always in the range [0, size].  */
  ULONGEST current;

#if USING_GUILE_BEFORE_2_2
  /* The size of the internal r/w buffers.
     Scheme ports aren't a straightforward mapping to memory r/w.
     Generally the user specifies how much to r/w and all access is
     unbuffered.  We don't try to provide equivalent access, but we allow
     the user to specify these values to help get something similar.  */
  unsigned read_buf_size, write_buf_size;
#endif
} ioscm_memory_port;

/* Copies of the original system input/output/error ports.
   These are recorded for debugging purposes.  */
static SCM orig_input_port_scm;
static SCM orig_output_port_scm;
static SCM orig_error_port_scm;

/* This is the stdio port descriptor, scm_ptob_descriptor.  */
#if USING_GUILE_BEFORE_2_2
static scm_t_bits stdio_port_desc;
#else
static scm_t_port_type *stdio_port_desc;
#endif

/* Note: scm_make_port_type takes a char * instead of a const char *.  */
static /*const*/ char stdio_port_desc_name[] = "gdb:stdio-port";

/* Names of each gdb port.  */
static const char input_port_name[] = "gdb:stdin";
static const char output_port_name[] = "gdb:stdout";
static const char error_port_name[] = "gdb:stderr";

/* This is the actual port used from Guile.
   We don't expose these to the user though, to ensure they're not
   overwritten.  */
static SCM input_port_scm;
static SCM output_port_scm;
static SCM error_port_scm;

/* Internal enum for specifying output port.  */
enum oport { GDB_STDOUT, GDB_STDERR };

/* This is the memory port descriptor, scm_ptob_descriptor.  */
#if USING_GUILE_BEFORE_2_2
static scm_t_bits memory_port_desc;
#else
static scm_t_port_type *memory_port_desc;
#endif

/* Note: scm_make_port_type takes a char * instead of a const char *.  */
static /*const*/ char memory_port_desc_name[] = "gdb:memory-port";

#if USING_GUILE_BEFORE_2_2

/* The default amount of memory to fetch for each read/write request.
   Scheme ports don't provide a way to specify the size of a read,
   which is important to us to minimize the number of inferior interactions,
   which over a remote link can be important.  To compensate we augment the
   port API with a new function that let's the user specify how much the next
   read request should fetch.  This is the initial value for each new port.  */
static const unsigned default_read_buf_size = 16;
static const unsigned default_write_buf_size = 16;

/* Arbitrarily limit memory port buffers to 1 byte to 4K.  */
static const unsigned min_memory_port_buf_size = 1;
static const unsigned max_memory_port_buf_size = 4096;

/* "out of range" error message for buf sizes.  */
static char *out_of_range_buf_size;

#else

/* The maximum values to use for get_natural_buffer_sizes.  */
static const unsigned natural_buf_size = 16;

#endif

/* Keywords used by open-memory.  */
static SCM mode_keyword;
static SCM start_keyword;
static SCM size_keyword;

/* Helper to do the low level work of opening a port.  */

#if USING_GUILE_BEFORE_2_2

static SCM
ioscm_open_port (scm_t_bits port_type, long mode_bits, scm_t_bits stream)
{
  SCM port;

#if 0 /* TODO: Guile doesn't export this.  What to do?  */
  scm_i_scm_pthread_mutex_lock (&scm_i_port_table_mutex);
#endif

  port = scm_new_port_table_entry (port_type);

  SCM_SET_CELL_TYPE (port, port_type | mode_bits);
  SCM_SETSTREAM (port, stream);

#if 0 /* TODO: Guile doesn't export this.  What to do?  */
  scm_i_pthread_mutex_unlock (&scm_i_port_table_mutex);
#endif

  return port;
}

#else

static SCM
ioscm_open_port (scm_t_port_type *port_type, long mode_bits, scm_t_bits stream)
{
  return scm_c_make_port (port_type, mode_bits, stream);
}

#endif


/* Support for connecting Guile's stdio ports to GDB's stdio ports.  */

/* Like fputstrn_filtered, but don't escape characters, except nul.
   Also like fputs_filtered, but a length is specified.  */

static void
fputsn_filtered (const char *s, size_t size, struct ui_file *stream)
{
  size_t i;

  for (i = 0; i < size; ++i)
    {
      if (s[i] == '\0')
	fputs_filtered ("\\000", stream);
      else
	fputc_filtered (s[i], stream);
    }
}

#if USING_GUILE_BEFORE_2_2

/* The scm_t_ptob_descriptor.input_waiting "method".
   Return a lower bound on the number of bytes available for input.  */

static int
ioscm_input_waiting (SCM port)
{
  int fdes = 0;

  if (! scm_is_eq (port, input_port_scm))
    return 0;

#ifdef HAVE_POLL
  {
    /* This is copied from libguile/fports.c.  */
    struct pollfd pollfd = { fdes, POLLIN, 0 };
    static int use_poll = -1;

    if (use_poll < 0)
      {
	/* This is copied from event-loop.c: poll cannot be used for stdin on
	   m68k-motorola-sysv.  */
	struct pollfd test_pollfd = { fdes, POLLIN, 0 };

	if (poll (&test_pollfd, 1, 0) == 1 && (test_pollfd.revents & POLLNVAL))
	  use_poll = 0;
	else
	  use_poll = 1;
      }

    if (use_poll)
      {
	/* Guile doesn't export SIGINT hooks like Python does.
	   For now pass EINTR to scm_syserror, that's what fports.c does.  */
	if (poll (&pollfd, 1, 0) < 0)
	  scm_syserror (FUNC_NAME);

	return pollfd.revents & POLLIN ? 1 : 0;
      }
  }
  /* Fall through.  */
#endif

  {
    struct timeval timeout;
    fd_set input_fds;
    int num_fds = fdes + 1;
    int num_found;

    memset (&timeout, 0, sizeof (timeout));
    FD_ZERO (&input_fds);
    FD_SET (fdes, &input_fds);

    num_found = interruptible_select (num_fds,
				      &input_fds, NULL, NULL,
				      &timeout);
    if (num_found < 0)
      {
	/* Guile doesn't export SIGINT hooks like Python does.
	   For now pass EINTR to scm_syserror, that's what fports.c does.  */
	scm_syserror (FUNC_NAME);
      }
    return num_found > 0 && FD_ISSET (fdes, &input_fds);
  }
}

/* The scm_t_ptob_descriptor.fill_input "method".  */

static int
ioscm_fill_input (SCM port)
{
  /* Borrowed from libguile/fports.c.  */
  long count;
  scm_t_port *pt = SCM_PTAB_ENTRY (port);

  /* If we're called on stdout,stderr, punt.  */
  if (! scm_is_eq (port, input_port_scm))
    return (scm_t_wchar) EOF; /* Set errno and return -1?  */

  gdb_flush (gdb_stdout);
  gdb_flush (gdb_stderr);

  count = gdb_stdin->read ((char *) pt->read_buf, pt->read_buf_size);
  if (count == -1)
    scm_syserror (FUNC_NAME);
  if (count == 0)
    return (scm_t_wchar) EOF;

  pt->read_pos = pt->read_buf;
  pt->read_end = pt->read_buf + count;
  return *pt->read_buf;
}

/* Write to gdb's stdout or stderr.  */

static void
ioscm_write (SCM port, const void *data, size_t size)
{

  /* If we're called on stdin, punt.  */
  if (scm_is_eq (port, input_port_scm))
    return;

  gdbscm_gdb_exception exc {};
  try
    {
      if (scm_is_eq (port, error_port_scm))
	fputsn_filtered ((const char *) data, size, gdb_stderr);
      else
	fputsn_filtered ((const char *) data, size, gdb_stdout);
    }
  catch (const gdb_exception &except)
    {
      exc = unpack (except);
    }
  GDBSCM_HANDLE_GDB_EXCEPTION (exc);
}

/* Flush gdb's stdout or stderr.  */

static void
ioscm_flush (SCM port)
{
  /* If we're called on stdin, punt.  */
  if (scm_is_eq (port, input_port_scm))
    return;

  if (scm_is_eq (port, error_port_scm))
    gdb_flush (gdb_stderr);
  else
    gdb_flush (gdb_stdout);
}

#else /* !USING_GUILE_BEFORE_2_2 */

/* Read up to COUNT bytes into bytevector DST at offset START.  Return the
   number of bytes read, zero for the end of file.  */

static size_t
ioscm_read_from_port (SCM port, SCM dst, size_t start, size_t count)
{
  long read;
  char *read_buf;

  /* If we're called on stdout,stderr, punt.  */
  if (! scm_is_eq (port, input_port_scm))
    return 0;

  gdb_flush (gdb_stdout);
  gdb_flush (gdb_stderr);

  read_buf = (char *) SCM_BYTEVECTOR_CONTENTS (dst) + start;
  read = gdb_stdin->read (read_buf, count);
  if (read == -1)
    scm_syserror (FUNC_NAME);

  return (size_t) read;
}

/* Write to gdb's stdout or stderr.  */

static size_t
ioscm_write (SCM port, SCM src, size_t start, size_t count)
{
  const char *data = (char *) SCM_BYTEVECTOR_CONTENTS (src) + start;

  /* If we're called on stdin, punt.  */
  if (scm_is_eq (port, input_port_scm))
    return 0;

  gdbscm_gdb_exception exc {};
  try
    {
      if (scm_is_eq (port, error_port_scm))
	fputsn_filtered ((const char *) data, count, gdb_stderr);
      else
	fputsn_filtered ((const char *) data, count, gdb_stdout);
    }
  catch (const gdb_exception &except)
    {
      exc = unpack (except);
    }
  GDBSCM_HANDLE_GDB_EXCEPTION (exc);

  return count;
}

#endif /* !USING_GUILE_BEFORE_2_2 */

/* Initialize the gdb stdio port type.

   N.B. isatty? will fail on these ports, it is only supported for file
   ports.  IWBN if we could "subclass" file ports.  */

static void
ioscm_init_gdb_stdio_port (void)
{
  stdio_port_desc = scm_make_port_type (stdio_port_desc_name,
#if USING_GUILE_BEFORE_2_2
					ioscm_fill_input,
#else
					ioscm_read_from_port,
#endif
					ioscm_write);

#if USING_GUILE_BEFORE_2_2
  scm_set_port_input_waiting (stdio_port_desc, ioscm_input_waiting);
  scm_set_port_flush (stdio_port_desc, ioscm_flush);
#else
  scm_set_port_read_wait_fd (stdio_port_desc, STDIN_FILENO);
#endif
}

#define GDB_STDIO_BUFFER_DEFAULT_SIZE 1024

#if USING_GUILE_BEFORE_2_2

/* Subroutine of ioscm_make_gdb_stdio_port to simplify it.
   Set up the buffers of port PORT.
   MODE_BITS are the mode bits of PORT.  */

static void
ioscm_init_stdio_buffers (SCM port, long mode_bits)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  int size = mode_bits & SCM_BUF0 ? 0 : GDB_STDIO_BUFFER_DEFAULT_SIZE;
  int writing = (mode_bits & SCM_WRTNG) != 0;

  /* This is heavily copied from scm_fport_buffer_add.  */

  if (!writing && size > 0)
    {
      pt->read_buf
	= (unsigned char *) scm_gc_malloc_pointerless (size, "port buffer");
      pt->read_pos = pt->read_end = pt->read_buf;
      pt->read_buf_size = size;
    }
  else
    {
      pt->read_pos = pt->read_buf = pt->read_end = &pt->shortbuf;
      pt->read_buf_size = 1;
    }

  if (writing && size > 0)
    {
      pt->write_buf
	= (unsigned char *) scm_gc_malloc_pointerless (size, "port buffer");
      pt->write_pos = pt->write_buf;
      pt->write_buf_size = size;
    }
  else
    {
      pt->write_buf = pt->write_pos = &pt->shortbuf;
      pt->write_buf_size = 1;
    }
  pt->write_end = pt->write_buf + pt->write_buf_size;
}

#else

static void
ioscm_init_stdio_buffers (SCM port, long mode_bits)
{
  if (mode_bits & SCM_BUF0)
    scm_setvbuf (port, scm_from_utf8_symbol ("none"), scm_from_size_t (0));
  else
    scm_setvbuf (port, scm_from_utf8_symbol ("block"),
		 scm_from_size_t (GDB_STDIO_BUFFER_DEFAULT_SIZE));
}

#endif

/* Create a gdb stdio port.  */

static SCM
ioscm_make_gdb_stdio_port (int fd)
{
  int is_a_tty = isatty (fd);
  const char *name;
  const char *mode_str;
  long mode_bits;
  SCM port;

  switch (fd)
    {
    case 0:
      name = input_port_name;
      mode_str = is_a_tty ? "r0" : "r";
      break;
    case 1:
      name = output_port_name;
      mode_str = is_a_tty ? "w0" : "w";
      break;
    case 2:
      name = error_port_name;
      mode_str = is_a_tty ? "w0" : "w";
      break;
    default:
      gdb_assert_not_reached ("bad stdio file descriptor");
    }

  mode_bits = scm_mode_bits ((char *) mode_str);
  port = ioscm_open_port (stdio_port_desc, mode_bits, 0);

  scm_set_port_filename_x (port, gdbscm_scm_from_c_string (name));

  ioscm_init_stdio_buffers (port, mode_bits);

  return port;
}

/* (stdio-port? object) -> boolean */

static SCM
gdbscm_stdio_port_p (SCM scm)
{
#if USING_GUILE_BEFORE_2_2
  /* This is copied from SCM_FPORTP.  */
  return scm_from_bool (!SCM_IMP (scm)
			&& (SCM_TYP16 (scm) == stdio_port_desc));
#else
  return scm_from_bool (SCM_PORTP (scm)
			&& (SCM_PORT_TYPE (scm) == stdio_port_desc));
#endif
}

/* GDB's ports are accessed via functions to keep them read-only.  */

/* (input-port) -> port */

static SCM
gdbscm_input_port (void)
{
  return input_port_scm;
}

/* (output-port) -> port */

static SCM
gdbscm_output_port (void)
{
  return output_port_scm;
}

/* (error-port) -> port */

static SCM
gdbscm_error_port (void)
{
  return error_port_scm;
}

/* Support for sending GDB I/O to Guile ports.  */

ioscm_file_port::ioscm_file_port (SCM port)
  : m_port (port)
{}

void
ioscm_file_port::flush ()
{
}

void
ioscm_file_port::write (const char *buffer, long length_buffer)
{
  scm_c_write (m_port, buffer, length_buffer);
}


/* Helper routine for with-{output,error}-to-port.  */

static SCM
ioscm_with_output_to_port_worker (SCM port, SCM thunk, enum oport oport,
				  const char *func_name)
{
  SCM result;

  SCM_ASSERT_TYPE (gdbscm_is_true (scm_output_port_p (port)), port,
		   SCM_ARG1, func_name, _("output port"));
  SCM_ASSERT_TYPE (gdbscm_is_true (scm_thunk_p (thunk)), thunk,
		   SCM_ARG2, func_name, _("thunk"));

  set_batch_flag_and_restore_page_info save_page_info;

  scoped_restore restore_async = make_scoped_restore (&current_ui->async, 0);

  ui_file_up port_file (new ioscm_file_port (port));

  scoped_restore save_file = make_scoped_restore (oport == GDB_STDERR
						  ? &gdb_stderr : &gdb_stdout);

  {
    gdb::optional<ui_out_redirect_pop> redirect_popper;
    if (oport == GDB_STDERR)
      gdb_stderr = port_file.get ();
    else
      {
	current_uiout->redirect (port_file.get ());
	redirect_popper.emplace (current_uiout);

	gdb_stdout = port_file.get ();
      }

    result = gdbscm_safe_call_0 (thunk, NULL);
  }

  if (gdbscm_is_exception (result))
    gdbscm_throw (result);

  return result;
}

/* (%with-gdb-output-to-port port thunk) -> object
   This function is experimental.
   IWBN to not include "gdb" in the name, but it would collide with a standard
   procedure, and it's common to import the gdb module without a prefix.
   There are ways around this, but they're more cumbersome.

   This has % in the name because it's experimental, and we want the
   user-visible version to come from module (gdb experimental).  */

static SCM
gdbscm_percent_with_gdb_output_to_port (SCM port, SCM thunk)
{
  return ioscm_with_output_to_port_worker (port, thunk, GDB_STDOUT, FUNC_NAME);
}

/* (%with-gdb-error-to-port port thunk) -> object
   This function is experimental.
   IWBN to not include "gdb" in the name, but it would collide with a standard
   procedure, and it's common to import the gdb module without a prefix.
   There are ways around this, but they're more cumbersome.

   This has % in the name because it's experimental, and we want the
   user-visible version to come from module (gdb experimental).  */

static SCM
gdbscm_percent_with_gdb_error_to_port (SCM port, SCM thunk)
{
  return ioscm_with_output_to_port_worker (port, thunk, GDB_STDERR, FUNC_NAME);
}

/* Support for r/w memory via ports.  */

/* Perform an "lseek" to OFFSET,WHENCE on memory port IOMEM.
   OFFSET must be in the range [0,size].
   The result is non-zero for success, zero for failure.  */

static int
ioscm_lseek_address (ioscm_memory_port *iomem, LONGEST offset, int whence)
{
  CORE_ADDR new_current;

  gdb_assert (iomem->current <= iomem->size);

  switch (whence)
    {
    case SEEK_CUR:
      /* Catch over/underflow.  */
      if ((offset < 0 && iomem->current + offset > iomem->current)
	  || (offset > 0 && iomem->current + offset < iomem->current))
	return 0;
      new_current = iomem->current + offset;
      break;
    case SEEK_SET:
      new_current = offset;
      break;
    case SEEK_END:
      if (offset == 0)
	{
	  new_current = iomem->size;
	  break;
	}
      /* TODO: Not supported yet.  */
      return 0;
    default:
      return 0;
    }

  if (new_current > iomem->size)
    return 0;
  iomem->current = new_current;
  return 1;
}

#if USING_GUILE_BEFORE_2_2

/* "fill_input" method for memory ports.  */

static int
gdbscm_memory_port_fill_input (SCM port)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  size_t to_read;

  /* "current" is the offset of the first byte we want to read.  */
  gdb_assert (iomem->current <= iomem->size);
  if (iomem->current == iomem->size)
    return EOF;

  /* Don't read outside the allowed memory range.  */
  to_read = pt->read_buf_size;
  if (to_read > iomem->size - iomem->current)
    to_read = iomem->size - iomem->current;

  if (target_read_memory (iomem->start + iomem->current, pt->read_buf,
			  to_read) != 0)
    gdbscm_memory_error (FUNC_NAME, _("error reading memory"), SCM_EOL);

  iomem->current += to_read;
  pt->read_pos = pt->read_buf;
  pt->read_end = pt->read_buf + to_read;
  return *pt->read_buf;
}

/* "end_input" method for memory ports.
   Clear the read buffer and adjust the file position for unread bytes.  */

static void
gdbscm_memory_port_end_input (SCM port, int offset)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  size_t remaining = pt->read_end - pt->read_pos;

  /* Note: Use of "int offset" is specified by Guile ports API.  */
  if ((offset < 0 && remaining + offset > remaining)
      || (offset > 0 && remaining + offset < remaining))
    {
      gdbscm_out_of_range_error (FUNC_NAME, 0, scm_from_int (offset),
				 _("overflow in offset calculation"));
    }
  offset += remaining;

  if (offset > 0)
    {
      pt->read_pos = pt->read_end;
      /* Throw error if unread-char used at beginning of file
	 then attempting to write.  Seems correct.  */
      if (!ioscm_lseek_address (iomem, -offset, SEEK_CUR))
	{
	  gdbscm_out_of_range_error (FUNC_NAME, 0, scm_from_int (offset),
				     _("bad offset"));
	}
    }

  pt->rw_active = SCM_PORT_NEITHER;
}

/* "flush" method for memory ports.  */

static void
gdbscm_memory_port_flush (SCM port)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  size_t to_write = pt->write_pos - pt->write_buf;

  if (to_write == 0)
    return;

  /* There's no way to indicate a short write, so if the request goes past
     the end of the port's memory range, flag an error.  */
  if (to_write > iomem->size - iomem->current)
    {
      gdbscm_out_of_range_error (FUNC_NAME, 0,
				 gdbscm_scm_from_ulongest (to_write),
				 _("writing beyond end of memory range"));
    }

  if (target_write_memory (iomem->start + iomem->current, pt->write_buf,
			   to_write) != 0)
    gdbscm_memory_error (FUNC_NAME, _("error writing memory"), SCM_EOL);

  iomem->current += to_write;
  pt->write_pos = pt->write_buf;
  pt->rw_active = SCM_PORT_NEITHER;
}

/* "seek" method for memory ports.  */

static scm_t_off
gdbscm_memory_port_seek (SCM port, scm_t_off offset, int whence)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  CORE_ADDR result;
  int rc;

  if (pt->rw_active == SCM_PORT_WRITE)
    {
      if (offset != 0 || whence != SEEK_CUR)
	{
	  gdbscm_memory_port_flush (port);
	  rc = ioscm_lseek_address (iomem, offset, whence);
	  result = iomem->current;
	}
      else
	{
	  /* Read current position without disturbing the buffer,
	     but flag an error if what's in the buffer goes outside the
	     allowed range.  */
	  CORE_ADDR current = iomem->current;
	  size_t delta = pt->write_pos - pt->write_buf;

	  if (current + delta < current
	      || current + delta > iomem->size)
	    rc = 0;
	  else
	    {
	      result = current + delta;
	      rc = 1;
	    }
	}
    }
  else if (pt->rw_active == SCM_PORT_READ)
    {
      if (offset != 0 || whence != SEEK_CUR)
	{
	  scm_end_input (port);
	  rc = ioscm_lseek_address (iomem, offset, whence);
	  result = iomem->current;
	}
      else
	{
	  /* Read current position without disturbing the buffer
	     (particularly the unread-char buffer).  */
	  CORE_ADDR current = iomem->current;
	  size_t remaining = pt->read_end - pt->read_pos;

	  if (current - remaining > current
	      || current - remaining < iomem->start)
	    rc = 0;
	  else
	    {
	      result = current - remaining;
	      rc = 1;
	    }

	  if (rc != 0 && pt->read_buf == pt->putback_buf)
	    {
	      size_t saved_remaining = pt->saved_read_end - pt->saved_read_pos;

	      if (result - saved_remaining > result
		  || result - saved_remaining < iomem->start)
		rc = 0;
	      else
		result -= saved_remaining;
	    }
	}
    }
  else /* SCM_PORT_NEITHER */
    {
      rc = ioscm_lseek_address (iomem, offset, whence);
      result = iomem->current;
    }

  if (rc == 0)
    {
      gdbscm_out_of_range_error (FUNC_NAME, 0,
				 gdbscm_scm_from_longest (offset),
				 _("bad seek"));
    }

  /* TODO: The Guile API doesn't support 32x64.  We can't fix that here,
     and there's no need to throw an error if the new address can't be
     represented in a scm_t_off.  But we could return something less
     clumsy.  */
  return result;
}

/* "write" method for memory ports.  */

static void
gdbscm_memory_port_write (SCM port, const void *void_data, size_t size)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  const gdb_byte *data = (const gdb_byte *) void_data;

  /* There's no way to indicate a short write, so if the request goes past
     the end of the port's memory range, flag an error.  */
  if (size > iomem->size - iomem->current)
    {
      gdbscm_out_of_range_error (FUNC_NAME, 0, gdbscm_scm_from_ulongest (size),
				 _("writing beyond end of memory range"));
    }

  if (pt->write_buf == &pt->shortbuf)
    {
      /* Unbuffered port.  */
      if (target_write_memory (iomem->start + iomem->current, data, size) != 0)
	gdbscm_memory_error (FUNC_NAME, _("error writing memory"), SCM_EOL);
      iomem->current += size;
      return;
    }

  /* Note: The edge case of what to do when the buffer exactly fills is
     debatable.  Guile flushes when the buffer exactly fills up, so we
     do too.  It's counter-intuitive to my mind, but in case there's a
     subtlety somewhere that depends on this, we do the same.  */

  {
    size_t space = pt->write_end - pt->write_pos;

    if (size < space)
      {
	/* Data fits in buffer, and does not fill it.  */
	memcpy (pt->write_pos, data, size);
	pt->write_pos += size;
      }
    else
      {
	memcpy (pt->write_pos, data, space);
	pt->write_pos = pt->write_end;
	gdbscm_memory_port_flush (port);
	{
	  const gdb_byte *ptr = data + space;
	  size_t remaining = size - space;

	  if (remaining >= pt->write_buf_size)
	    {
	      if (target_write_memory (iomem->start + iomem->current, ptr,
				       remaining) != 0)
		gdbscm_memory_error (FUNC_NAME, _("error writing memory"),
				     SCM_EOL);
	      iomem->current += remaining;
	    }
	  else
	    {
	      memcpy (pt->write_pos, ptr, remaining);
	      pt->write_pos += remaining;
	    }
	}
      }
  }
}

/* "close" method for memory ports.  */

static int
gdbscm_memory_port_close (SCM port)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);

  gdbscm_memory_port_flush (port);

  if (pt->read_buf == pt->putback_buf)
    pt->read_buf = pt->saved_read_buf;
  if (pt->read_buf != &pt->shortbuf)
    xfree (pt->read_buf);
  if (pt->write_buf != &pt->shortbuf)
    xfree (pt->write_buf);
  scm_gc_free (iomem, sizeof (*iomem), "memory port");

  return 0;
}

/* "free" method for memory ports.  */

static size_t
gdbscm_memory_port_free (SCM port)
{
  gdbscm_memory_port_close (port);

  return 0;
}

/* Re-initialize a memory port, updating its read/write buffer sizes.
   An exception is thrown if the port is unbuffered.
   TODO: Allow switching buffered/unbuffered.
   An exception is also thrown if data is still buffered, except in the case
   where the buffer size isn't changing (since that's just a nop).  */

static void
ioscm_reinit_memory_port (SCM port, size_t read_buf_size,
			  size_t write_buf_size, const char *func_name)
{
  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);

  gdb_assert (read_buf_size >= min_memory_port_buf_size
	      && read_buf_size <= max_memory_port_buf_size);
  gdb_assert (write_buf_size >= min_memory_port_buf_size
	      && write_buf_size <= max_memory_port_buf_size);

  /* First check if the port is unbuffered.  */

  if (pt->read_buf == &pt->shortbuf)
    {
      gdb_assert (pt->write_buf == &pt->shortbuf);
      scm_misc_error (func_name, _("port is unbuffered: ~a"),
		      scm_list_1 (port));
    }

  /* Next check if anything is buffered.  */

  if (read_buf_size != pt->read_buf_size
      && pt->read_end != pt->read_buf)
    {
      scm_misc_error (func_name, _("read buffer not empty: ~a"),
		      scm_list_1 (port));
    }

  if (write_buf_size != pt->write_buf_size
      && pt->write_pos != pt->write_buf)
    {
      scm_misc_error (func_name, _("write buffer not empty: ~a"),
		      scm_list_1 (port));
    }

  /* Now we can update the buffer sizes, but only if the size has changed.  */

  if (read_buf_size != pt->read_buf_size)
    {
      iomem->read_buf_size = read_buf_size;
      pt->read_buf_size = read_buf_size;
      xfree (pt->read_buf);
      pt->read_buf = (unsigned char *) xmalloc (pt->read_buf_size);
      pt->read_pos = pt->read_end = pt->read_buf;
    }

  if (write_buf_size != pt->write_buf_size)
    {
      iomem->write_buf_size = write_buf_size;
      pt->write_buf_size = write_buf_size;
      xfree (pt->write_buf);
      pt->write_buf = (unsigned char *) xmalloc (pt->write_buf_size);
      pt->write_pos = pt->write_buf;
      pt->write_end = pt->write_buf + pt->write_buf_size;
    }
}

#else /* !USING_GUILE_BEFORE_2_2 */

/* The semantics get weird if the buffer size is larger than the port range,
   so provide a better default buffer size.  */

static void
gdbscm_get_natural_buffer_sizes (SCM port, size_t *read_size,
				 size_t *write_size)
{
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);

  size_t size = natural_buf_size;
  if (iomem != NULL && iomem->size < size)
    size = iomem->size;
  *read_size = *write_size = size;
}

/* Read up to COUNT bytes into bytevector DST at offset START.  Return the
   number of bytes read, zero for the end of file.  */

static size_t
gdbscm_memory_port_read (SCM port, SCM dst, size_t start, size_t count)
{
  gdb_byte *read_buf;
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);

  /* "current" is the offset of the first byte we want to read.  */
  gdb_assert (iomem->current <= iomem->size);
  if (iomem->current == iomem->size)
    return 0;

  /* Don't read outside the allowed memory range.  */
  if (count > iomem->size - iomem->current)
    count = iomem->size - iomem->current;

  read_buf = (gdb_byte *) SCM_BYTEVECTOR_CONTENTS (dst) + start;
  if (target_read_memory (iomem->start + iomem->current, read_buf,
			  count) != 0)
    gdbscm_memory_error (FUNC_NAME, _("error reading memory"), SCM_EOL);

  iomem->current += count;
  return count;
}

static size_t
gdbscm_memory_port_write (SCM port, SCM src, size_t start, size_t count)
{
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  const gdb_byte *data =
    (const gdb_byte *) SCM_BYTEVECTOR_CONTENTS (src) + start;

  /* If the request goes past the end of the port's memory range, flag an
     error.  */
  if (count > iomem->size - iomem->current)
    gdbscm_out_of_range_error (FUNC_NAME, 0, scm_from_size_t (count),
			       _("writing beyond end of memory range"));

  if (target_write_memory (iomem->start + iomem->current, data,
			   count) != 0)
    gdbscm_memory_error (FUNC_NAME, _("error writing memory"),
			 SCM_EOL);

  iomem->current += count;

  return count;
}

static scm_t_off
gdbscm_memory_port_seek (SCM port, scm_t_off offset, int whence)
{
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  int rc;

  rc = ioscm_lseek_address (iomem, offset, whence);
  if (rc == 0)
    gdbscm_out_of_range_error (FUNC_NAME, 0,
			       gdbscm_scm_from_longest (offset),
			       _("bad seek"));

  /* TODO: The Guile API doesn't support 32x64.  We can't fix that here,
     and there's no need to throw an error if the new address can't be
     represented in a scm_t_off.  But we could return something less
     clumsy.  */
  return iomem->current;
}

static void
gdbscm_memory_port_close (SCM port)
{
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);
  scm_gc_free (iomem, sizeof (*iomem), "memory port");
  SCM_SETSTREAM (port, NULL);
}

#endif /* !USING_GUILE_BEFORE_2_2 */

/* "print" method for memory ports.  */

static int
gdbscm_memory_port_print (SCM exp, SCM port, scm_print_state *pstate)
{
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (exp);

  scm_puts ("#<", port);
  scm_print_port_mode (exp, port);
  /* scm_print_port_mode includes a trailing space.  */
  gdbscm_printf (port, "%s %s-%s", memory_port_desc_name,
		 hex_string (iomem->start), hex_string (iomem->end));
  scm_putc ('>', port);
  return 1;
}

/* Create the port type used for memory.  */

static void
ioscm_init_memory_port_type (void)
{
  memory_port_desc = scm_make_port_type (memory_port_desc_name,
#if USING_GUILE_BEFORE_2_2
					 gdbscm_memory_port_fill_input,
#else
					 gdbscm_memory_port_read,
#endif
					 gdbscm_memory_port_write);

#if USING_GUILE_BEFORE_2_2
  scm_set_port_end_input (memory_port_desc, gdbscm_memory_port_end_input);
  scm_set_port_flush (memory_port_desc, gdbscm_memory_port_flush);
  scm_set_port_free (memory_port_desc, gdbscm_memory_port_free);
#else
  scm_set_port_get_natural_buffer_sizes (memory_port_desc,
					 gdbscm_get_natural_buffer_sizes);
#endif
  scm_set_port_seek (memory_port_desc, gdbscm_memory_port_seek);
  scm_set_port_close (memory_port_desc, gdbscm_memory_port_close);
  scm_set_port_print (memory_port_desc, gdbscm_memory_port_print);
}

/* Helper for gdbscm_open_memory to parse the mode bits.
   An exception is thrown if MODE is invalid.  */

static long
ioscm_parse_mode_bits (const char *func_name, const char *mode)
{
  const char *p;
  long mode_bits;

  if (*mode != 'r' && *mode != 'w')
    {
      gdbscm_out_of_range_error (func_name, 0,
				 gdbscm_scm_from_c_string (mode),
				 _("bad mode string"));
    }
  for (p = mode + 1; *p != '\0'; ++p)
    {
      switch (*p)
	{
	case '0':
	case 'b':
	case '+':
	  break;
	default:
	  gdbscm_out_of_range_error (func_name, 0,
				     gdbscm_scm_from_c_string (mode),
				     _("bad mode string"));
	}
    }

  /* Kinda awkward to convert the mode from SCM -> string only to have Guile
     convert it back to SCM, but that's the API we have to work with.  */
  mode_bits = scm_mode_bits ((char *) mode);

  return mode_bits;
}

/* Return the memory object to be used as a "stream" associated with a memory
   port for the START--END range.  */

static ioscm_memory_port *
ioscm_init_memory_port_stream (CORE_ADDR start, CORE_ADDR end)
{
  ioscm_memory_port *iomem;

  gdb_assert (start <= end);

  iomem = (ioscm_memory_port *) scm_gc_malloc_pointerless (sizeof (*iomem),
							   "memory port");

  iomem->start = start;
  iomem->end = end;
  iomem->size = end - start;
  iomem->current = 0;

  return iomem;
}

#if USING_GUILE_BEFORE_2_2

/* Helper for gdbscm_open_memory to finish initializing the port.
   The port has address range [start,end).
   This means that address of 0xff..ff is not accessible.
   I can live with that.  */

static void
ioscm_init_memory_port_buffers (SCM port)
{
  ioscm_memory_port *iomem = (ioscm_memory_port *) SCM_STREAM (port);

  int buffered = (SCM_CELL_WORD_0 (port) & SCM_BUF0) == 0;
  if (buffered)
    {
      iomem->read_buf_size = default_read_buf_size;
      iomem->write_buf_size = default_write_buf_size;
    }
  else
    {
      iomem->read_buf_size = 1;
      iomem->write_buf_size = 1;
    }

  scm_t_port *pt = SCM_PTAB_ENTRY (port);
  /* Match the expectation of `binary-port?'.  */
  pt->encoding = NULL;
  pt->rw_random = 1;
  pt->read_buf_size = iomem->read_buf_size;
  pt->write_buf_size = iomem->write_buf_size;
  if (buffered)
    {
      pt->read_buf = (unsigned char *) xmalloc (pt->read_buf_size);
      pt->write_buf = (unsigned char *) xmalloc (pt->write_buf_size);
    }
  else
    {
      pt->read_buf = &pt->shortbuf;
      pt->write_buf = &pt->shortbuf;
    }
  pt->read_pos = pt->read_end = pt->read_buf;
  pt->write_pos = pt->write_buf;
  pt->write_end = pt->write_buf + pt->write_buf_size;
}

#endif

/* (open-memory [#:mode string] [#:start address] [#:size integer]) -> port
   Return a port that can be used for reading and writing memory.
   MODE is a string, and must be one of "r", "w", or "r+".
   "0" may be appended to MODE to mark the port as unbuffered.
   For compatibility "b" (binary) may also be appended, but we ignore it:
   memory ports are binary only.

   The chunk of memory that can be accessed can be bounded.
   If both START,SIZE are unspecified, all of memory can be accessed
   (except 0xff..ff).  If only START is specified, all of memory from that
   point on can be accessed (except 0xff..ff).  If only SIZE if specified,
   all memory in [0,SIZE) can be accessed.  If both are specified, all memory
   in [START,START+SIZE) can be accessed.

   Note: If it becomes useful enough we can later add #:end as an alternative
   to #:size.  For now it is left out.

   The result is a Scheme port, and its semantics are a bit odd for accessing
   memory (e.g., unget), but we don't try to hide this.  It's a port.

   N.B. Seeks on the port must be in the range [0,size].
   This is for similarity with bytevector ports, and so that one can seek
   to the first byte.  */

static SCM
gdbscm_open_memory (SCM rest)
{
  const SCM keywords[] = {
    mode_keyword, start_keyword, size_keyword, SCM_BOOL_F
  };
  char *mode = NULL;
  CORE_ADDR start = 0;
  CORE_ADDR end;
  int mode_arg_pos = -1, start_arg_pos = -1, size_arg_pos = -1;
  ULONGEST size;
  SCM port;
  long mode_bits;

  gdbscm_parse_function_args (FUNC_NAME, SCM_ARG1, keywords, "#sUU", rest,
			      &mode_arg_pos, &mode,
			      &start_arg_pos, &start,
			      &size_arg_pos, &size);

  scm_dynwind_begin ((scm_t_dynwind_flags) 0);

  if (mode == NULL)
    mode = xstrdup ("r");
  scm_dynwind_free (mode);

  if (size_arg_pos > 0)
    {
      /* For now be strict about start+size overflowing.  If it becomes
	 a nuisance we can relax things later.  */
      if (start + size < start)
	{
	  gdbscm_out_of_range_error (FUNC_NAME, 0,
				scm_list_2 (gdbscm_scm_from_ulongest (start),
					    gdbscm_scm_from_ulongest (size)),
				     _("start+size overflows"));
	}
      end = start + size;
    }
  else
    end = ~(CORE_ADDR) 0;

  mode_bits = ioscm_parse_mode_bits (FUNC_NAME, mode);

  /* Edge case: empty range -> unbuffered.
     There's no need to disallow empty ranges, but we need an unbuffered port
     to get the semantics right.  */
  if (size == 0)
    mode_bits |= SCM_BUF0;

  auto stream = ioscm_init_memory_port_stream (start, end);
  port = ioscm_open_port (memory_port_desc, mode_bits,
			  (scm_t_bits) stream);

#if USING_GUILE_BEFORE_2_2
  ioscm_init_memory_port_buffers (port);
#endif

  scm_dynwind_end ();

  /* TODO: Set the file name as "memory-start-end"?  */
  return port;
}

/* Return non-zero if OBJ is a memory port.  */

static int
gdbscm_is_memory_port (SCM obj)
{
#if USING_GUILE_BEFORE_2_2
  return !SCM_IMP (obj) && (SCM_TYP16 (obj) == memory_port_desc);
#else
  return SCM_PORTP (obj) && (SCM_PORT_TYPE (obj) == memory_port_desc);
#endif
}

/* (memory-port? obj) -> boolean */

static SCM
gdbscm_memory_port_p (SCM obj)
{
  return scm_from_bool (gdbscm_is_memory_port (obj));
}

/* (memory-port-range port) -> (start end) */

static SCM
gdbscm_memory_port_range (SCM port)
{
  ioscm_memory_port *iomem;

  SCM_ASSERT_TYPE (gdbscm_is_memory_port (port), port, SCM_ARG1, FUNC_NAME,
		   memory_port_desc_name);

  iomem = (ioscm_memory_port *) SCM_STREAM (port);
  return scm_list_2 (gdbscm_scm_from_ulongest (iomem->start),
		     gdbscm_scm_from_ulongest (iomem->end));
}

/* (memory-port-read-buffer-size port) -> integer */

static SCM
gdbscm_memory_port_read_buffer_size (SCM port)
{
#if USING_GUILE_BEFORE_2_2
  ioscm_memory_port *iomem;

  SCM_ASSERT_TYPE (gdbscm_is_memory_port (port), port, SCM_ARG1, FUNC_NAME,
		   memory_port_desc_name);

  iomem = (ioscm_memory_port *) SCM_STREAM (port);
  return scm_from_uint (iomem->read_buf_size);
#else
  return scm_from_uint (0);
#endif
}

/* (set-memory-port-read-buffer-size! port size) -> unspecified
   An exception is thrown if read data is still buffered or if the port
   is unbuffered.  */

static SCM
gdbscm_set_memory_port_read_buffer_size_x (SCM port, SCM size)
{
#if USING_GUILE_BEFORE_2_2
  ioscm_memory_port *iomem;

  SCM_ASSERT_TYPE (gdbscm_is_memory_port (port), port, SCM_ARG1, FUNC_NAME,
		   memory_port_desc_name);
  SCM_ASSERT_TYPE (scm_is_integer (size), size, SCM_ARG2, FUNC_NAME,
		   _("integer"));

  if (!scm_is_unsigned_integer (size, min_memory_port_buf_size,
				max_memory_port_buf_size))
    {
      gdbscm_out_of_range_error (FUNC_NAME, SCM_ARG2, size,
				 out_of_range_buf_size);
    }

  iomem = (ioscm_memory_port *) SCM_STREAM (port);
  ioscm_reinit_memory_port (port, scm_to_uint (size), iomem->write_buf_size,
			    FUNC_NAME);

  return SCM_UNSPECIFIED;
#else
  return scm_setvbuf (port, scm_from_utf8_symbol ("block"), size);
#endif
}

/* (memory-port-write-buffer-size port) -> integer */

static SCM
gdbscm_memory_port_write_buffer_size (SCM port)
{
#if USING_GUILE_BEFORE_2_2
  ioscm_memory_port *iomem;

  SCM_ASSERT_TYPE (gdbscm_is_memory_port (port), port, SCM_ARG1, FUNC_NAME,
		   memory_port_desc_name);

  iomem = (ioscm_memory_port *) SCM_STREAM (port);
  return scm_from_uint (iomem->write_buf_size);
#else
  return scm_from_uint (0);
#endif
}

/* (set-memory-port-write-buffer-size! port size) -> unspecified
   An exception is thrown if write data is still buffered or if the port
   is unbuffered.  */

static SCM
gdbscm_set_memory_port_write_buffer_size_x (SCM port, SCM size)
{
#if USING_GUILE_BEFORE_2_2
  ioscm_memory_port *iomem;

  SCM_ASSERT_TYPE (gdbscm_is_memory_port (port), port, SCM_ARG1, FUNC_NAME,
		   memory_port_desc_name);
  SCM_ASSERT_TYPE (scm_is_integer (size), size, SCM_ARG2, FUNC_NAME,
		   _("integer"));

  if (!scm_is_unsigned_integer (size, min_memory_port_buf_size,
				max_memory_port_buf_size))
    {
      gdbscm_out_of_range_error (FUNC_NAME, SCM_ARG2, size,
				 out_of_range_buf_size);
    }

  iomem = (ioscm_memory_port *) SCM_STREAM (port);
  ioscm_reinit_memory_port (port, iomem->read_buf_size, scm_to_uint (size),
			    FUNC_NAME);

  return SCM_UNSPECIFIED;
#else
  return scm_setvbuf (port, scm_from_utf8_symbol ("block"), size);
#endif
}

/* Initialize gdb ports.  */

static const scheme_function port_functions[] =
{
  { "input-port", 0, 0, 0, as_a_scm_t_subr (gdbscm_input_port),
    "\
Return gdb's input port." },

  { "output-port", 0, 0, 0, as_a_scm_t_subr (gdbscm_output_port),
    "\
Return gdb's output port." },

  { "error-port", 0, 0, 0, as_a_scm_t_subr (gdbscm_error_port),
    "\
Return gdb's error port." },

  { "stdio-port?", 1, 0, 0, as_a_scm_t_subr (gdbscm_stdio_port_p),
    "\
Return #t if the object is a gdb:stdio-port." },

  { "open-memory", 0, 0, 1, as_a_scm_t_subr (gdbscm_open_memory),
    "\
Return a port that can be used for reading/writing inferior memory.\n\
\n\
  Arguments: [#:mode string] [#:start address] [#:size integer]\n\
  Returns: A port object." },

  { "memory-port?", 1, 0, 0, as_a_scm_t_subr (gdbscm_memory_port_p),
    "\
Return #t if the object is a memory port." },

  { "memory-port-range", 1, 0, 0, as_a_scm_t_subr (gdbscm_memory_port_range),
    "\
Return the memory range of the port as (start end)." },

  { "memory-port-read-buffer-size", 1, 0, 0,
    as_a_scm_t_subr (gdbscm_memory_port_read_buffer_size),
    "\
Return the size of the read buffer for the memory port." },

  { "set-memory-port-read-buffer-size!", 2, 0, 0,
    as_a_scm_t_subr (gdbscm_set_memory_port_read_buffer_size_x),
    "\
Set the size of the read buffer for the memory port.\n\
\n\
  Arguments: port integer\n\
  Returns: unspecified." },

  { "memory-port-write-buffer-size", 1, 0, 0,
    as_a_scm_t_subr (gdbscm_memory_port_write_buffer_size),
    "\
Return the size of the write buffer for the memory port." },

  { "set-memory-port-write-buffer-size!", 2, 0, 0,
    as_a_scm_t_subr (gdbscm_set_memory_port_write_buffer_size_x),
    "\
Set the size of the write buffer for the memory port.\n\
\n\
  Arguments: port integer\n\
  Returns: unspecified." },

  END_FUNCTIONS
};

static const scheme_function private_port_functions[] =
{
#if 0 /* TODO */
  { "%with-gdb-input-from-port", 2, 0, 0,
    as_a_scm_t_subr (gdbscm_percent_with_gdb_input_from_port),
    "\
Temporarily set GDB's input port to PORT and then invoke THUNK.\n\
\n\
  Arguments: port thunk\n\
  Returns: The result of calling THUNK.\n\
\n\
This procedure is experimental." },
#endif

  { "%with-gdb-output-to-port", 2, 0, 0,
    as_a_scm_t_subr (gdbscm_percent_with_gdb_output_to_port),
    "\
Temporarily set GDB's output port to PORT and then invoke THUNK.\n\
\n\
  Arguments: port thunk\n\
  Returns: The result of calling THUNK.\n\
\n\
This procedure is experimental." },

  { "%with-gdb-error-to-port", 2, 0, 0,
    as_a_scm_t_subr (gdbscm_percent_with_gdb_error_to_port),
    "\
Temporarily set GDB's error port to PORT and then invoke THUNK.\n\
\n\
  Arguments: port thunk\n\
  Returns: The result of calling THUNK.\n\
\n\
This procedure is experimental." },

  END_FUNCTIONS
};

void
gdbscm_initialize_ports (void)
{
  /* Save the original stdio ports for debugging purposes.  */

  orig_input_port_scm = scm_current_input_port ();
  orig_output_port_scm = scm_current_output_port ();
  orig_error_port_scm = scm_current_error_port ();

  /* Set up the stdio ports.  */

  ioscm_init_gdb_stdio_port ();
  input_port_scm = ioscm_make_gdb_stdio_port (0);
  output_port_scm = ioscm_make_gdb_stdio_port (1);
  error_port_scm = ioscm_make_gdb_stdio_port (2);

  /* Set up memory ports.  */

  ioscm_init_memory_port_type ();

  /* Install the accessor functions.  */

  gdbscm_define_functions (port_functions, 1);
  gdbscm_define_functions (private_port_functions, 0);

  /* Keyword args for open-memory.  */

  mode_keyword = scm_from_latin1_keyword ("mode");
  start_keyword = scm_from_latin1_keyword ("start");
  size_keyword = scm_from_latin1_keyword ("size");

#if USING_GUILE_BEFORE_2_2
  /* Error message text for "out of range" memory port buffer sizes.  */

  out_of_range_buf_size = xstrprintf ("size not between %u - %u",
				      min_memory_port_buf_size,
				      max_memory_port_buf_size);
#endif
}
