/* $Id: connection_imp.h,v 1.6 2006/07/01 07:37:48 hurtta Exp $ */

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


/* service_list.c -------------------------------------------- */

#ifdef REMOTE_MBX

#ifdef I_NETINET_IN
#include <netinet/in.h>
#include <arpa/inet.h>
#endif

typedef union socket_addr
{
    struct sockaddr         sa;     /* general version */
#ifdef I_NETINET_IN
    struct sockaddr_in      sin;    /* INET family */
#endif
} SOCKADDR;

typedef enum { PORT_end = 0, PORT_smtp = 25, PORT_pop3 = 110, 
	       PORT_imap4 = 143, PORT_submission = 587
 } PORTS;



extern struct service_entry * service_list;
extern int                    service_count;

#define    STFLAG_browser     0x01
#define    STFLAG_mbox        0x02
#define    STFLAG_smtp_like   0x04

#define    STFLAG_is_imap   0x0100
#define    STFLAG_is_pop    0x0200
#define    STFLAG_is_submission    0x0400
#define    STFLAG_is_smtp          0x0800

extern CONST struct service_type * IMAP_SERVICE;
extern CONST struct service_type * POP_SERVICE;
extern CONST struct service_type * SUBMISSION_SERVICE;
extern CONST struct service_type * SMTP_SERVICE;


#define             SE_given_alias     0x01
#define             SE_given_addr      0x02
#define             SE_given_port      0x04
#define             SE_temporary       0x08
#define             SE_system          0x10
#define             SE_given_name_addr 0x20
#define             SE_rescan_name_addr 0x40

#ifdef ANSI_C
struct     SE_option;
#endif

/* return:  0 = failure,
            1 = option ok
*/
typedef int SE_option_parse P_((struct     SE_option *X,
				const char       *name,   /* without prefix */
				const char       * value));

/* return: malloced string -- caller must free */
typedef char * SE_option_values P_((struct     SE_option *X, 
				    const char *prefix));

typedef void SE_option_zero   P_((struct     SE_option *X));
typedef void SE_option_free   P_((struct     SE_option *X));
typedef void SE_option_merge  P_((struct     SE_option *target, 
				  struct     SE_option *source));



#define SE_option_t_magic       0xF907

extern struct service_entry {
    int      flags;
    char *   official_name;
    char *   * aliases_list;
    int        aliases_count;
    SOCKADDR * addr_list;
    int        addr_count;

    char    ** addr_name_list;
    int        addr_name_count;

    CONST struct service_type  * service;

    int      * port_list;
    int        port_count;    

    struct     SE_option {
	struct SE_option_type {
	    unsigned short magic;    /* SE_option_t_magic */
	    SE_option_parse   * parse_on_option;
	    SE_option_values  * give_values;
	    SE_option_zero    * zero_options;
	    SE_option_free    * free_options;	    
	    SE_option_merge   * merge_options;
	} * type;
	char * prefix;

	/* Anonymous type */
	struct SE_option_value  * value;       	
    }        * option_list;
    int        option_count;
}  * give_service_entry P_((const char *hostname, int flag));   

extern void free_temporary_service_entry P_((struct service_entry **Y));


#endif

/* remote_mbx.c ---------------------------------------------- */



#ifdef POLL_METHOD

struct Read_Buffer {
    char      *read_buffer;
    int       read_len;
};
struct Write_Buffer {
    char      *write_buffer;
    int       write_len;
};

extern int ReadFromSocket P_((int fd, struct Read_Buffer *buffer,
			      int wanted));
extern int find_crlf P_((struct Read_Buffer *buffer, int add_null));
extern void zero_Read_Buffer P_((struct Read_Buffer *buffer));
extern void free_Read_Buffer P_((struct Read_Buffer *buffer));
extern void cut_line P_((struct Read_Buffer *buffer, int len));
extern void zero_Write_Buffer P_((struct Write_Buffer *buffer));
extern void free_Write_Buffer P_((struct Write_Buffer *buffer));
extern int WriteToSocket P_((int fd, struct Write_Buffer *buffer));
extern void cut_Write_Buffer P_((struct Write_Buffer *buffer, int n));
extern void add_to_Write_Buffer P_((struct Write_Buffer *buffer,
				    char **str,int l));

