/* The common simulator framework for GDB, the GNU Debugger.

   Copyright 2002-2021 Free Software Foundation, Inc.

   Contributed by Andrew Cagney and Red Hat.

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

/* This must come before any other includes.  */
#include "defs.h"

#include "hw-main.h"
#include "hw-base.h"

#include "sim-io.h"
#include "sim-assert.h"

struct hw_instance_data
{
  hw_finish_instance_method *to_finish;
  struct hw_instance *instances;
};

static hw_finish_instance_method abort_hw_finish_instance;

void
create_hw_instance_data (struct hw *me)
{
  me->instances_of_hw = HW_ZALLOC (me, struct hw_instance_data);
  set_hw_finish_instance (me, abort_hw_finish_instance);
}

void
delete_hw_instance_data (struct hw *me)
{
  /* NOP */
}


static void
abort_hw_finish_instance (struct hw *hw,
			  struct hw_instance *instance)
{
  hw_abort (hw, "no instance finish method");
}

void
set_hw_finish_instance (struct hw *me,
			hw_finish_instance_method *finish)
{
  me->instances_of_hw->to_finish = finish;
}


#if 0
void
clean_hw_instances (struct hw *me)
{
  struct hw_instance **instance = &me->instances;
  while (*instance != NULL)
    {
      struct hw_instance *old_instance = *instance;
      hw_instance_delete (old_instance);
      instance = &me->instances;
    }
}
#endif


void
hw_instance_delete (struct hw_instance *instance)
{
#if 1
  hw_abort (hw_instance_hw (instance), "not implemented");
#else
  struct hw *me = hw_instance_hw (instance);
  if (instance->to_instance_delete == NULL)
    hw_abort (me, "no delete method");
  instance->method->delete (instance);
  if (instance->args != NULL)
    free (instance->args);
  if (instance->path != NULL)
    free (instance->path);
  if (instance->child == NULL)
    {
      /* only remove leaf nodes */
      struct hw_instance **curr = &me->instances;
      while (*curr != instance)
	{
	  ASSERT (*curr != NULL);
	  curr = &(*curr)->next;
	}
      *curr = instance->next;
    }
  else
    {
      /* check it isn't in the instance list */
      struct hw_instance *curr = me->instances;
      while (curr != NULL)
	{
	  ASSERT (curr != instance);
	  curr = curr->next;
	}
      /* unlink the child */
      ASSERT (instance->child->parent == instance);
      instance->child->parent = NULL;
    }
  cap_remove (me->ihandles, instance);
  free (instance);
#endif
}


static int
panic_hw_instance_read (struct hw_instance *instance,
			void *addr,
			unsigned_word len)
{
  hw_abort (hw_instance_hw (instance), "no read method");
  return -1;
}



static int
panic_hw_instance_write (struct hw_instance *instance,
			 const void *addr,
			 unsigned_word len)
{
  hw_abort (hw_instance_hw (instance), "no write method");
  return -1;
}


static int
panic_hw_instance_seek (struct hw_instance *instance,
			unsigned_word pos_hi,
			unsigned_word pos_lo)
{
  hw_abort (hw_instance_hw (instance), "no seek method");
  return -1;
}


int
hw_instance_call_method (struct hw_instance *instance,
			 const char *method_name,
			 int n_stack_args,
			 unsigned_cell stack_args[/*n_stack_args*/],
			 int n_stack_returns,
			 unsigned_cell stack_returns[/*n_stack_args*/])
{
#if 1
  hw_abort (hw_instance_hw (instance), "not implemented");
  return -1;
#else
  struct hw *me = instance->owner;
  const hw_instance_methods *method = instance->method->methods;
  if (method == NULL)
    {
      hw_abort (me, "no methods (want %s)", method_name);
    }
  while (method->name != NULL)
    {
      if (strcmp (method->name, method_name) == 0)
	{
	  return method->method (instance,
				 n_stack_args, stack_args,
				 n_stack_returns, stack_returns);
	}
      method++;
    }
  hw_abort (me, "no %s method", method_name);
  return 0;
#endif
}


#define set_hw_instance_read(instance, method)\
((instance)->to_instance_read = (method))

#define set_hw_instance_write(instance, method)\
((instance)->to_instance_write = (method))

#define set_hw_instance_seek(instance, method)\
((instance)->to_instance_seek = (method))


#if 0
static void
set_hw_instance_finish (struct hw *me,
			hw_instance_finish_method *method)
{
  if (me->instances_of_hw == NULL)
    me->instances_of_hw = HW_ZALLOC (me, struct hw_instance_data);
  me->instances_of_hw->to_finish = method;
}
#endif


struct hw_instance *
hw_instance_create (struct hw *me,
		    struct hw_instance *parent,
		    const char *path,
		    const char *args)
{
  struct hw_instance *instance = ZALLOC (struct hw_instance);
  /*instance->unit*/
  /* link this instance into the devices list */
  instance->hw_of_instance = me;
  instance->parent_of_instance = NULL;
  /* link this instance into the front of the devices instance list */
  instance->sibling_of_instance = me->instances_of_hw->instances;
  me->instances_of_hw->instances = instance;
  if (parent != NULL)
    {
      ASSERT (parent->child_of_instance == NULL);
      parent->child_of_instance = instance;
      instance->parent_of_instance = parent;
    }
  instance->args_of_instance = hw_strdup (me, args);
  instance->path_of_instance = hw_strdup (me, path);
  set_hw_instance_read (instance, panic_hw_instance_read);
  set_hw_instance_write (instance, panic_hw_instance_write);
  set_hw_instance_seek (instance, panic_hw_instance_seek);
  hw_handle_add_ihandle (me, instance);
  me->instances_of_hw->to_finish (me, instance);
  return instance;
}


struct hw_instance *
hw_instance_interceed (struct hw_instance *parent,
		       const char *path,
		       const char *args)
{
#if 1
  return NULL;
#else
  struct hw_instance *instance = ZALLOC (struct hw_instance);
  /*instance->unit*/
  /* link this instance into the devices list */
  if (me != NULL)
    {
      ASSERT (parent == NULL);
      instance->hw_of_instance = me;
      instance->parent_of_instance = NULL;
      /* link this instance into the front of the devices instance list */
      instance->sibling_of_instance = me->instances_of_hw->instances;
      me->instances_of_hw->instances = instance;
    }
  if (parent != NULL)
    {
      struct hw_instance **previous;
      ASSERT (parent->child_of_instance == NULL);
      parent->child_of_instance = instance;
      instance->owner = parent->owner;
      instance->parent_of_instance = parent;
      /* in the devices instance list replace the parent instance with
	 this one */
      instance->next = parent->next;
      /* replace parent with this new node */
      previous = &instance->owner->instances;
      while (*previous != parent)
	{
	  ASSERT (*previous != NULL);
	  previous = &(*previous)->next;
	}
      *previous = instance;
    }
  instance->data = data;
  instance->args = (args == NULL ? NULL : (char *) strdup (args));
  instance->path = (path == NULL ? NULL : (char *) strdup (path));
  cap_add (instance->owner->ihandles, instance);
  return instance;
#endif
}
