From 01df8322b585735b3f32106d3e323694e8eb8757 Mon Sep 17 00:00:00 2001 From: Viktor Szakats Date: Mon, 20 Dec 2010 23:01:06 +0000 Subject: [PATCH] 2010-12-20 23:59 UTC+0100 Viktor Szakats (harbour.01 syenar.hu) * src/3rd/png/pngrio.c * src/3rd/png/pngconf.h * src/3rd/png/pngwtran.c * src/3rd/png/pngpread.c * src/3rd/png/pngset.c * src/3rd/png/LICENSE * src/3rd/png/pngrutil.c * src/3rd/png/pngwutil.c * src/3rd/png/pngread.c * src/3rd/png/png.c * src/3rd/png/pngget.c * src/3rd/png/png.h * src/3rd/png/pngpriv.h * src/3rd/png/pngrtran.c * src/3rd/png/Makefile * src/3rd/pcre/pcre.h * src/3rd/pcre/pcrevutf.c * src/3rd/pcre/pcreexec.c * src/3rd/pcre/pcreinal.h * src/3rd/pcre/pcredfa.c * src/3rd/pcre/pcrecomp.c * src/3rd/pcre/pcre.dif * src/3rd/pcre/config.h * src/3rd/pcre/pcreprni.h * src/3rd/pcre/pcrestud.c * src/3rd/pcre/Makefile + update pcre to 8.11, png to 1.4.5 changelogs: http://www.pcre.org/changelog.txt http://www.libpng.org/pub/png/src/libpng-1.4.5-README.txt build-tested in a couple of cross scenarios, looks ok. Patch from Tamas Tevesz. * contrib/hbtip/sendmail.prg % Minor. --- harbour/ChangeLog | 37 +++++ harbour/contrib/hbtip/sendmail.prg | 8 +- harbour/src/3rd/pcre/Makefile | 4 +- harbour/src/3rd/pcre/config.h | 6 +- harbour/src/3rd/pcre/pcre.dif | 8 +- harbour/src/3rd/pcre/pcre.h | 76 +++++----- harbour/src/3rd/pcre/pcrecomp.c | 158 +++++++++++++++++---- harbour/src/3rd/pcre/pcredfa.c | 40 ++++-- harbour/src/3rd/pcre/pcreexec.c | 126 +++++++++++------ harbour/src/3rd/pcre/pcreinal.h | 218 +++++++++++++++++------------ harbour/src/3rd/pcre/pcreprni.h | 17 ++- harbour/src/3rd/pcre/pcrestud.c | 5 +- harbour/src/3rd/pcre/pcrevutf.c | 17 ++- harbour/src/3rd/png/LICENSE | 4 +- harbour/src/3rd/png/Makefile | 4 +- harbour/src/3rd/png/png.c | 12 +- harbour/src/3rd/png/png.h | 46 ++++-- harbour/src/3rd/png/pngconf.h | 2 +- harbour/src/3rd/png/pngget.c | 14 +- harbour/src/3rd/png/pngpread.c | 4 +- harbour/src/3rd/png/pngpriv.h | 5 +- harbour/src/3rd/png/pngread.c | 55 +++----- harbour/src/3rd/png/pngrio.c | 4 +- harbour/src/3rd/png/pngrtran.c | 37 ++++- harbour/src/3rd/png/pngrutil.c | 122 +++++++++++----- harbour/src/3rd/png/pngset.c | 17 ++- harbour/src/3rd/png/pngwtran.c | 3 + harbour/src/3rd/png/pngwutil.c | 6 +- 28 files changed, 698 insertions(+), 357 deletions(-) diff --git a/harbour/ChangeLog b/harbour/ChangeLog index 8b095e8436..84d9d08d40 100644 --- a/harbour/ChangeLog +++ b/harbour/ChangeLog @@ -16,6 +16,43 @@ The license applies to all entries newer than 2009-04-28. */ +2010-12-20 23:59 UTC+0100 Viktor Szakats (harbour.01 syenar.hu) + * src/3rd/png/pngrio.c + * src/3rd/png/pngconf.h + * src/3rd/png/pngwtran.c + * src/3rd/png/pngpread.c + * src/3rd/png/pngset.c + * src/3rd/png/LICENSE + * src/3rd/png/pngrutil.c + * src/3rd/png/pngwutil.c + * src/3rd/png/pngread.c + * src/3rd/png/png.c + * src/3rd/png/pngget.c + * src/3rd/png/png.h + * src/3rd/png/pngpriv.h + * src/3rd/png/pngrtran.c + * src/3rd/png/Makefile + * src/3rd/pcre/pcre.h + * src/3rd/pcre/pcrevutf.c + * src/3rd/pcre/pcreexec.c + * src/3rd/pcre/pcreinal.h + * src/3rd/pcre/pcredfa.c + * src/3rd/pcre/pcrecomp.c + * src/3rd/pcre/pcre.dif + * src/3rd/pcre/config.h + * src/3rd/pcre/pcreprni.h + * src/3rd/pcre/pcrestud.c + * src/3rd/pcre/Makefile + + update pcre to 8.11, png to 1.4.5 + changelogs: + http://www.pcre.org/changelog.txt + http://www.libpng.org/pub/png/src/libpng-1.4.5-README.txt + build-tested in a couple of cross scenarios, looks ok. + Patch from Tamas Tevesz. + + * contrib/hbtip/sendmail.prg + % Minor. + 2010-12-20 21:04 UTC+0100 Viktor Szakats (harbour.01 syenar.hu) * contrib/hbtip/sendmail.prg - Deleted debug line. diff --git a/harbour/contrib/hbtip/sendmail.prg b/harbour/contrib/hbtip/sendmail.prg index 5948313977..00109a3b1b 100644 --- a/harbour/contrib/hbtip/sendmail.prg +++ b/harbour/contrib/hbtip/sendmail.prg @@ -88,8 +88,6 @@ FUNCTION hb_SendMail( cServer, nPort, cFrom, xTo, xCC, xBCC, cBody, cSubject, ; LOCAL cBCC LOCAL tmp - LOCAL cFromRaw := tip_GetRawEMail( cFrom ) - LOCAL oInMail LOCAL oUrl LOCAL oUrl1 @@ -319,7 +317,7 @@ FUNCTION hb_SendMail( cServer, nPort, cFrom, xTo, xCC, xBCC, cBody, cSubject, ; ENDIF - oInMail:oUrl:cUserid := cFromRaw + oInMail:oUrl:cUserid := tip_GetRawEMail( cFrom ) oInMail:Write( hb_MailAssemble( cFrom, xTo, xCC, cBody, cSubject, aFiles, nPriority, lRead, cReplyTo, cCharset, cEncoding ) ) oInMail:Commit() @@ -353,8 +351,6 @@ FUNCTION hb_MailAssemble( cFrom, xTo, xCC, cBody, cSubject, ; LOCAL cFext LOCAL cData - LOCAL cFromRaw := tip_GetRawEMail( cFrom ) - IF ! ISARRAY( aFiles ) aFiles := {} ENDIF @@ -493,7 +489,7 @@ FUNCTION hb_MailAssemble( cFrom, xTo, xCC, cBody, cSubject, ; NEXT IF lRead - oMail:hHeaders[ "Disposition-Notification-To" ] := cFromRaw + oMail:hHeaders[ "Disposition-Notification-To" ] := tip_GetRawEMail( cFrom ) ENDIF IF nPriority != 3 diff --git a/harbour/src/3rd/pcre/Makefile b/harbour/src/3rd/pcre/Makefile index d384f6aaf1..1d530e230f 100644 --- a/harbour/src/3rd/pcre/Makefile +++ b/harbour/src/3rd/pcre/Makefile @@ -72,8 +72,8 @@ else endif # ORIGIN http://www.pcre.org/ -# VER 8.10 -# URL http://sourceforge.net/projects/pcre/files/pcre/8.10/pcre-8.10.zip/download +# VER 8.11 +# URL http://sourceforge.net/projects/pcre/files/pcre/8.11/pcre-8.11.zip/download # DIFF pcre.dif # # MAP LICENCE diff --git a/harbour/src/3rd/pcre/config.h b/harbour/src/3rd/pcre/config.h index 460c783ba0..0a876f5e60 100644 --- a/harbour/src/3rd/pcre/config.h +++ b/harbour/src/3rd/pcre/config.h @@ -250,7 +250,7 @@ them both to 0; an emulation function will be used. */ #define PACKAGE_NAME "PCRE" /* Define to the full name and version of this package. */ -#define PACKAGE_STRING "PCRE 8.10" +#define PACKAGE_STRING "PCRE 8.11" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "pcre" @@ -259,7 +259,7 @@ them both to 0; an emulation function will be used. */ #define PACKAGE_URL "" /* Define to the version of this package. */ -#define PACKAGE_VERSION "8.10" +#define PACKAGE_VERSION "8.11" /* If you are compiling for a system other than a Unix-like system or @@ -315,7 +315,7 @@ them both to 0; an emulation function will be used. */ /* Version number of package */ #ifndef VERSION -#define VERSION "8.10" +#define VERSION "8.11" #endif /* Define to empty if `const' does not conform to ANSI C. */ diff --git a/harbour/src/3rd/pcre/pcre.dif b/harbour/src/3rd/pcre/pcre.dif index 85b99e0032..1c0d01dc7e 100644 --- a/harbour/src/3rd/pcre/pcre.dif +++ b/harbour/src/3rd/pcre/pcre.dif @@ -1,6 +1,6 @@ diff -urN pcre.orig/pcrefinf.c pcre/pcrefinf.c ---- pcre.orig/pcrefinf.c 2010-06-26 14:10:17.887330037 +0200 -+++ pcre/pcrefinf.c 2010-06-26 14:10:18.107331394 +0200 +--- pcre.orig/pcrefinf.c 2010-12-20 22:31:27.992038219 +0100 ++++ pcre/pcrefinf.c 2010-12-20 22:31:28.802038337 +0100 @@ -126,7 +126,7 @@ case PCRE_INFO_MINLENGTH: *((int *)where) = @@ -11,8 +11,8 @@ diff -urN pcre.orig/pcrefinf.c pcre/pcrefinf.c case PCRE_INFO_LASTLITERAL: diff -urN pcre.orig/pcreglob.c pcre/pcreglob.c ---- pcre.orig/pcreglob.c 2010-06-26 14:10:17.907330491 +0200 -+++ pcre/pcreglob.c 2010-06-26 14:10:18.107331394 +0200 +--- pcre.orig/pcreglob.c 2010-12-20 22:31:28.052038497 +0100 ++++ pcre/pcreglob.c 2010-12-20 22:31:28.822040758 +0100 @@ -74,11 +74,17 @@ PCRE_EXP_DATA_DEFN int (*pcre_callout)(pcre_callout_block *) = NULL; diff --git a/harbour/src/3rd/pcre/pcre.h b/harbour/src/3rd/pcre/pcre.h index febb617422..ec454ee60d 100644 --- a/harbour/src/3rd/pcre/pcre.h +++ b/harbour/src/3rd/pcre/pcre.h @@ -42,9 +42,9 @@ POSSIBILITY OF SUCH DAMAGE. /* The current PCRE version information. */ #define PCRE_MAJOR 8 -#define PCRE_MINOR 10 +#define PCRE_MINOR 11 #define PCRE_PRERELEASE -#define PCRE_DATE 2010-06-25 +#define PCRE_DATE 2010-12-10 /* When an application links to a PCRE DLL in Windows, the symbols that are imported have to be identified as such. When building PCRE, the appropriate @@ -96,42 +96,44 @@ extern "C" { #endif /* Options. Some are compile-time only, some are run-time only, and some are -both, so we keep them all distinct. */ +both, so we keep them all distinct. However, almost all the bits in the options +word are now used. In the long run, we may have to re-use some of the +compile-time only bits for runtime options, or vice versa. */ -#define PCRE_CASELESS 0x00000001 -#define PCRE_MULTILINE 0x00000002 -#define PCRE_DOTALL 0x00000004 -#define PCRE_EXTENDED 0x00000008 -#define PCRE_ANCHORED 0x00000010 -#define PCRE_DOLLAR_ENDONLY 0x00000020 -#define PCRE_EXTRA 0x00000040 -#define PCRE_NOTBOL 0x00000080 -#define PCRE_NOTEOL 0x00000100 -#define PCRE_UNGREEDY 0x00000200 -#define PCRE_NOTEMPTY 0x00000400 -#define PCRE_UTF8 0x00000800 -#define PCRE_NO_AUTO_CAPTURE 0x00001000 -#define PCRE_NO_UTF8_CHECK 0x00002000 -#define PCRE_AUTO_CALLOUT 0x00004000 -#define PCRE_PARTIAL_SOFT 0x00008000 +#define PCRE_CASELESS 0x00000001 /* Compile */ +#define PCRE_MULTILINE 0x00000002 /* Compile */ +#define PCRE_DOTALL 0x00000004 /* Compile */ +#define PCRE_EXTENDED 0x00000008 /* Compile */ +#define PCRE_ANCHORED 0x00000010 /* Compile, exec, DFA exec */ +#define PCRE_DOLLAR_ENDONLY 0x00000020 /* Compile */ +#define PCRE_EXTRA 0x00000040 /* Compile */ +#define PCRE_NOTBOL 0x00000080 /* Exec, DFA exec */ +#define PCRE_NOTEOL 0x00000100 /* Exec, DFA exec */ +#define PCRE_UNGREEDY 0x00000200 /* Compile */ +#define PCRE_NOTEMPTY 0x00000400 /* Exec, DFA exec */ +#define PCRE_UTF8 0x00000800 /* Compile */ +#define PCRE_NO_AUTO_CAPTURE 0x00001000 /* Compile */ +#define PCRE_NO_UTF8_CHECK 0x00002000 /* Compile, exec, DFA exec */ +#define PCRE_AUTO_CALLOUT 0x00004000 /* Compile */ +#define PCRE_PARTIAL_SOFT 0x00008000 /* Exec, DFA exec */ #define PCRE_PARTIAL 0x00008000 /* Backwards compatible synonym */ -#define PCRE_DFA_SHORTEST 0x00010000 -#define PCRE_DFA_RESTART 0x00020000 -#define PCRE_FIRSTLINE 0x00040000 -#define PCRE_DUPNAMES 0x00080000 -#define PCRE_NEWLINE_CR 0x00100000 -#define PCRE_NEWLINE_LF 0x00200000 -#define PCRE_NEWLINE_CRLF 0x00300000 -#define PCRE_NEWLINE_ANY 0x00400000 -#define PCRE_NEWLINE_ANYCRLF 0x00500000 -#define PCRE_BSR_ANYCRLF 0x00800000 -#define PCRE_BSR_UNICODE 0x01000000 -#define PCRE_JAVASCRIPT_COMPAT 0x02000000 -#define PCRE_NO_START_OPTIMIZE 0x04000000 -#define PCRE_NO_START_OPTIMISE 0x04000000 -#define PCRE_PARTIAL_HARD 0x08000000 -#define PCRE_NOTEMPTY_ATSTART 0x10000000 -#define PCRE_UCP 0x20000000 +#define PCRE_DFA_SHORTEST 0x00010000 /* DFA exec */ +#define PCRE_DFA_RESTART 0x00020000 /* DFA exec */ +#define PCRE_FIRSTLINE 0x00040000 /* Compile */ +#define PCRE_DUPNAMES 0x00080000 /* Compile */ +#define PCRE_NEWLINE_CR 0x00100000 /* Compile, exec, DFA exec */ +#define PCRE_NEWLINE_LF 0x00200000 /* Compile, exec, DFA exec */ +#define PCRE_NEWLINE_CRLF 0x00300000 /* Compile, exec, DFA exec */ +#define PCRE_NEWLINE_ANY 0x00400000 /* Compile, exec, DFA exec */ +#define PCRE_NEWLINE_ANYCRLF 0x00500000 /* Compile, exec, DFA exec */ +#define PCRE_BSR_ANYCRLF 0x00800000 /* Compile, exec, DFA exec */ +#define PCRE_BSR_UNICODE 0x01000000 /* Compile, exec, DFA exec */ +#define PCRE_JAVASCRIPT_COMPAT 0x02000000 /* Compile */ +#define PCRE_NO_START_OPTIMIZE 0x04000000 /* Compile, exec, DFA exec */ +#define PCRE_NO_START_OPTIMISE 0x04000000 /* Synonym */ +#define PCRE_PARTIAL_HARD 0x08000000 /* Exec, DFA exec */ +#define PCRE_NOTEMPTY_ATSTART 0x10000000 /* Exec, DFA exec */ +#define PCRE_UCP 0x20000000 /* Compile */ /* Exec-time and get/set-time error codes */ @@ -159,6 +161,8 @@ both, so we keep them all distinct. */ #define PCRE_ERROR_RECURSIONLIMIT (-21) #define PCRE_ERROR_NULLWSLIMIT (-22) /* No longer actually used */ #define PCRE_ERROR_BADNEWLINE (-23) +#define PCRE_ERROR_BADOFFSET (-24) +#define PCRE_ERROR_SHORTUTF8 (-25) /* Request types for pcre_fullinfo() */ diff --git a/harbour/src/3rd/pcre/pcrecomp.c b/harbour/src/3rd/pcre/pcrecomp.c index 18e57715fa..e3005360a7 100644 --- a/harbour/src/3rd/pcre/pcrecomp.c +++ b/harbour/src/3rd/pcre/pcrecomp.c @@ -408,6 +408,7 @@ static const char error_texts[] = "different names for subpatterns of the same number are not allowed\0" "(*MARK) must have an argument\0" "this version of PCRE is not compiled with PCRE_UCP support\0" + "\\c must be followed by an ASCII character\0" ; /* Table to identify digits and hex digits. This is used when compiling @@ -841,7 +842,8 @@ else break; /* For \c, a following letter is upper-cased; then the 0x40 bit is flipped. - This coding is ASCII-specific, but then the whole concept of \cx is + An error is given if the byte following \c is not an ASCII character. This + coding is ASCII-specific, but then the whole concept of \cx is ASCII-specific. (However, an EBCDIC equivalent has now been added.) */ case CHAR_c: @@ -851,11 +853,15 @@ else *errorcodeptr = ERR2; break; } - -#ifndef EBCDIC /* ASCII/UTF-8 coding */ +#ifndef EBCDIC /* ASCII/UTF-8 coding */ + if (c > 127) /* Excludes all non-ASCII in either mode */ + { + *errorcodeptr = ERR68; + break; + } if (c >= CHAR_a && c <= CHAR_z) c -= 32; c ^= 0x40; -#else /* EBCDIC coding */ +#else /* EBCDIC coding */ if (c >= CHAR_a && c <= CHAR_z) c += 64; c ^= 0xC0; #endif @@ -1099,10 +1105,21 @@ top-level call starts at the beginning of the pattern. All other calls must start at a parenthesis. It scans along a pattern's text looking for capturing subpatterns, and counting them. If it finds a named pattern that matches the name it is given, it returns its number. Alternatively, if the name is NULL, it -returns when it reaches a given numbered subpattern. We know that if (?P< is -encountered, the name will be terminated by '>' because that is checked in the -first pass. Recursion is used to keep track of subpatterns that reset the -capturing group numbers - the (?| feature. +returns when it reaches a given numbered subpattern. Recursion is used to keep +track of subpatterns that reset the capturing group numbers - the (?| feature. + +This function was originally called only from the second pass, in which we know +that if (?< or (?' or (?P< is encountered, the name will be correctly +terminated because that is checked in the first pass. There is now one call to +this function in the first pass, to check for a recursive back reference by +name (so that we can make the whole group atomic). In this case, we need check +only up to the current position in the pattern, and that is still OK because +and previous occurrences will have been checked. To make this work, the test +for "end of pattern" is a check against cd->end_pattern in the main loop, +instead of looking for a binary zero. This means that the special first-pass +call can adjust cd->end_pattern temporarily. (Checks for binary zero while +processing items within the loop are OK, because afterwards the main loop will +terminate.) Arguments: ptrptr address of the current character pointer (updated) @@ -1110,6 +1127,7 @@ Arguments: name name to seek, or NULL if seeking a numbered subpattern lorn name length, or subpattern number if name is NULL xmode TRUE if we are in /x mode + utf8 TRUE if we are in UTF-8 mode count pointer to the current capturing subpattern number (updated) Returns: the number of the named subpattern, or -1 if not found @@ -1117,7 +1135,7 @@ Returns: the number of the named subpattern, or -1 if not found static int find_parens_sub(uschar **ptrptr, compile_data *cd, const uschar *name, int lorn, - BOOL xmode, int *count) + BOOL xmode, BOOL utf8, int *count) { uschar *ptr = *ptrptr; int start_count = *count; @@ -1202,9 +1220,11 @@ if (ptr[0] == CHAR_LEFT_PARENTHESIS) } /* Past any initial parenthesis handling, scan for parentheses or vertical -bars. */ +bars. Stop if we get to cd->end_pattern. Note that this is important for the +first-pass call when this value is temporarily adjusted to stop at the current +position. So DO NOT change this to a test for binary zero. */ -for (; *ptr != 0; ptr++) +for (; ptr < cd->end_pattern; ptr++) { /* Skip over backslashed characters and also entire \Q...\E */ @@ -1278,7 +1298,15 @@ for (; *ptr != 0; ptr++) if (xmode && *ptr == CHAR_NUMBER_SIGN) { - while (*(++ptr) != 0 && *ptr != CHAR_NL) {}; + ptr++; + while (*ptr != 0) + { + if (IS_NEWLINE(ptr)) { ptr += cd->nllen - 1; break; } + ptr++; +#ifdef SUPPORT_UTF8 + if (utf8) while ((*ptr & 0xc0) == 0x80) ptr++; +#endif + } if (*ptr == 0) goto FAIL_EXIT; continue; } @@ -1287,7 +1315,7 @@ for (; *ptr != 0; ptr++) if (*ptr == CHAR_LEFT_PARENTHESIS) { - int rc = find_parens_sub(&ptr, cd, name, lorn, xmode, count); + int rc = find_parens_sub(&ptr, cd, name, lorn, xmode, utf8, count); if (rc > 0) return rc; if (*ptr == 0) goto FAIL_EXIT; } @@ -1333,12 +1361,14 @@ Arguments: name name to seek, or NULL if seeking a numbered subpattern lorn name length, or subpattern number if name is NULL xmode TRUE if we are in /x mode + utf8 TRUE if we are in UTF-8 mode Returns: the number of the found subpattern, or -1 if not found */ static int -find_parens(compile_data *cd, const uschar *name, int lorn, BOOL xmode) +find_parens(compile_data *cd, const uschar *name, int lorn, BOOL xmode, + BOOL utf8) { uschar *ptr = (uschar *)cd->start_pattern; int count = 0; @@ -1351,7 +1381,7 @@ matching closing parens. That is why we have to have a loop. */ for (;;) { - rc = find_parens_sub(&ptr, cd, name, lorn, xmode, &count); + rc = find_parens_sub(&ptr, cd, name, lorn, xmode, utf8, &count); if (rc > 0 || *ptr++ == 0) break; } @@ -1724,9 +1754,12 @@ for (;;) case OP_MARK: case OP_PRUNE_ARG: case OP_SKIP_ARG: - case OP_THEN_ARG: code += code[1]; break; + + case OP_THEN_ARG: + code += code[1+LINK_SIZE]; + break; } /* Add in the fixed length from the table */ @@ -1827,9 +1860,12 @@ for (;;) case OP_MARK: case OP_PRUNE_ARG: case OP_SKIP_ARG: - case OP_THEN_ARG: code += code[1]; break; + + case OP_THEN_ARG: + code += code[1+LINK_SIZE]; + break; } /* Add in the fixed length from the table */ @@ -2105,10 +2141,13 @@ for (code = first_significant_code(code + _pcre_OP_lengths[*code], NULL, 0, TRUE case OP_MARK: case OP_PRUNE_ARG: case OP_SKIP_ARG: - case OP_THEN_ARG: code += code[1]; break; + case OP_THEN_ARG: + code += code[1+LINK_SIZE]; + break; + /* None of the remaining opcodes are required to match a character. */ default: @@ -2506,8 +2545,15 @@ if ((options & PCRE_EXTENDED) != 0) while ((cd->ctypes[*ptr] & ctype_space) != 0) ptr++; if (*ptr == CHAR_NUMBER_SIGN) { - while (*(++ptr) != 0) + ptr++; + while (*ptr != 0) + { if (IS_NEWLINE(ptr)) { ptr += cd->nllen; break; } + ptr++; +#ifdef SUPPORT_UTF8 + if (utf8) while ((*ptr & 0xc0) == 0x80) ptr++; +#endif + } } else break; } @@ -2543,8 +2589,15 @@ if ((options & PCRE_EXTENDED) != 0) while ((cd->ctypes[*ptr] & ctype_space) != 0) ptr++; if (*ptr == CHAR_NUMBER_SIGN) { - while (*(++ptr) != 0) + ptr++; + while (*ptr != 0) + { if (IS_NEWLINE(ptr)) { ptr += cd->nllen; break; } + ptr++; +#ifdef SUPPORT_UTF8 + if (utf8) while ((*ptr & 0xc0) == 0x80) ptr++; +#endif + } } else break; } @@ -3117,9 +3170,14 @@ for (;; ptr++) if ((cd->ctypes[c] & ctype_space) != 0) continue; if (c == CHAR_NUMBER_SIGN) { - while (*(++ptr) != 0) + ptr++; + while (*ptr != 0) { if (IS_NEWLINE(ptr)) { ptr += cd->nllen - 1; break; } + ptr++; +#ifdef SUPPORT_UTF8 + if (utf8) while ((*ptr & 0xc0) == 0x80) ptr++; +#endif } if (*ptr != 0) continue; @@ -3494,9 +3552,14 @@ for (;; ptr++) for (c = 0; c < 32; c++) classbits[c] |= ~cbits[c+cbit_word]; continue; + /* Perl 5.004 onwards omits VT from \s, but we must preserve it + if it was previously set by something earlier in the character + class. */ + case ESC_s: - for (c = 0; c < 32; c++) classbits[c] |= cbits[c+cbit_space]; - classbits[1] &= ~0x08; /* Perl 5.004 onwards omits VT from \s */ + classbits[0] |= cbits[cbit_space]; + classbits[1] |= cbits[cbit_space+1] & ~0x08; + for (c = 2; c < 32; c++) classbits[c] |= cbits[c+cbit_space]; continue; case ESC_S: @@ -4808,7 +4871,12 @@ for (;; ptr++) *errorcodeptr = ERR66; goto FAILED; } - *code++ = verbs[i].op; + *code = verbs[i].op; + if (*code++ == OP_THEN) + { + PUT(code, 0, code - bcptr->current_branch - 1); + code += LINK_SIZE; + } } else @@ -4818,7 +4886,12 @@ for (;; ptr++) *errorcodeptr = ERR59; goto FAILED; } - *code++ = verbs[i].op_arg; + *code = verbs[i].op_arg; + if (*code++ == OP_THEN_ARG) + { + PUT(code, 0, code - bcptr->current_branch - 1); + code += LINK_SIZE; + } *code++ = arglen; memcpy(code, arg, arglen); code += arglen; @@ -5012,7 +5085,7 @@ for (;; ptr++) /* Search the pattern for a forward reference */ else if ((i = find_parens(cd, name, namelen, - (options & PCRE_EXTENDED) != 0)) > 0) + (options & PCRE_EXTENDED) != 0, utf8)) > 0) { PUT2(code, 2+LINK_SIZE, i); code[1+LINK_SIZE]++; @@ -5313,11 +5386,17 @@ for (;; ptr++) while ((cd->ctypes[*ptr] & ctype_word) != 0) ptr++; namelen = (int)(ptr - name); - /* In the pre-compile phase, do a syntax check and set a dummy - reference number. */ + /* In the pre-compile phase, do a syntax check. We used to just set + a dummy reference number, because it was not used in the first pass. + However, with the change of recursive back references to be atomic, + we have to look for the number so that this state can be identified, as + otherwise the incorrect length is computed. If it's not a backwards + reference, the dummy number will do. */ if (lengthptr != NULL) { + const uschar *temp; + if (namelen == 0) { *errorcodeptr = ERR62; @@ -5333,7 +5412,22 @@ for (;; ptr++) *errorcodeptr = ERR48; goto FAILED; } - recno = 0; + + /* The name table does not exist in the first pass, so we cannot + do a simple search as in the code below. Instead, we have to scan the + pattern to find the number. It is important that we scan it only as + far as we have got because the syntax of named subpatterns has not + been checked for the rest of the pattern, and find_parens() assumes + correct syntax. In any case, it's a waste of resources to scan + further. We stop the scan at the current point by temporarily + adjusting the value of cd->endpattern. */ + + temp = cd->end_pattern; + cd->end_pattern = ptr; + recno = find_parens(cd, name, namelen, + (options & PCRE_EXTENDED) != 0, utf8); + cd->end_pattern = temp; + if (recno < 0) recno = 0; /* Forward ref; set dummy number */ } /* In the real compile, seek the name in the table. We check the name @@ -5358,7 +5452,7 @@ for (;; ptr++) } else if ((recno = /* Forward back reference */ find_parens(cd, name, namelen, - (options & PCRE_EXTENDED) != 0)) <= 0) + (options & PCRE_EXTENDED) != 0, utf8)) <= 0) { *errorcodeptr = ERR15; goto FAILED; @@ -5469,7 +5563,7 @@ for (;; ptr++) if (called == NULL) { if (find_parens(cd, NULL, recno, - (options & PCRE_EXTENDED) != 0) < 0) + (options & PCRE_EXTENDED) != 0, utf8) < 0) { *errorcodeptr = ERR15; goto FAILED; @@ -6799,6 +6893,8 @@ while (ptr[skipatstart] == CHAR_LEFT_PARENTHESIS && { skipatstart += 7; options |= PCRE_UTF8; continue; } else if (strncmp((char *)(ptr+skipatstart+2), STRING_UCP_RIGHTPAR, 4) == 0) { skipatstart += 6; options |= PCRE_UCP; continue; } + else if (strncmp((char *)(ptr+skipatstart+2), STRING_NO_START_OPT_RIGHTPAR, 13) == 0) + { skipatstart += 15; options |= PCRE_NO_START_OPTIMIZE; continue; } if (strncmp((char *)(ptr+skipatstart+2), STRING_CR_RIGHTPAR, 3) == 0) { skipatstart += 5; newnl = PCRE_NEWLINE_CR; } diff --git a/harbour/src/3rd/pcre/pcredfa.c b/harbour/src/3rd/pcre/pcredfa.c index 3fdb0246e2..61603cbdf7 100644 --- a/harbour/src/3rd/pcre/pcredfa.c +++ b/harbour/src/3rd/pcre/pcredfa.c @@ -831,7 +831,12 @@ for (;;) /*-----------------------------------------------------------------*/ case OP_EOD: - if (ptr >= end_subject) { ADD_ACTIVE(state_offset + 1, 0); } + if (ptr >= end_subject) + { + if ((md->moptions & PCRE_PARTIAL_HARD) != 0) + could_continue = TRUE; + else { ADD_ACTIVE(state_offset + 1, 0); } + } break; /*-----------------------------------------------------------------*/ @@ -871,7 +876,9 @@ for (;;) /*-----------------------------------------------------------------*/ case OP_EODN: - if (clen == 0 || (IS_NEWLINE(ptr) && ptr == end_subject - md->nllen)) + if (clen == 0 && (md->moptions & PCRE_PARTIAL_HARD) != 0) + could_continue = TRUE; + else if (clen == 0 || (IS_NEWLINE(ptr) && ptr == end_subject - md->nllen)) { ADD_ACTIVE(state_offset + 1, 0); } break; @@ -879,7 +886,9 @@ for (;;) case OP_DOLL: if ((md->moptions & PCRE_NOTEOL) == 0) { - if (clen == 0 || + if (clen == 0 && (md->moptions & PCRE_PARTIAL_HARD) != 0) + could_continue = TRUE; + else if (clen == 0 || ((md->poptions & PCRE_DOLLAR_ENDONLY) == 0 && IS_NEWLINE(ptr) && ((ims & PCRE_MULTILINE) != 0 || ptr == end_subject - md->nllen) )) @@ -2744,8 +2753,8 @@ for (;;) ((md->moptions & PCRE_PARTIAL_SOFT) != 0 && /* Soft partial and */ match_count < 0) /* no matches */ ) && /* And... */ - ptr >= end_subject && /* Reached end of subject */ - ptr > current_subject) /* Matched non-empty string */ + ptr >= end_subject && /* Reached end of subject */ + ptr > md->start_used_ptr) /* Inspected non-empty string */ { if (offsetcount >= 2) { @@ -2835,6 +2844,7 @@ if (re == NULL || subject == NULL || workspace == NULL || (offsets == NULL && offsetcount > 0)) return PCRE_ERROR_NULL; if (offsetcount < 0) return PCRE_ERROR_BADCOUNT; if (wscount < 20) return PCRE_ERROR_DFA_WSSIZE; +if (start_offset < 0 || start_offset > length) return PCRE_ERROR_BADOFFSET; /* We need to find the pointer to any study data before we test for byte flipping, so we scan the extra_data block first. This may set two fields in the @@ -2953,16 +2963,14 @@ back the character offset. */ #ifdef SUPPORT_UTF8 if (utf8 && (options & PCRE_NO_UTF8_CHECK) == 0) { - if (_pcre_valid_utf8((uschar *)subject, length) >= 0) - return PCRE_ERROR_BADUTF8; + int tb; + if ((tb = _pcre_valid_utf8((uschar *)subject, length)) >= 0) + return (tb == length && (options & PCRE_PARTIAL_HARD) != 0)? + PCRE_ERROR_SHORTUTF8 : PCRE_ERROR_BADUTF8; if (start_offset > 0 && start_offset < length) { - int tb = ((uschar *)subject)[start_offset]; - if (tb > 127) - { - tb &= 0xc0; - if (tb != 0 && tb != 0xc0) return PCRE_ERROR_BADUTF8_OFFSET; - } + tb = ((USPTR)subject)[start_offset] & 0xc0; + if (tb == 0x80) return PCRE_ERROR_BADUTF8_OFFSET; } } #endif @@ -3049,9 +3057,11 @@ for (;;) /* There are some optimizations that avoid running the match if a known starting point is not found. However, there is an option that disables - these, for testing and for ensuring that all callouts do actually occur. */ + these, for testing and for ensuring that all callouts do actually occur. + The option can be set in the regex by (*NO_START_OPT) or passed in + match-time options. */ - if ((options & PCRE_NO_START_OPTIMIZE) == 0) + if (((options | re->options) & PCRE_NO_START_OPTIMIZE) == 0) { /* Advance to a known first byte. */ diff --git a/harbour/src/3rd/pcre/pcreexec.c b/harbour/src/3rd/pcre/pcreexec.c index 14299d0359..e2cc68a296 100644 --- a/harbour/src/3rd/pcre/pcreexec.c +++ b/harbour/src/3rd/pcre/pcreexec.c @@ -294,7 +294,7 @@ argument of match(), which never changes. */ #define RMATCH(ra,rb,rc,rd,re,rf,rg,rw)\ {\ - heapframe *newframe = (pcre_stack_malloc)(sizeof(heapframe));\ + heapframe *newframe = (heapframe *)(pcre_stack_malloc)(sizeof(heapframe));\ if (newframe == NULL) RRETURN(PCRE_ERROR_NOMEMORY);\ frame->Xwhere = rw; \ newframe->Xeptr = ra;\ @@ -422,17 +422,18 @@ immediately. The second one is used when we already know we are past the end of the subject. */ #define CHECK_PARTIAL()\ - if (md->partial != 0 && eptr >= md->end_subject && eptr > mstart)\ - {\ - md->hitend = TRUE;\ - if (md->partial > 1) MRRETURN(PCRE_ERROR_PARTIAL);\ + if (md->partial != 0 && eptr >= md->end_subject && \ + eptr > md->start_used_ptr) \ + { \ + md->hitend = TRUE; \ + if (md->partial > 1) MRRETURN(PCRE_ERROR_PARTIAL); \ } #define SCHECK_PARTIAL()\ - if (md->partial != 0 && eptr > mstart)\ - {\ - md->hitend = TRUE;\ - if (md->partial > 1) MRRETURN(PCRE_ERROR_PARTIAL);\ + if (md->partial != 0 && eptr > md->start_used_ptr) \ + { \ + md->hitend = TRUE; \ + if (md->partial > 1) MRRETURN(PCRE_ERROR_PARTIAL); \ } @@ -488,7 +489,7 @@ heap storage. Set up the top-level frame here; others are obtained from the heap whenever RMATCH() does a "recursion". See the macro definitions above. */ #ifdef NO_RECURSE -heapframe *frame = (pcre_stack_malloc)(sizeof(heapframe)); +heapframe *frame = (heapframe *)(pcre_stack_malloc)(sizeof(heapframe)); if (frame == NULL) RRETURN(PCRE_ERROR_NOMEMORY); frame->Xprevframe = NULL; /* Marks the top level */ @@ -710,36 +711,47 @@ for (;;) case OP_FAIL: MRRETURN(MATCH_NOMATCH); + /* COMMIT overrides PRUNE, SKIP, and THEN */ + case OP_COMMIT: RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, ims, eptrb, flags, RM52); - if (rrc != MATCH_NOMATCH) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && + rrc != MATCH_SKIP && rrc != MATCH_SKIP_ARG && + rrc != MATCH_THEN) + RRETURN(rrc); MRRETURN(MATCH_COMMIT); + /* PRUNE overrides THEN */ + case OP_PRUNE: RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, ims, eptrb, flags, RM51); - if (rrc != MATCH_NOMATCH) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); MRRETURN(MATCH_PRUNE); case OP_PRUNE_ARG: RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top, md, ims, eptrb, flags, RM56); - if (rrc != MATCH_NOMATCH) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); md->mark = ecode + 2; RRETURN(MATCH_PRUNE); + /* SKIP overrides PRUNE and THEN */ + case OP_SKIP: RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, ims, eptrb, flags, RM53); - if (rrc != MATCH_NOMATCH) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN) + RRETURN(rrc); md->start_match_ptr = eptr; /* Pass back current position */ MRRETURN(MATCH_SKIP); case OP_SKIP_ARG: RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top, md, ims, eptrb, flags, RM57); - if (rrc != MATCH_NOMATCH) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN) + RRETURN(rrc); /* Pass back the current skip name by overloading md->start_match_ptr and returning the special MATCH_SKIP_ARG return code. This will either be @@ -749,17 +761,24 @@ for (;;) md->start_match_ptr = ecode + 2; RRETURN(MATCH_SKIP_ARG); + /* For THEN (and THEN_ARG) we pass back the address of the bracket or + the alt that is at the start of the current branch. This makes it possible + to skip back past alternatives that precede the THEN within the current + branch. */ + case OP_THEN: RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, ims, eptrb, flags, RM54); if (rrc != MATCH_NOMATCH) RRETURN(rrc); + md->start_match_ptr = ecode - GET(ecode, 1); MRRETURN(MATCH_THEN); case OP_THEN_ARG: - RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1], offset_top, md, - ims, eptrb, flags, RM58); + RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode] + ecode[1+LINK_SIZE], + offset_top, md, ims, eptrb, flags, RM58); if (rrc != MATCH_NOMATCH) RRETURN(rrc); - md->mark = ecode + 2; + md->start_match_ptr = ecode - GET(ecode, 1); + md->mark = ecode + LINK_SIZE + 2; RRETURN(MATCH_THEN); /* Handle a capturing bracket. If there is space in the offset vector, save @@ -804,7 +823,9 @@ for (;;) { RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, ims, eptrb, flags, RM1); - if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) + RRETURN(rrc); md->capture_last = save_capture_last; ecode += GET(ecode, 1); } @@ -865,7 +886,9 @@ for (;;) RMATCH(eptr, ecode + _pcre_OP_lengths[*ecode], offset_top, md, ims, eptrb, flags, RM2); - if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) + RRETURN(rrc); ecode += GET(ecode, 1); } /* Control never reaches here. */ @@ -1066,7 +1089,8 @@ for (;;) ecode += 1 + LINK_SIZE + GET(ecode, LINK_SIZE + 2); while (*ecode == OP_ALT) ecode += GET(ecode, 1); } - else if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) + else if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) { RRETURN(rrc); /* Need braces because of following else */ } @@ -1194,7 +1218,9 @@ for (;;) mstart = md->start_match_ptr; /* In case \K reset it */ break; } - if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) + RRETURN(rrc); ecode += GET(ecode, 1); } while (*ecode == OP_ALT); @@ -1228,7 +1254,9 @@ for (;;) do ecode += GET(ecode,1); while (*ecode == OP_ALT); break; } - if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) + RRETURN(rrc); ecode += GET(ecode,1); } while (*ecode == OP_ALT); @@ -1365,7 +1393,8 @@ for (;;) (pcre_free)(new_recursive.offset_save); MRRETURN(MATCH_MATCH); } - else if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) + else if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) { DPRINTF(("Recursion gave error %d\n", rrc)); if (new_recursive.offset_save != stacksave) @@ -1408,7 +1437,9 @@ for (;;) mstart = md->start_match_ptr; break; } - if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc); + if (rrc != MATCH_NOMATCH && + (rrc != MATCH_THEN || md->start_match_ptr != ecode)) + RRETURN(rrc); ecode += GET(ecode,1); } while (*ecode == OP_ALT); @@ -1674,37 +1705,40 @@ for (;;) if (eptr < md->end_subject) { if (!IS_NEWLINE(eptr)) MRRETURN(MATCH_NOMATCH); } else - { if (md->noteol) MRRETURN(MATCH_NOMATCH); } + { + if (md->noteol) MRRETURN(MATCH_NOMATCH); + SCHECK_PARTIAL(); + } ecode++; break; } - else + else /* Not multiline */ { if (md->noteol) MRRETURN(MATCH_NOMATCH); - if (!md->endonly) - { - if (eptr != md->end_subject && - (!IS_NEWLINE(eptr) || eptr != md->end_subject - md->nllen)) - MRRETURN(MATCH_NOMATCH); - ecode++; - break; - } + if (!md->endonly) goto ASSERT_NL_OR_EOS; } + /* ... else fall through for endonly */ /* End of subject assertion (\z) */ case OP_EOD: if (eptr < md->end_subject) MRRETURN(MATCH_NOMATCH); + SCHECK_PARTIAL(); ecode++; break; /* End of subject or ending \n assertion (\Z) */ case OP_EODN: - if (eptr != md->end_subject && + ASSERT_NL_OR_EOS: + if (eptr < md->end_subject && (!IS_NEWLINE(eptr) || eptr != md->end_subject - md->nllen)) MRRETURN(MATCH_NOMATCH); + + /* Either at end of string or \n before end. */ + + SCHECK_PARTIAL(); ecode++; break; @@ -5600,6 +5634,7 @@ if ((options & ~PUBLIC_EXEC_OPTIONS) != 0) return PCRE_ERROR_BADOPTION; if (re == NULL || subject == NULL || (offsets == NULL && offsetcount > 0)) return PCRE_ERROR_NULL; if (offsetcount < 0) return PCRE_ERROR_BADCOUNT; +if (start_offset < 0 || start_offset > length) return PCRE_ERROR_BADOFFSET; /* This information is for finding all the numbers associated with a given name, for condition testing. */ @@ -5766,16 +5801,14 @@ back the character offset. */ #ifdef SUPPORT_UTF8 if (utf8 && (options & PCRE_NO_UTF8_CHECK) == 0) { - if (_pcre_valid_utf8((USPTR)subject, length) >= 0) - return PCRE_ERROR_BADUTF8; + int tb; + if ((tb = _pcre_valid_utf8((USPTR)subject, length)) >= 0) + return (tb == length && md->partial > 1)? + PCRE_ERROR_SHORTUTF8 : PCRE_ERROR_BADUTF8; if (start_offset > 0 && start_offset < length) { - int tb = ((USPTR)subject)[start_offset]; - if (tb > 127) - { - tb &= 0xc0; - if (tb != 0 && tb != 0xc0) return PCRE_ERROR_BADUTF8_OFFSET; - } + tb = ((USPTR)subject)[start_offset] & 0xc0; + if (tb == 0x80) return PCRE_ERROR_BADUTF8_OFFSET; } } #endif @@ -5903,9 +5936,10 @@ for(;;) /* There are some optimizations that avoid running the match if a known starting point is not found, or if a known later character is not present. However, there is an option that disables these, for testing and for ensuring - that all callouts do actually occur. */ + that all callouts do actually occur. The option can be set in the regex by + (*NO_START_OPT) or passed in match-time options. */ - if ((options & PCRE_NO_START_OPTIMIZE) == 0) + if (((options | re->options) & PCRE_NO_START_OPTIMIZE) == 0) { /* Advance to a unique first byte if there is one. */ diff --git a/harbour/src/3rd/pcre/pcreinal.h b/harbour/src/3rd/pcre/pcreinal.h index e293602fe6..5f736d13ac 100644 --- a/harbour/src/3rd/pcre/pcreinal.h +++ b/harbour/src/3rd/pcre/pcreinal.h @@ -408,9 +408,10 @@ capturing parenthesis numbers in back references. */ /* When UTF-8 encoding is being used, a character is no longer just a single byte. The macros for character handling generate simple sequences when used in -byte-mode, and more complicated ones for UTF-8 characters. BACKCHAR should -never be called in byte mode. To make sure it can never even appear when UTF-8 -support is omitted, we don't even define it. */ +byte-mode, and more complicated ones for UTF-8 characters. GETCHARLENTEST is +not used when UTF-8 is not supported, so it is not defined, and BACKCHAR should +never be called in byte mode. To make sure they can never even appear when +UTF-8 support is omitted, we don't even define them. */ #ifndef SUPPORT_UTF8 #define GETCHAR(c, eptr) c = *eptr; @@ -418,43 +419,83 @@ support is omitted, we don't even define it. */ #define GETCHARINC(c, eptr) c = *eptr++; #define GETCHARINCTEST(c, eptr) c = *eptr++; #define GETCHARLEN(c, eptr, len) c = *eptr; +/* #define GETCHARLENTEST(c, eptr, len) */ /* #define BACKCHAR(eptr) */ #else /* SUPPORT_UTF8 */ +/* These macros were originally written in the form of loops that used data +from the tables whose names start with _pcre_utf8_table. They were rewritten by +a user so as not to use loops, because in some environments this gives a +significant performance advantage, and it seems never to do any harm. */ + +/* Base macro to pick up the remaining bytes of a UTF-8 character, not +advancing the pointer. */ + +#define GETUTF8(c, eptr) \ + { \ + if ((c & 0x20) == 0) \ + c = ((c & 0x1f) << 6) | (eptr[1] & 0x3f); \ + else if ((c & 0x10) == 0) \ + c = ((c & 0x0f) << 12) | ((eptr[1] & 0x3f) << 6) | (eptr[2] & 0x3f); \ + else if ((c & 0x08) == 0) \ + c = ((c & 0x07) << 18) | ((eptr[1] & 0x3f) << 12) | \ + ((eptr[2] & 0x3f) << 6) | (eptr[3] & 0x3f); \ + else if ((c & 0x04) == 0) \ + c = ((c & 0x03) << 24) | ((eptr[1] & 0x3f) << 18) | \ + ((eptr[2] & 0x3f) << 12) | ((eptr[3] & 0x3f) << 6) | \ + (eptr[4] & 0x3f); \ + else \ + c = ((c & 0x01) << 30) | ((eptr[1] & 0x3f) << 24) | \ + ((eptr[2] & 0x3f) << 18) | ((eptr[3] & 0x3f) << 12) | \ + ((eptr[4] & 0x3f) << 6) | (eptr[5] & 0x3f); \ + } + /* Get the next UTF-8 character, not advancing the pointer. This is called when we know we are in UTF-8 mode. */ #define GETCHAR(c, eptr) \ c = *eptr; \ - if (c >= 0xc0) \ - { \ - int gcii; \ - int gcaa = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ \ - int gcss = 6*gcaa; \ - c = (c & _pcre_utf8_table3[gcaa]) << gcss; \ - for (gcii = 1; gcii <= gcaa; gcii++) \ - { \ - gcss -= 6; \ - c |= (eptr[gcii] & 0x3f) << gcss; \ - } \ - } + if (c >= 0xc0) GETUTF8(c, eptr); /* Get the next UTF-8 character, testing for UTF-8 mode, and not advancing the pointer. */ #define GETCHARTEST(c, eptr) \ c = *eptr; \ - if (utf8 && c >= 0xc0) \ + if (utf8 && c >= 0xc0) GETUTF8(c, eptr); + +/* Base macro to pick up the remaining bytes of a UTF-8 character, advancing +the pointer. */ + +#define GETUTF8INC(c, eptr) \ { \ - int gcii; \ - int gcaa = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ \ - int gcss = 6*gcaa; \ - c = (c & _pcre_utf8_table3[gcaa]) << gcss; \ - for (gcii = 1; gcii <= gcaa; gcii++) \ + if ((c & 0x20) == 0) \ + c = ((c & 0x1f) << 6) | (*eptr++ & 0x3f); \ + else if ((c & 0x10) == 0) \ { \ - gcss -= 6; \ - c |= (eptr[gcii] & 0x3f) << gcss; \ + c = ((c & 0x0f) << 12) | ((*eptr & 0x3f) << 6) | (eptr[1] & 0x3f); \ + eptr += 2; \ + } \ + else if ((c & 0x08) == 0) \ + { \ + c = ((c & 0x07) << 18) | ((*eptr & 0x3f) << 12) | \ + ((eptr[1] & 0x3f) << 6) | (eptr[2] & 0x3f); \ + eptr += 3; \ + } \ + else if ((c & 0x04) == 0) \ + { \ + c = ((c & 0x03) << 24) | ((*eptr & 0x3f) << 18) | \ + ((eptr[1] & 0x3f) << 12) | ((eptr[2] & 0x3f) << 6) | \ + (eptr[3] & 0x3f); \ + eptr += 4; \ + } \ + else \ + { \ + c = ((c & 0x01) << 30) | ((*eptr & 0x3f) << 24) | \ + ((eptr[1] & 0x3f) << 18) | ((eptr[2] & 0x3f) << 12) | \ + ((eptr[3] & 0x3f) << 6) | (eptr[4] & 0x3f); \ + eptr += 5; \ } \ } @@ -463,32 +504,49 @@ know we are in UTF-8 mode. */ #define GETCHARINC(c, eptr) \ c = *eptr++; \ - if (c >= 0xc0) \ - { \ - int gcaa = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ \ - int gcss = 6*gcaa; \ - c = (c & _pcre_utf8_table3[gcaa]) << gcss; \ - while (gcaa-- > 0) \ - { \ - gcss -= 6; \ - c |= (*eptr++ & 0x3f) << gcss; \ - } \ - } + if (c >= 0xc0) GETUTF8INC(c, eptr); /* Get the next character, testing for UTF-8 mode, and advancing the pointer. This is called when we don't know if we are in UTF-8 mode. */ #define GETCHARINCTEST(c, eptr) \ c = *eptr++; \ - if (utf8 && c >= 0xc0) \ + if (utf8 && c >= 0xc0) GETUTF8INC(c, eptr); + +/* Base macro to pick up the remaining bytes of a UTF-8 character, not +advancing the pointer, incrementing the length. */ + +#define GETUTF8LEN(c, eptr, len) \ { \ - int gcaa = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ \ - int gcss = 6*gcaa; \ - c = (c & _pcre_utf8_table3[gcaa]) << gcss; \ - while (gcaa-- > 0) \ + if ((c & 0x20) == 0) \ { \ - gcss -= 6; \ - c |= (*eptr++ & 0x3f) << gcss; \ + c = ((c & 0x1f) << 6) | (eptr[1] & 0x3f); \ + len++; \ + } \ + else if ((c & 0x10) == 0) \ + { \ + c = ((c & 0x0f) << 12) | ((eptr[1] & 0x3f) << 6) | (eptr[2] & 0x3f); \ + len += 2; \ + } \ + else if ((c & 0x08) == 0) \ + {\ + c = ((c & 0x07) << 18) | ((eptr[1] & 0x3f) << 12) | \ + ((eptr[2] & 0x3f) << 6) | (eptr[3] & 0x3f); \ + len += 3; \ + } \ + else if ((c & 0x04) == 0) \ + { \ + c = ((c & 0x03) << 24) | ((eptr[1] & 0x3f) << 18) | \ + ((eptr[2] & 0x3f) << 12) | ((eptr[3] & 0x3f) << 6) | \ + (eptr[4] & 0x3f); \ + len += 4; \ + } \ + else \ + {\ + c = ((c & 0x01) << 30) | ((eptr[1] & 0x3f) << 24) | \ + ((eptr[2] & 0x3f) << 18) | ((eptr[3] & 0x3f) << 12) | \ + ((eptr[4] & 0x3f) << 6) | (eptr[5] & 0x3f); \ + len += 5; \ } \ } @@ -497,19 +555,7 @@ if there are extra bytes. This is called when we know we are in UTF-8 mode. */ #define GETCHARLEN(c, eptr, len) \ c = *eptr; \ - if (c >= 0xc0) \ - { \ - int gcii; \ - int gcaa = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ \ - int gcss = 6*gcaa; \ - c = (c & _pcre_utf8_table3[gcaa]) << gcss; \ - for (gcii = 1; gcii <= gcaa; gcii++) \ - { \ - gcss -= 6; \ - c |= (eptr[gcii] & 0x3f) << gcss; \ - } \ - len += gcaa; \ - } + if (c >= 0xc0) GETUTF8LEN(c, eptr, len); /* Get the next UTF-8 character, testing for UTF-8 mode, not advancing the pointer, incrementing length if there are extra bytes. This is called when we @@ -517,19 +563,7 @@ do not know if we are in UTF-8 mode. */ #define GETCHARLENTEST(c, eptr, len) \ c = *eptr; \ - if (utf8 && c >= 0xc0) \ - { \ - int gcii; \ - int gcaa = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ \ - int gcss = 6*gcaa; \ - c = (c & _pcre_utf8_table3[gcaa]) << gcss; \ - for (gcii = 1; gcii <= gcaa; gcii++) \ - { \ - gcss -= 6; \ - c |= (eptr[gcii] & 0x3f) << gcss; \ - } \ - len += gcaa; \ - } + if (utf8 && c >= 0xc0) GETUTF8LEN(c, eptr, len); /* If the pointer is not at the start of a character, move it back until it is. This is called only in UTF-8 mode - we don't put a test within the macro @@ -537,7 +571,7 @@ because almost all calls are already within a block of UTF-8 only code. */ #define BACKCHAR(eptr) while((*eptr & 0xc0) == 0x80) eptr-- -#endif +#endif /* SUPPORT_UTF8 */ /* In case there is no definition of offsetof() provided - though any proper @@ -581,7 +615,7 @@ time, run time, or study time, respectively. */ PCRE_DOTALL|PCRE_DOLLAR_ENDONLY|PCRE_EXTRA|PCRE_UNGREEDY|PCRE_UTF8| \ PCRE_NO_AUTO_CAPTURE|PCRE_NO_UTF8_CHECK|PCRE_AUTO_CALLOUT|PCRE_FIRSTLINE| \ PCRE_DUPNAMES|PCRE_NEWLINE_BITS|PCRE_BSR_ANYCRLF|PCRE_BSR_UNICODE| \ - PCRE_JAVASCRIPT_COMPAT|PCRE_UCP) + PCRE_JAVASCRIPT_COMPAT|PCRE_UCP|PCRE_NO_START_OPTIMIZE) #define PUBLIC_EXEC_OPTIONS \ (PCRE_ANCHORED|PCRE_NOTBOL|PCRE_NOTEOL|PCRE_NOTEMPTY|PCRE_NOTEMPTY_ATSTART| \ @@ -898,15 +932,16 @@ so that PCRE works on both ASCII and EBCDIC platforms, in non-UTF-mode only. */ #define STRING_DEFINE "DEFINE" -#define STRING_CR_RIGHTPAR "CR)" -#define STRING_LF_RIGHTPAR "LF)" -#define STRING_CRLF_RIGHTPAR "CRLF)" -#define STRING_ANY_RIGHTPAR "ANY)" -#define STRING_ANYCRLF_RIGHTPAR "ANYCRLF)" -#define STRING_BSR_ANYCRLF_RIGHTPAR "BSR_ANYCRLF)" -#define STRING_BSR_UNICODE_RIGHTPAR "BSR_UNICODE)" -#define STRING_UTF8_RIGHTPAR "UTF8)" -#define STRING_UCP_RIGHTPAR "UCP)" +#define STRING_CR_RIGHTPAR "CR)" +#define STRING_LF_RIGHTPAR "LF)" +#define STRING_CRLF_RIGHTPAR "CRLF)" +#define STRING_ANY_RIGHTPAR "ANY)" +#define STRING_ANYCRLF_RIGHTPAR "ANYCRLF)" +#define STRING_BSR_ANYCRLF_RIGHTPAR "BSR_ANYCRLF)" +#define STRING_BSR_UNICODE_RIGHTPAR "BSR_UNICODE)" +#define STRING_UTF8_RIGHTPAR "UTF8)" +#define STRING_UCP_RIGHTPAR "UCP)" +#define STRING_NO_START_OPT_RIGHTPAR "NO_START_OPT)" #else /* SUPPORT_UTF8 */ @@ -1152,15 +1187,16 @@ only. */ #define STRING_DEFINE STR_D STR_E STR_F STR_I STR_N STR_E -#define STRING_CR_RIGHTPAR STR_C STR_R STR_RIGHT_PARENTHESIS -#define STRING_LF_RIGHTPAR STR_L STR_F STR_RIGHT_PARENTHESIS -#define STRING_CRLF_RIGHTPAR STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS -#define STRING_ANY_RIGHTPAR STR_A STR_N STR_Y STR_RIGHT_PARENTHESIS -#define STRING_ANYCRLF_RIGHTPAR STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS -#define STRING_BSR_ANYCRLF_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS -#define STRING_BSR_UNICODE_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_U STR_N STR_I STR_C STR_O STR_D STR_E STR_RIGHT_PARENTHESIS -#define STRING_UTF8_RIGHTPAR STR_U STR_T STR_F STR_8 STR_RIGHT_PARENTHESIS -#define STRING_UCP_RIGHTPAR STR_U STR_C STR_P STR_RIGHT_PARENTHESIS +#define STRING_CR_RIGHTPAR STR_C STR_R STR_RIGHT_PARENTHESIS +#define STRING_LF_RIGHTPAR STR_L STR_F STR_RIGHT_PARENTHESIS +#define STRING_CRLF_RIGHTPAR STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS +#define STRING_ANY_RIGHTPAR STR_A STR_N STR_Y STR_RIGHT_PARENTHESIS +#define STRING_ANYCRLF_RIGHTPAR STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS +#define STRING_BSR_ANYCRLF_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS +#define STRING_BSR_UNICODE_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_U STR_N STR_I STR_C STR_O STR_D STR_E STR_RIGHT_PARENTHESIS +#define STRING_UTF8_RIGHTPAR STR_U STR_T STR_F STR_8 STR_RIGHT_PARENTHESIS +#define STRING_UCP_RIGHTPAR STR_U STR_C STR_P STR_RIGHT_PARENTHESIS +#define STRING_NO_START_OPT_RIGHTPAR STR_N STR_O STR_UNDERSCORE STR_S STR_T STR_A STR_R STR_T STR_UNDERSCORE STR_O STR_P STR_T STR_RIGHT_PARENTHESIS #endif /* SUPPORT_UTF8 */ @@ -1514,8 +1550,9 @@ in UTF-8 mode. The code that uses this table must know about such things. */ 3, 3, /* RREF, NRREF */ \ 1, /* DEF */ \ 1, 1, /* BRAZERO, BRAMINZERO */ \ - 3, 1, 3, /* MARK, PRUNE, PRUNE_ARG, */ \ - 1, 3, 1, 3, /* SKIP, SKIP_ARG, THEN, THEN_ARG, */ \ + 3, 1, 3, /* MARK, PRUNE, PRUNE_ARG */ \ + 1, 3, /* SKIP, SKIP_ARG */ \ + 1+LINK_SIZE, 3+LINK_SIZE, /* THEN, THEN_ARG */ \ 1, 1, 1, 3, 1 /* COMMIT, FAIL, ACCEPT, CLOSE, SKIPZERO */ @@ -1534,7 +1571,8 @@ enum { ERR0, ERR1, ERR2, ERR3, ERR4, ERR5, ERR6, ERR7, ERR8, ERR9, ERR30, ERR31, ERR32, ERR33, ERR34, ERR35, ERR36, ERR37, ERR38, ERR39, ERR40, ERR41, ERR42, ERR43, ERR44, ERR45, ERR46, ERR47, ERR48, ERR49, ERR50, ERR51, ERR52, ERR53, ERR54, ERR55, ERR56, ERR57, ERR58, ERR59, - ERR60, ERR61, ERR62, ERR63, ERR64, ERR65, ERR66, ERR67, ERRCOUNT }; + ERR60, ERR61, ERR62, ERR63, ERR64, ERR65, ERR66, ERR67, ERR68, + ERRCOUNT }; /* The real format of the start of the pcre block; the index of names and the code vector run on as long as necessary after the end. We store an explicit diff --git a/harbour/src/3rd/pcre/pcreprni.h b/harbour/src/3rd/pcre/pcreprni.h index 49d93174cc..c7d8629477 100644 --- a/harbour/src/3rd/pcre/pcreprni.h +++ b/harbour/src/3rd/pcre/pcreprni.h @@ -537,11 +537,26 @@ for(;;) case OP_MARK: case OP_PRUNE_ARG: case OP_SKIP_ARG: - case OP_THEN_ARG: fprintf(f, " %s %s", OP_names[*code], code + 2); extra += code[1]; break; + case OP_THEN: + if (print_lengths) + fprintf(f, " %s %d", OP_names[*code], GET(code, 1)); + else + fprintf(f, " %s", OP_names[*code]); + break; + + case OP_THEN_ARG: + if (print_lengths) + fprintf(f, " %s %d %s", OP_names[*code], GET(code, 1), + code + 2 + LINK_SIZE); + else + fprintf(f, " %s %s", OP_names[*code], code + 2 + LINK_SIZE); + extra += code[1+LINK_SIZE]; + break; + /* Anything else is just an item with no data*/ default: diff --git a/harbour/src/3rd/pcre/pcrestud.c b/harbour/src/3rd/pcre/pcrestud.c index 54e65ad98c..7acdb5deb4 100644 --- a/harbour/src/3rd/pcre/pcrestud.c +++ b/harbour/src/3rd/pcre/pcrestud.c @@ -419,10 +419,13 @@ for (;;) case OP_MARK: case OP_PRUNE_ARG: case OP_SKIP_ARG: - case OP_THEN_ARG: cc += _pcre_OP_lengths[op] + cc[1]; break; + case OP_THEN_ARG: + cc += _pcre_OP_lengths[op] + cc[1+LINK_SIZE]; + break; + /* For the record, these are the opcodes that are matched by "default": OP_ACCEPT, OP_CLOSE, OP_COMMIT, OP_FAIL, OP_PRUNE, OP_SET_SOM, OP_SKIP, OP_THEN. */ diff --git a/harbour/src/3rd/pcre/pcrevutf.c b/harbour/src/3rd/pcre/pcrevutf.c index e74ad42457..dcc9660fb5 100644 --- a/harbour/src/3rd/pcre/pcrevutf.c +++ b/harbour/src/3rd/pcre/pcrevutf.c @@ -72,6 +72,20 @@ Arguments: Returns: < 0 if the string is a valid UTF-8 string >= 0 otherwise; the value is the offset of the bad byte + +Bad bytes can be: + + . An isolated byte whose most significant bits are 0x80, because this + can only correctly appear within a UTF-8 character; + + . A byte whose most significant bits are 0xc0, but whose other bits indicate + that there are more than 3 additional bytes (i.e. an RFC 2279 starting + byte, which is no longer valid under RFC 3629); + + . + +The returned offset may also be equal to the length of the string; this means +that one or more bytes is missing from the final UTF-8 character. */ int @@ -93,7 +107,8 @@ for (p = string; length-- > 0; p++) if (c < 128) continue; if (c < 0xc0) return p - string; ab = _pcre_utf8_table4[c & 0x3f]; /* Number of additional bytes */ - if (length < ab || ab > 3) return p - string; + if (ab > 3) return p - string; /* Too many for RFC 3629 */ + if (length < ab) return p + 1 + length - string; /* Missing bytes */ length -= ab; /* Check top bits in the second byte */ diff --git a/harbour/src/3rd/png/LICENSE b/harbour/src/3rd/png/LICENSE index 756ebd0457..734398fc5d 100644 --- a/harbour/src/3rd/png/LICENSE +++ b/harbour/src/3rd/png/LICENSE @@ -10,7 +10,7 @@ this sentence. This code is released under the libpng license. -libpng versions 1.2.6, August 15, 2004, through 1.4.4, September 23, 2010, are +libpng versions 1.2.6, August 15, 2004, through 1.4.5, December 9, 2010, are Copyright (c) 2004, 2006-2010 Glenn Randers-Pehrson, and are distributed according to the same disclaimer and license as libpng-1.2.5 with the following individual added to the list of Contributing Authors @@ -108,4 +108,4 @@ certification mark of the Open Source Initiative. Glenn Randers-Pehrson glennrp at users.sourceforge.net -September 23, 2010 +December 9, 2010 diff --git a/harbour/src/3rd/png/Makefile b/harbour/src/3rd/png/Makefile index 48e8d5155a..6fd6bafdd8 100644 --- a/harbour/src/3rd/png/Makefile +++ b/harbour/src/3rd/png/Makefile @@ -72,8 +72,8 @@ else endif # ORIGIN http://www.libpng.org/pub/png/libpng.html -# VER 1.4.4 -# URL http://sourceforge.net/projects/libpng/files/01-libpng-master/1.4.4/lpng144.zip/download +# VER 1.4.5 +# URL http://sourceforge.net/projects/libpng/files/libpng14/1.4.5/lpng145.zip/download # DIFF # # MAP LICENSE diff --git a/harbour/src/3rd/png/png.c b/harbour/src/3rd/png/png.c index f2e5888fa0..00d258dffa 100644 --- a/harbour/src/3rd/png/png.c +++ b/harbour/src/3rd/png/png.c @@ -17,11 +17,7 @@ #include "pngpriv.h" /* Generate a compiler error if there is an old png.h in the search path. */ -typedef version_1_4_4 Your_png_h_is_not_version_1_4_4; - -/* Version information for C files. This had better match the version - * string defined in png.h. - */ +typedef version_1_4_5 Your_png_h_is_not_version_1_4_5; /* Tells libpng that we have already handled the first "num_bytes" bytes * of the PNG file signature. If the PNG data is embedded into another @@ -551,13 +547,13 @@ png_get_copyright(png_structp png_ptr) #else #ifdef __STDC__ return ((png_charp) PNG_STRING_NEWLINE \ - "libpng version 1.4.4 - September 23, 2010" PNG_STRING_NEWLINE \ + "libpng version 1.4.5 - December 9, 2010" PNG_STRING_NEWLINE \ "Copyright (c) 1998-2010 Glenn Randers-Pehrson" PNG_STRING_NEWLINE \ "Copyright (c) 1996-1997 Andreas Dilger" PNG_STRING_NEWLINE \ "Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc." \ PNG_STRING_NEWLINE); #else - return ((png_charp) "libpng version 1.4.4 - September 23, 2010\ + return ((png_charp) "libpng version 1.4.5 - December 9, 2010\ Copyright (c) 1998-2010 Glenn Randers-Pehrson\ Copyright (c) 1996-1997 Andreas Dilger\ Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc."); @@ -678,7 +674,7 @@ png_convert_size(size_t size) */ void /* PRIVATE */ -png_64bit_product (long v1, long v2, unsigned long *hi_product, +png_64bit_product(long v1, long v2, unsigned long *hi_product, unsigned long *lo_product) { int a, b, c, d; diff --git a/harbour/src/3rd/png/png.h b/harbour/src/3rd/png/png.h index 805be120f5..b1f1bc364e 100644 --- a/harbour/src/3rd/png/png.h +++ b/harbour/src/3rd/png/png.h @@ -1,7 +1,7 @@ /* png.h - header file for PNG reference library * - * libpng version 1.4.4 - September 23, 2010 + * libpng version 1.4.5 - December 9, 2010 * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -11,7 +11,7 @@ * Authors and maintainers: * libpng versions 0.71, May 1995, through 0.88, January 1996: Guy Schalnat * libpng versions 0.89c, June 1996, through 0.96, May 1997: Andreas Dilger - * libpng versions 0.97, January 1998, through 1.4.4 - September 23, 2010: Glenn + * libpng versions 0.97, January 1998, through 1.4.5 - December 9, 2010: Glenn * See also "Contributing Authors", below. * * Note about libpng version numbers: @@ -146,7 +146,13 @@ * 1.4.3rc01-03 14 10403 14.so.14.3[.0] * 1.4.3 14 10403 14.so.14.3[.0] * 1.4.4beta01-08 14 10404 14.so.14.4[.0] - * 1.4.4rc01-06 14 10404 14.so.14.4[.0] + * 1.4.4rc01-05 14 10404 14.so.14.4[.0] + * 1.4.4 14 10404 14.so.14.4[.0] + * 1.4.5beta01-04 14 10405 14.so.14.5[.0] + * 1.4.5rc01 14 10405 14.so.14.5[.0] + * 1.4.5beta05-07 14 10405 14.so.14.5[.0] + * 1.4.5rc02-03 14 10405 14.so.14.5[.0] + * 1.4.5 14 10405 14.so.14.5[.0] * * Henceforth the source version will match the shared-library major * and minor numbers; the shared-library major version number will be @@ -178,7 +184,7 @@ * * This code is released under the libpng license. * - * libpng versions 1.2.6, August 15, 2004, through 1.4.4, September 23, 2010, are + * libpng versions 1.2.6, August 15, 2004, through 1.4.5, December 9, 2010, are * Copyright (c) 2004, 2006-2010 Glenn Randers-Pehrson, and are * distributed according to the same disclaimer and license as libpng-1.2.5 * with the following individual added to the list of Contributing Authors: @@ -290,13 +296,13 @@ * Y2K compliance in libpng: * ========================= * - * September 23, 2010 + * December 9, 2010 * * Since the PNG Development group is an ad-hoc body, we can't make * an official declaration. * * This is your unofficial assurance that libpng from version 0.71 and - * upward through 1.4.4 are Y2K compliant. It is my belief that earlier + * upward through 1.4.5 are Y2K compliant. It is my belief that earlier * versions were also Y2K compliant. * * Libpng only has three year fields. One is a 2-byte unsigned integer @@ -352,9 +358,9 @@ */ /* Version information for png.h - this should match the version in png.c */ -#define PNG_LIBPNG_VER_STRING "1.4.4" +#define PNG_LIBPNG_VER_STRING "1.4.5" #define PNG_HEADER_VERSION_STRING \ - " libpng version 1.4.4 - September 23, 2010\n" + " libpng version 1.4.5 - December 9, 2010\n" #define PNG_LIBPNG_VER_SONUM 14 #define PNG_LIBPNG_VER_DLLNUM 14 @@ -362,7 +368,7 @@ /* These should match the first 3 components of PNG_LIBPNG_VER_STRING: */ #define PNG_LIBPNG_VER_MAJOR 1 #define PNG_LIBPNG_VER_MINOR 4 -#define PNG_LIBPNG_VER_RELEASE 4 +#define PNG_LIBPNG_VER_RELEASE 5 /* This should match the numeric part of the final component of * PNG_LIBPNG_VER_STRING, omitting any leading zero: */ @@ -392,7 +398,7 @@ * version 1.0.0 was mis-numbered 100 instead of 10000). From * version 1.0.1 it's xxyyzz, where x=major, y=minor, z=release */ -#define PNG_LIBPNG_VER 10404 /* 1.4.4 */ +#define PNG_LIBPNG_VER 10405 /* 1.4.5 */ #ifndef PNG_VERSION_INFO_ONLY /* Include the compression library's header */ @@ -1476,7 +1482,7 @@ struct png_struct_def /* This triggers a compiler error in png.c, if png.c and png.h * do not agree upon the version number. */ -typedef png_structp version_1_4_4; +typedef png_structp version_1_4_5; typedef png_struct FAR * FAR * png_structpp; @@ -2645,12 +2651,24 @@ PNG_EXPORT(png_bytep,png_get_io_chunk_name) ((png_uint_32)(*((buf) + 1)) << 16) + \ ((png_uint_32)(*((buf) + 2)) << 8) + \ ((png_uint_32)(*((buf) + 3)))) + + /* The following definition introduces an API incompatibility (but not + * an ABI incompatibility) with libpng-1.4.0 through 1.4.4. Prior to + * libpng-1.4.5 the macro, which is used by default, returned (incorrectly) + * a (png_uint_32), while the function, if used instead, correctly returned + * a (png_uint_16). + * + * Libpng versions 1.0.x and 1.2.x only used a function so are not affected + * by this potential API incompatibility between macros. + */ # define png_get_uint_16(buf) \ - (((png_uint_32)(*(buf)) << 8) + \ - ((png_uint_32)(*((buf) + 1)))) + ((png_uint_16) \ + (((unsigned int)(*(buf)) << 8) + \ + ((unsigned int)(*((buf) + 1))))) + # define png_get_int_32(buf) \ ((png_int_32)((*(buf) & 0x80) \ - ? -((png_int_32)((png_get_uint_32(buf) ^ 0xffffffff)+1)) \ + ? -((png_int_32)((png_get_uint_32(buf) ^ 0xffffffffL) + 1)) \ : (png_int_32)png_get_uint_32(buf))) #else PNG_EXPORT(png_uint_32,png_get_uint_32) PNGARG((png_bytep buf)); diff --git a/harbour/src/3rd/png/pngconf.h b/harbour/src/3rd/png/pngconf.h index 41b13e9fb6..8a6d83698b 100644 --- a/harbour/src/3rd/png/pngconf.h +++ b/harbour/src/3rd/png/pngconf.h @@ -1,7 +1,7 @@ /* pngconf.h - machine configurable file for libpng * - * libpng version 1.4.4 - September 23, 2010 + * libpng version 1.4.5 - December 9, 2010 * For conditions of distribution and use, see copyright notice in png.h * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) diff --git a/harbour/src/3rd/png/pngget.c b/harbour/src/3rd/png/pngget.c index abe721bd58..9b3a9ccee1 100644 --- a/harbour/src/3rd/png/pngget.c +++ b/harbour/src/3rd/png/pngget.c @@ -858,7 +858,7 @@ png_get_unknown_chunks(png_structp png_ptr, png_infop info_ptr, #ifdef PNG_READ_RGB_TO_GRAY_SUPPORTED png_byte PNGAPI -png_get_rgb_to_gray_status (png_structp png_ptr) +png_get_rgb_to_gray_status(png_structp png_ptr) { return (png_byte)(png_ptr? png_ptr->rgb_to_gray_status : 0); } @@ -883,24 +883,24 @@ png_get_compression_buffer_size(png_structp png_ptr) /* These functions were added to libpng 1.2.6 and were enabled * by default in libpng-1.4.0 */ png_uint_32 PNGAPI -png_get_user_width_max (png_structp png_ptr) +png_get_user_width_max(png_structp png_ptr) { return (png_ptr? png_ptr->user_width_max : 0); } png_uint_32 PNGAPI -png_get_user_height_max (png_structp png_ptr) +png_get_user_height_max(png_structp png_ptr) { return (png_ptr? png_ptr->user_height_max : 0); } /* This function was added to libpng 1.4.0 */ png_uint_32 PNGAPI -png_get_chunk_cache_max (png_structp png_ptr) +png_get_chunk_cache_max(png_structp png_ptr) { return (png_ptr? png_ptr->user_chunk_cache_max : 0); } /* This function was added to libpng 1.4.1 */ png_alloc_size_t PNGAPI -png_get_chunk_malloc_max (png_structp png_ptr) +png_get_chunk_malloc_max(png_structp png_ptr) { return (png_ptr? png_ptr->user_chunk_malloc_max : 0); @@ -910,13 +910,13 @@ png_get_chunk_malloc_max (png_structp png_ptr) /* These functions were added to libpng 1.4.0 */ #ifdef PNG_IO_STATE_SUPPORTED png_uint_32 PNGAPI -png_get_io_state (png_structp png_ptr) +png_get_io_state(png_structp png_ptr) { return png_ptr->io_state; } png_bytep PNGAPI -png_get_io_chunk_name (png_structp png_ptr) +png_get_io_chunk_name(png_structp png_ptr) { return png_ptr->chunk_name; } diff --git a/harbour/src/3rd/png/pngpread.c b/harbour/src/3rd/png/pngpread.c index e33b4286fa..9c69a89d18 100644 --- a/harbour/src/3rd/png/pngpread.c +++ b/harbour/src/3rd/png/pngpread.c @@ -1109,6 +1109,8 @@ png_push_process_row(png_structp png_ptr) break; } + + default: case 6: { png_push_have_row(png_ptr, png_ptr->row_buf + 1); @@ -1726,7 +1728,7 @@ png_push_have_row(png_structp png_ptr, png_bytep row) } void PNGAPI -png_progressive_combine_row (png_structp png_ptr, +png_progressive_combine_row(png_structp png_ptr, png_bytep old_row, png_bytep new_row) { PNG_CONST int FARDATA png_pass_dsp_mask[7] = diff --git a/harbour/src/3rd/png/pngpriv.h b/harbour/src/3rd/png/pngpriv.h index 8b0621c033..7112c8da11 100644 --- a/harbour/src/3rd/png/pngpriv.h +++ b/harbour/src/3rd/png/pngpriv.h @@ -1,7 +1,7 @@ /* pngpriv.h - private declarations for use inside libpng * - * libpng version 1.4.4 - September 23, 2010 + * libpng version 1.4.5 - December 9, 2010 * For conditions of distribution and use, see copyright notice in png.h * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) @@ -290,6 +290,9 @@ PNG_EXTERN void png_reset_crc PNGARG((png_structp png_ptr)); PNG_EXTERN void png_write_data PNGARG((png_structp png_ptr, png_bytep data, png_size_t length)); +/* Read and check the PNG file signature */ +PNG_EXTERN void png_read_sig PNGARG((png_structp png_ptr, png_infop info_ptr)); + /* Read the chunk header (length + type name) */ PNG_EXTERN png_uint_32 png_read_chunk_header PNGARG((png_structp png_ptr)); diff --git a/harbour/src/3rd/png/pngread.c b/harbour/src/3rd/png/pngread.c index 92060d2bc6..4806448075 100644 --- a/harbour/src/3rd/png/pngread.c +++ b/harbour/src/3rd/png/pngread.c @@ -1,7 +1,7 @@ /* pngread.c - read a PNG file * - * Last changed in libpng 1.4.1 [February 25, 2010] + * Last changed in libpng 1.4.5 [December 9, 2010] * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -214,34 +214,12 @@ void PNGAPI png_read_info(png_structp png_ptr, png_infop info_ptr) { png_debug(1, "in png_read_info"); - + if (png_ptr == NULL || info_ptr == NULL) return; - - /* If we haven't checked all of the PNG signature bytes, do so now. */ - if (png_ptr->sig_bytes < 8) - { - png_size_t num_checked = png_ptr->sig_bytes, - num_to_check = 8 - num_checked; -#ifdef PNG_IO_STATE_SUPPORTED - png_ptr->io_state = PNG_IO_READING | PNG_IO_SIGNATURE; -#endif - - png_read_data(png_ptr, &(info_ptr->signature[num_checked]), num_to_check); - png_ptr->sig_bytes = 8; - - if (png_sig_cmp(info_ptr->signature, num_checked, num_to_check)) - { - if (num_checked < 4 && - png_sig_cmp(info_ptr->signature, num_checked, num_to_check - 4)) - png_error(png_ptr, "Not a PNG file"); - else - png_error(png_ptr, "PNG file corrupted by ASCII conversion"); - } - if (num_checked < 3) - png_ptr->mode |= PNG_HAVE_PNG_SIGNATURE; - } + /* Read and check the PNG file signature. */ + png_read_sig(png_ptr, info_ptr); for (;;) { @@ -426,7 +404,7 @@ void PNGAPI png_read_update_info(png_structp png_ptr, png_infop info_ptr) { png_debug(1, "in png_read_update_info"); - + if (png_ptr == NULL) return; if (!(png_ptr->flags & PNG_FLAG_ROW_INIT)) @@ -448,7 +426,7 @@ void PNGAPI png_start_read_image(png_structp png_ptr) { png_debug(1, "in png_start_read_image"); - + if (png_ptr == NULL) return; if (!(png_ptr->flags & PNG_FLAG_ROW_INIT)) @@ -465,10 +443,10 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) 0xff}; PNG_CONST int png_pass_mask[7] = {0x80, 0x08, 0x88, 0x22, 0xaa, 0x55, 0xff}; int ret; - + if (png_ptr == NULL) return; - + png_debug2(1, "in png_read_row (row %lu, pass %d)", (unsigned long) png_ptr->row_number, png_ptr->pass); @@ -524,6 +502,7 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) return; } break; + case 1: if ((png_ptr->row_number & 0x07) || png_ptr->width < 5) { @@ -534,6 +513,7 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) return; } break; + case 2: if ((png_ptr->row_number & 0x07) != 4) { @@ -544,6 +524,7 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) return; } break; + case 3: if ((png_ptr->row_number & 3) || png_ptr->width < 3) { @@ -554,6 +535,7 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) return; } break; + case 4: if ((png_ptr->row_number & 3) != 2) { @@ -564,6 +546,7 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) return; } break; + case 5: if ((png_ptr->row_number & 1) || png_ptr->width < 2) { @@ -574,6 +557,8 @@ png_read_row(png_structp png_ptr, png_bytep row, png_bytep dsp_row) return; } break; + + default: case 6: if (!(png_ptr->row_number & 1)) { @@ -724,7 +709,7 @@ png_read_rows(png_structp png_ptr, png_bytepp row, png_bytepp dp; png_debug(1, "in png_read_rows"); - + if (png_ptr == NULL) return; rp = row; @@ -775,7 +760,7 @@ png_read_image(png_structp png_ptr, png_bytepp image) png_bytepp rp; png_debug(1, "in png_read_image"); - + if (png_ptr == NULL) return; @@ -813,7 +798,7 @@ void PNGAPI png_read_end(png_structp png_ptr, png_infop info_ptr) { png_debug(1, "in png_read_end"); - + if (png_ptr == NULL) return; png_crc_finish(png_ptr, 0); /* Finish off CRC from last IDAT chunk */ @@ -993,7 +978,7 @@ png_destroy_read_struct(png_structpp png_ptr_ptr, png_infopp info_ptr_ptr, #endif png_debug(1, "in png_destroy_read_struct"); - + if (png_ptr_ptr != NULL) png_ptr = *png_ptr_ptr; if (png_ptr == NULL) @@ -1069,7 +1054,7 @@ png_read_destroy(png_structp png_ptr, png_infop info_ptr, #endif png_debug(1, "in png_read_destroy"); - + if (info_ptr != NULL) png_info_destroy(png_ptr, info_ptr); diff --git a/harbour/src/3rd/png/pngrio.c b/harbour/src/3rd/png/pngrio.c index 59059caf69..cab7114a92 100644 --- a/harbour/src/3rd/png/pngrio.c +++ b/harbour/src/3rd/png/pngrio.c @@ -1,7 +1,7 @@ /* pngrio.c - functions for data input * - * Last changed in libpng 1.4.1 [February 25, 2010] + * Last changed in libpng 1.4.5 [December 9, 2010] * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -33,7 +33,7 @@ void /* PRIVATE */ png_read_data(png_structp png_ptr, png_bytep data, png_size_t length) { png_debug1(4, "reading %d bytes", (int)length); - + if (png_ptr->read_data_fn != NULL) (*(png_ptr->read_data_fn))(png_ptr, data, length); else diff --git a/harbour/src/3rd/png/pngrtran.c b/harbour/src/3rd/png/pngrtran.c index b5e8f1a26f..4497514311 100644 --- a/harbour/src/3rd/png/pngrtran.c +++ b/harbour/src/3rd/png/pngrtran.c @@ -1,7 +1,7 @@ /* pngrtran.c - transforms the data in a row for PNG readers * - * Last changed in libpng 1.4.2 [May 6, 2010] + * Last changed in libpng 1.4.5 [December 9, 2010] * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -26,7 +26,7 @@ void PNGAPI png_set_crc_action(png_structp png_ptr, int crit_action, int ancil_action) { png_debug(1, "in png_set_crc_action"); - + if (png_ptr == NULL) return; @@ -98,7 +98,7 @@ png_set_background(png_structp png_ptr, int need_expand, double background_gamma) { png_debug(1, "in png_set_background"); - + if (png_ptr == NULL) return; if (background_gamma_code == PNG_BACKGROUND_GAMMA_UNKNOWN) @@ -686,6 +686,11 @@ png_set_rgb_to_gray_fixed(png_structp png_ptr, int error_action, break; case 3: png_ptr->transformations |= PNG_RGB_TO_GRAY_ERR; + break; + + default: + png_error(png_ptr, "invalid error action in png_set_rgb_to_gray"); + break; } if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE) #ifdef PNG_READ_EXPAND_SUPPORTED @@ -828,6 +833,8 @@ png_init_read_transformations(png_structp png_ptr) } break; + default: + case 8: case 16: @@ -1028,6 +1035,9 @@ png_init_read_transformations(png_structp png_ptr) gs = 1.0 / (png_ptr->background_gamma * png_ptr->screen_gamma); break; + + default: + png_error(png_ptr, "invalid background gamma type"); } png_ptr->background_1.gray = (png_uint_16)(pow( @@ -1626,6 +1636,9 @@ png_do_unpack(png_row_infop row_info, png_bytep row) } break; } + + default: + break; } row_info->bit_depth = 8; row_info->pixel_depth = (png_byte)(8 * row_info->channels); @@ -1682,6 +1695,9 @@ png_do_unshift(png_row_infop row_info, png_bytep row, png_color_8p sig_bits) switch (row_info->bit_depth) { + default: + break; + case 2: { png_bytep bp; @@ -2798,6 +2814,9 @@ png_do_background(png_row_infop row_info, png_bytep row, } break; } + + default: + break; } break; } @@ -3230,6 +3249,9 @@ png_do_background(png_row_infop row_info, png_bytep row, } break; } + + default: + break; } if (row_info->color_type & PNG_COLOR_MASK_ALPHA) @@ -3428,6 +3450,9 @@ png_do_gamma(png_row_infop row_info, png_bytep row, } break; } + + default: + break; } } } @@ -3522,6 +3547,9 @@ png_do_expand_palette(png_row_infop row_info, png_bytep row, } break; } + + default: + break; } row_info->bit_depth = 8; row_info->pixel_depth = 8; @@ -3672,6 +3700,9 @@ png_do_expand(png_row_infop row_info, png_bytep row, } break; } + + default: + break; } row_info->bit_depth = 8; diff --git a/harbour/src/3rd/png/pngrutil.c b/harbour/src/3rd/png/pngrutil.c index 11e412b729..5429887a51 100644 --- a/harbour/src/3rd/png/pngrutil.c +++ b/harbour/src/3rd/png/pngrutil.c @@ -1,7 +1,7 @@ /* pngrutil.c - utilities to read a PNG file * - * Last changed in libpng 1.4.4 [August 26, 2010] + * Last changed in libpng 1.4.5 [December 9, 2010] * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -23,23 +23,29 @@ png_uint_32 PNGAPI png_get_uint_31(png_structp png_ptr, png_bytep buf) { - png_uint_32 i = png_get_uint_32(buf); - if (i > PNG_UINT_31_MAX) + png_uint_32 val = png_get_uint_32(buf); + + if (val > PNG_UINT_31_MAX) png_error(png_ptr, "PNG unsigned integer out of range"); - return (i); + return (val); } + #ifndef PNG_USE_READ_MACROS +/* The parentheses around "PNGAPI function_name" in the following three + * functions are necessary because they allow the macros to co-exist with + * these (unused but exported) functions. + */ + /* Grab an unsigned 32-bit integer from a buffer in big-endian format. */ png_uint_32 (PNGAPI png_get_uint_32)(png_bytep buf) { - png_uint_32 i = - ((png_uint_32)(*(buf )) << 24) + - ((png_uint_32)(*(buf + 1)) << 16) + - ((png_uint_32)(*(buf + 2)) << 8) + - ((png_uint_32)(*(buf + 3)) ) ; + png_uint_32 uval = png_get_uint_32(buf); + if ((uval & 0x80000000L) == 0) /* non-negative */ + return uval; - return (i); + uval = (uval ^ 0xffffffffL) + 1; /* 2's complement: -x = ~x+1 */ + return -(png_int_32)uval; } /* Grab a signed 32-bit integer from a buffer in big-endian format. The @@ -50,26 +56,65 @@ png_get_uint_32)(png_bytep buf) png_int_32 (PNGAPI png_get_int_32)(png_bytep buf) { - png_uint_32 u = png_get_uint_32(buf); - if ((u & 0x80000000) == 0) /* non-negative */ - return u; + png_uint_32 uval = png_get_uint_32(buf); + if ((uval & 0x80000000L) == 0) /* non-negative */ + return uval; - u = (u ^ 0xffffffff) + 1; /* 2's complement: -x = ~x+1 */ - return -(png_int_32)u; + uval = (uval ^ 0xffffffffL) + 1; /* 2's complement: -x = ~x+1 */ + return -(png_int_32)uval; } /* Grab an unsigned 16-bit integer from a buffer in big-endian format. */ png_uint_16 (PNGAPI png_get_uint_16)(png_bytep buf) { - png_uint_16 i = - ((png_uint_32)(*buf) << 8) + - ((png_uint_32)(*(buf + 1))); + /* ANSI-C requires an int value to accomodate at least 16 bits so this + * works and allows the compiler not to worry about possible narrowing + * on 32 bit systems. (Pre-ANSI systems did not make integers smaller + * than 16 bits either.) + */ + unsigned int val = + ((unsigned int)(*buf) << 8) + + ((unsigned int)(*(buf + 1))); - return (i); + return (png_uint_16)val; } #endif /* PNG_USE_READ_MACROS */ +/* Read and check the PNG file signature */ +void /* PRIVATE */ +png_read_sig(png_structp png_ptr, png_infop info_ptr) +{ + png_size_t num_checked, num_to_check; + + /* Exit if the user application does not expect a signature. */ + if (png_ptr->sig_bytes >= 8) + return; + + num_checked = png_ptr->sig_bytes; + num_to_check = 8 - num_checked; + +#ifdef PNG_IO_STATE_SUPPORTED + png_ptr->io_state = PNG_IO_READING | PNG_IO_SIGNATURE; +#endif + + /* The signature must be serialized in a single I/O call. */ + png_read_data(png_ptr, &(info_ptr->signature[num_checked]), num_to_check); + png_ptr->sig_bytes = 8; + + if (png_sig_cmp(info_ptr->signature, num_checked, num_to_check)) + { + if (num_checked < 4 && + png_sig_cmp(info_ptr->signature, num_checked, num_to_check - 4)) + png_error(png_ptr, "Not a PNG file"); + + else + png_error(png_ptr, "PNG file corrupted by ASCII conversion"); + } + if (num_checked < 3) + png_ptr->mode |= PNG_HAVE_PNG_SIGNATURE; +} + /* Read the chunk header (length + type name). * Put the type name into png_ptr->chunk_name, and return the length. */ @@ -80,32 +125,31 @@ png_read_chunk_header(png_structp png_ptr) png_uint_32 length; #ifdef PNG_IO_STATE_SUPPORTED - /* Inform the I/O callback that the chunk header is being read. - * PNG_IO_CHUNK_HDR requires a single I/O call. - */ png_ptr->io_state = PNG_IO_READING | PNG_IO_CHUNK_HDR; #endif - /* Read the length and the chunk name */ + /* Read the length and the chunk name. + * This must be performed in a single I/O call. + */ png_read_data(png_ptr, buf, 8); length = png_get_uint_31(png_ptr, buf); - /* Put the chunk name into png_ptr->chunk_name */ + /* Put the chunk name into png_ptr->chunk_name. */ png_memcpy(png_ptr->chunk_name, buf + 4, 4); png_debug2(0, "Reading %s chunk, length = %lu", png_ptr->chunk_name, length); - /* Reset the crc and run it over the chunk name */ + /* Reset the crc and run it over the chunk name. */ png_reset_crc(png_ptr); png_calculate_crc(png_ptr, png_ptr->chunk_name, 4); - /* Check to see if chunk name is valid */ + /* Check to see if chunk name is valid. */ png_check_chunk_name(png_ptr, png_ptr->chunk_name); #ifdef PNG_IO_STATE_SUPPORTED - /* Inform the I/O callback that chunk data will (possibly) be read. - * PNG_IO_CHUNK_DATA does NOT require a specific number of I/O calls. + /* It is unspecified how many I/O calls will be performed + * during the serialization of the chunk data. */ png_ptr->io_state = PNG_IO_READING | PNG_IO_CHUNK_DATA; #endif @@ -119,6 +163,7 @@ png_crc_read(png_structp png_ptr, png_bytep buf, png_size_t length) { if (png_ptr == NULL) return; + png_read_data(png_ptr, buf, length); png_calculate_crc(png_ptr, buf, length); } @@ -138,6 +183,7 @@ png_crc_finish(png_structp png_ptr, png_uint_32 skip) { png_crc_read(png_ptr, png_ptr->zbuf, png_ptr->zbuf_size); } + if (i) { png_crc_read(png_ptr, png_ptr->zbuf, i); @@ -152,11 +198,13 @@ png_crc_finish(png_structp png_ptr, png_uint_32 skip) { png_chunk_warning(png_ptr, "CRC error"); } + else { png_chunk_benign_error(png_ptr, "CRC error"); return (0); } + return (1); } @@ -179,6 +227,7 @@ png_crc_error(png_structp png_ptr) (PNG_FLAG_CRC_ANCILLARY_USE | PNG_FLAG_CRC_ANCILLARY_NOWARN)) need_crc = 0; } + else /* critical */ { if (png_ptr->flags & PNG_FLAG_CRC_CRITICAL_IGNORE) @@ -186,11 +235,10 @@ png_crc_error(png_structp png_ptr) } #ifdef PNG_IO_STATE_SUPPORTED - /* Inform the I/O callback that the chunk CRC is being read */ - /* PNG_IO_CHUNK_CRC requires the I/O to be done at once */ png_ptr->io_state = PNG_IO_READING | PNG_IO_CHUNK_CRC; #endif + /* The chunk CRC must be serialized in a single I/O call. */ png_read_data(png_ptr, crc_bytes, 4); if (need_crc) @@ -198,6 +246,7 @@ png_crc_error(png_structp png_ptr) crc = png_get_uint_32(crc_bytes); return ((int)(crc != png_ptr->crc)); } + else return (0); } @@ -237,6 +286,7 @@ png_inflate(png_structp png_ptr, const png_byte *data, png_size_t size, if (avail < copy) copy = avail; png_memcpy(output + count, png_ptr->zbuf, copy); } + count += avail; } @@ -270,9 +320,11 @@ png_inflate(png_structp png_ptr, const png_byte *data, png_size_t size, case Z_BUF_ERROR: msg = "Buffer error in compressed datastream in %s chunk"; break; + case Z_DATA_ERROR: msg = "Data error in compressed datastream in %s chunk"; break; + default: msg = "Incomplete compressed datastream in %s chunk"; break; @@ -372,6 +424,7 @@ png_decompress_chunk(png_structp png_ptr, int comp_type, png_warning(png_ptr, "png_inflate logic error"); png_free(png_ptr, text); } + else png_warning(png_ptr, "Not enough memory to decompress chunk"); } @@ -3109,17 +3162,10 @@ png_read_finish_row(png_structp png_ptr) { while (!png_ptr->idat_size) { - png_byte chunk_length[4]; - png_crc_finish(png_ptr, 0); - - png_read_data(png_ptr, chunk_length, 4); - png_ptr->idat_size = png_get_uint_31(png_ptr, chunk_length); - png_reset_crc(png_ptr); - png_crc_read(png_ptr, png_ptr->chunk_name, 4); + png_ptr->idat_size = png_read_chunk_header(png_ptr); if (png_memcmp(png_ptr->chunk_name, png_IDAT, 4)) png_error(png_ptr, "Not enough image data"); - } png_ptr->zstream.avail_in = (uInt)png_ptr->zbuf_size; png_ptr->zstream.next_in = png_ptr->zbuf; diff --git a/harbour/src/3rd/png/pngset.c b/harbour/src/3rd/png/pngset.c index 1f972c4edb..76f173e4e0 100644 --- a/harbour/src/3rd/png/pngset.c +++ b/harbour/src/3rd/png/pngset.c @@ -1,7 +1,7 @@ /* pngset.c - storage of image information into info struct * - * Last changed in libpng 1.4.1 [February 25, 2010] + * Last changed in libpng 1.4.5 [December 9, 2010] * Copyright (c) 1998-2010 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -690,6 +690,13 @@ png_set_text_2(png_structp png_ptr, png_infop info_ptr, png_textp text_ptr, if (text_ptr[i].key == NULL) continue; + if (text_ptr[i].compression < PNG_TEXT_COMPRESSION_NONE || + text_ptr[i].compression >= PNG_TEXT_COMPRESSION_LAST) + { + png_warning(png_ptr, "text compression mode is out of range"); + continue; + } + key_len = png_strlen(text_ptr[i].key); if (text_ptr[i].compression <= 0) @@ -1004,7 +1011,7 @@ png_set_unknown_chunk_location(png_structp png_ptr, png_infop info_ptr, #ifdef PNG_MNG_FEATURES_SUPPORTED png_uint_32 PNGAPI -png_permit_mng_features (png_structp png_ptr, png_uint_32 mng_features) +png_permit_mng_features(png_structp png_ptr, png_uint_32 mng_features) { png_debug(1, "in png_permit_mng_features"); @@ -1118,7 +1125,7 @@ png_set_invalid(png_structp png_ptr, png_infop info_ptr, int mask) #ifdef PNG_SET_USER_LIMITS_SUPPORTED /* This function was added to libpng 1.2.6 */ void PNGAPI -png_set_user_limits (png_structp png_ptr, png_uint_32 user_width_max, +png_set_user_limits(png_structp png_ptr, png_uint_32 user_width_max, png_uint_32 user_height_max) { /* Images with dimensions larger than these limits will be @@ -1133,7 +1140,7 @@ png_set_user_limits (png_structp png_ptr, png_uint_32 user_width_max, /* This function was added to libpng 1.4.0 */ void PNGAPI -png_set_chunk_cache_max (png_structp png_ptr, +png_set_chunk_cache_max(png_structp png_ptr, png_uint_32 user_chunk_cache_max) { if (png_ptr) @@ -1142,7 +1149,7 @@ png_set_chunk_cache_max (png_structp png_ptr, /* This function was added to libpng 1.4.1 */ void PNGAPI -png_set_chunk_malloc_max (png_structp png_ptr, +png_set_chunk_malloc_max(png_structp png_ptr, png_alloc_size_t user_chunk_malloc_max) { if (png_ptr) diff --git a/harbour/src/3rd/png/pngwtran.c b/harbour/src/3rd/png/pngwtran.c index 070caa544d..2925a93377 100644 --- a/harbour/src/3rd/png/pngwtran.c +++ b/harbour/src/3rd/png/pngwtran.c @@ -195,6 +195,9 @@ png_do_pack(png_row_infop row_info, png_bytep row, png_uint_32 bit_depth) *dp = (png_byte)v; break; } + + default: + break; } row_info->bit_depth = (png_byte)bit_depth; row_info->pixel_depth = (png_byte)(bit_depth * row_info->channels); diff --git a/harbour/src/3rd/png/pngwutil.c b/harbour/src/3rd/png/pngwutil.c index 19feb1d98c..8f7c7c24df 100644 --- a/harbour/src/3rd/png/pngwutil.c +++ b/harbour/src/3rd/png/pngwutil.c @@ -246,10 +246,12 @@ png_text_compress(png_structp png_ptr, */ /* Set up the compression buffers */ + /* TODO: the following cast hides a potential overflow problem. */ png_ptr->zstream.avail_in = (uInt)text_len; + /* NOTE: assume zlib doesn't overwrite the input */ png_ptr->zstream.next_in = (Bytef *)text; - png_ptr->zstream.avail_out = (uInt)png_ptr->zbuf_size; - png_ptr->zstream.next_out = (Bytef *)png_ptr->zbuf; + png_ptr->zstream.avail_out = png_ptr->zbuf_size; + png_ptr->zstream.next_out = png_ptr->zbuf; /* This is the same compression loop as in png_write_row() */ do