static char rcsid[] = "@(#)$Id: shared_connect.c,v 1.10 2006/06/29 17:26:41 hurtta Exp $";

/******************************************************************************
 *  The Elm (ME+) Mail System  -  $Revision: 1.10 $   $State: Exp $
 *
 *  Author: Kari Hurtta <hurtta+elm@posti.FMI.FI>
 *****************************************************************************/

/*
 * This file is compiled only if dlopen() is available, so
 * that file does not need to be guarded with #ifdef 
 */

#include "headers.h"

DEBUG_VAR(Debug,__FILE__,"dl");

#include "shared_imp.h"
#include "rc_imp.h"
#include "save_opts.h"
#include "cs_imp.h"
#include "connection_imp.h"
#include "ss_imp.h"

#if ANSI_C
#define S_(x) static x;
#else
#define S_(x)
#endif

#define SHARED_CONNECT_magic	0xF901


struct sl_connect_data {
  uint16            magic;      

};



S_(sl_reg_functions sl_reg_connect)
static int sl_reg_connect P_((struct ImpInfo *i,
			      int reg_idx));
static int sl_reg_connect(i,reg_idx)
     struct ImpInfo *i;
     int reg_idx;
{
    /* union hack to avoid warnings about casting
     * between pointer-to-object and pointer-to-function
     */

    int res = 0;

    
    union F6 {
	void *                       ptr;
	provides_shared_SEOT_f     * f6;
    } f6;


    struct reg_list *r = & (i->regs[reg_idx]);

    if (&use_shared_connect != r->var)
	panic("SHARED PANIC",__FILE__,__LINE__,
	      "sl_reg_connect",
	      "Wrong variable",0);
    
    if (r->r.connect->magic != SHARED_CONNECT_magic)
	panic("SHARED PANIC",__FILE__,__LINE__,
	      "sl_reg_connect",
	      "Bad magic bumber",0);

    f6.ptr = dlsym(i->handle,  "provides_shared_SEOT");

    if (!f6.f6) {
	DPRINT(Debug,7,(&Debug, " ... NO provides_shared_SEOT\n"));
    }




#ifdef REMOTE_MBX


    if (f6.f6) {
	    int count,x;
	    size_t   s_res6;
	    struct SE_option_type ** res6 = f6.f6(&count, &s_res6);

	    if (s_res6 != sizeof (**res6)) {
		DPRINT(Debug,1,(&Debug,"... struct SE_option_type mismatch: %d should be %d\n",
				s_res6,sizeof (**res6)));
	    } else {
		shared_SE_option_types = 
		    safe_realloc(shared_SE_option_types,
				 sizeof (shared_SE_option_types[0]) *
				 (shared_SE_option_type_count + count));

		DPRINT(Debug,7,(&Debug," ... provides_shared_SEOT:  (shared_SE_option_types) count %d\n",
				count));
		res = 1;
		
		for (x = 0; x < count; x++) {

		    if (res6[x]->magic != SE_option_t_magic) 
			panic("SHARED PANIC",__FILE__,__LINE__,
			      "sl_reg_connect",
			      "bad magic number on provides_shared_SEOT",0);


		    shared_SE_option_types[shared_SE_option_type_count
					  +x].T = res6[x];
		    shared_SE_option_types[shared_SE_option_type_count
					  +x].imp_idx = i;
		}
		shared_SE_option_type_count += count;
	    }
	}
#endif
	

    i->regs[reg_idx].valid   = res;
    
    DPRINT(Debug,7,(&Debug, 
		    "sl_reg_connect:  [%p]->regs[%d].valid = %d\n",
		    i,reg_idx,res));

   return res;
}

S_(sl_zero_reg_list sl_zero_connect)
static void sl_zero_connect P_((struct dt_shared_info *var,
				struct reg_list *r));
static void sl_zero_connect(var,r)
     struct dt_shared_info *var;
     struct reg_list *r;
{
    r->var     = var;
    r->valid   = 0;
    r->r.connect  = safe_malloc(sizeof (*r->r.connect));   /* never freed ... */
    r->r.connect->magic = SHARED_CONNECT_magic;
}

S_(sl_unreg_functions sl_unreg_connect)
static void sl_unreg_connect P_((struct ImpInfo *i, int reg_idx));
static void sl_unreg_connect(i,reg_idx)
     struct ImpInfo *i; 
     int reg_idx;
{
    struct reg_list *r = & (i->regs[reg_idx] );
    r->valid   = 0;

}

static struct shared_loader connect_loader = {
    SHARED_LOADER_magic,
    sl_reg_connect,
    sl_zero_connect,
    sl_unreg_connect
};

SHAREDLIB use_shared_connect = {
    &connect_loader            /* loader */,
    0,                       
    NULL, 0,

    NULL
};

/* ------------------------------------------------------------------------ */


#ifdef REMOTE_MBX


#endif


/*
 * Local Variables:
 *  mode:c
 *  c-basic-offset:4
 * End:
 */


syntax highlighted by Code2HTML, v. 0.9.1