/* squid-gw.h */

/* Copyright 1997-2000 by Eberhard Mattes <em-gw@windhager.de>
   Donated to the public domain.  No warranty.

   1997-07-19 Initial version
   1997-09-06 Several functions moved to libem; "href" configuration
   1997-09-13 url_check_path() removed
   1998-02-19 Handle script macros in attributes
   1998-09-03 log_content_type_conflict
   1999-03-17 Support CONNECT (https/SSL)
   1999-05-10 "referer" configuration
   1999-08-26 allow/block embed
   2000-04-15 Make NAME_data const */

/* Buffer size for s_in file.  This is a global constant because it
   limits the value of the auto-html-limit attribute. */

#define S_IN_BUFSIZE	4096

/* Flags in the hash table for header fields. */

#define H_MERGE		0x0001	/* Multiple occurrences are merged */
#define H_MULTI		0x0002	/* Multiple occurrences are allowed */
#define H_MUTST		0x0004	/* Ditto, for testhttp only */
#define H_DUP		0x0008	/* Duplicates are removed */

/* Flags for url_parse(). */

#define UPF_WILDCARD		0x01
#define UPF_NODEFPORT		0x02

/* Flags for url_compare(). */

/* TODO: Currently, UCF_WILDCARD implies UCF_IGNORE_CASE */

#define UCF_IGNORE_CASE		0x01
#define UCF_EXACT		0x02
#define UCF_WILDCARD		0x04

/* Output of url_parse(). */

struct url
{
  enum
  {
    URL_CACHE_OBJECT,
    URL_CLSID,
    URL_FILE,
    URL_FTP,
    URL_GOPHER,
    URL_HTTP,
    URL_HTTPS,
    URL_JAVA,
    URL_JAVASCRIPT,
    URL_MAILTO,
    URL_NEWS,
    URL_NNTP,
    URL_PROSPERO,
    URL_TELNET,
    URL_WAIS,
    URL_NO_SCHEME,
    URL_OTHER_SCHEME,
    URL_WILDCARD,
    URL_HTTP_OR_HTTPS,
    URL_EMPTY
  } scheme;
  int scheme_start;
  int scheme_length;
  int user_start;
  int user_length;
  int password_start;
  int password_length;
  int host_start;
  int host_length;
  int port_start;
  int port_length;
  int path_start;
  int path_length;
  int query_start;
  int query_length;
  int fragment_start;
  int fragment_length;
  int type_start;
  int type_length;
  int total_length;
  long port;
};

/* What to do with rejected stuff (HTTP header fields, HTMLtags, HTML
   attributes). */

enum rej
{
  REJ_DROP,			/* Drop without any trace */
  REJ_PREFIX,			/* Prefix name with "REMOVED-" */
  REJ_COMMENT,			/* Replace with comment */
  REJ_ESCAPE,			/* Escape as text */
  REJ_COPY			/* Copy to output */
};

#define REJ_MASK(x)	(1 << (x))

#define RM_DROP		REJ_MASK (REJ_DROP)
#define RM_PREFIX	REJ_MASK (REJ_PREFIX)
#define RM_COMMENT	REJ_MASK (REJ_COMMENT)
#define RM_ESCAPE	REJ_MASK (REJ_ESCAPE)
#define RM_COPY		REJ_MASK (REJ_COPY)

/* Ditto, including whether to log or not. */

struct rej_policy
{
  enum rej output;
  int log;
};

/* Boolean value with -force flag.  We could use bits, but then we had
   to pay attention to not forgetting to use the bit mask. */

struct conf_bool
{
  int v;			/* Value, 0:false, other:true */
  int force;			/* -force level */
};

/* What to do with CDATA (scripts between <SCRIPT> and </SCRIPT>, or
   style sheets between <STYLE> and </STYLE>). */

enum cdata_policy
{
  CDATA_DROP,			/* Drop completely (used internally) */
  CDATA_HTML,			/* Treat as HTML */
  CDATA_VERBATIM		/* Copy verbatim */
};

/* How to parse cookies. */

enum cookies_mode
{
  PC_NOCHECK,			/* Don't parse cookies at all */
  PC_NETSCAPE,			/* Relaxed parsing as in Netscape's spec */
  PC_NETSCAPE_QUOTE,		/* Relaxed parsing, quote non-strict values */
  PC_RFC2109			/* Strict parsing according to RFC 2109 */
};

/* How to handle the Referer HTTP request field. */

