/*
 * irc_std.h: header to define things used in all the programs ircii
 * comes with
 *
 * hacked together from various other files by matthew green
 *
 * Copyright (c) 1992-2004 Matthew R. Green.
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 * 3. The name of the author may not be used to endorse or promote products
 *    derived from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
 * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT,
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 * SUCH DAMAGE.
 *
 * @(#)$eterna: irc_std.h,v 1.46 2004/07/03 10:22:35 mrg Exp $
 */

#ifndef __irc_std_h
#define __irc_std_h

/*
 * these things help with converting to/from char* and u_char*
 */
#define UP(s)			((u_char *)(s))
#define UPP(s)			((u_char **)(s))
#define CP(s)			((char *)(s))
#define CPP(s)			((char **)(s))
#define my_strlen(s)		strlen(CP(s))
#define my_strcmp(d,s)		strcmp(CP(d), CP(s))
#define my_strncmp(d,s,n)	strncmp(CP(d), CP(s), (n))
#define my_strcat(d,s)		strcat(CP(d), CP(s))
#define my_strncat(d,s,n)	strncat(CP(d), CP(s), (n))
#define my_strmcat(d,s,n)	strmcat(UP(d), UP(s), (n))
#define my_strcpy(d,s)		strcpy(CP(d), CP(s))
#define my_strncpy(d,s,n)	strncpy(CP(d), CP(s), (n))
#define my_strmcpy(d,s,n)	strmcpy(UP(d), UP(s), (n))
#define my_index(s,c)		UP(index(CP(s), (c)))
#define my_rindex(s,c)		UP(rindex(CP(s), (c)))
#define my_atoi(s)		atoi(CP(s))
#define my_atol(s)		atol(CP(s))
#define my_getenv(s)		UP(getenv(CP(s)))

#if !defined(__GNUC__) || __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 5)
#define __attribute__(x)        /* delete __attribute__ if non-gcc or gcc1 */
#endif

#ifndef lint
#define IRCII_RCSID_NAMED(x,n) static const char n[] __attribute__((__unused__)) = x
#else
#define IRCII_RCSID_NAMED(x,n)
#endif
#define IRCII_RCSID(x) IRCII_RCSID_NAMED(x,rcsid)

#ifdef _IBMR2
# include <sys/errno.h>
# include <sys/select.h>
#else
# include <errno.h>
#ifndef ERRNO_DECLARED
extern	int	errno;
#endif
#endif /* _IBMR2 */

#ifndef NBBY
# define NBBY	8		/* number of bits in a byte */
#endif /* NBBY */

#ifndef NFDBITS
# define NFDBITS	(sizeof(long) * NBBY)	/* bits per mask */
#endif /* NFDBITS */

#ifndef FD_SET
# define FD_SET(n, p)	((p)->fds_bits[(n)/NFDBITS] |= (1 << ((n) % NFDBITS)))
#endif /* FD_SET */

#ifndef FD_CLR
# define FD_CLR(n, p)	((p)->fds_bits[(n)/NFDBITS] &= ~(1 << ((n) % NFDBITS)))
#endif /* FD_CLR */

#ifndef FD_ISSET
# define FD_ISSET(n, p)	((p)->fds_bits[(n)/NFDBITS] & (1 << ((n) % NFDBITS)))
#endif /* FD_ISSET */

#ifndef FD_ZERO
# define FD_ZERO(p)	bzero((char *)(p), sizeof(*(p)))
#endif /* FD_ZERO */

#ifndef	FD_SETSIZE
# define FD_SETSIZE	32
#endif /* FD_SETSIZE */

typedef RETSIGTYPE sigfunc(int);

#ifdef USE_SIGACTION
sigfunc *my_signal(int, sigfunc *, int);
# define MY_SIGNAL(s_n, s_h, m_f) my_signal(s_n, s_h, m_f)
#else
# if USE_SIGSET
#  define MY_SIGNAL(s_n, s_h, m_f) sigset(s_n, s_h)
# else
#  define MY_SIGNAL(s_n, s_h, m_f) signal(s_n, s_h)
# endif /* USE_SIGSET */
#endif /* USE_SIGACTION */

#if defined(USE_SIGACTION) || defined(USE_SIGSET)
# undef SYSVSIGNALS
#endif /* USE_SIGACTION || USE_SIGSET */

