
/* $Copyright:	$
 * Copyright (c) 1984, 1985, 1986, 1987, 1988, 1989, 1990 
 * Sequent Computer Systems, Inc.   All rights reserved.
 *  
 * This software is furnished under a license and may be used
 * only in accordance with the terms of that license and with the
 * inclusion of the above copyright notice.   This software may not
 * be provided or otherwise made available to, or used by, any
 * other person.  No title to or ownership of the software is
 * hereby transferred.
 */

/*	Copyright (c) 1984 AT&T	*/
/*	  All Rights Reserved  	*/

/*	THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF AT&T	*/
/*	The copyright notice above does not evidence any   	*/
/*	actual or intended publication of such source code.	*/
#ident "$Header: modules.c 1.1 90/01/19 $@(#)modules.c	1.1 89/12/01"
#include <stdio.h>
#include "xsld.h"
#include <malloc.h>

#define MO_INCREMENT	50
#define SUCC_INCREMENT	5

extern char *gettxt();

static NAME *modules;
static MODULE mo_free = 0;
static MODULE mo_max = 0;
static int mo_count;

MODULE null_mo	= NULL_MODULE;
SUCCLIST null_succ = NULL_SUCC;

/*
 * Modules storage processing
 */
MODULE
add_module(name, lib)
  char *name;
  LIB lib;
{
  if (mo_max == mo_free){
    if (mo_max == 0){
      if ((modules = (NAME *)malloc(sizeof(NAME) * MO_INCREMENT)) == 0){
        fprintf(stderr, gettxt("xsld:17","Out of memory (modules.c (1))\n"));
        fatal();
      }
      mo_max = MO_INCREMENT;
    } else {
      mo_max += MO_INCREMENT;
      if ((modules = (NAME *)realloc((char *)modules, sizeof(NAME) * mo_max))
                   == 0){
        fprintf(stderr, gettxt("xsld:18","Out of memory (modules.c (2))\n"));
        fatal();
      }
    }
  }
  modules[mo_free].mo_name = na_store(name);
  modules[mo_free].mo_lib = lib;
  modules[mo_free].mo_used = FALSE;
  modules[mo_free].mo_msg_start = 0;
  modules[mo_free].mo_msg_end = 0;
  modules[mo_free].mo_func = 0;
  modules[mo_free].mo_set = 0;
  modules[mo_free].mo_pred_count = 0;
  modules[mo_free].mo_succ_free = 0;
  modules[mo_free].mo_succ_max = 0;
  modules[mo_free].mo_succ_used = FALSE;
  modules[mo_free].mo_def = null_symtab;
  modules[mo_free].mo_undef = null_symtab;
  modules[mo_free].mo_def_last = null_symtab;
  modules[mo_free].mo_undef_last = null_symtab;
  modules[mo_free].mo_badundef = FALSE;
  modules[mo_free].mo_badinit = FALSE;
  return mo_free++;
}

char *
mo_name(mo)
  MODULE mo;
{
  return modules[mo].mo_name;
}

void
mo_used_new(mo, used)
  MODULE mo;
  bool used;
{
  modules[mo].mo_used = used;
}

bool
mo_used(mo)
  MODULE mo;
{
  return modules[mo].mo_used;
}

void
mo_msg_start_new(mo, msg_start)
  MODULE mo;
  long msg_start;
{
  modules[mo].mo_msg_start = msg_start;
}

long
mo_msg_start(mo)
  MODULE mo;
{
  return modules[mo].mo_msg_start;
}
  
void
mo_msg_end_new(mo, msg_end)
  MODULE mo;
  long msg_end;
{
  modules[mo].mo_msg_end = msg_end;
}

long
mo_msg_end(mo)
  MODULE mo;
{
  return modules[mo].mo_msg_end;
}

void
mo_func_new(mo, func)
  MODULE mo;
  char *func;
{
  char *aux;
  modules[mo].mo_func = na_store(func);
}

char *
mo_func(mo)
  MODULE mo;
{
  return modules[mo].mo_func;
}

SYMTAB
mo_def(mo)
  MODULE mo;
{
  return modules[mo].mo_def;
}

void
mo_def_new(mo, sym)
  MODULE mo;
  SYMTAB sym;
{
  modules[mo].mo_def = sym;
}

SYMTAB
mo_undef(mo)
  MODULE mo;
{
  return modules[mo].mo_undef;
}

void
mo_undef_new(mo, sym)
  MODULE mo;
  SYMTAB sym;
{
  modules[mo].mo_undef = sym;
}

SYMTAB
mo_def_last(mo)
  MODULE mo;
{
  return modules[mo].mo_def_last;
}

void
mo_def_last_new(mo, sym)
  MODULE mo;
  SYMTAB sym;
{
  modules[mo].mo_def_last = sym;
}

SYMTAB
mo_undef_last(mo)
  MODULE mo;
{
  return modules[mo].mo_undef_last;
}

void
mo_undef_last_new(mo, sym)
  MODULE mo;
  SYMTAB sym;
{
  modules[mo].mo_undef_last = sym;
}
static MODULE mo_m_start;
static MODULE mo_m_end;

LIB
mo_lib(mo)
  MODULE mo;
{
  return modules[mo].mo_lib;
}

