File:  [Repository ATC2] / ADD_ver_10 / Attic / BasesDatos.c
Revision 1.1: download - view: text, annotated - select for diffs
Thu Jan 19 17:16:29 2006 UTC (18 years, 9 months ago) by rico
Branches: MAIN
CVS tags: HEAD
*** empty log message ***

/********************************************************************/
/*  BasesDatos.c                                                    */
/*                                                                  */
/*  Copyright (c) 1997-2006 Rafael Rico      (rafael.rico@uah.es)   */
/*                                                                  */
/*  This file is part of ADD version 5.10.                          */
/*                                                                  */
/*  ADD 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 2 of  */
/*  the License, or (at your option) any later version.             */
/*                                                                  */
/*  ADD 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 ADD; if not, write to the Free Software      */
/*  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA        */
/*  02111-1307  USA                                                 */
/*                                                                  */
/*  --------------------------- History --------------------------- */
/*                                                                  */
/*  Revision 1.2. 01/2006                                           */
/*  Added GPL License and JavaDoc style documentation               */
/*                                                                  */
/*  Revision 1.1. 09/2005                                           */
/*  Initial Revision                                                */
/*                                                                  */
/********************************************************************/

/******************************************************************************/
/* MÓDULO: BasesDatos.c                                                       */
/*                                                                            */
/* Este módulo carga en memoria la base de datos que modela la arquitectura   */
/* del repertorio IA16 (tabla de nemónicos y tabla de ubicaciones de datos)   */
/* y la tabla de tiempos de un procesador en ciclos (tiempo de ejecución de   */
/* operaciones, tiempo de acceso a operandos y tiempo de cómputo de           */
/* direcciones de memoria.                                                    */
/******************************************************************************/
/* Fecha: 19 de septiembre de 2005                                            */
/******************************************************************************/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "defines.h"
#include "tipos.h"
#include "basesdatos.h"


/* configuración */
extern struct argumentos configuracion;

/* bases de datos */
extern unsigned int num_nemonicos;
extern operacion *nemonicos;
extern unsigned int num_simbolos;
extern operando *simbolos;
extern unsigned int num_tiempos;
extern tiempo *ciclos;