#if defined(__svr4__) || defined(SVR4) || defined(__SVR4)
# if !defined(__svr4__)
#  define __svr4__
# endif /* __svr4__ */
# if !defined(SVR4)
#  define SVR4
# endif /* SVR4 */
# if !defined(__SVR4)
#  define __SVR4
# endif /* __SVR4 */
#endif /* __svr4__ || SVR4 || __SVR4 */

#ifdef _SEQUENT_
# define	u_short	ushort
# define	u_char	unchar
# define	u_long	ulong
# define	u_int	uint
# define	USE_TERMIO
# ifndef POSIX
#  define POSIX
# endif /* POSIX */
#endif /* _SEQUENT_ */

#ifndef NeXT
# if defined(STDC_HEADERS) || defined(HAVE_STRING_H)
#  include <string.h>
#  if defined(STDC_HEADERS)
#   include <stdlib.h>
#  endif /* HAVE_STDLIB_H */
#  if defined(HAVE_MEMORY_H)
#   include <memory.h>
#  endif /* HAVE_MEMORY_H */
#  undef index
#  undef rindex
#  undef bcopy
#  undef bzero
#  undef bcmp
#  define index strchr
#  define rindex strrchr
#  ifdef HAVE_MEMMOVE
#   define bcopy(s, d, n) memmove((d), (s), (n))
#  else
#   define bcopy(s, d, n) memcpy ((d), (s), (n))
#  endif /* HAVE_MEMMOVE */
#  define bcmp(s, t, n) memcmp ((s), (t), (n))
#  define bzero(s, n) memset ((s), 0, (n))
# else /* STDC_HEADERS || HAVE_STRING_H */
#  include <strings.h>
# endif /* STDC_HEADERS || HAVE_STRING_H */
#endif /* !NeXT */

#ifdef _Windows
# define IS_ABSOLUTE_PATH(file) ((file)[0] == '/' || (file)[0] == '\\' || ((file)[0] && (file)[1] == ':'))
#else
# define IS_ABSOLUTE_PATH(file) ((file)[0] == '/')
#endif

#if !defined(SYS_ERRLIST_DECLARED) && !defined(_Windows)
extern	char	*sys_errlist[];
extern	int	sys_nerr;
#endif

#ifdef _Windows
extern char FAR * FAR winsock_errors[];
# define strerror(e) ((e) >= 0 && (e) < sys_nerr ? sys_errlist[e] : ((e) >=WSABASEERR ? winsock_errors[(e) - WSABASEERR] : "(unknown)"))
#else
# ifdef NEED_STRERROR
#  undef strerror
#  define strerror(e) ((e) < 0 || (e) >= sys_nerr ? "(unknown)" : sys_errlist[e])
# endif
#endif

/* we need an unsigned 32 bit integer for dcc, how lame */

#ifdef UNSIGNED_LONG32

typedef		unsigned long		u_32int;

#else
# ifdef UNSIGNED_INT32

typedef		unsigned int		u_32int;

# else

typedef		unsigned long		u_32int;

# endif /* UNSIGNED_INT32 */
#endif /* UNSIGNED_LONG32 */

#if ! HAVE_RFC2553_NETDB

				/* RFC 2553 */
#undef	EAI_ADDRFAMILY
#define	EAI_ADDRFAMILY	 1	/* address family for hostname not supported */
#undef	EAI_AGAIN
#define	EAI_AGAIN	 2	/* temporary failure in name resolution */
#undef	EAI_BADFLAGS
#define	EAI_BADFLAGS	 3	/* invalid value for ai_flags */
#undef	EAI_FAIL
#define	EAI_FAIL	 4	/* non-recoverable failure in name resolution */
#undef	EAI_FAMILY
#define	EAI_FAMILY	 5	/* ai_family not supported */
#undef	EAI_MEMORY
#define	EAI_MEMORY	 6	/* memory allocation failure */
#undef	EAI_NODATA
#define	EAI_NODATA	 7	/* no address associated with hostname */
#undef	EAI_NONAME
#define	EAI_NONAME	 8	/* hostname nor servname provided, or not known */
#undef	EAI_SERVICE
#define	EAI_SERVICE	 9	/* servname not supported for ai_socktype */
#undef	EAI_SOCKTYPE
#define	EAI_SOCKTYPE	10	/* ai_socktype not supported */
#undef	EAI_SYSTEM
#define	EAI_SYSTEM	11	/* system error returned in errno */

				/* KAME extensions? */