void
mo_mark_start()
{
  mo_m_start = mo_free;
}

void
mo_mark_stop()
{
  mo_m_end = mo_free;
}

MODULE
mo_mark_begin()
{
  if (mo_m_start == mo_m_end)
    return null_mo;
  else
    return mo_m_start++;
}

MODULE
mo_mark_next()
{
  if (mo_m_start == mo_m_end)
    return null_mo;
  else
    return mo_m_start++;
}

bool
is_null_mo(mo)
  MODULE mo;
{
  return (mo == NULL_MODULE);
}

void
mo_print(mo)
  MODULE mo;
{
  fprintf(stdout, "%s", mo_name(mo));
  lib_print(mo_lib(mo));
}

static MODULE scan_pos;

MODULE
mo_scan_first()
{
  if (mo_free == 0)
    return null_mo;
  scan_pos = 0;
  return 0;
}

MODULE
mo_scan_next()
{
  if (++scan_pos == mo_free)
    return null_mo;
  return scan_pos;
}

int
mo_set(mo)
  MODULE mo;
{
  return modules[mo].mo_set;
}

void
mo_set_new(mo, set)
  MODULE mo;
  int set;
{
  modules[mo].mo_set = set;
}

void
mo_add_init(mo1, mo2, sym)
  MODULE mo1, mo2;
  SYMBOL sym;
{
  int succ_free = modules[mo1].mo_succ_free++;
  
  modules[mo2].mo_pred_count++;
  if (succ_free == modules[mo1].mo_succ_max){
    if (modules[mo1].mo_succ_max == 0){
      if ((modules[mo1].mo_succ = (SUCCLIST *)malloc(sizeof(SUCCLIST) * 
          SUCC_INCREMENT)) == 0){
        fprintf(stderr, gettxt("xsld:19","Out of memory (modules.c (3))\n"));
        fatal();
      }
      modules[mo1].mo_succ_max = SUCC_INCREMENT;
    } else {
      modules[mo1].mo_succ_max += SUCC_INCREMENT;
      if ((modules[mo1].mo_succ = (SUCCLIST *)realloc(
            (char *)modules[mo1].mo_succ, sizeof(SUCCLIST) * 
                  modules[mo1].mo_succ_max)) == 0){
        fprintf(stderr, gettxt("xsld:20","Out of memory (modules.c (4))\n"));
        fatal();
      }
    }
  }
  modules[mo1].mo_succ[succ_free].succ_mo = mo2;
  modules[mo1].mo_succ[succ_free].succ_sym = sym;
}

SUCCLIST
mo_succ_first(mo)
  MODULE mo;
{
  if (modules[mo].mo_succ_free == 0 || modules[mo].mo_succ_used)
    return null_succ;
  modules[mo].mo_succ_cur = 0;
  modules[mo].mo_succ_used = TRUE;
  return modules[mo].mo_succ[0];
}

SUCCLIST
mo_succ_next(mo)
  MODULE mo;
{
  int aux = ++modules[mo].mo_succ_cur;
  if (modules[mo].mo_succ_free == aux)
    return null_succ;
  return modules[mo].mo_succ[aux];
}

SYMBOL
succ_sym(succ)
  SUCCLIST succ;
{
  return succ.succ_sym;
}

MODULE
succ_mo(succ)
  SUCCLIST succ;
{
  return succ.succ_mo;
}

bool
is_null_succ(succ)
  SUCCLIST succ;
{
  return succ.succ_sym == NULL_SYMBOL && succ.succ_mo == NULL_MODULE;
}

void
mo_pred_count_new(mo, count)
  MODULE mo;
  int count;
{
  modules[mo].mo_pred_count = count;
}

int
mo_pred_count(mo)
  MODULE mo;
{
  return modules[mo].mo_pred_count;
}

void
mo_tag_new(mo, tag)
  MODULE mo;
  bool tag;
{
  modules[mo].mo_tag = tag;
}

bool
mo_tag(mo)
  MODULE mo;
{
  return modules[mo].mo_tag;
}

void mo_modules_set()
{
  register MODULE i;
  
  mo_count = 0;
  for (i = 0 ; i < mo_free ; i++)
    if (mo_used(i) && mo_func(i) != 0){
      modules[i].mo_succ_used = FALSE;
      mo_count++;
    }
}

int
mo_modules()
{
  return mo_count;
}

void
mo_modules_new(n)
  int n;
{
  mo_count = n;
}

void
mo_succ_sym_new(mo, s)
  MODULE mo;
  SYMBOL s;
{
  modules[mo].mo_succ_sym = s;
}

SYMBOL
mo_succ_sym(mo)
  MODULE mo;
{
  return modules[mo].mo_succ_sym;
}

bool
mo_badundef(mo)
  MODULE mo;
{
  return modules[mo].mo_badundef;
}

void
mo_badundef_new(mo, val)
  MODULE mo;
  bool val;
{
  modules[mo].mo_badundef = val;
}

bool
mo_badinit(mo)
  MODULE mo;
{
  return modules[mo].mo_badinit;
}

void
mo_badinit_new(mo, val)
  MODULE mo;
  bool val;
{
  modules[mo].mo_badinit = val;
}