void CargarArquitecturaIA16Nemonicos(FILE *f_ia16_nemos)
{
    unsigned int i;
    char linea[MAX_LINE];
    char *registro, *campo;
	char mensaje[MAX_LINE];


    sprintf(mensaje, "[CargarArquitecturaIA16Nemonicos] Cargando base de datos del repertorio IA16...");
	Notificar(mensaje, NO_ERROR, ECO_NO);

    /* salto los comentarios */
    do fgets (linea, MAX_LINE, f_ia16_nemos); while (linea[0]=='#');

    /* leo el número de registros (primera línea con información) */
    num_nemonicos = atoi(linea);

    sprintf(mensaje, "[CargarArquitecturaIA16Nemonicos] Reservo memoria para %d registros", num_nemonicos);
	Notificar(mensaje, NO_ERROR, ECO_NO);

    /* malloc reserva memoria; calloc reserva memoria y rellena con 0's */
    /* calloc es más lenta pero me asegura que los valores numéricos van */
    /* a ser 0 y las cadenas van a ser vacías */
    nemonicos = calloc(num_nemonicos, sizeof(operacion));
    if (nemonicos == NULL)
    {
        sprintf(mensaje, "[CargarArquitecturaIA16Nemonicos] Memoria insuficiente");
		Notificar(mensaje, ERROR_SALIR, ECO_NO);
		/* el programa finaliza si no hay memoria suficiente */
    }

    sprintf(mensaje, "[CargarArquitecturaIA16Nemonicos] Cargando datos de nemónicos...");
	Notificar(mensaje, NO_ERROR, ECO_NO);

    i = 0;
    while(i<num_nemonicos)
    {
        /* salto los comentarios */
        do fgets (linea, MAX_LINE, f_ia16_nemos); while(linea[0]=='#');

        /* hago un barrido de la línea hasta encontrar el final de línea */
        /* cada ocurrencia de '\t' la cambio por '\0' para convertirlo   */
        /* en una cadena separada (campo)                                */

        /* el puntero 'registro' me permite moverme por la línea */
        /* el puntero 'campo' se encarga se señalar el comienzo de los campos */
        registro = linea;
        campo = linea;
        while(*++registro!='\0')
        {
            if(*registro=='\t')
            {
                *registro = '\0';    /* finalizo un campo */
                /* campo nemonico */
                if(campo[0]!='-') strcpy(nemonicos[i].nemonico, campo);
                else
                {
                    switch(campo[1])
                    {
                        case 't':    /* tipo de nemonico */
                        nemonicos[i].tipo = atoi(campo+3);
                        break;

                        case '1':    /* modo del operando 1 (destino) explícito */
                        nemonicos[i].modo_op1 = atoi(campo+3);
                        break;

                        case '2':    /* modo del operando 2 (fuente) explícito */
                        nemonicos[i].modo_op2 = atoi(campo+3);
                        break;

                        case 'e':   /* implícitos escritos */
                        strcpy(nemonicos[i].implicitos_escritos, campo+3);
                        break;

                        case 'l':   /* implícitos leidos */
                        strcpy(nemonicos[i].implicitos_leidos, campo+3);
                        break;

                        default:
                        /* mandar un error a un fichero de log */
                        break;
                    }
                }
                campo = registro+1;    /* hago que apunte al siguiente */
            }
        }

        /* echo */
        /* printf("%3d %10s %d %d\t%15s\t%30s\n", i, operaciones[i].nemonico, 
                     operaciones[i].modo_fuente, operaciones[i].modo_destino, 
                     operaciones[i].implicitos_leidos, 
                     operaciones[i].implicitos_escritos); */
        /* _getch(); */

        i++;    /* índice del siguiente registro */
    }

    sprintf(mensaje, "[CargarArquitecturaIA16Nemonicos] La tabla de nemónicos se ha cargado con éxito");
	Notificar(mensaje, NO_ERROR, ECO_NO);
}


void CargarArquitecturaIA16Simbolos(FILE *f_ia16_ubis)
{
    unsigned int i;
    char linea[MAX_LINE];
    char *campo;
	char mensaje[MAX_LINE];

    sprintf(mensaje, "[CargarArquitecturaIA16Simbolos] Cargando base de datos del repertorio IA16...");
	Notificar(mensaje, NO_ERROR, ECO_NO);

    /* salto los comentarios */
    do fgets (linea, MAX_LINE, f_ia16_ubis); while (linea[0]=='#');

    /* leo el número de registros (primera línea con información) */
    num_simbolos = atoi(linea);

    sprintf(mensaje, "[CargarArquitecturaIA16Simbolos] Reservo memoria para %d registros", num_simbolos);
	Notificar(mensaje, NO_ERROR, ECO_NO);

    /* malloc reserva memoria; calloc reserva memoria y rellena con 0's */
    /* calloc es más lenta pero me asegura que los valores numéricos van */
    /* a ser 0 y las cadenas van a ser vacías */
    simbolos = calloc(num_simbolos, sizeof(operando));
    if (simbolos == NULL)
    {
        sprintf(mensaje, "[CargarArquitecturaIA16Simbolos] Memoria insuficiente");
		Notificar(mensaje, ERROR_SALIR, ECO_NO);
		/* el programa finaliza si no hay memoria suficiente */
    }

    sprintf(mensaje, "[CargarArquitecturaIA16Simbolos] Cargando datos de símbolos...");
	Notificar(mensaje, NO_ERROR, ECO_NO);

    i = 0;
    while(i<num_simbolos)
    {
        /* salto los comentarios */
        do fgets (linea, MAX_LINE, f_ia16_ubis); while(linea[0]=='#');

        campo = strtok(linea, "\t\n");    /* el separador de campos es '\t' */
                                          /* añado '\n' porque al final de linea */
                                          /* tengo ese caracter y lo toma por un campo */
        while(campo != NULL)
        {
            /* trato el campo capturado por la función strtok */
            /* campo símbolo */
            if(campo[0]!='-') strcpy(simbolos[i].simbolo, campo);
            else
            {
                switch(campo[1])
                {
                    case 'd':    /* dependencias */
                    strcpy(simbolos[i].dependencias, campo+3);
                    break;

                    case 's':    /* segmento por defecto */
                    simbolos[i].segmento = atoi (campo+3);
                    break;

                    case 't':    /* tipo de ubicación */
                    simbolos[i].tipo = atoi (campo+3);
                    break;

                    default:
                    /* mandar un error a un fichero de log */
                    break;
                }
            }
            /* capturo el siguiente campo */
            campo = strtok(NULL, "\t\n");
        }
		
		/* echo */
		/* printf(); */
		/* _getch(); */

		i++;    /* índice del siguiente registro */
    }

    sprintf(mensaje, "[CargarArquitecturaIA16Simbolos] La tabla de símbolos se ha cargado con éxito");
	Notificar(mensaje, NO_ERROR, ECO_NO);
}


