/*****************************************************************************

@@COPYRIGHT
Copyright:
This source code is the proprietary confidential property of PEP Modular
Computers GmbH. Reproduction, publication, or any form of distribution to
any party other than the licensee is strictly prohibited.
@@END

@@FILEDESC                                                                            
Title:		: sm.c

Description	: Initialize the C-functions and FBs in a subroutine-module

Name of the Library:	submod.l

@@END

@@COMMON				
Common description:


@@END				  

@@EDITION	1
Edition History
 #   date     	comments                                                by
-- ---------- 	------------------------------------------------------- ---
01 12-OCT-95	created													RB

@@END 

******************************************************************************/

/* export switch */
#define _SM_LIB_


/* includes */
#include <errno.h>
#include <modes.h>
#include <module.h>

#ifdef CLIP
#include <tasy0def.h>
#include <taio0def.h>
#include <I022def0.h>

int	fbl_come_from_resource;
int	usp_come_from_resource;

#endif /* CLIP */

#ifndef MOTOROLA
	#include <tasy0def.h>	/* for UFP-macro ... */
#endif
#ifdef CLIP
/* Pdr #98060007 : JDE 06/07/98 */
#include <tasy0apl.h>
#else
/* typedefs */
typedef struct
{
   u_int16 libno;            /* logical number in the application */
   char name[10];           /* procedure name */ 
} str_dfusf;

typedef struct
{
  u_int16 libno;             /* logical number in the appication */
  u_int16 nbinst;            /* number of instances */
  char name[12];            /* fbl name */ 
} str_def_fbl;

typedef struct
{
  ABP  activate;
  IBP  init;
  RBP  read;
  uint16 inst;
  void *mem;  
  uint16 size;
} str_fbl;
#endif /* CLIP */

#include <sm.h>

/* locals */
static UspInit = 0;
static FblInit = 0;

/* extern declarations */

/* globals */

/* function prototypes */

/* functions */


/* Description for internal functions not available by the user ->
   documented only in development documentation */
 
/* Description for functions available by the user -> documented functions */
/***************************************************************************
@@FUNCTIONS_USER

Name:     	SetSubCf
                      
Parameter:	number of C-function in list
				 
Description:  sets the pointer for Isagraf

Returns:      SUCCESS (OK) or




				error code
                           
@@END
****************************************************************************/

error_code  SetSubCf(
	long		nr,
	str_dfusf	*APL_USF,
	u_int16		NB_USF,
	UFP			*PFUCALL
)
{
	error_code err = SUCCESS;
	long	i;
	char	name[20];
	UFP		function;
		
	function = (UFP) (USP_SUBDEF_INIT[nr])(name);		/* get function name */
	for( i=0; i<NB_USF; i++ )
	{
	    if (strcmp(name, APL_USF[i].name) == 0 )
    	{
			PFUCALL[APL_USF[i].libno] = USP_SUBDEF_EXEC[nr];
			UspRead[nr] = function;
   			break;
	    }
	}

	return (err);
}
 
/***************************************************************************
@@FUNCTIONS_USER

Name:     	InitSubCf()
                      
Parameter:	str_dfusf	*APL_USF
			u_int16		NB_USF
			UFP			PFUCALL
				 
Description:
			Loads the subroutinemodule
			Sets up the functionpointer for isagraf C-functions

Returns:	SUCCESS (OK) or
			error code
              
@@END               
****************************************************************************/

error_code InitSubCf(
	str_dfusf	*APL_USF,
	u_int16		NB_USF,
	UFP			*PFUCALL
)
{
	error_code	err = SUCCESS;
	long	i;
	char	str[20];

#ifdef CLIP
	/* JDE 01/07/98 : Use resources to download isa_usp */
	u_int32		size,type;
	uchar		*data;
	char		filename[40];
	
	usp_come_from_resource = 0;

	/* isa_usp file */
	if ( (err = _getresource (RESOURCE_SUBMODCF_NAME, &size, &data, &type, filename )) == SUCCESS ) {
		if ( (err = sys_save_resource_in_file(filename,data,size,type)) != SUCCESS ) {
			sys_err ( E_SUBMOD_CONFIGFILE, 0 );
		}
		else usp_come_from_resource = 1;
	}
#endif /* CLIP */
	
	/* load module into memory: */	
	{
		char	*mod_name = SUBMODCF_NAME;
		mh_com	*pModHead;
		void	*pModExec;
		u_int32	mode,color=0;
		u_int16	tl,ar;
		error_code	err;
		
		tl = mktypelang(MT_SUBROUT,ML_ANY);
		ar = mkattrevs( MA_REENT, 0 );

		/* link to module with highest revision-number either on
		 * disk or in memory:
		 */	
		err = _os_load( mod_name, &pModHead, &pModExec, FAM_READ|FAM_EXEC,
						&tl, &ar, color );
		err = _os_link( &mod_name, &pModHead, &pModExec, &tl, &ar );
#ifdef CLIP
		/* JDE 01/07/98 : Use resources to download isa_usp */
		if ( usp_come_from_resource ) {
			/* Remove Module Subroutine to free space on disk */
			sys_delfic(filename);
		}
#endif /* CLIP */
		if( err ) return err;

	}

	init(SUBMODCF_NAME, IF_REV, SUBMODCF_NR);
	UspInit = 1;
	
	for( i=0; i<MAX_SUB_CF; i++ )
	{
		errno = 0;
		(USP_SUBDEF_INIT[i])(str);
		if( errno == E_ILLFNC ) {
			errno = 0;
			break; /* function not available, end of list reached */
		}
		SetSubCf( i, APL_USF, NB_USF, PFUCALL );
	}

	return (err);
}


