/*
 * $Id: msuck.h,v 1.2 2002/06/06 14:21:06 conrads Exp $
 */

#ifndef _SUCK_H_
#define _SUCK_H_

#include <sys/types.h>
#include <sys/param.h>
#include <stdio.h>
#include <regex.h>

#include "config.h"

#undef DEBUG

#define CONFIGFILENAME "suck.cfg"
#define XOVER_PATH_TEMPLATE	"/tmp/xover.%s"
#define ARTLIST_PATH_TEMPLATE "/tmp/xover.%s.filtered"

/*
 * various buffer/array sizes (add 1 in declarations for safety)
 */
#define MAXART		10		/* max chars in article number */
#define MAXBUFF		65535	/* article i/o buffer */
#define MAXERR		1023	/* max error message in regex routines */
#define MAXGROUP	127		/* max chars in a newsgroup name */
#define MAXLINE		2047	/* max input line */
#define MAXPAT		255		/* max chars in regex pattern in filters file */
#define MAXXOVER	4096	/* max size of an overview record */

/*
 * these can be used "as is" (no need to add 1 in declarations)
 */
#define MAXNEWSRCS	64		/* ridiculously high, but let's be generous */
#define MAXREGEXES	4096	/* max filters in filters file */
#define MAX_LOCAL_GROUPS	14400	/* max groups on local server -- need
					 			 * to lose this! */
#define MAX_REMOTE_GROUPS	100	/* max groups on remote server --
					 			 * need to lose this, too! */

/*
 * Use "extended" regular expressions similar (but not identical) to
 * egrep(1), ignore case, simple true/false results (no additional info as to
 * what matched is needed, since we're saving the original patterns and can
 * easily output them ourselves in the kill.log)
 * 
 * man re_format(7) for description of regex format to use in filters file
 */
#define REGEXFLAGS	(REG_EXTENDED | REG_ICASE | REG_NOSUB)

/*
 * Macro to test for the standard marker used by server to indicate the end
 * of list type results from a command
 */
#define END_OF_OUTPUT(s) ((strlen(s) == 3) ? (strcmp(s, ".\r\n") == 0) : 0)

/*
 * type to hold an article number in numeric format, requires 32-bit unsigned
 * int to hold max article number allowed by NNTP spec
 */
typedef unsigned long ARTNUM;

/*
 * Pointers to a group's mmapped data (not C strings!)
 */
typedef struct newsrc_info
{
	char *group;
	char *lastart;
} NEWSRC_INFO;

/*
 * Everything we need to manage a user-defined newsrc file
 */
typedef struct
{
	char pathname[PATH_MAX + 1];
	int fd;
	int size;
	char *addr;	/* pointer to first byte of mmapped region */
	NEWSRC_INFO mmapped[MAX_REMOTE_GROUPS];	/* Pointers to individual
						 					 * group info */
} NEWSRC;

/*
 * All the stuff we need to know about a remote server
 */
typedef struct
{
	char hostname[MAXHOSTNAMELEN + 1];	/* server name */
	NEWSRC *newsrc;	/* server newsgroup info */
	int numgroups;	/* number of groups in newsrc */
	int maxconns;	/* number of connections to try to use */
} SERVER;

/*
 * socket/stream info for a single connection
 * 
 * May redo this later so it can be included in the SERVER structure, but for
 * now it's simpler to do it this way, since a server can have more than one
 * connection (multiple sucks)
 */
typedef struct connection
{
	int sockfd;
	FILE *in;
	FILE *out;
} CONNECTION;

/*
 * Information for the local server's active groups
 */
typedef char ACTIVE_INFO[MAXGROUP + 1];

/*
 * Info for a user-defined filter
 * 
 * Not as complex as it looks, really  :-)
 */
typedef struct filter
{
	char action[2];	/* "K"eep or "D"elete article? */
	struct	/* regex for groups to apply this filter to */
	{
		char pattern[MAXPAT + 1];
		regex_t re;
	} group;

	/*
	 * regex of overview fields to match on. THIS NEEDS WORK IN
	 * FILTER.C!!! Just use plain field names in filters for now
	 */
	struct
	{
		char pattern[MAXPAT + 1];
		regex_t re;
	} field;
	struct	/* regex for the actual pattern we're looking for */
	{
		char pattern[MAXPAT + 1];
		regex_t re;
	} data;
} FILTER;

/* function prototypes */

extern ARTNUM ptrtonum(char *ptr);
extern int article_exists(const char *group, const char *artnum, const char *mess_id);
extern int connect_to_server(const char *servername, CONNECTION *server);
extern int do_xover(const char *group, ARTNUM lo, ARTNUM hi);
extern int file_exists(const char *pathname);
extern int filter_group(const char *group);
extern int get_active_info(CONNECTION server, const char *group, ARTNUM *active_lo, ARTNUM *active_hi);
extern int getarticles(const char *group, int numarts);
extern int load_newsrc(SERVER * server);
extern int open_logs(void);
extern int read_active(void);
extern int read_config(void);
extern int read_filters(void);
extern int read_newsrc(void);
extern int suck_group(SERVER * server, int i);
extern int touch(const char *pathname);
extern void cleanup(void);
extern void close_server(CONNECTION server);
extern void do_suck(SERVER * server);
extern void ptrtostr(char *ptr, char *str);
extern void quit_server(CONNECTION server);
extern void remove_filters(void);
extern void suck_server(SERVER * server);
extern void update_newsrc(char *newsrc, ARTNUM artnum);

#endif	/* !_SUCK_H_ */


syntax highlighted by Code2HTML, v. 0.9.1