void CargarTiemposProcesador(FILE *f_procesador)
{
    unsigned int i;
    char linea[MAX_LINE];
    char *campo;
	char mensaje[MAX_LINE];

    sprintf(mensaje, "[CargarTiemposProcesador] Cargando base de datos del procesador...");
	Notificar(mensaje, NO_ERROR, ECO_NO);

    /* salto los comentarios */
    do fgets (linea, MAX_LINE, f_procesador); while (linea[0]=='#');

    /* leo el número de registros (primera línea con información) */
    num_tiempos = atoi(linea);

    sprintf(mensaje, "[CargarTiemposProcesador] Reservo memoria para %d registros", num_tiempos);
	Notificar(mensaje, NO_ERROR, ECO_NO);

    /* malloc reserva memoria; calloc reserva memoria y rellena con 0's */
    /* calloc es más lenta pero me asegura que los valores numéricos van */
    /* a ser 0 y las cadenas van a ser vacías */
    ciclos = calloc(num_tiempos, sizeof(tiempo));
    if (ciclos == NULL)
    {
        sprintf(mensaje, "[CargarTiemposProcesador] Memoria insuficiente");
		Notificar(mensaje, ERROR_SALIR, ECO_NO);
		/* el programa finaliza si no hay memoria suficiente */
    }

    sprintf(mensaje, "[CargarTiemposProcesador] Cargando datos de tiempos...");
	Notificar(mensaje, NO_ERROR, ECO_NO);

    i = 0;
    while(i<num_tiempos)
    {
        /* salto los comentarios */
        do fgets (linea, MAX_LINE, f_procesador); while(linea[0]=='#');

        campo = strtok(linea, "\t\n");    /* el separador de campos es '\t' */
                                          /* añado '\n' porque al final de linea */
                                          /* tengo ese caracter y lo toma por un campo */
        while(campo != NULL)
        {
            /* trato el campo capturado por la función strtok */
            /* campo identificador */
            if(campo[0]!='-') strcpy(ciclos[i].identificador, campo);
            else
            {
                switch(campo[1])
                {
                    case 'c':    /* dependencias */
                    ciclos[i].ciclos = atoi (campo+3);
                    break;

                    default:
                    /* mandar un error a un fichero de log */
                    break;
                }
            }
            /* capturo el siguiente campo */
            campo = strtok(NULL, "\t\n");
        }

        /* echo */
        /* printf(); */
        /* _getch(); */
		
		i++;    /* índice del siguiente registro */
    }

    sprintf(mensaje, "[CargarTiemposProcesador] La tabla de tiempos se ha cargado con éxito");
	Notificar(mensaje, NO_ERROR, ECO_NO);
}


