#if !defined (NET_FOSSIL_SCM_FSL_CONFIG_H_INCLUDED)
#define NET_FOSSIL_SCM_FSL_CONFIG_H_INCLUDED
#include "autoconfig.h" /* auto-generated */
#if HAVE_C99_INT || (defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L))
/* C99 fixed integers... */
#if defined(__cplusplus) && !defined(__STDC_FORMAT_MACROS)
/* inttypes.h needs this for the PRI* and SCN* macros in C++ mode. */
# define __STDC_FORMAT_MACROS
#endif
#include <stdint.h>
#include <inttypes.h>
#define FSL_HAS_FIXED_INTEGERS 1
#else
#define FSL_HAS_FIXED_INTEGERS 0
#endif
/* C99 */
#if !defined(FSL_AUX_SCHEMA)
#error "Expecting FSL_AUX_SCHEMA to be defined by the configuration bits."
#endif
#if !defined(FSL_LIBRARY_VERSION)
#error "Expecting FSL_LIBRARY_VERSION to be defined by the configuration bits."
#endif
#if FSL_HAS_FIXED_INTEGERS
typedef int16_t fsl_int16_t;
typedef uint16_t fsl_uint16_t;
typedef int32_t fsl_int32_t;
typedef uint32_t fsl_uint32_t;
typedef int64_t fsl_int64_t;
typedef uint64_t fsl_uint64_t;
#define FSL_INT32_T_PFMT PRIi32
#define FSL_INT32_T_SFMT SCNi32
#define FSL_UINT32_T_PFMT PRIu32
#define FSL_UINT32_T_SFMT SCNu32
#define FSL_INT64_T_PFMT PRIi64
#define FSL_INT64_T_SFMT SCNi64
#define FSL_UINT64_T_PFMT PRIu64
#define FSL_UINT64_T_SFMT SCNu64
#else
/*
Guess some reasonable defaults...
TODO: some of the printf/scanf bits need customization for 64-vs-32
bits.
See FSL_SIZE_T_PFMT for some important notes regarding formatting
strings and sizeof()s.
*/
typedef short fsl_int16_t;
typedef unsigned short fsl_uint16_t;
typedef int fsl_int32_t;
typedef unsigned int fsl_uint32_t;
#define FSL_INT32_T_PFMT "i"
#define FSL_INT32_T_SFMT "i"
#define FSL_UINT32_T_PFMT "u"
#define FSL_UINT32_T_SFMT "u"
#if defined(HAVE_LONG_LONG) && HAVE_LONG_LONG
#if defined(_MSC_VER) || defined(__BORLANDC__)
typedef __int64 fsl_int64_t;
typedef unsigned __int64 fsl_uint64_t;
#else
typedef long long int fsl_int64_t;
typedef unsigned long long int fsl_uint64_t;
#endif
#define FSL_INT64_T_PFMT "lli"
#define FSL_INT64_T_SFMT "lli"
#define FSL_UINT64_T_PFMT "llu"
#define FSL_UINT64_T_SFMT "llu"
#else
/*
We have no long long...
*/
#if defined(_MSC_VER) || defined(__BORLANDC__)
typedef __int64 fsl_int64_t;
typedef unsigned __int64 fsl_uint64_t;
#else
/*
Make up a 64-bit integer type...
WARNING: on 32-bit platforms 'long' is very likely to be 4 bytes,
meaning that Fossil, while "generally functional and correct," and
certainly won't overrun any values on normal repos, could run into
overflow problems on some operations, e.g. the /stat page of the
fossil(1) repo needs to count above 2GB at times.
We "could" use sqlite_int64, BUT that header isn't included yet and
we cannot, for portability reasons involving some of the lower-level
config macros, include that header first. We "could" include it not
first, though. Okay, let's try falling back to that one...
*/
#include <sqlite3.h>
typedef sqlite3_int64 fsl_int64_t;
typedef sqlite3_uint64 fsl_uint64_t;
#endif
/* end MSC or BORLAND */
#define FSL_INT64_T_PFMT "lli"
#define FSL_INT64_T_SFMT "lli"
#define FSL_UINT64_T_PFMT "llu"
#define FSL_UINT64_T_SFMT "llu"
#endif
/* HAVE_LONG_LONG */
#endif
/* end configurable numeric bits.
Moving on to fixed and derived numeric bits...
*/
/** @typedef some_int_type fsl_int_t
**
** fsl_int_t is a signed integer type used to denote "relative"
** ranges and lengths, or to tell a routine that it should try to
** figure out the length of some byte array itself (e.g. by using
** fsl_strlen() on it). It is provided primarily for
** documentation/readability purposes, to avoid confusion with the
** widely varying integer semantics used by various APIs. This type
** is never used as a return type for functions which use "error code
** semantics." Those always use an unadorned integer type or some
** API-specific enum type.
**
** The library typedefs this to a 64-bit type if possible, else
** a 32-bit type.
**/
typedef fsl_int64_t fsl_int_t;
/**
** The unsigned counterpart of fsl_int_t.
*/
typedef fsl_uint64_t fsl_uint_t;
/**
** printf format specifier for fsl_int_t.
*/
#define FSL_INT_T_PFMT FSL_INT64_T_PFMT
/**
** scanf format specifier for fsl_int_t.
*/
#define FSL_INT_T_SFMT FSL_INT64_T_SFMT
/**
** printf format specifier for fsl_uint_t.
*/
#define FSL_UINT_T_PFMT FSL_UINT64_T_PFMT
/**
** scanf format specifier for fsl_uint_t.
*/
#define FSL_UINT_T_SFMT FSL_UINT64_T_SFMT
/** @def FSL_INT_T_PFMT
**
** Fossil's fsl_int_t equivalent of C99's PRIi32 and friends.
*/
/** @def FSL_INT_T_SFMT
**
** Fossil's fsl_int_t equivalent of C99's SCNi32 and friends.
*/
/** @def FSL_UINT_T_PFMT
**
** Fossil's fsl_int_t equivalent of C99's PRIu32 and friends.
*/
/** @def FSL_UINT_T_SFMT
**
** Fossil's fsl_int_t equivalent of C99's SCNu32 and friends.
*/
/**
** fsl_double_t is the double type used by the library. It is
** currently hard-coded to double but the API allows for it to
** eventually be used with long double, or potentially even with
** integers as a substitute (but note that Fossil generally stores
** times in Julian Date format, which requires double precision).
*/
typedef double fsl_double_t;
/** @def FSL_DOUBLE_T_PFMT
**
** Fossil's fsl_double_t-equivalent of FSL_INT_T_PFMT and friends.
*/
#define FSL_DOUBLE_T_PFMT "f"
/** @def FSL_JULIAN_T_PFMT
**
** An output format specifier for Julian-format doubles.
*/
#define FSL_JULIAN_T_PFMT ".17g"
/**
** fsl_size_t is an unsigned integer type used to denote absolute
** ranges and lengths. It is provided primarily for
** documentation/readability purposes, to avoid confusion with the
** widely varying integer semantics used by various APIs.
**/
typedef fsl_uint_t fsl_size_t;
/** @def FSL_SIZE_T_PFMT
**
** Fossil's fsl_size_t equivalent of C99's PRIu32 and friends.
**
** ACHTUNG: when passing arguments of this type of fsl_appendf(), or
** any function which uses it for formatting purposes, it is very
** important if if you pass _literal integers_ OR enum values, that
** they be cast to fsl_size_t, or the va_list handling might extract
** the wrong number of bytes from the argument list, leading to
** really weird side-effects via what is effectively memory
** corruption.
**
** That warning applies primarily to the following typedefs and their
** format specifiers: fsl_size_t, fsl_int_t, fsl_uint_t, fsl_id_t.
**
** The warning does not apply to strongly-typed arguments,
** e.g. variables of the proper type, so long as the format specifier
** string matches the argument type.
**
** For example:
**
** @code
** fsl_size_t sz = 3;
** fsl_fprintf( stdout, "%"FSL_SIZE_T_PFMT" %"FSL_SIZE_T_PFMT\n",
** sz, // OK!
** 3 // BAD! See below...
** );
** @endcode
**
** The "fix" is to cast the literal 3 to a fsl_size_t resp. the type
** appropriate for the format specifier. That ensures that there is
** no (or much less ;) confusion when va_arg() extracts arguments
** from the variadic array.
**
** Reminders to self:
**
** @code
** int i = 0;
** f_out(("#%d: %"FSL_ID_T_PFMT" %"FSL_ID_T_PFMT" %"FSL_ID_T_PFMT"\n",
** ++i, 1, 2, 3));
** f_out(("#%d: %"FSL_SIZE_T_PFMT" %"FSL_ID_T_PFMT" %"FSL_SIZE_T_PFMT"\n",
** ++i, (fsl_size_t)1, (fsl_id_t)2, (fsl_size_t)3));
** // This one is the (generally) problematic case:
** f_out(("#%d: %"FSL_SIZE_T_PFMT" %"FSL_ID_T_PFMT" %"FSL_SIZE_T_PFMT"\n",
** ++i, 1, 2, 3));
** @endcode
**
** The above was Tested with gcc, clang, tcc on a 32-bit linux
** platform. i could reproduce the above problem on all combinations
** i tried. Current code (20130824) seems to be behaving will.
**
*/
#define FSL_SIZE_T_PFMT FSL_UINT_T_PFMT
/** @def FSL_SIZE_T_SFMT
**
** Fossil's fsl_int_t equivalent of C99's SCNu32 and friends.
*/
#define FSL_SIZE_T_SFMT FSL_UINT_T_SFMT
/**
** fsl_id_t is a signed integer type used to store database record
** IDs. It is provided primarily for documentation/readability purposes,
** to avoid confusion with the widely varying integer semantics used
** by various APIs.
**
** This type "could" be 32-bit (instead of 64) because the
** oldest/largest Fossil repo (the TCL tree, with 15 years of
** history) currently (August 2013) has only 131k RIDs. HOWEVER,
** changing this type can have side-effects vis-a-vis va_arg() deep
** in the fsl_appendf() implementation if FSL_ID_T_PFMT is not 100%
** correct for this typedef. After changing this, _make sure_ to do a
** full clean rebuild and test thoroughly because changing a sizeof
** can produce weird side-effects (effectively memory corruption) on
** unclean rebuilds.
**/
typedef fsl_int32_t fsl_id_t;
/** @def FSL_ID_T_PFMT
**
** Fossil's fsl_id_t equivalent of C99's PRIi32 and friends.
**
** ACHTUNG: see FSL_SIZE_T_PFMT for important details.
*/
#define FSL_ID_T_PFMT FSL_INT32_T_PFMT
/** @def FSL_ID_T_SFMT
**
** Fossil's fsl_id_t equivalent of C99's SCNi32 and friends.
*/
#define FSL_ID_T_SFMT FSL_INT32_T_SFMT
/**
** The type used to represent type values. Unless noted otherwise,
** the general convention is Unix Epoch. That said, Fossil internally
** uses Julian Date for times, so this typedef is clearly the result
** of over-specification/over-thinking the problem. THAT said,
** application-level code more commonly works with Unix timestamps,
** so... here it is. Over-specified, perhaps, but not 100%
** unjustifiable.
*/
typedef fsl_int64_t /*uint64 instead of int64?*/ fsl_time_t;
#endif
/* NET_FOSSIL_SCM_FSL_CONFIG_H_INCLUDED */