/***************************************************************************
@@FUNCTIONS_USER

Name:     		DeinitSubCf
                      
Parameter:
				 
Description:  

Returns:      SUCCESS (OK) or
				error code
                           
@@END
****************************************************************************/

error_code  DeinitSubCf(void)
{

	if( UspInit ) 
	{
		UspInit = 0;
		term(0);
	}
#ifdef CLIP
		/* JDE 01/07/98 : Use resources to download isa_fbl & isa_usp */
		{
			int i,end,error;

			if ( fbl_come_from_resource ) {
				i=end=0;
				while (!end) {
					/* Remove isa_fbl Module Subroutine from memory */
					error = unlink(SUBMODFB_NAME);
					i++;
					end = !error || (i>10);
				}
			}

			if ( usp_come_from_resource ) {
				i=end=0;
				while (!end) {
					/* Remove isa_usp Module Subroutine from memory */
					error = unlink(SUBMODCF_NAME);
					i++;
					end = !error || (i>10);
				}
			}
		}
#endif /* CLIP */

	return (SUCCESS);
}

/***************************************************************************
@@FUNCTIONS_USER

Name:     	SetSubCf
                      
Parameter:	number of C-function in list
			...
				 
Description:  sets the pointer for Isagraf

Returns:      SUCCESS (OK) or
				error code
                           
@@END
****************************************************************************/

error_code  SetSubFb(
	long		nr,
	str_def_fbl	*APL_FBL,
	u_int16		NB_FBL,
	str_fbl		*DFBL
)
{
	error_code err = SUCCESS;
	long	i;
	char	name[20];
	uint16 libno;
	IBP		initproc;
	RBP 	readproc;
	ABP 	actproc;

		
	actproc = (ABP) (FBL_SUBDEF_INIT[nr])(name,&initproc,&readproc);		/* get function name */
	for( i=0; i<NB_FBL; i++ )
	{
		libno = APL_FBL[i].libno;
		if ( ! strcmp(name, APL_FBL[i].name) )
		{
			DFBL[libno].activate = FBL_SUBDEF_ACT[nr];
			FbAct[nr] = actproc;
			DFBL[libno].init     = FBL_SUBDEF_IN[nr];
			FbInit[nr] = initproc;
			DFBL[libno].read     = FBL_SUBDEF_READ[nr];
			FbRead[nr] = readproc;
			DFBL[libno].inst     = APL_FBL[i].nbinst;
			break;
		}
    }

	return (err);
}
 

/***************************************************************************
@@FUNCTIONS_USER

Name:     	InitSubFb()
                      
Parameter:	str_dfusf	*APL_FBL
			u_int16		NB_FBL
			str_fbl		*DFBL

Description:
			Loads the subroutinemodule
			Sets up the functionpointer for isagraf Function Blocks

Returns:	SUCCESS (OK) or
			error code
              
@@END               
****************************************************************************/

error_code InitSubFb(
	str_def_fbl	*APL_FBL,
	u_int16		NB_FBL,
	str_fbl		*DFBL
)
{
	error_code	err = SUCCESS;
	long	i;
	char	str[20];
	long	dummy;

#ifdef CLIP
	/* JDE 01/07/98 : Use resources to download isa_fbl */
	u_int32		size,type;
	uchar		*data;
	char		filename[40];
	int			come_from_resource = 0;

	/* isa_fbl file */
	if ( (err = _getresource (RESOURCE_SUBMODFB_NAME, &size, &data, &type, filename )) == SUCCESS ) {
		if ( (err = sys_save_resource_in_file(filename,data,size,type)) != SUCCESS ) {
			sys_err ( E_SUBMOD_CONFIGFILE, 0 );
		}
		else fbl_come_from_resource = 1;
	}
#endif /* CLIP */
		
	/* load module into memory: */	
	{
		char	*mod_name = SUBMODFB_NAME;
		mh_com	*pModHead;
		void	*pModExec;
		u_int32	mode,color=0;
		u_int16	tl,ar;
		error_code	err;
		
		tl = mktypelang(MT_SUBROUT,ML_ANY);
		ar = mkattrevs( MA_REENT, 0 );

		/* link to module with highest revision-number either on
		 * disk or in memory:
		 */
		err = _os_load( mod_name, &pModHead, &pModExec, FAM_READ|FAM_EXEC,
						&tl, &ar, color );
		err = _os_link( &mod_name, &pModHead, &pModExec, &tl, &ar );
#ifdef CLIP
		/* JDE 01/07/98 : Use resources to download isa_fbl */
		if ( fbl_come_from_resource ) {
			/* Remove Module Subroutine to free space on disk */
			sys_delfic(filename);
		}
#endif /* CLIP */
		if( err ) return err;
	}

	init(SUBMODFB_NAME, IF_REV, SUBMODFB_NR);
	FblInit = 1;

	for( i=0; i<MAX_SUB_CF; i++ )
	{
		errno = 0;
		(FBL_SUBDEF_INIT[i])(str,&dummy,&dummy);
		if( errno == E_ILLFNC ) 
		{
			errno = 0;
			break; /* function not available, end of list reached */
		}
		SetSubFb( i, APL_FBL, NB_FBL, DFBL );
	}

	return (err);
}



/* END OF FILE */
