/* handy.h
*
- * Copyright (c) 1991-1999, Larry Wall
+ * Copyright (c) 1991-2000, Larry Wall
*
* You may distribute under the terms of either the GNU General Public
* License or the Artistic License, as specified in the README file.
#endif
#define Null(type) ((type)NULL)
+
+/*
+=for apidoc AmU||Nullch
+Null character pointer.
+
+=for apidoc AmU||Nullsv
+Null SV pointer.
+
+=cut
+*/
+
#define Nullch Null(char*)
#define Nullfp Null(PerlIO*)
#define Nullsv Null(SV*)
just figure out all the headers such a test needs.
Andy Dougherty August 1996
*/
-/* bool is built-in for g++-2.6.3, which might be used for an extension.
- If the extension includes <_G_config.h> before this file then
- _G_HAVE_BOOL will be properly set. If, however, the extension includes
- this file first, then you will have to manually set -DHAS_BOOL in
- your command line to avoid a conflict.
+/* bool is built-in for g++-2.6.3 and later, which might be used
+ for extensions. <_G_config.h> defines _G_HAVE_BOOL, but we can't
+ be sure _G_config.h will be included before this file. _G_config.h
+ also defines _G_HAVE_BOOL for both gcc and g++, but only g++
+ actually has bool. Hence, _G_HAVE_BOOL is pretty useless for us.
+ g++ can be identified by __GNUG__.
+ Andy Dougherty February 2000
*/
-#ifdef _G_HAVE_BOOL
-# if _G_HAVE_BOOL
+#ifdef __GNUG__ /* GNU g++ has bool built-in */
# ifndef HAS_BOOL
-# define HAS_BOOL 1
+# define HAS_BOOL 1
# endif
-# endif
#endif
/* The NeXT dynamic loader headers will not build with the bool macro
# else
# define bool char
# endif
+# define HAS_BOOL 1
#endif
/* XXX A note on the perl source internal type system. The
Similarly, there is no guarantee that I16 and U16 have exactly 16
bits.
- For dealing with issues that may arise from various 32/64-bit
- systems, we will ask Configure to check out
+ For dealing with issues that may arise from various 32/64-bit
+ systems, we will ask Configure to check out
SHORTSIZE == sizeof(short)
INTSIZE == sizeof(int)
typedef U16TYPE U16;
typedef I32TYPE I32;
typedef U32TYPE U32;
-#ifdef Quad_t
+#ifdef PERL_CORE
+# ifdef HAS_QUAD
+# if QUADKIND == QUAD_IS_INT64_T
+# include <sys/types.h>
+# ifdef I_INTTYPES /* e.g. Linux has int64_t without <inttypes.h> */
+# include <inttypes.h>
+# endif
+# endif
typedef I64TYPE I64;
typedef U64TYPE U64;
-#endif
+# endif
+#endif /* PERL_CORE */
/* Mention I8SIZE, U8SIZE, I16SIZE, U16SIZE, I32SIZE, U32SIZE,
I64SIZE, and U64SIZE here so that metaconfig pulls them in. */
#define Ctl(ch) ((ch) & 037)
+/*
+=for apidoc Am|bool|strNE|char* s1|char* s2
+Test two strings to see if they are different. Returns true or
+false.
+
+=for apidoc Am|bool|strEQ|char* s1|char* s2
+Test two strings to see if they are equal. Returns true or false.
+
+=for apidoc Am|bool|strLT|char* s1|char* s2
+Test two strings to see if the first, C<s1>, is less than the second,
+C<s2>. Returns true or false.
+
+=for apidoc Am|bool|strLE|char* s1|char* s2
+Test two strings to see if the first, C<s1>, is less than or equal to the
+second, C<s2>. Returns true or false.
+
+=for apidoc Am|bool|strGT|char* s1|char* s2
+Test two strings to see if the first, C<s1>, is greater than the second,
+C<s2>. Returns true or false.
+
+=for apidoc Am|bool|strGE|char* s1|char* s2
+Test two strings to see if the first, C<s1>, is greater than or equal to
+the second, C<s2>. Returns true or false.
+
+=for apidoc Am|bool|strnNE|char* s1|char* s2|STRLEN len
+Test two strings to see if they are different. The C<len> parameter
+indicates the number of bytes to compare. Returns true or false. (A
+wrapper for C<strncmp>).
+
+=for apidoc Am|bool|strnEQ|char* s1|char* s2|STRLEN len
+Test two strings to see if they are equal. The C<len> parameter indicates
+the number of bytes to compare. Returns true or false. (A wrapper for
+C<strncmp>).
+
+=cut
+*/
+
#define strNE(s1,s2) (strcmp(s1,s2))
#define strEQ(s1,s2) (!strcmp(s1,s2))
#define strLT(s1,s2) (strcmp(s1,s2) < 0)
# endif
#endif
+/*
+=for apidoc Am|bool|isALNUM|char ch
+Returns a boolean indicating whether the C C<char> is an ASCII alphanumeric
+character (including underscore) or digit.
+
+=for apidoc Am|bool|isALPHA|char ch
+Returns a boolean indicating whether the C C<char> is an ASCII alphabetic
+character.
+
+=for apidoc Am|bool|isSPACE|char ch
+Returns a boolean indicating whether the C C<char> is whitespace.
+
+=for apidoc Am|bool|isDIGIT|char ch
+Returns a boolean indicating whether the C C<char> is an ASCII
+digit.
+
+=for apidoc Am|bool|isUPPER|char ch
+Returns a boolean indicating whether the C C<char> is an uppercase
+character.
+
+=for apidoc Am|bool|isLOWER|char ch
+Returns a boolean indicating whether the C C<char> is a lowercase
+character.
+
+=for apidoc Am|char|toUPPER|char ch
+Converts the specified character to uppercase.
+
+=for apidoc Am|char|toLOWER|char ch
+Converts the specified character to lowercase.
+
+=cut
+*/
+
#define isALNUM(c) (isALPHA(c) || isDIGIT(c) || (c) == '_')
#define isIDFIRST(c) (isALPHA(c) || (c) == '_')
#define isALPHA(c) (isUPPER(c) || isLOWER(c))
#define isSPACE(c) \
((c) == ' ' || (c) == '\t' || (c) == '\n' || (c) =='\r' || (c) == '\f')
+#define isPSXSPC(c) (isSPACE(c) || (c) == '\v')
+#define isBLANK(c) ((c) == ' ' || (c) == '\t')
#define isDIGIT(c) ((c) >= '0' && (c) <= '9')
#ifdef EBCDIC
/* In EBCDIC we do not do locales: therefore() isupper() is fine. */
# endif
#endif /* USE_NEXT_CTYPE */
+#define isPSXSPC_LC(c) (isSPACE_LC(c) || (c) == '\v')
+#define isBLANK_LC(c) isBLANK(c) /* could be wrong */
+
#define isALNUM_uni(c) is_uni_alnum(c)
#define isIDFIRST_uni(c) is_uni_idfirst(c)
#define isALPHA_uni(c) is_uni_alpha(c)
#define toTITLE_uni(c) to_uni_title(c)
#define toLOWER_uni(c) to_uni_lower(c)
+#define isPSXSPC_uni(c) (isSPACE_uni(c) ||(c) == '\f')
+#define isBLANK_uni(c) isBLANK(c) /* could be wrong */
+
#define isALNUM_LC_uni(c) (c < 256 ? isALNUM_LC(c) : is_uni_alnum_lc(c))
#define isIDFIRST_LC_uni(c) (c < 256 ? isIDFIRST_LC(c) : is_uni_idfirst_lc(c))
#define isALPHA_LC_uni(c) (c < 256 ? isALPHA_LC(c) : is_uni_alpha_lc(c))
#define toTITLE_LC_uni(c) (c < 256 ? toUPPER_LC(c) : to_uni_title_lc(c))
#define toLOWER_LC_uni(c) (c < 256 ? toLOWER_LC(c) : to_uni_lower_lc(c))
+#define isPSXSPC_LC_uni(c) (isSPACE_LC_uni(c) ||(c) == '\f')
+#define isBLANK_LC_uni(c) isBLANK(c) /* could be wrong */
+
#define isALNUM_utf8(p) is_utf8_alnum(p)
#define isIDFIRST_utf8(p) is_utf8_idfirst(p)
#define isALPHA_utf8(p) is_utf8_alpha(p)
#define toTITLE_utf8(p) to_utf8_title(p)
#define toLOWER_utf8(p) to_utf8_lower(p)
-#define isALNUM_LC_utf8(p) isALNUM_LC_uni(utf8_to_uv(p, 0))
-#define isIDFIRST_LC_utf8(p) isIDFIRST_LC_uni(utf8_to_uv(p, 0))
-#define isALPHA_LC_utf8(p) isALPHA_LC_uni(utf8_to_uv(p, 0))
-#define isSPACE_LC_utf8(p) isSPACE_LC_uni(utf8_to_uv(p, 0))
-#define isDIGIT_LC_utf8(p) isDIGIT_LC_uni(utf8_to_uv(p, 0))
-#define isUPPER_LC_utf8(p) isUPPER_LC_uni(utf8_to_uv(p, 0))
-#define isLOWER_LC_utf8(p) isLOWER_LC_uni(utf8_to_uv(p, 0))
-#define isALNUMC_LC_utf8(p) isALNUMC_LC_uni(utf8_to_uv(p, 0))
-#define isCNTRL_LC_utf8(p) isCNTRL_LC_uni(utf8_to_uv(p, 0))
-#define isGRAPH_LC_utf8(p) isGRAPH_LC_uni(utf8_to_uv(p, 0))
-#define isPRINT_LC_utf8(p) isPRINT_LC_uni(utf8_to_uv(p, 0))
-#define isPUNCT_LC_utf8(p) isPUNCT_LC_uni(utf8_to_uv(p, 0))
-#define toUPPER_LC_utf8(p) toUPPER_LC_uni(utf8_to_uv(p, 0))
-#define toTITLE_LC_utf8(p) toTITLE_LC_uni(utf8_to_uv(p, 0))
-#define toLOWER_LC_utf8(p) toLOWER_LC_uni(utf8_to_uv(p, 0))
+#define isPSXSPC_utf8(c) (isSPACE_utf8(c) ||(c) == '\f')
+#define isBLANK_utf8(c) isBLANK(c) /* could be wrong */
+
+#define STRLEN_MAX ((STRLEN)-1)
+
+#define isALNUM_LC_utf8(p) isALNUM_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isIDFIRST_LC_utf8(p) isIDFIRST_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isALPHA_LC_utf8(p) isALPHA_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isSPACE_LC_utf8(p) isSPACE_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isDIGIT_LC_utf8(p) isDIGIT_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isUPPER_LC_utf8(p) isUPPER_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isLOWER_LC_utf8(p) isLOWER_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isALNUMC_LC_utf8(p) isALNUMC_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isCNTRL_LC_utf8(p) isCNTRL_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isGRAPH_LC_utf8(p) isGRAPH_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isPRINT_LC_utf8(p) isPRINT_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define isPUNCT_LC_utf8(p) isPUNCT_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define toUPPER_LC_utf8(p) toUPPER_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define toTITLE_LC_utf8(p) toTITLE_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+#define toLOWER_LC_utf8(p) toLOWER_LC_uni(utf8_to_uv_chk(p, STRLEN_MAX, 0, 0))
+
+#define isPSXSPC_LC_utf8(c) (isSPACE_LC_utf8(c) ||(c) == '\f')
+#define isBLANK_LC_utf8(c) isBLANK(c) /* could be wrong */
#ifdef EBCDIC
EXT int ebcdic_control (int);
#endif
-/* This looks obsolete (IZ):
-
+/*
XXX LEAKTEST doesn't really work in perl5. There are direct calls to
safemalloc() in the source, so LEAKTEST won't pick them up.
+ (The main "offenders" are extensions.)
Further, if you try LEAKTEST, you'll also end up calling
Safefree, which might call safexfree() on some things that weren't
malloced with safexmalloc. The correct "fix" to this, if anyone
--Andy Dougherty August 1996
*/
+/*
+=for apidoc Am|SV*|NEWSV|int id|STRLEN len
+Creates a new SV. A non-zero C<len> parameter indicates the number of
+bytes of preallocated string space the SV should have. An extra byte for a
+tailing NUL is also reserved. (SvPOK is not set for the SV even if string
+space is allocated.) The reference count for the new SV is set to 1.
+C<id> is an integer id between 0 and 1299 (used to identify leaks).
+
+=for apidoc Am|void|New|int id|void* ptr|int nitems|type
+The XSUB-writer's interface to the C C<malloc> function.
+
+=for apidoc Am|void|Newc|int id|void* ptr|int nitems|type|cast
+The XSUB-writer's interface to the C C<malloc> function, with
+cast.
+
+=for apidoc Am|void|Newz|int id|void* ptr|int nitems|type
+The XSUB-writer's interface to the C C<malloc> function. The allocated
+memory is zeroed with C<memzero>.
+
+=for apidoc Am|void|Renew|void* ptr|int nitems|type
+The XSUB-writer's interface to the C C<realloc> function.
+
+=for apidoc Am|void|Renewc|void* ptr|int nitems|type|cast
+The XSUB-writer's interface to the C C<realloc> function, with
+cast.
+
+=for apidoc Am|void|Safefree|void* ptr
+The XSUB-writer's interface to the C C<free> function.
+
+=for apidoc Am|void|Move|void* src|void* dest|int nitems|type
+The XSUB-writer's interface to the C C<memmove> function. The C<src> is the
+source, C<dest> is the destination, C<nitems> is the number of items, and C<type> is
+the type. Can do overlapping moves. See also C<Copy>.
+
+=for apidoc Am|void|Copy|void* src|void* dest|int nitems|type
+The XSUB-writer's interface to the C C<memcpy> function. The C<src> is the
+source, C<dest> is the destination, C<nitems> is the number of items, and C<type> is
+the type. May fail on overlapping copies. See also C<Move>.
+
+=for apidoc Am|void|Zero|void* dest|int nitems|type
+
+The XSUB-writer's interface to the C C<memzero> function. The C<dest> is the
+destination, C<nitems> is the number of items, and C<type> is the type.
+
+=for apidoc Am|void|StructCopy|type src|type dest|type
+This is an architecture-independent macro to copy one structure to another.
+
+=cut
+*/
+
#ifndef lint
#define NEWSV(x,len) newSV(len)