/*
 *  This file is part of ixemul.library for the Amiga.
 *  Copyright (C) 1991, 1992  Markus M. Wild
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Library General Public
 *  License as published by the Free Software Foundation; either
 *  version 2 of the License, or (at your option) any later version.
 *
 *  This library 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
 *  Library General Public License for more details.
 *
 *  You should have received a copy of the GNU Library General Public
 *  License along with this library; if not, write to the Free
 *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */

#define KERNEL
#include "ixemul.h"
#include <libraries/arpbase.h>

#include <exec/memory.h>

#undef DEBUG

#ifdef DEBUG
#define DP(a) kprintf a
#else
#define DP(a)
#endif

/* not changed after the library is initialized */
struct ixemul_base *ixemulbase = 0;
int _dos20;

/* used by gnulib.. I was too lazy to convert that library as well ;-) */
void *MathIeeeDoubBasBase, *MathIeeeDoubTransBase,
     *MathIeeeSingBasBase, *MathIeeeSingTransBase;

struct ixemul_base *
ix_init (struct ixemul_base *ixbase)
{
  ixbase->ix_nfile = NOFILE;
  ixbase->ix_file_tab = (struct file *)
    AllocMem (NOFILE * sizeof(struct file), MEMF_PUBLIC | MEMF_CLEAR);
  ixbase->ix_fileNFILE = ixbase->ix_file_tab + ixbase->ix_nfile;
  ixbase->ix_lastf = ixbase->ix_file_tab;
  ixbase->ix_membuf_limit = MEM_BUF_MAX_SIZE;
  bzero (& ixbase->ix_md, sizeof (struct malloc_data));
#ifdef DEBUG
  dump_remember (& ixbase->ix_md);
#endif
  ixbase->ix_translate_dots = 1;

  ixemulbase = ixbase;

  /* patch our library to optimally adapt to the given hardware */
  ix_patch_functions (ixbase);

  if (ixbase->ix_file_tab)
    {
      ixbase->ix_arp_base = 
        (struct ArpBase *) OpenLibrary (ArpName, ArpVersion);
      
      if (ixbase->ix_arp_base)
        {
      	  /* Arpbase is so kind to provide us with 3 free further libraries ;-) */
          ixbase->ix_dos_base = 
	    (struct DOSBase *) ixbase->ix_arp_base->DosBase;
	    
	  _dos20 = ((struct Library *)ixbase->ix_dos_base)->lib_Version >= 36;

	  ixbase->ix_intui_base =
	    (struct IntuitionBase *) ixbase->ix_arp_base->IntuiBase;
	    
	  ixbase->ix_gfx_base =
	    (struct GfxBase *) ixbase->ix_arp_base->GfxBase;
	    
	  /* now go for the math-libraries */
	  ixbase->ix_ms_base = (struct MathIeeeSingBasBase *) 
            OpenLibrary ("mathieeesingbas.library", 0);

	  if (ixbase->ix_ms_base)
	    {
	      ixbase->ix_mst_base = (struct MathIeeeSingTransBase *)
	        OpenLibrary ("mathieeesingtrans.library", 0);
	        
	      if (ixbase->ix_mst_base)
	        {
	          ixbase->ix_md_base = (struct MathIeeeDoubBasBase *)
	            OpenLibrary ("mathieeedoubbas.library", 0);

		  if (ixbase->ix_md_base)
		    {
		      ixbase->ix_mdt_base = (struct MathIeeeDoubTransBase *)
		        OpenLibrary ("mathieeedoubtrans.library", 0);

		      MathIeeeDoubBasBase = ixbase->ix_md_base;
		      MathIeeeSingBasBase = ixbase->ix_ms_base;
		      MathIeeeDoubTransBase = ixbase->ix_mdt_base;
		      MathIeeeSingTransBase = ixbase->ix_mst_base;

		      InitSemaphore (& ixbase->ix_semaph);

		      configure_context_switch ();

#if 0
		      NewList ((struct List *) &ix.ix_socket_list);
#endif

		      if (ixbase->ix_mdt_base)
			return ixbase;

		      ix_panic ("can't open `mathieeedoubtrans.library'");

		      /* else we have to backup what we obtained */
		      CloseLibrary (ixbase->ix_md_base);
		    }
		  else
		    ix_panic ("can't open `mathieeedoubbas.library'");
		  
		  CloseLibrary (ixbase->ix_mst_base);
		}
	      else
	      	ix_panic ("can't open `mathieeesingtrans.library'");
		
	      CloseLibrary (ixbase->ix_ms_base);
	    }
	  else
	    ix_panic ("can't open `mathieeesingbas.library'");
	   
	  CloseLibrary (ixbase->ix_arp_base);
	}
      else
        ix_panic ("can't open `arp.library'");
	
      FreeMem (ixbase->ix_file_tab, NOFILE * sizeof(struct file));
    }
  else
    ix_panic ("out of memory");
  
  return 0;
}      


void
ix_lock_base ()
{
  ObtainSemaphore (& ix.ix_semaph);
}

void
ix_unlock_base ()
{
  ReleaseSemaphore (& ix.ix_semaph);
}