#endif


#ifdef REMOTE_MBX


#define REMOTE_ACCOUNT_magic    0xF504

struct remote_account {
    unsigned short magic;    /* REMOTE_ACCOUNT_magic */
    SOCKADDR  hostaddr;

    struct streamsched *stream;
    int    service_idx;

    char    * username;
    char    * host;
};

extern void zero_remote_account P_((struct remote_account *ra));
extern void free_remote_account P_((struct remote_account *ra));

extern int connect_remote_account P_((struct remote_account *ra,
				      int *got,
				      struct service_entry *se,
				      PORTS default_portlist[],
				      PORTS force_port));
extern int split_remote_name P_((char *name,
				 struct remote_account *X,
				 struct service_entry **se,
				 char **rest,
				 int lookup_flags));



#ifdef ANSI_C
struct connection_cache;
struct folder_browser;
#endif

typedef void  cache_zero_connection P_((struct connection_cache *c));
typedef void  cache_free_connection P_((struct connection_cache *c));

typedef int  cache_open_connection P_((struct connection_cache *c));
typedef int  cache_login_connection P_((struct connection_cache *c,
					const struct string *password /* May be NULL */));
typedef int  cache_close_connection P_((struct connection_cache *c));

typedef void cache_folder_from_connection P_((struct connection_cache *c,
					      struct folder_info *f));
typedef void cache_browser_from_connection P_((struct connection_cache *c,
					       struct folder_browser *d));

#define CONNECTION_TYPE_magic   0xF906

struct connection_type { 
    unsigned short                magic;   /* CONNECTION_TYPE_magic */
    CONST char                    * type_name;
    cache_zero_connection         * cache_zero_it;
    cache_free_connection         * cache_free_it;
    cache_open_connection         * cache_open_it;
    cache_login_connection        * cache_login_it;
    cache_close_connection        * cache_close_it;      
    cache_folder_from_connection  * cache_folder_from_it;
    cache_browser_from_connection * cache_browser_from_it;

    
};

/* Structure is on connection cache list if not given to
   folder - structure ...
*/

enum connection_state { 
    CON_greeting = -1,
    CON_error = 0, CON_open = 1, CON_logged = 2 };

struct connection_cache {
    struct connection_type  * type;

    /* Either one from these only should be on non-NULL */
    struct connection_cache * next;       
    struct folder_info      *f;
    struct folder_browser   *d;

    struct remote_account   C;
    uint16                  port;    /* 0 == default port */
    enum connection_state   state;

    union {
	void                         * any;
	struct generic_connection_1  * g1_con;
	struct generic_connection_2  * g2_con;

        struct IMAP_CON              * imap_con;
    } a;
};

/* May not be 
      uin16 port
   because this is promoted to int
*/


extern struct connection_cache * 
locate_from_cache P_((const char * username,
		      const char * host,
		      const struct connection_type *con_type,
		      int port    /* 0 == default port */));


extern struct connection_cache * create_connection P_((struct connection_type *T));
extern void  free_connection P_((struct connection_cache **c));

extern int  join_connection P_((struct connection_cache *c,
				struct remote_account *X,
				enum connection_state st));

extern int  login_connection P_((struct connection_cache *c,
				 const struct string *password /* May be NULL */));

extern void folder_from_connection P_((struct connection_cache *c,
				       struct folder_info *f));

extern void browser_from_connection P_((struct connection_cache *c,
					struct folder_browser *d));

extern void  close_connection P_((struct connection_cache *c));

extern void  cache_connection P_((struct connection_cache *c));

#endif

/*
 * Local Variables:
 *  mode:c
 *  c-basic-offset:4
 *  buffer-file-coding-system: iso-8859-1
 * End:
 */



syntax highlighted by Code2HTML, v. 0.9.1