#undef	EAI_BADHINTS
#define	EAI_BADHINTS	12
#undef	EAI_PROTOCOL
#define	EAI_PROTOCOL	13
#undef	EAI_MAX
#define	EAI_MAX		14

				/* RFC 2553 */
#undef	NI_MAXHOST
#define	NI_MAXHOST	1025
#undef	NI_MAXSERV
#define	NI_MAXSERV	32

#undef	NI_NOFQDN
#define	NI_NOFQDN	0x00000001
#undef	NI_NUMERICHOST
#define	NI_NUMERICHOST	0x00000002
#undef	NI_NAMEREQD
#define	NI_NAMEREQD	0x00000004
#undef	NI_NUMERICSERV
#define	NI_NUMERICSERV	0x00000008
#undef	NI_DGRAM
#define	NI_DGRAM	0x00000010

				/* RFC 2553 */
#undef	AI_PASSIVE
#define	AI_PASSIVE	0x00000001 /* get address to use bind() */
#undef	AI_CANONNAME
#define	AI_CANONNAME	0x00000002 /* fill ai_canonname */

				/* KAME extensions ? */
#undef	AI_NUMERICHOST
#define	AI_NUMERICHOST	0x00000004 /* prevent name resolution */
#undef	AI_MASK
#define	AI_MASK		(AI_PASSIVE | AI_CANONNAME | AI_NUMERICHOST)

				/* RFC 2553 */
#undef	AI_ALL
#define	AI_ALL		0x00000100 /* IPv6 and IPv4-mapped (with AI_V4MAPPED) */
#undef	AI_V4MAPPED_CFG
#define	AI_V4MAPPED_CFG	0x00000200 /* accept IPv4-mapped if kernel supports */
#undef	AI_ADDRCONFIG
#define	AI_ADDRCONFIG	0x00000400 /* only if any address is assigned */
#undef	AI_V4MAPPED
#define	AI_V4MAPPED	0x00000800 /* accept IPv4-mapped IPv6 address */

#endif /* ! HAVE_RFC2553_NETDB */

#if ! HAVE_SOCKLEN_T
typedef int socklen_t;
#endif /* HAVE_SOCKLEN_T */

#if ! HAVE_RFC2553_NETDB && ! HAVE_ADDRINFO

struct addrinfo {
	int	ai_flags;	/* AI_PASSIVE, AI_CANONNAME, AI_NUMERICHOST */
	int	ai_family;	/* PF_xxx */
	int	ai_socktype;	/* SOCK_xxx */
	int	ai_protocol;	/* 0 or IPPROTO_xxx for IPv4 and IPv6 */
	size_t	ai_addrlen;	/* length of ai_addr */
	char	*ai_canonname;	/* canonical name for hostname */
	struct sockaddr *ai_addr;	/* binary address */
	struct addrinfo *ai_next;	/* next structure in linked list */
};

int     getaddrinfo(const char *, const char *,
		const struct addrinfo *, struct addrinfo **);
int     getnameinfo(const struct sockaddr *, socklen_t, char *,
		size_t, char *, size_t, int);
void    freeaddrinfo(struct addrinfo *);
char   *gai_strerror(int);

#endif /* ! HAVE_RFC2553_NETDB && ! HAVE_ADDRINFO */

#ifndef HAVE_SNPRINTF
int snprintf(char *str, size_t count, const char *fmt, ...);
#endif /* HAVE_SNPRINTF */

#ifndef HAVE_VSNPRINTF
int vsnprintf(char *str, size_t count, const char *fmt, va_list args);
#endif /* HAVE_VSNPRINTF */

#ifdef INET6
# define SOCKADDR_STORAGE struct sockaddr_storage
# define SS_FAMILY(ss) (ss)->ss_family
#else
# define SOCKADDR_STORAGE struct sockaddr_in
# define SS_FAMILY(ss) (ss)->sin_family
#endif

#endif /* __irc_std_h */


syntax highlighted by Code2HTML, v. 0.9.1