void CargarArquitecturaIA16()
{
	FILE *f_ia16_nemos, *f_ia16_ubis;
	char mensaje[MAX_LINE];

    
	/* abro el fichero de nemónicos de la arquitectura del repertorio */
    if((f_ia16_nemos  = fopen(configuracion.ficheronemos, "r")) != NULL)
    {
        sprintf(mensaje, "[CargarArquitecturaIA16] El fichero '%s' se ha abierto con éxito", configuracion.ficheronemos);
		Notificar(mensaje, NO_ERROR, ECO_NO);

        CargarArquitecturaIA16Nemonicos(f_ia16_nemos);

        /* cierro el fichero de nemónicos */
        if(fclose(f_ia16_nemos))
		{
			sprintf(mensaje, "[CargarArquitecturaIA16] El fichero '%s' no se ha podido cerrar", configuracion.ficheronemos);
			Notificar(mensaje, ERROR_SEGUIR, ECO_NO);
		}
    }
    else
	{
		sprintf(mensaje, "[CargarArquitecturaIA16] El fichero '%s' no se ha podido abrir", configuracion.ficheronemos);
		Notificar(mensaje, ERROR_SALIR, ECO_NO);
	}


    /* abro el fichero de ubicaciones de la arquitectura del repertorio */
    if((f_ia16_ubis  = fopen(configuracion.ficheroubis, "r")) != NULL)
    {
        sprintf(mensaje, "[CargarArquitecturaIA16] El fichero '%s' se ha abierto con éxito", configuracion.ficheroubis);
		Notificar(mensaje, NO_ERROR, ECO_NO);

        CargarArquitecturaIA16Simbolos(f_ia16_ubis);

        /* cierro el fichero de ubicaciones */
        if(fclose(f_ia16_ubis))
		{
			sprintf(mensaje, "[CargarArquitecturaIA16] El fichero '%s' no se ha podido cerrar", configuracion.ficheroubis);
			Notificar(mensaje, ERROR_SEGUIR, ECO_NO);
		}
    }
    else
	{
		sprintf(mensaje, "[CargarArquitecturaIA16] El fichero '%s' no se ha podido abrir", configuracion.ficheroubis);
		Notificar(mensaje, ERROR_SALIR, ECO_NO);
	}
}


void CargarProcesador()
{
	FILE *f_procesador;
	char mensaje[MAX_LINE];


	/* abro el fichero con la tabla de tiempos del procesador */
    if((f_procesador  = fopen(configuracion.ficherociclos, "r")) != NULL)
    {
        sprintf(mensaje, "[CargarProcesador] El fichero '%s' se ha abierto con éxito", configuracion.ficherociclos);
		Notificar(mensaje, NO_ERROR, ECO_NO);

        CargarTiemposProcesador(f_procesador);

        /* cierro el fichero del procesador */
        if(fclose(f_procesador))
		{
			sprintf(mensaje, "[CargarProcesador] El fichero '%s' no se ha podido cerrar", configuracion.ficherociclos);
			Notificar(mensaje, ERROR_SEGUIR, ECO_NO);
		}
    }
    else
	{
		sprintf(mensaje, "[CargarProcesador] El fichero '%s' no se ha podido abrir", configuracion.ficherociclos);
		Notificar(mensaje, ERROR_SALIR, ECO_NO);	
	}
}


/* carga de las bases de datos */

void CargarBasesDatos()
{
	CargarArquitecturaIA16();
	if(configuracion.cpi == SI) CargarProcesador();
}


/* libera memoria bases de datos */

void LiberarMemoriaBasesDatos()
{
    free(nemonicos);
    free(simbolos);
	if(configuracion.cpi == SI) free(ciclos);
}



#if 0

    /* la función strtok de <string.h> descompone la línea en campos */
	/* OJO: modifica la cadena de caracteres de la línea que se le pasa */
    
    /* capturo el primer campo */    
    campo = strtok(linea, "\t");
    while(campo != NULL)
    {
        /* trato el campo */
        
        /* capturo el siguiente campo */
        campo = strtok( NULL, seps );
        /* seps son los separadores, en este caso '\t' */
    }

    /* la función getopt del POSIX hace algo parecido */
#endif


FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>