enum referer_policy
{
  REF_DROP,			/* Drop (and log) */
  REF_KEEP_ALL,			/* Keep unconditionally */
  REF_KEEP_SAME_SITE,		/* Keep if from same site */
  REF_KEEP_MATCH		/* Keep if matching wildcard */
};

/* HTTP configuration. */

struct conf_http
{
  const char *server;
  int port;
  int server_timeout;
  int client_timeout;
  const char *user_agent;
  int log_content_type;
  int log_content_type_conflict;
  int log_missing_content_type;
  int log_redirected;
  int log_request;
  int log_request_header;
  int log_response_header;
  int log_simple_response;
  int log_unknown_content_type;
  int log_user_agent;
  int log_stats;
  enum cookies_mode parse_cookies;
  enum referer_policy referer;
  const char *referer_mask;
  struct url referer_url;
  int auto_html_limit;
  struct conf_bool filter_html;
  struct conf_bool block_cookies;
  struct conf_bool block_javascript;
  struct conf_bool block_style;	/* Not yet used */
  struct rej_policy field_dangerous;
  struct rej_policy field_unknown;
  struct rej_policy field_silent;
  struct rej_policy field_privacy;
  struct rej_policy field_invalid;
  int test;			/* testhttp */
};

/* HTML configuration. */

/* IMPORTANT: Don't forget to update html_default_config() if you
   change this structure! */

struct conf_html
{
  struct conf_bool block_java;		/* Block "<APPLET>" */
  struct conf_bool block_object;	/* Block "<OBJECT>" */
  struct conf_bool block_embed;		/* Block "<EMBED>" */
  struct conf_bool block_javascript;	/* Block JavaScript */
  struct conf_bool block_style;		/* Block style sheets */
  int use_callback;			/* Call html_callback() */
  int log_incorrect_tags;		/* Log "<a<b>" */
  int log_key;				/* Log unknown tag/attribute pairs */
  int log_script_macros;		/* Log script macros in attributes */
  int attr_value_limit;			/* Maximum value length */
  struct conf_bool drop_meta_content_type;
  struct rej_policy tag_dangerous;
  struct rej_policy tag_invalid;
  struct rej_policy tag_unknown;
  struct rej_policy attr_dangerous;
  struct rej_policy attr_unknown;
  struct rej_policy attr_on;
  struct rej_policy attr_novalue;
  struct rej_policy attr_alphanumeric;
  struct rej_policy ref_unknown;
  struct rej_policy meta_unknown_name;
  enum cdata_policy script;
  enum cdata_policy style;
};

/* Configuration. */

extern struct conf_http cf_http;
extern struct conf_html cf_html;

/* Files. */

extern EMI_FILE *c_in, *s_in;
extern EMO_FILE *c_out, *s_out;

/* Debugging. */

extern int debug_server;

/* Request URL. */

extern struct url req_url;	/* http.c */
extern const char *req_url_str;	/* http.c */

/* HTML callback etc. */

enum html_type
{
  HTML_NONE, HTML_TAG, HTML_COMMENT, HTML_MARKUPDECL
};

/* squid-gw.c */

void quit (int) ATTR_NORETURN;
void html_callback (enum html_type, int);
void config_browsers (const char *);
int ctype_policy (const char *, char ***);
int config_destinations (const char *, const struct url *, const char *,
			 const char **, const char **);
int config_href (const char *, const struct url *);
int config_connect (const char *, int, octet *, const char **);

/* http.c */

void http_default_config (void);
void http_read_request (void);
int http_process_request (void);
void http_send_request (void);
void http_send_request1 (void);
void http_response (void);
void http_copy (EMO_FILE *, EMI_FILE *, long);
int http_method (const char *, int);
int check_pragma (const octet *, size_t);
int check_refresh (const octet *, size_t, int);
int parse_cookies_mode (const char *);
int parse_referer_mode (const char *);
void http_connect (void);

/* connect.c */

char **connect_addr_list (const char *);
void http_connect2 (const octet *, int, const char *, int);

/* html.c */

void html_default_config (void);
void html_copy (EMO_FILE *, EMI_FILE *, long);

/* url.c */

int url_parse (struct url *, const octet *, int, unsigned);
int url_decode (char *, int, const char *, int);
int url_compare (const octet *, const struct url *,
		 const octet *, const struct url *, unsigned);
int parse_connect (char *, size_t, int *, const char *);

/* cookies.c */

int cookies_parse_cookie (const octet *);
int cookies_parse_set_cookie (const octet *);
size_t cookies_rebuild_length (void);
int cookies_rebuild (octet *, size_t);

/* utils.c */

int parse_rej_policy (const char *, struct rej_policy *, unsigned);
