[PENNMUSH-ANNOUNCE] 1.7.4-patch13

dunemush@pennmush.org dunemush at pennmush.org
Mon, 3 Dec 2001 10:09:50 -0600


This is patch13 to PennMUSH 1.7.4. After applying this patch, you will
have version 1.7.4p13

To apply this patch, save it to a file in your top-level MUSH directory,
and do the following:
	patch -p1 < 1.7.4-patch13
	make install

If you use GNU patch 2.2, you probably want the above to be 'patch -b -p1',
not just 'patch -p1'.

Unix (or cygwin) users need not worry about failed hunks in src/switchinc.c,
hdrs/switches.h, hdrs/cmds.h, or hdrs/funs.h. These files are automatically
rebuilt on compile.

Then @shutdown and restart your MUSH.
    - Alan/Javelin

In this patch:

Minor changes:
  * options.h.dist mentions Darwin as well as MacOS X. [DW]
  * PCRE updated to 3.7. [SW]
  * When CHAN_NAME_LEN is increased beyond 30, the @chan/list header
    line is misaligned, and other strange things can happen to
    @chan/list. Reported by Bladed Thoth
Fixes:
  * Crash bug in chat channels reported by BladedThoth.

Prereq: 1.7.4p12
*** 1_7_4.187/Patchlevel Tue, 13 Nov 2001 17:29:19 -0600 dunemush (pennmush/5_Patchlevel 1.30 600)
--- 1_7_4.188(w)/Patchlevel Fri, 30 Nov 2001 11:34:29 -0600 dunemush (pennmush/5_Patchlevel 1.30 600)
***************
*** 1,2 ****
  Do not edit this file. It is maintained by the official PennMUSH patches.
! This is PennMUSH 1.7.4p12
--- 1,2 ----
  Do not edit this file. It is maintained by the official PennMUSH patches.
! This is PennMUSH 1.7.4p13
*** 1_7_4.187/CHANGES Tue, 13 Nov 2001 17:29:19 -0600 dunemush (pennmush/8_CHANGES 1.219.1.56 600)
--- 1_7_4.188(w)/CHANGES Fri, 30 Nov 2001 12:04:55 -0600 dunemush (pennmush/8_CHANGES 1.219.1.57 600)
***************
*** 17,22 ****
--- 17,33 ----
  
  ==========================================================================
  
+ Version 1.7.4 patchlevel 13		       November 30, 2001
+ 
+ Minor changes:
+   * options.h.dist mentions Darwin as well as MacOS X. [DW]
+   * PCRE updated to 3.7. [SW]
+   * When CHAN_NAME_LEN is increased beyond 30, the @chan/list header
+     line is misaligned, and other strange things can happen to
+     @chan/list. Reported by Bladed Thoth
+ Fixes:
+   * Crash bug in chat channels reported by BladedThoth.
+ 
  Version 1.7.4 patchlevel 12		       November 9, 2001
  
  Minor changes:
*** 1_7_4.187/game/txt/hlp/pennvers.hlp Tue, 13 Nov 2001 17:29:19 -0600 dunemush (pennmush/12_pennvers.h 1.169.1.42.1.1 600)
--- 1_7_4.188(w)/game/txt/hlp/pennvers.hlp Fri, 30 Nov 2001 12:04:58 -0600 dunemush (pennmush/12_pennvers.h 1.169.1.42.1.1 600)
***************
*** 1,5 ****
  & changes
! & 1.7.4p12
  This is a list of changes in this patchlevel which are probably of
  interest to players. More information about new commands and functions
  can probably be gotten via 'help <name of whatever>'. 'help credits'
--- 1,5 ----
  & changes
! & 1.7.4p13
  This is a list of changes in this patchlevel which are probably of
  interest to players. More information about new commands and functions
  can probably be gotten via 'help <name of whatever>'. 'help credits'
***************
*** 11,16 ****
--- 11,28 ----
  A list of the patchlevels associated with each release can
  be read in 'help patchlevels'.
  
+ Version 1.7.4 patchlevel 13		       November 30, 2001
+ 
+ Minor changes:
+   * options.h.dist mentions Darwin as well as MacOS X. [DW]
+   * PCRE updated to 3.7. [SW]
+   * When CHAN_NAME_LEN is increased beyond 30, the @chan/list header
+     line is misaligned, and other strange things can happen to
+     @chan/list. Reported by Bladed Thoth
+ Fixes:
+   * Crash bug in chat channels reported by BladedThoth.
+ 
+ & 1.7.4p12
  Version 1.7.4 patchlevel 12		       November 9, 2001
  
  Minor changes:
***************
*** 4912,4918 ****
  For information on a specific patchlevel of one of the versions listed,
  type 'help <version>p<patchlevel>'. For example, 'help 1.7.2p3'
  
! 1.7.4: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12
  1.7.3: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14
  1.7.2: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18,
         19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35
--- 4924,4930 ----
  For information on a specific patchlevel of one of the versions listed,
  type 'help <version>p<patchlevel>'. For example, 'help 1.7.2p3'
  
! 1.7.4: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13
  1.7.3: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14
  1.7.2: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18,
         19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35
*** 1_7_4.187/src/switchinc.c Tue, 13 Nov 2001 17:29:19 -0600 dunemush (pennmush/b/32_switchinc. 1.3.1.2.1.6.1.18.1.2.1.2.2.5.1.4.2.4.1.1.1.2.1.5.1.2 660)
--- 1_7_4.188(w)/src/switchinc.c Mon, 03 Dec 2001 10:09:25 -0600 dunemush (pennmush/b/32_switchinc. 1.3.1.2.1.6.1.18.1.2.1.2.2.5.1.4.2.4.1.1.1.2.1.5.1.2 660)
***************
*** 1,516 ****
  {
!   "ACCESS", SWITCH_ACCESS
! }
! ,
! {
!   "ADD", SWITCH_ADD
! }
! ,
! {
!   "ALL", SWITCH_ALL
! }
! ,
! {
!   "ATTRIBS", SWITCH_ATTRIBS
! }
! ,
! {
!   "BAN", SWITCH_BAN
! }
! ,
! {
!   "BLIND", SWITCH_BLIND
! }
! ,
! {
!   "BRIEF", SWITCH_BRIEF
! }
! ,
! {
!   "CHECK", SWITCH_CHECK
! }
! ,
! {
!   "CHOWN", SWITCH_CHOWN
! }
! ,
! {
!   "CLEAR", SWITCH_CLEAR
! }
! ,
! {
!   "CMD", SWITCH_CMD
! }
! ,
! {
!   "COMMANDS", SWITCH_COMMANDS
! }
! ,
! {
!   "CONN", SWITCH_CONN
! }
! ,
! {
!   "CONNECT", SWITCH_CONNECT
! }
! ,
! {
!   "CONNECTED", SWITCH_CONNECTED
! }
! ,
! {
!   "CONTENTS", SWITCH_CONTENTS
! }
! ,
! {
!   "COSTS", SWITCH_COSTS
! }
! ,
! {
!   "COUNT", SWITCH_COUNT
! }
! ,
! {
!   "CREATE", SWITCH_CREATE
! }
! ,
! {
!   "DATABASE", SWITCH_DATABASE
! }
! ,
! {
!   "DB", SWITCH_DB
! }
! ,
! {
!   "DEBUG", SWITCH_DEBUG
! }
! ,
! {
!   "DECOMPILE", SWITCH_DECOMPILE
! }
! ,
! {
!   "DEFAULTS", SWITCH_DEFAULTS
! }
! ,
! {
!   "DELETE", SWITCH_DELETE
! }
! ,
! {
!   "DELIMIT", SWITCH_DELIMIT
! }
! ,
! {
!   "DESCRIBE", SWITCH_DESCRIBE
! }
! ,
! {
!   "DESTROY", SWITCH_DESTROY
! }
! ,
! {
!   "DISABLE", SWITCH_DISABLE
! }
! ,
! {
!   "DOWN", SWITCH_DOWN
! }
! ,
! {
!   "DSTATS", SWITCH_DSTATS
! }
! ,
! {
!   "EMIT", SWITCH_EMIT
! }
! ,
! {
!   "ENABLE", SWITCH_ENABLE
! }
! ,
! {
!   "ERR", SWITCH_ERR
! }
! ,
! {
!   "EXITS", SWITCH_EXITS
! }
! ,
! {
!   "FILE", SWITCH_FILE
! }
! ,
! {
!   "FIRST", SWITCH_FIRST
! }
! ,
! {
!   "FLAGS", SWITCH_FLAGS
! }
! ,
! {
!   "FOLDERS", SWITCH_FOLDERS
! }
! ,
! {
!   "FORWARD", SWITCH_FORWARD
! }
! ,
! {
!   "FSTATS", SWITCH_FSTATS
! }
! ,
! {
!   "FULL", SWITCH_FULL
! }
! ,
! {
!   "FUNCTIONS", SWITCH_FUNCTIONS
! }
! ,
! {
!   "FWD", SWITCH_FWD
! }
! ,
! {
!   "GAG", SWITCH_GAG
! }
! ,
! {
!   "GLOBALS", SWITCH_GLOBALS
! }
! ,
! {
!   "HEADER", SWITCH_HEADER
! }
! ,
! {
!   "HERE", SWITCH_HERE
! }
! ,
! {
!   "HIDE", SWITCH_HIDE
! }
! ,
! {
!   "ILIST", SWITCH_ILIST
! }
! ,
! {
!   "INVENTORY", SWITCH_INVENTORY
! }
! ,
! {
!   "IPRINT", SWITCH_IPRINT
! }
! ,
! {
!   "JOIN", SWITCH_JOIN
! }
! ,
! {
!   "LIST", SWITCH_LIST
! }
! ,
! {
!   "LOWERCASE", SWITCH_LOWERCASE
! }
! ,
! {
!   "ME", SWITCH_ME
! }
! ,
! {
!   "MEMBERS", SWITCH_MEMBERS
! }
! ,
! {
!   "MOD", SWITCH_MOD
! }
! ,
! {
!   "MORTAL", SWITCH_MORTAL
! }
! ,
! {
!   "MOTD", SWITCH_MOTD
! }
! ,
! {
!   "MUTE", SWITCH_MUTE
! }
! ,
! {
!   "NAME", SWITCH_NAME
! }
! ,
! {
!   "NO", SWITCH_NO
! }
! ,
! {
!   "NOEVAL", SWITCH_NOEVAL
! }
! ,
! {
!   "NOFLAGCOPY", SWITCH_NOFLAGCOPY
! }
! ,
! {
!   "NOISY", SWITCH_NOISY
! }
! ,
! {
!   "NOSIG", SWITCH_NOSIG
! }
! ,
! {
!   "NOSPACE", SWITCH_NOSPACE
! }
! ,
! {
!   "NOTIFY", SWITCH_NOTIFY
! }
! ,
! {
!   "NUKE", SWITCH_NUKE
! }
! ,
! {
!   "OFF", SWITCH_OFF
! }
! ,
! {
!   "ON", SWITCH_ON
! }
! ,
! {
!   "OUTSIDE", SWITCH_OUTSIDE
! }
! ,
! {
!   "OVERRIDE", SWITCH_OVERRIDE
! }
! ,
! {
!   "PANIC", SWITCH_PANIC
! }
! ,
! {
!   "PARANOID", SWITCH_PARANOID
! }
! ,
! {
!   "PLAYERS", SWITCH_PLAYERS
! }
! ,
! {
!   "PORT", SWITCH_PORT
! }
! ,
! {
!   "POSE", SWITCH_POSE
! }
! ,
! {
!   "PRESERVE", SWITCH_PRESERVE
! }
! ,
! {
!   "PRINT", SWITCH_PRINT
! }
! ,
! {
!   "PRIVS", SWITCH_PRIVS
! }
! ,
! {
!   "PURGE", SWITCH_PURGE
! }
! ,
! {
!   "QUICK", SWITCH_QUICK
! }
! ,
! {
!   "QUIET", SWITCH_QUIET
! }
! ,
! {
!   "READ", SWITCH_READ
! }
! ,
! {
!   "REBOOT", SWITCH_REBOOT
! }
! ,
! {
!   "REGISTER", SWITCH_REGISTER
! }
! ,
! {
!   "REMOVE", SWITCH_REMOVE
! }
! ,
! {
!   "RENAME", SWITCH_RENAME
! }
! ,
! {
!   "RESTORE", SWITCH_RESTORE
! }
! ,
! {
!   "RESTRICT", SWITCH_RESTRICT
! }
! ,
! {
!   "RETROACTIVE", SWITCH_RETROACTIVE
! }
! ,
! {
!   "ROOM", SWITCH_ROOM
! }
! ,
! {
!   "ROOMS", SWITCH_ROOMS
! }
! ,
! {
!   "ROYALTY", SWITCH_ROYALTY
! }
! ,
! {
!   "SEE", SWITCH_SEE
! }
! ,
! {
!   "SEEFLAG", SWITCH_SEEFLAG
! }
! ,
! {
!   "SELF", SWITCH_SELF
! }
! ,
! {
!   "SEND", SWITCH_SEND
! }
! ,
! {
!   "SET", SWITCH_SET
! }
! ,
! {
!   "SILENT", SWITCH_SILENT
! }
! ,
! {
!   "SKIPDEFAULTS", SWITCH_SKIPDEFAULTS
! }
! ,
! {
!   "SPEAK", SWITCH_SPEAK
! }
! ,
! {
!   "STATS", SWITCH_STATS
! }
! ,
! {
!   "SUMMARY", SWITCH_SUMMARY
! }
! ,
! {
!   "TABLES", SWITCH_TABLES
! }
! ,
! {
!   "TAG", SWITCH_TAG
! }
! ,
! {
!   "TELEPORT", SWITCH_TELEPORT
! }
! ,
! {
!   "TF", SWITCH_TF
! }
! ,
! {
!   "THINGS", SWITCH_THINGS
! }
! ,
! {
!   "TITLE", SWITCH_TITLE
! }
! ,
! {
!   "TRACE", SWITCH_TRACE
! }
! ,
! {
!   "UNCLEAR", SWITCH_UNCLEAR
! }
! ,
! {
!   "UNFOLDER", SWITCH_UNFOLDER
! }
! ,
! {
!   "UNGAG", SWITCH_UNGAG
! }
! ,
! {
!   "UNHIDE", SWITCH_UNHIDE
! }
! ,
! {
!   "UNMUTE", SWITCH_UNMUTE
! }
! ,
! {
!   "UNTAG", SWITCH_UNTAG
! }
! ,
! {
!   "UNTIL", SWITCH_UNTIL
! }
! ,
! {
!   "URGENT", SWITCH_URGENT
! }
! ,
! {
!   "USEFLAG", SWITCH_USEFLAG
! }
! ,
! {
!   "WHAT", SWITCH_WHAT
! }
! ,
! {
!   "WHO", SWITCH_WHO
! }
! ,
! {
!   "WIPE", SWITCH_WIPE
! }
! ,
! {
!   "WIZ", SWITCH_WIZ
! }
! ,
! {
!   "WIZARD", SWITCH_WIZARD
! }
! ,
! {
!   "YES", SWITCH_YES
! }
! ,
! {
!   "ZONE", SWITCH_ZONE
! }
  ,
--- 1,388 ----
  {
! "ACCESS", SWITCH_ACCESS}
! 
! , {
! "ADD", SWITCH_ADD}
! 
! , {
! "ALL", SWITCH_ALL}
! 
! , {
! "ATTRIBS", SWITCH_ATTRIBS}
! 
! , {
! "BAN", SWITCH_BAN}
! 
! , {
! "BLIND", SWITCH_BLIND}
! 
! , {
! "BRIEF", SWITCH_BRIEF}
! 
! , {
! "CHECK", SWITCH_CHECK}
! 
! , {
! "CHOWN", SWITCH_CHOWN}
! 
! , {
! "CLEAR", SWITCH_CLEAR}
! 
! , {
! "CMD", SWITCH_CMD}
! 
! , {
! "COMMANDS", SWITCH_COMMANDS}
! 
! , {
! "CONN", SWITCH_CONN}
! 
! , {
! "CONNECT", SWITCH_CONNECT}
! 
! , {
! "CONNECTED", SWITCH_CONNECTED}
! 
! , {
! "CONTENTS", SWITCH_CONTENTS}
! 
! , {
! "COSTS", SWITCH_COSTS}
! 
! , {
! "COUNT", SWITCH_COUNT}
! 
! , {
! "CREATE", SWITCH_CREATE}
! 
! , {
! "DATABASE", SWITCH_DATABASE}
! 
! , {
! "DB", SWITCH_DB}
! 
! , {
! "DEBUG", SWITCH_DEBUG}
! 
! , {
! "DECOMPILE", SWITCH_DECOMPILE}
! 
! , {
! "DEFAULTS", SWITCH_DEFAULTS}
! 
! , {
! "DELETE", SWITCH_DELETE}
! 
! , {
! "DELIMIT", SWITCH_DELIMIT}
! 
! , {
! "DESCRIBE", SWITCH_DESCRIBE}
! 
! , {
! "DESTROY", SWITCH_DESTROY}
! 
! , {
! "DISABLE", SWITCH_DISABLE}
! 
! , {
! "DOWN", SWITCH_DOWN}
! 
! , {
! "DSTATS", SWITCH_DSTATS}
! 
! , {
! "EMIT", SWITCH_EMIT}
! 
! , {
! "ENABLE", SWITCH_ENABLE}
! 
! , {
! "ERR", SWITCH_ERR}
! 
! , {
! "EXITS", SWITCH_EXITS}
! 
! , {
! "FILE", SWITCH_FILE}
! 
! , {
! "FIRST", SWITCH_FIRST}
! 
! , {
! "FLAGS", SWITCH_FLAGS}
! 
! , {
! "FOLDERS", SWITCH_FOLDERS}
! 
! , {
! "FORWARD", SWITCH_FORWARD}
! 
! , {
! "FSTATS", SWITCH_FSTATS}
! 
! , {
! "FULL", SWITCH_FULL}
! 
! , {
! "FUNCTIONS", SWITCH_FUNCTIONS}
! 
! , {
! "FWD", SWITCH_FWD}
! 
! , {
! "GAG", SWITCH_GAG}
! 
! , {
! "GLOBALS", SWITCH_GLOBALS}
! 
! , {
! "HEADER", SWITCH_HEADER}
! 
! , {
! "HERE", SWITCH_HERE}
! 
! , {
! "HIDE", SWITCH_HIDE}
! 
! , {
! "ILIST", SWITCH_ILIST}
! 
! , {
! "INVENTORY", SWITCH_INVENTORY}
! 
! , {
! "IPRINT", SWITCH_IPRINT}
! 
! , {
! "JOIN", SWITCH_JOIN}
! 
! , {
! "LIST", SWITCH_LIST}
! 
! , {
! "LOWERCASE", SWITCH_LOWERCASE}
! 
! , {
! "ME", SWITCH_ME}
! 
! , {
! "MEMBERS", SWITCH_MEMBERS}
! 
! , {
! "MOD", SWITCH_MOD}
! 
! , {
! "MORTAL", SWITCH_MORTAL}
! 
! , {
! "MOTD", SWITCH_MOTD}
! 
! , {
! "MUTE", SWITCH_MUTE}
! 
! , {
! "NAME", SWITCH_NAME}
! 
! , {
! "NO", SWITCH_NO}
! 
! , {
! "NOEVAL", SWITCH_NOEVAL}
! 
! , {
! "NOFLAGCOPY", SWITCH_NOFLAGCOPY}
! 
! , {
! "NOISY", SWITCH_NOISY}
! 
! , {
! "NOSIG", SWITCH_NOSIG}
! 
! , {
! "NOSPACE", SWITCH_NOSPACE}
! 
! , {
! "NOTIFY", SWITCH_NOTIFY}
! 
! , {
! "NUKE", SWITCH_NUKE}
! 
! , {
! "OFF", SWITCH_OFF}
! 
! , {
! "ON", SWITCH_ON}
! 
! , {
! "OUTSIDE", SWITCH_OUTSIDE}
! 
! , {
! "OVERRIDE", SWITCH_OVERRIDE}
! 
! , {
! "PANIC", SWITCH_PANIC}
! 
! , {
! "PARANOID", SWITCH_PARANOID}
! 
! , {
! "PLAYERS", SWITCH_PLAYERS}
! 
! , {
! "PORT", SWITCH_PORT}
! 
! , {
! "POSE", SWITCH_POSE}
! 
! , {
! "PRESERVE", SWITCH_PRESERVE}
! 
! , {
! "PRINT", SWITCH_PRINT}
! 
! , {
! "PRIVS", SWITCH_PRIVS}
! 
! , {
! "PURGE", SWITCH_PURGE}
! 
! , {
! "QUICK", SWITCH_QUICK}
! 
! , {
! "QUIET", SWITCH_QUIET}
! 
! , {
! "READ", SWITCH_READ}
! 
! , {
! "REBOOT", SWITCH_REBOOT}
! 
! , {
! "REGISTER", SWITCH_REGISTER}
! 
! , {
! "REMOVE", SWITCH_REMOVE}
! 
! , {
! "RENAME", SWITCH_RENAME}
! 
! , {
! "RESTORE", SWITCH_RESTORE}
! 
! , {
! "RESTRICT", SWITCH_RESTRICT}
! 
! , {
! "RETROACTIVE", SWITCH_RETROACTIVE}
! 
! , {
! "ROOM", SWITCH_ROOM}
! 
! , {
! "ROOMS", SWITCH_ROOMS}
! 
! , {
! "ROYALTY", SWITCH_ROYALTY}
! 
! , {
! "SEE", SWITCH_SEE}
! 
! , {
! "SEEFLAG", SWITCH_SEEFLAG}
! 
! , {
! "SELF", SWITCH_SELF}
! 
! , {
! "SEND", SWITCH_SEND}
! 
! , {
! "SET", SWITCH_SET}
! 
! , {
! "SILENT", SWITCH_SILENT}
! 
! , {
! "SKIPDEFAULTS", SWITCH_SKIPDEFAULTS}
! 
! , {
! "SPEAK", SWITCH_SPEAK}
! 
! , {
! "STATS", SWITCH_STATS}
! 
! , {
! "SUMMARY", SWITCH_SUMMARY}
! 
! , {
! "TABLES", SWITCH_TABLES}
! 
! , {
! "TAG", SWITCH_TAG}
! 
! , {
! "TELEPORT", SWITCH_TELEPORT}
! 
! , {
! "TF", SWITCH_TF}
! 
! , {
! "THINGS", SWITCH_THINGS}
! 
! , {
! "TITLE", SWITCH_TITLE}
! 
! , {
! "TRACE", SWITCH_TRACE}
! 
! , {
! "UNCLEAR", SWITCH_UNCLEAR}
! 
! , {
! "UNFOLDER", SWITCH_UNFOLDER}
! 
! , {
! "UNGAG", SWITCH_UNGAG}
! 
! , {
! "UNHIDE", SWITCH_UNHIDE}
! 
! , {
! "UNMUTE", SWITCH_UNMUTE}
! 
! , {
! "UNTAG", SWITCH_UNTAG}
! 
! , {
! "UNTIL", SWITCH_UNTIL}
! 
! , {
! "URGENT", SWITCH_URGENT}
! 
! , {
! "USEFLAG", SWITCH_USEFLAG}
! 
! , {
! "WHAT", SWITCH_WHAT}
! 
! , {
! "WHO", SWITCH_WHO}
! 
! , {
! "WIPE", SWITCH_WIPE}
! 
! , {
! "WIZ", SWITCH_WIZ}
! 
! , {
! "WIZARD", SWITCH_WIZARD}
! 
! , {
! "YES", SWITCH_YES}
! 
! , {
! "ZONE", SWITCH_ZONE}
! 
  ,
*** 1_7_4.187/src/extchat.c Fri, 09 Nov 2001 13:23:58 -0600 dunemush (pennmush/c/23_extchat.c 1.1.1.1.1.1.1.1.1.2.1.1.1.3.1.1.1.5.1.1.1.1.1.5.1.2.1.3.1.3.1.1.1.4.1.2.1.6.1.2.1.1.2.4.2.9.1.2.1.2.1.3.1.2.1.2 660)
--- 1_7_4.188(w)/src/extchat.c Mon, 03 Dec 2001 10:09:23 -0600 dunemush (pennmush/c/23_extchat.c 1.1.1.1.1.1.1.1.1.2.1.1.1.3.1.1.1.5.1.1.1.1.1.5.1.2.1.3.1.3.1.1.1.4.1.2.1.6.1.2.1.1.2.4.2.9.1.2.1.2.1.3.1.2.1.2 660)
***************
*** 1419,1427 ****
  
    if (!name || !*name) {
      p = Chanlist(player);
!     /* Javelin: I set it so if you leave off the channel name.
!      * it doesn't list the channels. If you don't like, 
!      * get rid of it here. -DTC */
      silent = 1;
      notify(player, T("Done."));
    } else {
--- 1419,1428 ----
  
    if (!name || !*name) {
      p = Chanlist(player);
!     if (!p) {
!       notify(player, T("You are not on any channels."));
!       return;
!     }
      silent = 1;
      notify(player, T("Done."));
    } else {
***************
*** 1553,1563 ****
    char cleanname[CHAN_NAME_LEN];
    const char thirtyblanks[31] = "                              ";
    char blanks[31];
  
    if (SUPPORT_PUEBLO)
      notify_noenter(player, tprintf("%cSAMP%c", TAG_START, TAG_END));
!   notify_format(player, "%-*s %-5s %8s %-16s %-8s",
! 		CHAN_NAME_LEN,
  		"Name", "Users", "Msgs", T("Chan Type"), "Status");
    for (c = channels; c; c = c->next) {
      strcpy(cleanname, remove_markup(ChanName(c), NULL));
--- 1554,1564 ----
    char cleanname[CHAN_NAME_LEN];
    const char thirtyblanks[31] = "                              ";
    char blanks[31];
+   int numblanks;
  
    if (SUPPORT_PUEBLO)
      notify_noenter(player, tprintf("%cSAMP%c", TAG_START, TAG_END));
!   notify_format(player, "%-30s %-5s %8s %-16s %-8s",
  		"Name", "Users", "Msgs", T("Chan Type"), "Status");
    for (c = channels; c; c = c->next) {
      strcpy(cleanname, remove_markup(ChanName(c), NULL));
***************
*** 1570,1577 ****
  		TAG_START, TAG_END);
        else
  	sprintf(numusers, "%5ld", ChanNumUsers(c));
!       strcpy(blanks, thirtyblanks);
!       blanks[strlen(ChanName(c)) - strlen(cleanname)] = '\0';
        notify_format(player,
  		    "%-30s%s %s %8ld [%c%c%c%c%c%c%c %c%c%c%c%c%c] [%-3s %c%c]",
  		    ChanName(c), blanks, numusers, ChanNumMsgs(c),
--- 1571,1583 ----
  		TAG_START, TAG_END);
        else
  	sprintf(numusers, "%5ld", ChanNumUsers(c));
!       numblanks = strlen(ChanName(c)) - strlen(cleanname);
!       if (numblanks > 0 && numblanks < 31) {
! 	strcpy(blanks, thirtyblanks);
! 	blanks[numblanks] = '\0';
!       } else {
! 	blanks[0] = '\0';
!       }
        notify_format(player,
  		    "%-30s%s %s %8ld [%c%c%c%c%c%c%c %c%c%c%c%c%c] [%-3s %c%c]",
  		    ChanName(c), blanks, numusers, ChanNumMsgs(c),
*** 1_7_4.187/hdrs/version.h Tue, 13 Nov 2001 17:29:19 -0600 dunemush (pennmush/c/47_version.h 1.32.1.2.1.7.1.9.1.1.1.1.1.1 660)
--- 1_7_4.188(w)/hdrs/version.h Mon, 03 Dec 2001 10:09:26 -0600 dunemush (pennmush/c/47_version.h 1.32.1.2.1.7.1.9.1.1.1.1.1.1 660)
***************
*** 1,2 ****
! #define VERSION "PennMUSH version 1.7.4 patchlevel 12 [11/09/2001]"
! #define SHORTVN "PennMUSH 1.7.4p12"
--- 1,2 ----
! #define VERSION "PennMUSH version 1.7.4 patchlevel 13 [11/30/2001]"
! #define SHORTVN "PennMUSH 1.7.4p13"
*** 1_7_4.187/options.h.dist Tue, 31 Jul 2001 16:27:51 -0500 dunemush (pennmush/d/33_options.h. 1.10.1.1.1.1.1.2.1.1.1.1.1.1.1.3 600)
--- 1_7_4.188(w)/options.h.dist Wed, 14 Nov 2001 12:33:26 -0600 dunemush (pennmush/d/33_options.h. 1.10.1.1.1.1.1.2.1.1.1.1.1.1.1.3.1.1 600)
***************
*** 54,60 ****
   * your operating system's malloc. 
   * Set the value of MALLOC_PACKAGE  to one of these values:
   *  0 -- Use my system's malloc. Required for Win32 systems.
!  *       Recommended for FreeBSD, Linux, Mac OS X, and other operating systems 
   *       where you think the malloc routines are efficient and debugged.
   *       Otherwise, use only as a last resort.
   *  1 -- Use the CSRI malloc package in normal mode. 
--- 54,60 ----
   * your operating system's malloc. 
   * Set the value of MALLOC_PACKAGE  to one of these values:
   *  0 -- Use my system's malloc. Required for Win32 systems.
!  *       Recommended for FreeBSD, Linux, Mac OS X/Darwin, and other OS's
   *       where you think the malloc routines are efficient and debugged.
   *       Otherwise, use only as a last resort.
   *  1 -- Use the CSRI malloc package in normal mode. 
*** 1_7_4.187/src/pcre.c Tue, 15 May 2001 15:59:50 -0500 dunemush (pennmush/d/36_pcre.c 1.4.1.3.1.3.1.1.1.1.1.1.1.1 660)
--- 1_7_4.188(w)/src/pcre.c Mon, 03 Dec 2001 10:09:25 -0600 dunemush (pennmush/d/36_pcre.c 1.4.1.3.1.3.1.1.1.1.1.1.1.2 660)
***************
*** 9,15 ****
  
  Written by: Philip Hazel <ph10@cam.ac.uk>
  
!            Copyright (c) 1997-2000 University of Cambridge
  
  -----------------------------------------------------------------------------
  Permission is granted to anyone to use this software for any purpose on any
--- 9,15 ----
  
  Written by: Philip Hazel <ph10@cam.ac.uk>
  
!            Copyright (c) 1997-2001 University of Cambridge
  
  -----------------------------------------------------------------------------
  Permission is granted to anyone to use this software for any purpose on any
***************
*** 35,71 ****
  /*********** THIS IS AN ALTERED VERSION! ****************/
  /*
     This is an altered version of pcre. It has been altered by
!    Alan Schwartz ("Javelin") for inclusion in PennMUSH.
     Some changes include:
      * All pcre code combined into pcre.c/pcre.h pair
      * includes of config/confmagic.h
      * pcre_malloc and pcre_free changed to malloc and free
!     * Deleted some never-used functions (pcre_version, pcre_info)
!     * Tries to avoid infinitly-long backtracking (Raevnos)
  */
  
  #include "config.h"
  #define BACKTRACK_LIMIT 2500
  
  #include <stdio.h>
- #ifdef I_LIMITS
  #include <limits.h>
- #else
- #ifdef I_VALUES
- #include <values.h>
- #endif
- #endif
- #ifdef I_STRING
  #include <string.h>
- #else
- #include <strings.h>
- #endif
- #include <ctype.h>
  #ifdef BACKTRACK_LIMIT
- #ifdef I_SETJMP
  #include <setjmp.h>
  #endif
- #endif
  #include "pcre.h"
  #include "confmagic.h"
  
--- 35,60 ----
  /*********** THIS IS AN ALTERED VERSION! ****************/
  /*
     This is an altered version of pcre. It has been altered by
!    Alan Schwartz ("Javelin") and Shawn Wagner ("Raevnos") for
!    inclusion in PennMUSH.
     Some changes include:
      * All pcre code combined into pcre.c/pcre.h pair
      * includes of config/confmagic.h
      * pcre_malloc and pcre_free changed to malloc and free
!     * Deleted some never-used functions (pcre_version, pcre_info, etc.)
!     * Tries to avoid infinitely-long backtracking (Raevnos)
!     * Remove unused UTF-8 support.
  */
  
  #include "config.h"
  #define BACKTRACK_LIMIT 2500
  
  #include <stdio.h>
  #include <limits.h>
  #include <string.h>
  #ifdef BACKTRACK_LIMIT
  #include <setjmp.h>
  #endif
  #include "pcre.h"
  #include "confmagic.h"
  
***************
*** 83,102 ****
  #define DPRINTF(p)		/*nothing */
  #endif
  
- /* Allow compilation as C++ source code, should anybody want to do that. */
- 
- #ifdef __cplusplus
- #define class pcre_class
- #endif
- 
- 
  #ifdef BACKTRACK_LIMIT
  jmp_buf backtrack_jmp;
  static unsigned int backtrack_count = 0;
  #endif
  
! /* Number of items on the nested bracket stacks at compile time. This should
! not be set greater than 200. */
  
  #define BRASTACK_SIZE 200
  
--- 72,87 ----
  #define DPRINTF(p)		/*nothing */
  #endif
  
  #ifdef BACKTRACK_LIMIT
  jmp_buf backtrack_jmp;
  static unsigned int backtrack_count = 0;
  #endif
  
! /* Maximum number of items on the nested bracket stacks at compile time. This
! applies to the nesting of all kinds of parentheses. It does not limit
! un-nested, non-capturing parentheses. This number can be made bigger if
! necessary - it is used to dimension one int and one unsigned char vector at
! compile time. */
  
  #define BRASTACK_SIZE 200
  
***************
*** 104,114 ****
  /* The number of bytes in a literal character string above which we can't add
  any more is different when UTF-8 characters may be encountered. */
  
- #ifdef SUPPORT_UTF8
- #define MAXLIT 250
- #else
  #define MAXLIT 255
- #endif
  
  
  /* Min and max values for the common repeats; for the maxima, 0 => infinity */
--- 89,95 ----
***************
*** 130,136 ****
    "class", "Ref", "Recurse",
    "Alt", "Ket", "KetRmax", "KetRmin", "Assert", "Assert not",
    "AssertB", "AssertB not", "Reverse", "Once", "Cond", "Cref",
!   "Brazero", "Braminzero", "Bra"
  };
  #endif
  
--- 111,117 ----
    "class", "Ref", "Recurse",
    "Alt", "Ket", "KetRmax", "KetRmin", "Assert", "Assert not",
    "AssertB", "AssertB not", "Reverse", "Once", "Cond", "Cref",
!   "Brazero", "Braminzero", "Branumber", "Bra"
  };
  #endif
  
***************
*** 146,154 ****
    0, 0, 0, 0, 0, 0, 0, 0,	/* H - O */
    0, 0, 0, -ESC_S, 0, 0, 0, -ESC_W,	/* P - W */
    0, 0, -ESC_Z, '[', '\\', ']', '^', '_',	/* X - _ */
!   '`', 7, -ESC_b, 0, -ESC_d, 27, '\f', 0,	/* ` - g */
!   0, 0, 0, 0, 0, 0, '\n', 0,	/* h - o */
!   0, 0, '\r', -ESC_s, '\t', 0, 0, -ESC_w,	/* p - w */
    0, 0, -ESC_z			/* x - z */
  };
  
--- 127,135 ----
    0, 0, 0, 0, 0, 0, 0, 0,	/* H - O */
    0, 0, 0, -ESC_S, 0, 0, 0, -ESC_W,	/* P - W */
    0, 0, -ESC_Z, '[', '\\', ']', '^', '_',	/* X - _ */
!   '`', 7, -ESC_b, 0, -ESC_d, ESC_E, ESC_F, 0,	/* ` - g */
!   0, 0, 0, 0, 0, 0, ESC_N, 0,	/* h - o */
!   0, 0, ESC_R, -ESC_s, ESC_T, 0, 0, -ESC_w,	/* p - w */
    0, 0, -ESC_z			/* x - z */
  };
  
***************
*** 218,223 ****
--- 199,206 ----
  indirections below, which are can be changed by the caller, but are shared
  between all threads. */
  
+ #define pcre_malloc malloc
+ #define pcre_free free
  
  /*************************************************
  *    Macros and tables for character handling    *
***************
*** 227,293 ****
  byte. The macros for character handling generate simple sequences when used in
  byte-mode, and more complicated ones for UTF-8 characters. */
  
- #ifndef SUPPORT_UTF8
  #define GETCHARINC(c, eptr) c = *eptr++;
  #define GETCHARLEN(c, eptr, len) c = *eptr;
  #define BACKCHAR(eptr)
  
- #else				/* SUPPORT_UTF8 */
- 
- /* Get the next UTF-8 character, advancing the pointer */
- 
- #define GETCHARINC(c, eptr) \
-   c = *eptr++; \
-   if (md->utf8 && (c & 0xc0) == 0xc0) \
-     { \
-     int a = utf8_table4[c & 0x3f];  /* Number of additional bytes */ \
-     int s = 6 - a;                  /* Amount to shift next byte */  \
-     c &= utf8_table3[a];            /* Low order bits from first byte */ \
-     while (a-- > 0) \
-       { \
-       c |= (*eptr++ & 0x3f) << s; \
-       s += 6; \
-       } \
-     }
- 
- /* Get the next UTF-8 character, not advancing the pointer, setting length */
- 
- #define GETCHARLEN(c, eptr, len) \
-   c = *eptr; \
-   len = 1; \
-   if (md->utf8 && (c & 0xc0) == 0xc0) \
-     { \
-     int i; \
-     int a = utf8_table4[c & 0x3f];  /* Number of additional bytes */ \
-     int s = 6 - a;                  /* Amount to shift next byte */  \
-     c &= utf8_table3[a];            /* Low order bits from first byte */ \
-     for (i = 1; i <= a; i++) \
-       { \
-       c |= (eptr[i] & 0x3f) << s; \
-       s += 6; \
-       } \
-     len += a; \
-     }
- 
- /* If the pointer is not at the start of a character, move it back until
- it is. */
- 
- #define BACKCHAR(eptr) while((*eptr & 0xc0) == 0x80) eptr--;
- 
- #endif
- 
- 
- 
- /*************************************************
- *             Default character tables           *
- *************************************************/
- 
- /* A default set of character tables is included in the PCRE binary. Its source
- is built by the maketables auxiliary program, which uses the default C ctypes
- functions, and put in the file chartables.c. These tables are used by PCRE
- whenever the caller of pcre_compile() does not provide an alternate set of
- tables. */
- 
  /*************************************************
  *      Perl-Compatible Regular Expressions       *
  *************************************************/
--- 210,219 ----
***************
*** 475,613 ****
  
  
  
- #ifdef SUPPORT_UTF8
- /*************************************************
- *           Tables for UTF-8 support             *
- *************************************************/
- 
- /* These are the breakpoints for different numbers of bytes in a UTF-8
- character. */
- 
- static int utf8_table1[] =
-   { 0x7f, 0x7ff, 0xffff, 0x1fffff, 0x3ffffff, 0x7fffffff };
- 
- /* These are the indicator bits and the mask for the data bits to set in the
- first byte of a character, indexed by the number of additional bytes. */
- 
- static int utf8_table2[] = { 0, 0xc0, 0xe0, 0xf0, 0xf8, 0xfc };
- static int utf8_table3[] = { 0xff, 0x1f, 0x0f, 0x07, 0x03, 0x01 };
- 
- /* Table of the number of extra characters, indexed by the first character
- masked with 0x3f. The highest number for a valid UTF-8 character is in fact
- 0x3d. */
- 
- static uschar utf8_table4[] = {
-   1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-   1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-   2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
-   3, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5
- };
- 
- 
- /*************************************************
- *       Convert character value to UTF-8         *
- *************************************************/
- 
- /* This function takes an integer value in the range 0 - 0x7fffffff
- and encodes it as a UTF-8 character in 0 to 6 bytes.
- 
- Arguments:
-   cvalue     the character value
-   buffer     pointer to buffer for result - at least 6 bytes long
- 
- Returns:     number of characters placed in the buffer
- */
- 
- static int
- ord2utf8(int cvalue, uschar * buffer)
- {
-   register int i, j;
-   for (i = 0; i < sizeof(utf8_table1) / sizeof(int); i++)
-     if (cvalue <= utf8_table1[i])
-       break;
-   *buffer++ = utf8_table2[i] | (cvalue & utf8_table3[i]);
-   cvalue >>= 6 - i;
-   for (j = 0; j < i; j++) {
-     *buffer++ = 0x80 | (cvalue & 0x3f);
-     cvalue >>= 6;
-   }
-   return i + 1;
- }
- #endif
- 
- 
- 
- 
- /*************************************************
- *        Return info about compiled pattern      *
- *************************************************/
- 
- /* This is a newer "info" function which has an extensible interface so
- that additional items can be added compatibly.
- 
- Arguments:
-   external_re      points to compiled code
-   external_study   points to study data, or NULL
-   what             what information is required
-   where            where to put the information
- 
- Returns:           0 if data returned, negative on error
- */
- 
- int
- pcre_fullinfo(const pcre * external_re, const pcre_extra * study_data, int what,
- 	      void *where)
- {
-   const real_pcre *re = (const real_pcre *) external_re;
-   const real_pcre_extra *study = (const real_pcre_extra *) study_data;
- 
-   if (re == NULL || where == NULL)
-     return PCRE_ERROR_NULL;
-   if (re->magic_number != MAGIC_NUMBER)
-     return PCRE_ERROR_BADMAGIC;
- 
-   switch (what) {
-   case PCRE_INFO_OPTIONS:
-     *((unsigned long int *) where) = re->options & PUBLIC_OPTIONS;
-     break;
- 
-   case PCRE_INFO_SIZE:
-     *((size_t *) where) = re->size;
-     break;
- 
-   case PCRE_INFO_CAPTURECOUNT:
-     *((int *) where) = re->top_bracket;
-     break;
- 
-   case PCRE_INFO_BACKREFMAX:
-     *((int *) where) = re->top_backref;
-     break;
- 
-   case PCRE_INFO_FIRSTCHAR:
-     *((int *) where) =
-       ((re->options & PCRE_FIRSTSET) != 0) ? re->first_char :
-       ((re->options & PCRE_STARTLINE) != 0) ? -1 : -2;
-     break;
- 
-   case PCRE_INFO_FIRSTTABLE:
-     *((const uschar **) where) =
-       (study != NULL && (study->options & PCRE_STUDY_MAPPED) != 0) ?
-       study->start_bits : NULL;
-     break;
- 
-   case PCRE_INFO_LASTLITERAL:
-     *((int *) where) = ((re->options & PCRE_REQCHSET) != 0) ? re->req_char : -1;
-     break;
- 
-   default:
-     return PCRE_ERROR_BADOPTION;
-   }
- 
-   return 0;
- }
- 
- 
- 
  #ifdef DEBUG
  /*************************************************
  *        Debugging function to print chars       *
--- 401,406 ----
***************
*** 753,779 ****
           which can be greater than 0xff, but only if the ddd are hex digits. */
  
      case 'x':
- #ifdef SUPPORT_UTF8
-       if (ptr[1] == '{' && (options & PCRE_UTF8) != 0) {
- 	const uschar *pt = ptr + 2;
- 	register int count = 0;
- 	c = 0;
- 	while ((cd->ctypes[*pt] & ctype_xdigit) != 0) {
- 	  count++;
- 	  c = c * 16 + cd->lcc[*pt] -
- 	    (((cd->ctypes[*pt] & ctype_digit) != 0) ? '0' : 'W');
- 	  pt++;
- 	}
- 	if (*pt == '}') {
- 	  if (c < 0 || count > 8)
- 	    *errorptr = ERR34;
- 	  ptr = pt;
- 	  break;
- 	}
- 	/* If the sequence of hex digits does not end with '}', then we don't
- 	   recognize this construct; fall through to the normal \x handling. */
-       }
- #endif
  
        /* Read just a single hex char */
  
--- 546,551 ----
***************
*** 1001,1010 ****
        /* Skip over things that don't match chars */
  
      case OP_REVERSE:
        cc++;
        /* Fall through */
  
-     case OP_CREF:
      case OP_OPT:
        cc++;
        /* Fall through */
--- 773,783 ----
        /* Skip over things that don't match chars */
  
      case OP_REVERSE:
+     case OP_BRANUMBER:
+     case OP_CREF:
        cc++;
        /* Fall through */
  
      case OP_OPT:
        cc++;
        /* Fall through */
***************
*** 1026,1036 ****
  
      case OP_CHARS:
        branchlength += *(++cc);
- #ifdef SUPPORT_UTF8
-       for (d = 1; d <= *cc; d++)
- 	if ((cc[d] & 0xc0) == 0x80)
- 	  branchlength--;
- #endif
        cc += *cc + 1;
        break;
  
--- 799,804 ----
***************
*** 1059,1065 ****
        /* Check a class for variable quantification */
  
      case OP_CLASS:
!       cc += (*cc == OP_REF) ? 2 : 33;
  
        switch (*cc) {
        case OP_CRSTAR:
--- 827,833 ----
        /* Check a class for variable quantification */
  
      case OP_CLASS:
!       cc += 33;
  
        switch (*cc) {
        case OP_CRSTAR:
***************
*** 1168,1174 ****
  
  Arguments:
    options      the option bits
!   brackets     points to number of brackets used
    code         points to the pointer to the current code point
    ptrptr       points to the current pattern pointer
    errorptr     points to pointer to error message
--- 936,942 ----
  
  Arguments:
    options      the option bits
!   brackets     points to number of extracting brackets used
    code         points to the pointer to the current code point
    ptrptr       points to the current pattern pointer
    errorptr     points to pointer to error message
***************
*** 1218,1224 ****
      int class_charcount;
      int class_lastchar;
      int newoptions;
!     int condref;
      int subreqchar;
  
      c = *ptr;
--- 986,992 ----
      int class_charcount;
      int class_lastchar;
      int newoptions;
!     int skipbytes;
      int subreqchar;
  
      c = *ptr;
***************
*** 1228,1234 ****
        if (c == '#') {
  	/* The space before the ; is to avoid a warning on a silly compiler
  	   on the Macintosh. */
! 	while ((c = *(++ptr)) != 0 && c != '\n') ;
  	continue;
        }
      }
--- 996,1002 ----
        if (c == '#') {
  	/* The space before the ; is to avoid a warning on a silly compiler
  	   on the Macintosh. */
! 	while ((c = *(++ptr)) != 0 && c != NEWLINE) ;
  	continue;
        }
      }
***************
*** 1412,1423 ****
  	  /* Fall through if single character, but don't at present allow
  	     chars > 255 in UTF-8 mode. */
  
- #ifdef SUPPORT_UTF8
- 	  if (c > 255) {
- 	    *errorptr = ERR33;
- 	    goto FAILED;
- 	  }
- #endif
  	}
  
  	/* A single character may be followed by '-' to form a range. However,
--- 1180,1185 ----
***************
*** 1442,1453 ****
  	    const uschar *oldptr = ptr;
  	    d = check_escape(&ptr, errorptr, *brackets, options, TRUE, cd);
  
- #ifdef SUPPORT_UTF8
- 	    if (d > 255) {
- 	      *errorptr = ERR33;
- 	      goto FAILED;
- 	    }
- #endif
  	    /* \b is backslash; any other special means the '-' was literal */
  
  	    if (d < 0) {
--- 1204,1209 ----
***************
*** 1747,1753 ****
  	   OP_BRAZERO in front of it, and because the group appears once in the
  	   data, whereas in other cases it appears the minimum number of times. For
  	   this reason, it is simplest to treat this case separately, as otherwise
! 	   the code gets far too mess. There are several special subcases when the
  	   minimum is zero. */
  
  	if (repeat_min == 0) {
--- 1503,1509 ----
  	   OP_BRAZERO in front of it, and because the group appears once in the
  	   data, whereas in other cases it appears the minimum number of times. For
  	   this reason, it is simplest to treat this case separately, as otherwise
! 	   the code gets far too messy. There are several special subcases when the
  	   minimum is zero. */
  
  	if (repeat_min == 0) {
***************
*** 1888,1894 ****
  
      case '(':
        newoptions = options;
!       condref = -1;
  
        if (*(++ptr) == '?') {
  	int set, unset;
--- 1644,1650 ----
  
      case '(':
        newoptions = options;
!       skipbytes = 0;
  
        if (*(++ptr) == '?') {
  	int set, unset;
***************
*** 1909,1915 ****
  	case '(':
  	  bravalue = OP_COND;	/* Conditional group */
  	  if ((cd->ctypes[*(++ptr)] & ctype_digit) != 0) {
! 	    condref = *ptr - '0';
  	    while (*(++ptr) != ')')
  	      condref = condref * 10 + *ptr - '0';
  	    if (condref == 0) {
--- 1665,1671 ----
  	case '(':
  	  bravalue = OP_COND;	/* Conditional group */
  	  if ((cd->ctypes[*(++ptr)] & ctype_digit) != 0) {
! 	    int condref = *ptr - '0';
  	    while (*(++ptr) != ')')
  	      condref = condref * 10 + *ptr - '0';
  	    if (condref == 0) {
***************
*** 1917,1922 ****
--- 1673,1682 ----
  	      goto FAILED;
  	    }
  	    ptr++;
+ 	    code[3] = OP_CREF;
+ 	    code[4] = condref >> 8;
+ 	    code[5] = condref & 255;
+ 	    skipbytes = 3;
  	  } else
  	    ptr--;
  	  break;
***************
*** 2028,2041 ****
  	}
        }
  
!       /* Else we have a referencing group; adjust the opcode. */
  
        else {
! 	if (++(*brackets) > EXTRACT_MAX) {
! 	  *errorptr = ERR13;
! 	  goto FAILED;
! 	}
! 	bravalue = OP_BRA + *brackets;
        }
  
        /* Process nested bracketed re. Assertions may not be repeated, but other
--- 1788,1806 ----
  	}
        }
  
!       /* Else we have a referencing group; adjust the opcode. If the bracket
!          number is greater than EXTRACT_BASIC_MAX, we set the opcode one higher, and
!          arrange for the true number to follow later, in an OP_BRANUMBER item. */
  
        else {
! 	if (++(*brackets) > EXTRACT_BASIC_MAX) {
! 	  bravalue = OP_BRA + EXTRACT_BASIC_MAX + 1;
! 	  code[3] = OP_BRANUMBER;
! 	  code[4] = *brackets >> 8;
! 	  code[5] = *brackets & 255;
! 	  skipbytes = 3;
! 	} else
! 	  bravalue = OP_BRA + *brackets;
        }
  
        /* Process nested bracketed re. Assertions may not be repeated, but other
***************
*** 2049,2060 ****
  
        if (!compile_regex(options | PCRE_INGROUP,	/* Set for all nested groups */
  			 ((options & PCRE_IMS) != (newoptions & PCRE_IMS)) ? newoptions & PCRE_IMS : -1,	/* Pass ims options if changed */
! 			 brackets,	/* Bracket level */
  			 &tempcode,	/* Where to put code (updated) */
  			 &ptr,	/* Input pointer (updated) */
  			 errorptr,	/* Where to put an error message */
  			 (bravalue == OP_ASSERTBACK || bravalue == OP_ASSERTBACK_NOT),	/* TRUE if back assert */
! 			 condref,	/* Condition reference number */
  			 &subreqchar,	/* For possible last char */
  			 &subcountlits,	/* For literal count */
  			 cd))	/* Tables block */
--- 1814,1825 ----
  
        if (!compile_regex(options | PCRE_INGROUP,	/* Set for all nested groups */
  			 ((options & PCRE_IMS) != (newoptions & PCRE_IMS)) ? newoptions & PCRE_IMS : -1,	/* Pass ims options if changed */
! 			 brackets,	/* Extracting bracket count */
  			 &tempcode,	/* Where to put code (updated) */
  			 &ptr,	/* Input pointer (updated) */
  			 errorptr,	/* Where to put an error message */
  			 (bravalue == OP_ASSERTBACK || bravalue == OP_ASSERTBACK_NOT),	/* TRUE if back assert */
! 			 skipbytes,	/* Skip over OP_COND/OP_BRANUMBER */
  			 &subreqchar,	/* For possible last char */
  			 &subcountlits,	/* For literal count */
  			 cd))	/* Tables block */
***************
*** 2068,2074 ****
        /* If this is a conditional bracket, check that there are no more than
           two branches in the group. */
  
!       if (bravalue == OP_COND) {
  	uschar *tc = code;
  	condcount = 0;
  
--- 1833,1839 ----
        /* If this is a conditional bracket, check that there are no more than
           two branches in the group. */
  
!       else if (bravalue == OP_COND) {
  	uschar *tc = code;
  	condcount = 0;
  
***************
*** 2130,2138 ****
  
        if (c < 0) {
  	if (-c >= ESC_REF) {
  	  previous = code;
  	  *code++ = OP_REF;
! 	  *code++ = -c - ESC_REF;
  	} else {
  	  previous = (-c > ESC_b && -c < ESC_Z) ? code : NULL;
  	  *code++ = -c;
--- 1895,1905 ----
  
        if (c < 0) {
  	if (-c >= ESC_REF) {
+ 	  int number = -c - ESC_REF;
  	  previous = code;
  	  *code++ = OP_REF;
! 	  *code++ = number >> 8;
! 	  *code++ = number & 255;
  	} else {
  	  previous = (-c > ESC_b && -c < ESC_Z) ? code : NULL;
  	  *code++ = -c;
***************
*** 2163,2169 ****
  	  if (c == '#') {
  	    /* The space before the ; is to avoid a warning on a silly compiler
  	       on the Macintosh. */
! 	    while ((c = *(++ptr)) != 0 && c != '\n') ;
  	    if (c == 0)
  	      break;
  	    continue;
--- 1930,1936 ----
  	  if (c == '#') {
  	    /* The space before the ; is to avoid a warning on a silly compiler
  	       on the Macintosh. */
! 	    while ((c = *(++ptr)) != 0 && c != NEWLINE) ;
  	    if (c == 0)
  	      break;
  	    continue;
***************
*** 2185,2200 ****
  	  /* If a character is > 127 in UTF-8 mode, we have to turn it into
  	     two or more characters in the UTF-8 encoding. */
  
- #ifdef SUPPORT_UTF8
- 	  if (c > 127 && (options & PCRE_UTF8) != 0) {
- 	    uschar buffer[8];
- 	    int len = ord2utf8(c, buffer);
- 	    for (c = 0; c < len; c++)
- 	      *code++ = buffer[c];
- 	    length += len;
- 	    continue;
- 	  }
- #endif
  	}
  
  	/* Ordinary character or single-char escape */
--- 1952,1957 ----
***************
*** 2256,2262 ****
    ptrptr      -> the address of the current pattern pointer
    errorptr    -> pointer to error message
    lookbehind  TRUE if this is a lookbehind assertion
!   condref     >= 0 for OPT_CREF setting at start of conditional group
    reqchar     -> place to put the last required character, or a negative number
    countlits   -> place to put the shortest literal count of any branch
    cd          points to the data block with tables pointers
--- 2013,2019 ----
    ptrptr      -> the address of the current pattern pointer
    errorptr    -> pointer to error message
    lookbehind  TRUE if this is a lookbehind assertion
!   skipbytes   skip this many bytes at start (for OP_COND, OP_BRANUMBER)
    reqchar     -> place to put the last required character, or a negative number
    countlits   -> place to put the shortest literal count of any branch
    cd          points to the data block with tables pointers
***************
*** 2267,2273 ****
  static BOOL
  compile_regex(int options, int optchanged, int *brackets, uschar ** codeptr,
  	      const uschar ** ptrptr, const char **errorptr, BOOL lookbehind,
! 	      int condref, int *reqchar, int *countlits, compile_data * cd)
  {
    const uschar *ptr = *ptrptr;
    uschar *code = *codeptr;
--- 2024,2030 ----
  static BOOL
  compile_regex(int options, int optchanged, int *brackets, uschar ** codeptr,
  	      const uschar ** ptrptr, const char **errorptr, BOOL lookbehind,
! 	      int skipbytes, int *reqchar, int *countlits, compile_data * cd)
  {
    const uschar *ptr = *ptrptr;
    uschar *code = *codeptr;
***************
*** 2279,2293 ****
  
    *reqchar = -1;
    *countlits = INT_MAX;
!   code += 3;
! 
! /* At the start of a reference-based conditional group, insert the reference
! number as an OP_CREF item. */
! 
!   if (condref >= 0) {
!     *code++ = OP_CREF;
!     *code++ = condref;
!   }
  
  /* Loop for each alternative branch */
  
--- 2036,2042 ----
  
    *reqchar = -1;
    *countlits = INT_MAX;
!   code += 3 + skipbytes;
  
  /* Loop for each alternative branch */
  
***************
*** 2430,2436 ****
        break;
  
      case OP_CREF:
!       code += 2;
        break;
  
      case OP_WORD_BOUNDARY:
--- 2179,2186 ----
        break;
  
      case OP_CREF:
!     case OP_BRANUMBER:
!       code += 3;
        break;
  
      case OP_WORD_BOUNDARY:
***************
*** 2653,2664 ****
  
  /* Can't support UTF8 unless PCRE has been compiled to include the code. */
  
- #ifndef SUPPORT_UTF8
    if ((options & PCRE_UTF8) != 0) {
      *errorptr = ERR32;
      return NULL;
    }
- #endif
  
  /* We can't pass back an error message if errorptr is NULL; I guess the best we
  can do is just return NULL. */
--- 2403,2412 ----
***************
*** 2705,2710 ****
--- 2453,2459 ----
    while ((c = *(++ptr)) != 0) {
      int min, max;
      int class_charcount;
+     int bracket_length;
  
      if ((options & PCRE_EXTENDED) != 0) {
        if ((compile_block.ctypes[c] & ctype_space) != 0)
***************
*** 2712,2718 ****
        if (c == '#') {
  	/* The space before the ; is to avoid a warning on a silly compiler
  	   on the Macintosh. */
! 	while ((c = *(++ptr)) != 0 && c != '\n') ;
  	continue;
        }
      }
--- 2461,2467 ----
        if (c == '#') {
  	/* The space before the ; is to avoid a warning on a silly compiler
  	   on the Macintosh. */
! 	while ((c = *(++ptr)) != 0 && c != NEWLINE) ;
  	continue;
        }
      }
***************
*** 2739,2745 ****
        }
        length++;
  
!       /* A back reference needs an additional char, plus either one or 5
           bytes for a repeat. We also need to keep the value of the highest
           back reference. */
  
--- 2488,2494 ----
        }
        length++;
  
!       /* A back reference needs an additional 2 bytes, plus either one or 5
           bytes for a repeat. We also need to keep the value of the highest
           back reference. */
  
***************
*** 2747,2753 ****
  	int refnum = -c - ESC_REF;
  	if (refnum > top_backref)
  	  top_backref = refnum;
! 	length++;		/* For single back reference */
  	if (ptr[1] == '{' && is_counted_repeat(ptr + 2, &compile_block)) {
  	  ptr =
  	    read_repeat_counts(ptr + 2, &min, &max, errorptr, &compile_block);
--- 2496,2502 ----
  	int refnum = -c - ESC_REF;
  	if (refnum > top_backref)
  	  top_backref = refnum;
! 	length += 2;		/* For single back reference */
  	if (ptr[1] == '{' && is_counted_repeat(ptr + 2, &compile_block)) {
  	  ptr =
  	    read_repeat_counts(ptr + 2, &min, &max, errorptr, &compile_block);
***************
*** 2861,2866 ****
--- 2610,2616 ----
  
      case '(':
        branch_newextra = 0;
+       bracket_length = 3;
  
        /* Handle special forms of bracket, which all start (? */
  
***************
*** 2923,2929 ****
  	case '(':
  	  if ((compile_block.ctypes[ptr[3]] & ctype_digit) != 0) {
  	    ptr += 4;
! 	    length += 2;
  	    while ((compile_block.ctypes[*ptr] & ctype_digit) != 0)
  	      ptr++;
  	    if (*ptr != ')') {
--- 2673,2679 ----
  	case '(':
  	  if ((compile_block.ctypes[ptr[3]] & ctype_digit) != 0) {
  	    ptr += 4;
! 	    length += 3;
  	    while ((compile_block.ctypes[*ptr] & ctype_digit) != 0)
  	      ptr++;
  	    if (*ptr != ')') {
***************
*** 3045,3060 ****
        }
  
        /* Extracting brackets must be counted so we can process escapes in a
!          Perlish way. */
  
!       else
  	bracount++;
  
!       /* Non-special forms of bracket. Save length for computing whole length
!          at end if there's a repeat that requires duplication of the group. Also
!          save the current value of branch_extra, and start the new group with
!          the new value. If non-zero, this will either be 2 for a (?imsx: group, or 3
!          for a lookbehind assertion. */
  
        if (brastackptr >= sizeof(brastack) / sizeof(int)) {
  	*errorptr = ERR19;
--- 2795,2813 ----
        }
  
        /* Extracting brackets must be counted so we can process escapes in a
!          Perlish way. If the number exceeds EXTRACT_BASIC_MAX we are going to
!          need an additional 3 bytes of store per extracting bracket. */
  
!       else {
  	bracount++;
+ 	if (bracount > EXTRACT_BASIC_MAX)
+ 	  bracket_length += 3;
+       }
  
!       /* Save length for computing whole length at end if there's a repeat that
!          requires duplication of the group. Also save the current value of
!          branch_extra, and start the new group with the new value. If non-zero, this
!          will either be 2 for a (?imsx: group, or 3 for a lookbehind assertion. */
  
        if (brastackptr >= sizeof(brastack) / sizeof(int)) {
  	*errorptr = ERR19;
***************
*** 3065,3071 ****
        branch_extra = branch_newextra;
  
        brastack[brastackptr++] = length;
!       length += 3;
        continue;
  
        /* Handle ket. Look for subsequent max/min; for certain sets of values we
--- 2818,2824 ----
        branch_extra = branch_newextra;
  
        brastack[brastackptr++] = length;
!       length += bracket_length;
        continue;
  
        /* Handle ket. Look for subsequent max/min; for certain sets of values we
***************
*** 3148,3154 ****
  	  if (c == '#') {
  	    /* The space before the ; is to avoid a warning on a silly compiler
  	       on the Macintosh. */
! 	    while ((c = *(++ptr)) != 0 && c != '\n') ;
  	    continue;
  	  }
  	}
--- 2901,2907 ----
  	  if (c == '#') {
  	    /* The space before the ; is to avoid a warning on a silly compiler
  	       on the Macintosh. */
! 	    while ((c = *(++ptr)) != 0 && c != NEWLINE) ;
  	    continue;
  	  }
  	}
***************
*** 3166,3180 ****
  	    ptr = saveptr;
  	    break;
  	  }
! #ifdef SUPPORT_UTF8
! 	  if (c > 127 && (options & PCRE_UTF8) != 0) {
! 	    int i;
! 	    for (i = 0; i < sizeof(utf8_table1) / sizeof(int); i++)
! 	      if (c <= utf8_table1[i])
! 		break;
! 	    runlength += i;
! 	  }
! #endif
  	}
  
  	/* Ordinary character or single-char escape */
--- 2919,2925 ----
  	    ptr = saveptr;
  	    break;
  	  }
! 
  	}
  
  	/* Ordinary character or single-char escape */
***************
*** 3207,3213 ****
  difference to the value of the offsetof(). */
  
    size = length + offsetof(real_pcre, code[0]);
!   re = (real_pcre *) malloc(size);
  
    if (re == NULL) {
      *errorptr = ERR21;
--- 2952,2958 ----
  difference to the value of the offsetof(). */
  
    size = length + offsetof(real_pcre, code[0]);
!   re = (real_pcre *) (pcre_malloc) (size);
  
    if (re == NULL) {
      *errorptr = ERR21;
***************
*** 3229,3235 ****
    code = re->code;
    *code = OP_BRA;
    bracount = 0;
!   (void) compile_regex(options, -1, &bracount, &code, &ptr, errorptr, FALSE, -1,
  		       &reqchar, &countlits, &compile_block);
    re->top_bracket = bracount;
    re->top_backref = top_backref;
--- 2974,2980 ----
    code = re->code;
    *code = OP_BRA;
    bracount = 0;
!   (void) compile_regex(options, -1, &bracount, &code, &ptr, errorptr, FALSE, 0,
  		       &reqchar, &countlits, &compile_block);
    re->top_bracket = bracount;
    re->top_backref = top_backref;
***************
*** 3258,3264 ****
  /* Failed to compile */
  
    if (*errorptr != NULL) {
!     free(re);
    PCRE_ERROR_RETURN:
      *erroroffset = ptr - (const uschar *) pattern;
      return NULL;
--- 3003,3009 ----
  /* Failed to compile */
  
    if (*errorptr != NULL) {
!     (pcre_free) (re);
    PCRE_ERROR_RETURN:
      *erroroffset = ptr - (const uschar *) pattern;
      return NULL;
***************
*** 3339,3345 ****
      printf("%3d ", code - code_base);
  
      if (*code >= OP_BRA) {
!       printf("%3d Bra %d", (code[1] << 8) + code[2], *code - OP_BRA);
        code += 2;
      }
  
--- 3084,3093 ----
      printf("%3d ", code - code_base);
  
      if (*code >= OP_BRA) {
!       if (*code - OP_BRA > EXTRACT_BASIC_MAX)
! 	printf("%3d Bra extra", (code[1] << 8) + code[2]);
!       else
! 	printf("%3d Bra %d", (code[1] << 8) + code[2], *code - OP_BRA);
        code += 2;
      }
  
***************
*** 3350,3365 ****
  	code++;
  	break;
  
-       case OP_COND:
- 	printf("%3d Cond", (code[1] << 8) + code[2]);
- 	code += 2;
- 	break;
- 
-       case OP_CREF:
- 	printf(" %.2d %s", code[1], OP_names[*code]);
- 	code++;
- 	break;
- 
        case OP_CHARS:
  	charlength = *(++code);
  	printf("%3d ", charlength);
--- 3098,3103 ----
***************
*** 3379,3389 ****
        case OP_ASSERTBACK:
        case OP_ASSERTBACK_NOT:
        case OP_ONCE:
- 	printf("%3d %s", (code[1] << 8) + code[2], OP_names[*code]);
- 	code += 2;
- 	break;
- 
        case OP_REVERSE:
  	printf("%3d %s", (code[1] << 8) + code[2], OP_names[*code]);
  	code += 2;
  	break;
--- 3117,3126 ----
        case OP_ASSERTBACK:
        case OP_ASSERTBACK_NOT:
        case OP_ONCE:
        case OP_REVERSE:
+       case OP_BRANUMBER:
+       case OP_COND:
+       case OP_CREF:
  	printf("%3d %s", (code[1] << 8) + code[2], OP_names[*code]);
  	code += 2;
  	break;
***************
*** 3472,3479 ****
  	break;
  
        case OP_REF:
! 	printf("    \\%d", *(++code));
! 	code++;
  	goto CLASS_REF_REPEAT;
  
        case OP_CLASS:
--- 3209,3216 ----
  	break;
  
        case OP_REF:
! 	printf("    \\%d", (code[1] << 8) | code[2]);
! 	code += 3;
  	goto CLASS_REF_REPEAT;
  
        case OP_CLASS:
***************
*** 3558,3564 ****
  
    if (code - re->code > length) {
      *errorptr = ERR23;
!     free(re);
      *erroroffset = ptr - (uschar *) pattern;
      return NULL;
    }
--- 3295,3301 ----
  
    if (code - re->code > length) {
      *errorptr = ERR23;
!     (pcre_free) (re);
      *erroroffset = ptr - (uschar *) pattern;
      return NULL;
    }
***************
*** 3703,3710 ****
         here; that is handled in the code for KET. */
  
      if (op > OP_BRA) {
        int number = op - OP_BRA;
!       int offset = number << 1;
  
  #ifdef DEBUG
        printf("start bracket %d subject=", number);
--- 3440,3454 ----
         here; that is handled in the code for KET. */
  
      if (op > OP_BRA) {
+       int offset;
        int number = op - OP_BRA;
! 
!       /* For extended extraction brackets (large number), we have to fish out the
!          number from a dummy opcode at the start. */
! 
!       if (number > EXTRACT_BASIC_MAX)
! 	number = (ecode[4] << 8) | ecode[5];
!       offset = number << 1;
  
  #ifdef DEBUG
        printf("start bracket %d subject=", number);
***************
*** 3733,3738 ****
--- 3477,3483 ----
  	md->offset_vector[offset] = save_offset1;
  	md->offset_vector[offset + 1] = save_offset2;
  	md->offset_vector[md->offset_end - number] = save_offset3;
+ 
  	return FALSE;
        }
  
***************
*** 3763,3774 ****
  
      case OP_COND:
        if (ecode[3] == OP_CREF) {	/* Condition is extraction test */
! 	int offset = ecode[4] << 1;	/* Doubled reference number */
  	return match(eptr,
  		     ecode +
! 		     ((offset < offset_top && md->offset_vector[offset] >= 0) ?
! 		      5 : 3 + (ecode[1] << 8) + ecode[2]), offset_top, md, ims,
! 		     eptrb, match_isgroup);
        }
  
        /* The condition is an assertion. Call match() to evaluate it - setting
--- 3508,3520 ----
  
      case OP_COND:
        if (ecode[3] == OP_CREF) {	/* Condition is extraction test */
! 	int offset = (ecode[4] << 9) | (ecode[5] << 1);	/* Doubled ref number */
  	return match(eptr,
  		     ecode +
! 		     ((offset < offset_top
! 		       && md->offset_vector[offset] >=
! 		       0) ? 6 : 3 + (ecode[1] << 8) + ecode[2]), offset_top, md,
! 		     ims, eptrb, match_isgroup);
        }
  
        /* The condition is an assertion. Call match() to evaluate it - setting
***************
*** 3787,3796 ****
        }
        /* Control never reaches here */
  
!       /* Skip over conditional reference data if encountered (should not be) */
  
      case OP_CREF:
!       ecode += 2;
        break;
  
        /* End of the pattern. If PCRE_NOTEMPTY is set, fail if we have matched
--- 3533,3544 ----
        }
        /* Control never reaches here */
  
!       /* Skip over conditional reference or large extraction number data if
!          encountered. */
  
      case OP_CREF:
!     case OP_BRANUMBER:
!       ecode += 3;
        break;
  
        /* End of the pattern. If PCRE_NOTEMPTY is set, fail if we have matched
***************
*** 3866,3880 ****
           back a number of characters, not bytes. */
  
      case OP_REVERSE:
- #ifdef SUPPORT_UTF8
-       c = (ecode[1] << 8) + ecode[2];
-       for (i = 0; i < c; i++) {
- 	eptr--;
- 	BACKCHAR(eptr)
-       }
- #else
        eptr -= (ecode[1] << 8) + ecode[2];
- #endif
  
        if (eptr < md->start_subject)
  	return FALSE;
--- 3614,3620 ----
***************
*** 3904,3910 ****
  	if (c < 16)
  	  save = stacksave;
  	else {
! 	  save = (int *) malloc((c + 1) * sizeof(int));
  	  if (save == NULL) {
  	    save = stacksave;
  	    c = 15;
--- 3644,3650 ----
  	if (c < 16)
  	  save = stacksave;
  	else {
! 	  save = (int *) (pcre_malloc) ((c + 1) * sizeof(int));
  	  if (save == NULL) {
  	    save = stacksave;
  	    c = 15;
***************
*** 3918,3924 ****
  	for (i = 1; i <= c; i++)
  	  md->offset_vector[md->offset_end - i] = save[i];
  	if (save != stacksave)
! 	  free(save);
  	if (!rc)
  	  return FALSE;
  
--- 3658,3664 ----
  	for (i = 1; i <= c; i++)
  	  md->offset_vector[md->offset_end - i] = save[i];
  	if (save != stacksave)
! 	  (pcre_free) (save);
  	if (!rc)
  	  return FALSE;
  
***************
*** 4066,4073 ****
  	   extraction by setting the offsets and bumping the high water mark. */
  
  	if (*prev != OP_COND) {
  	  int number = *prev - OP_BRA;
! 	  int offset = number << 1;
  
  #ifdef DEBUG
  	  printf("end bracket %d", number);
--- 3806,3820 ----
  	   extraction by setting the offsets and bumping the high water mark. */
  
  	if (*prev != OP_COND) {
+ 	  int offset;
  	  int number = *prev - OP_BRA;
! 
! 	  /* For extended extraction brackets (large number), we have to fish out
! 	     the number from a dummy opcode at the start. */
! 
! 	  if (number > EXTRACT_BASIC_MAX)
! 	    number = (prev[4] << 8) | prev[5];
! 	  offset = number << 1;
  
  #ifdef DEBUG
  	  printf("end bracket %d", number);
***************
*** 4126,4132 ****
        if (md->notbol && eptr == md->start_subject)
  	return FALSE;
        if ((ims & PCRE_MULTILINE) != 0) {
! 	if (eptr != md->start_subject && eptr[-1] != '\n')
  	  return FALSE;
  	ecode++;
  	break;
--- 3873,3879 ----
        if (md->notbol && eptr == md->start_subject)
  	return FALSE;
        if ((ims & PCRE_MULTILINE) != 0) {
! 	if (eptr != md->start_subject && eptr[-1] != NEWLINE)
  	  return FALSE;
  	ecode++;
  	break;
***************
*** 4147,4153 ****
      case OP_DOLL:
        if ((ims & PCRE_MULTILINE) != 0) {
  	if (eptr < md->end_subject) {
! 	  if (*eptr != '\n')
  	    return FALSE;
  	} else {
  	  if (md->noteol)
--- 3894,3900 ----
      case OP_DOLL:
        if ((ims & PCRE_MULTILINE) != 0) {
  	if (eptr < md->end_subject) {
! 	  if (*eptr != NEWLINE)
  	    return FALSE;
  	} else {
  	  if (md->noteol)
***************
*** 4160,4166 ****
  	  return FALSE;
  	if (!md->endonly) {
  	  if (eptr < md->end_subject - 1 ||
! 	      (eptr == md->end_subject - 1 && *eptr != '\n'))
  	    return FALSE;
  
  	  ecode++;
--- 3907,3913 ----
  	  return FALSE;
  	if (!md->endonly) {
  	  if (eptr < md->end_subject - 1 ||
! 	      (eptr == md->end_subject - 1 && *eptr != NEWLINE))
  	    return FALSE;
  
  	  ecode++;
***************
*** 4181,4187 ****
  
      case OP_EODN:
        if (eptr < md->end_subject - 1 ||
! 	  (eptr == md->end_subject - 1 && *eptr != '\n'))
  	return FALSE;
        ecode++;
        break;
--- 3928,3934 ----
  
      case OP_EODN:
        if (eptr < md->end_subject - 1 ||
! 	  (eptr == md->end_subject - 1 && *eptr != NEWLINE))
  	return FALSE;
        ecode++;
        break;
***************
*** 4204,4218 ****
        /* Match a single character type; inline for speed */
  
      case OP_ANY:
!       if ((ims & PCRE_DOTALL) == 0 && eptr < md->end_subject && *eptr == '\n')
  	return FALSE;
        if (eptr++ >= md->end_subject)
  	return FALSE;
- #ifdef SUPPORT_UTF8
-       if (md->utf8)
- 	while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80)
- 	  eptr++;
- #endif
        ecode++;
        break;
  
--- 3951,3961 ----
        /* Match a single character type; inline for speed */
  
      case OP_ANY:
!       if ((ims & PCRE_DOTALL) == 0 && eptr < md->end_subject
! 	  && *eptr == NEWLINE)
  	return FALSE;
        if (eptr++ >= md->end_subject)
  	return FALSE;
        ecode++;
        break;
  
***************
*** 4263,4270 ****
      case OP_REF:
        {
  	int length;
! 	int offset = ecode[1] << 1;	/* Doubled reference number */
! 	ecode += 2;		/* Advance past the item */
  
  	/* If the reference is unset, set the length to be longer than the amount
  	   of subject left; this ensures that every attempt at a match fails. We
--- 4006,4013 ----
      case OP_REF:
        {
  	int length;
! 	int offset = (ecode[1] << 9) | (ecode[2] << 1);	/* Doubled ref number */
! 	ecode += 3;		/* Advance past item */
  
  	/* If the reference is unset, set the length to be longer than the amount
  	   of subject left; this ensures that every attempt at a match fails. We
***************
*** 4410,4423 ****
  	  if (eptr >= md->end_subject)
  	    return FALSE;
  	  GETCHARINC(c, eptr)
- 	    /* Get character; increment eptr */
- #ifdef SUPPORT_UTF8
- 	    /* We do not yet support class members > 255 */
- 	    if (c > 255)
- 	    return FALSE;
- #endif
  
! 	  if ((data[c / 8] & (1 << (c & 7))) != 0)
  	    continue;
  	  return FALSE;
  	}
--- 4153,4161 ----
  	  if (eptr >= md->end_subject)
  	    return FALSE;
  	  GETCHARINC(c, eptr)
  
! 	    /* Get character; increment eptr */
! 	    if ((data[c / 8] & (1 << (c & 7))) != 0)
  	    continue;
  	  return FALSE;
  	}
***************
*** 4439,4450 ****
  	      return FALSE;
  	    GETCHARINC(c, eptr)
  	      /* Get character; increment eptr */
! #ifdef SUPPORT_UTF8
! 	      /* We do not yet support class members > 255 */
! 	      if (c > 255)
! 	      return FALSE;
! #endif
! 	    if ((data[c / 8] & (1 << (c & 7))) != 0)
  	      continue;
  	    return FALSE;
  	  }
--- 4177,4183 ----
  	      return FALSE;
  	    GETCHARINC(c, eptr)
  	      /* Get character; increment eptr */
! 	      if ((data[c / 8] & (1 << (c & 7))) != 0)
  	      continue;
  	    return FALSE;
  	  }
***************
*** 4461,4472 ****
  	      break;
  	    GETCHARLEN(c, eptr, len)
  	      /* Get character, set length if UTF-8 */
! #ifdef SUPPORT_UTF8
! 	      /* We do not yet support class members > 255 */
! 	      if (c > 255)
! 	      break;
! #endif
! 	    if ((data[c / 8] & (1 << (c & 7))) == 0)
  	      break;
  	    eptr += len;
  	  }
--- 4194,4200 ----
  	      break;
  	    GETCHARLEN(c, eptr, len)
  	      /* Get character, set length if UTF-8 */
! 	      if ((data[c / 8] & (1 << (c & 7))) == 0)
  	      break;
  	    eptr += len;
  	  }
***************
*** 4475,4483 ****
  	    if (match(eptr--, ecode, offset_top, md, ims, eptrb, 0))
  	      return TRUE;
  
- #ifdef SUPPORT_UTF8
- 	    BACKCHAR(eptr)
- #endif
  	  }
  	  return FALSE;
  	}
--- 4203,4208 ----
***************
*** 4802,4823 ****
        if (min > 0)
  	switch (ctype) {
  	case OP_ANY:
- #ifdef SUPPORT_UTF8
- 	  if (md->utf8) {
- 	    for (i = 1; i <= min; i++) {
- 	      if (eptr >= md->end_subject ||
- 		  (*eptr++ == '\n' && (ims & PCRE_DOTALL) == 0))
- 		return FALSE;
- 	      while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80)
- 		eptr++;
- 	    }
- 	    break;
- 	  }
- #endif
  	  /* Non-UTF8 can be faster */
  	  if ((ims & PCRE_DOTALL) == 0) {
  	    for (i = 1; i <= min; i++)
! 	      if (*eptr++ == '\n')
  		return FALSE;
  	  } else
  	    eptr += min;
--- 4527,4536 ----
        if (min > 0)
  	switch (ctype) {
  	case OP_ANY:
  	  /* Non-UTF8 can be faster */
  	  if ((ims & PCRE_DOTALL) == 0) {
  	    for (i = 1; i <= min; i++)
! 	      if (*eptr++ == NEWLINE)
  		return FALSE;
  	  } else
  	    eptr += min;
***************
*** 4878,4890 ****
  	  c = *eptr++;
  	  switch (ctype) {
  	  case OP_ANY:
! 	    if ((ims & PCRE_DOTALL) == 0 && c == '\n')
  	      return FALSE;
- #ifdef SUPPORT_UTF8
- 	    if (md->utf8)
- 	      while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80)
- 		eptr++;
- #endif
  	    break;
  
  	  case OP_NOT_DIGIT:
--- 4591,4598 ----
  	  c = *eptr++;
  	  switch (ctype) {
  	  case OP_ANY:
! 	    if ((ims & PCRE_DOTALL) == 0 && c == NEWLINE)
  	      return FALSE;
  	    break;
  
  	  case OP_NOT_DIGIT:
***************
*** 4932,4960 ****
  	  /* Special code is required for UTF8, but when the maximum is unlimited
  	     we don't need it. */
  
- #ifdef SUPPORT_UTF8
- 	  if (md->utf8 && max < INT_MAX) {
- 	    if ((ims & PCRE_DOTALL) == 0) {
- 	      for (i = min; i < max; i++) {
- 		if (eptr >= md->end_subject || *eptr++ == '\n')
- 		  break;
- 		while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80)
- 		  eptr++;
- 	      }
- 	    } else {
- 	      for (i = min; i < max; i++) {
- 		eptr++;
- 		while (eptr < md->end_subject && (*eptr & 0xc0) == 0x80)
- 		  eptr++;
- 	      }
- 	    }
- 	    break;
- 	  }
- #endif
  	  /* Non-UTF8 can be faster */
  	  if ((ims & PCRE_DOTALL) == 0) {
  	    for (i = min; i < max; i++) {
! 	      if (eptr >= md->end_subject || *eptr == '\n')
  		break;
  	      eptr++;
  	    }
--- 4640,4649 ----
  	  /* Special code is required for UTF8, but when the maximum is unlimited
  	     we don't need it. */
  
  	  /* Non-UTF8 can be faster */
  	  if ((ims & PCRE_DOTALL) == 0) {
  	    for (i = min; i < max; i++) {
! 	      if (eptr >= md->end_subject || *eptr == NEWLINE)
  		break;
  	      eptr++;
  	    }
***************
*** 5024,5034 ****
  	while (eptr >= pp) {
  	  if (match(eptr--, ecode, offset_top, md, ims, eptrb, 0))
  	    return TRUE;
- #ifdef SUPPORT_UTF8
- 	  if (md->utf8)
- 	    while (eptr > pp && (*eptr & 0xc0) == 0x80)
- 	      eptr--;
- #endif
  	}
  	return FALSE;
        }
--- 4713,4718 ----
***************
*** 5085,5090 ****
--- 4769,4775 ----
    volatile match_data match_block;
    volatile BOOL using_temporary_offsets = FALSE;
  
+ 
  #ifdef BACKTRACK_LIMIT
    backtrack_count = 0;
    if (setjmp(backtrack_jmp)) {
***************
*** 5108,5115 ****
      const uschar *req_char_ptr = start_match - 1;
      const real_pcre *re = (const real_pcre *) external_re;
      const real_pcre_extra *extra = (const real_pcre_extra *) external_extra;
!     BOOL anchored = ((re->options | options) & PCRE_ANCHORED) != 0;
!     BOOL startline = (re->options & PCRE_STARTLINE) != 0;
  
      if ((options & ~PUBLIC_EXEC_OPTIONS) != 0)
        return PCRE_ERROR_BADOPTION;
--- 4793,4800 ----
      const uschar *req_char_ptr = start_match - 1;
      const real_pcre *re = (const real_pcre *) external_re;
      const real_pcre_extra *extra = (const real_pcre_extra *) external_extra;
!     BOOL anchored;
!     BOOL startline;
  
      if ((options & ~PUBLIC_EXEC_OPTIONS) != 0)
        return PCRE_ERROR_BADOPTION;
***************
*** 5119,5124 ****
--- 4804,4812 ----
      if (re->magic_number != MAGIC_NUMBER)
        return PCRE_ERROR_BADMAGIC;
  
+     anchored = ((re->options | options) & PCRE_ANCHORED) != 0;
+     startline = (re->options & PCRE_STARTLINE) != 0;
+ 
      match_block.start_pattern = re->code;
      match_block.start_subject = (const uschar *) subject;
      match_block.end_subject = match_block.start_subject + length;
***************
*** 5151,5157 ****
  
      if (re->top_backref > 0 && re->top_backref >= ocount / 3) {
        ocount = re->top_backref * 3 + 3;
!       match_block.offset_vector = (int *) malloc(ocount * sizeof(int));
        if (match_block.offset_vector == NULL)
  	return PCRE_ERROR_NOMEMORY;
        using_temporary_offsets = TRUE;
--- 4839,4845 ----
  
      if (re->top_backref > 0 && re->top_backref >= ocount / 3) {
        ocount = re->top_backref * 3 + 3;
!       match_block.offset_vector = (int *) (pcre_malloc) (ocount * sizeof(int));
        if (match_block.offset_vector == NULL)
  	return PCRE_ERROR_NOMEMORY;
        using_temporary_offsets = TRUE;
***************
*** 5242,5248 ****
  
        else if (startline) {
  	if (start_match > match_block.start_subject + start_offset) {
! 	  while (start_match < end_subject && start_match[-1] != '\n')
  	    start_match++;
  	}
        }
--- 4930,4936 ----
  
        else if (startline) {
  	if (start_match > match_block.start_subject + start_offset) {
! 	  while (start_match < end_subject && start_match[-1] != NEWLINE)
  	    start_match++;
  	}
        }
***************
*** 5342,5353 ****
  	  match_block.offset_overflow = TRUE;
  
  	DPRINTF(("Freeing temporary memory\n"));
! 	free(match_block.offset_vector);
        }
  
        rc = match_block.offset_overflow ? 0 : match_block.end_offset_top / 2;
  
!       if (match_block.offset_end < 2)
  	rc = 0;
        else {
  	offsets[0] = start_match - match_block.start_subject;
--- 5030,5041 ----
  	  match_block.offset_overflow = TRUE;
  
  	DPRINTF(("Freeing temporary memory\n"));
! 	(pcre_free) (match_block.offset_vector);
        }
  
        rc = match_block.offset_overflow ? 0 : match_block.end_offset_top / 2;
  
!       if (offsetcount < 2)
  	rc = 0;
        else {
  	offsets[0] = start_match - match_block.start_subject;
***************
*** 5366,5830 ****
  
      if (using_temporary_offsets) {
        DPRINTF(("Freeing temporary memory\n"));
!       free(match_block.offset_vector);
      }
  
      DPRINTF((">>>> returning %d\n", match_block.errorcode));
- 
    }
- 
    return match_block.errorcode;
  }
  
  /* End of pcre.c */
  /*************************************************
! *      Perl-Compatible Regular Expressions       *
  *************************************************/
  
! /*
! PCRE is a library of functions to support regular expressions whose syntax
! and semantics are as close as possible to those of the Perl 5 language.
! 
! Written by: Philip Hazel <ph10@cam.ac.uk>
! 
!            Copyright (c) 1997-2000 University of Cambridge
! 
! -----------------------------------------------------------------------------
! Permission is granted to anyone to use this software for any purpose on any
! computer system, and to redistribute it freely, subject to the following
! restrictions:
! 
! 1. This software is distributed in the hope that it will be useful,
!    but WITHOUT ANY WARRANTY; without even the implied warranty of
!    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
! 
! 2. The origin of this software must not be misrepresented, either by
!    explicit claim or by omission.
! 
! 3. Altered versions must be plainly marked as such, and must not be
!    misrepresented as being the original software.
  
! 4. If PCRE is embedded in any software that is released under the GNU
!    General Purpose Licence (GPL), then the terms of that licence shall
!    supersede any condition above with which it is incompatible.
! -----------------------------------------------------------------------------
  
! See the file Tech.Notes for some information on the internals.
  */
  
! 
  
  
  
  /*************************************************
! *           Create PCRE character tables         *
  *************************************************/
  
! /* This function builds a set of character tables for use by PCRE and returns
! a pointer to them. They are build using the ctype functions, and consequently
! their contents will depend upon the current locale setting. When compiled as
! part of the library, the store is obtained via pcre_malloc(), but when compiled
! inside dftables, use malloc().
  
! Arguments:   none
! Returns:     pointer to the contiguous block of data
  */
  
! unsigned const char *
! pcre_maketables(void)
  {
!   unsigned char *yield, *p;
!   int i;
  
! #ifndef DFTABLES
!   yield = (unsigned char *) malloc(tables_length);
! #else
!   yield = (unsigned char *) malloc(tables_length);
! #endif
  
!   if (yield == NULL)
!     return NULL;
!   p = yield;
  
! /* First comes the lower casing table */
  
!   for (i = 0; i < 256; i++)
!     *p++ = tolower(i);
! 
! /* Next the case-flipping table */
! 
!   for (i = 0; i < 256; i++)
!     *p++ = islower(i) ? toupper(i) : tolower(i);
! 
! /* Then the character class tables. Don't try to be clever and save effort
! on exclusive ones - in some locales things may be different. */
! 
!   memset(p, 0, cbit_length);
!   for (i = 0; i < 256; i++) {
!     if (isdigit(i)) {
!       p[cbit_digit + i / 8] |= 1 << (i & 7);
!       p[cbit_word + i / 8] |= 1 << (i & 7);
!     }
!     if (isupper(i)) {
!       p[cbit_upper + i / 8] |= 1 << (i & 7);
!       p[cbit_word + i / 8] |= 1 << (i & 7);
!     }
!     if (islower(i)) {
!       p[cbit_lower + i / 8] |= 1 << (i & 7);
!       p[cbit_word + i / 8] |= 1 << (i & 7);
!     }
!     if (i == '_')
!       p[cbit_word + i / 8] |= 1 << (i & 7);
!     if (isspace(i))
!       p[cbit_space + i / 8] |= 1 << (i & 7);
!     if (isxdigit(i))
!       p[cbit_xdigit + i / 8] |= 1 << (i & 7);
!     if (isgraph(i))
!       p[cbit_graph + i / 8] |= 1 << (i & 7);
!     if (isprint(i))
!       p[cbit_print + i / 8] |= 1 << (i & 7);
!     if (ispunct(i))
!       p[cbit_punct + i / 8] |= 1 << (i & 7);
!     if (iscntrl(i))
!       p[cbit_cntrl + i / 8] |= 1 << (i & 7);
!   }
!   p += cbit_length;
! 
! /* Finally, the character type table */
! 
!   for (i = 0; i < 256; i++) {
!     int x = 0;
!     if (isspace(i))
!       x += ctype_space;
!     if (isalpha(i))
!       x += ctype_letter;
!     if (isdigit(i))
!       x += ctype_digit;
!     if (isxdigit(i))
!       x += ctype_xdigit;
!     if (isalnum(i) || i == '_')
!       x += ctype_word;
!     if (strchr("*+?{^.$|()[", i) != 0)
!       x += ctype_meta;
!     *p++ = x;
!   }
! 
!   return yield;
! }
! 
! /* End of maketables.c */
! /*************************************************
! *      Perl-Compatible Regular Expressions       *
! *************************************************/
! 
! /*
! This is a library of functions to support regular expressions whose syntax
! and semantics are as close as possible to those of the Perl 5 language. See
! the file Tech.Notes for some information on the internals.
! 
! Written by: Philip Hazel <ph10@cam.ac.uk>
! 
!            Copyright (c) 1997-2000 University of Cambridge
! 
! -----------------------------------------------------------------------------
! Permission is granted to anyone to use this software for any purpose on any
! computer system, and to redistribute it freely, subject to the following
! restrictions:
! 
! 1. This software is distributed in the hope that it will be useful,
!    but WITHOUT ANY WARRANTY; without even the implied warranty of
!    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
! 
! 2. The origin of this software must not be misrepresented, either by
!    explicit claim or by omission.
! 
! 3. Altered versions must be plainly marked as such, and must not be
!    misrepresented as being the original software.
! 
! 4. If PCRE is embedded in any software that is released under the GNU
!    General Purpose Licence (GPL), then the terms of that licence shall
!    supersede any condition above with which it is incompatible.
! -----------------------------------------------------------------------------
! */
! 
! /* This module contains some convenience functions for extracting substrings
! from the subject string after a regex match has succeeded. The original idea
! for these functions came from Scott Wimer <scottw@cgibuilder.com>. */
! 
! 
! 
! /*************************************************
! *      Copy captured string to given buffer      *
! *************************************************/
! 
! /* This function copies a single captured substring into a given buffer.
! Note that we use memcpy() rather than strncpy() in case there are binary zeros
! in the string.
! 
! Arguments:
!   subject        the subject string that was matched
!   ovector        pointer to the offsets table
!   stringcount    the number of substrings that were captured
!                    (i.e. the yield of the pcre_exec call, unless
!                    that was zero, in which case it should be 1/3
!                    of the offset table size)
!   stringnumber   the number of the required substring
!   buffer         where to put the substring
!   size           the size of the buffer
! 
! Returns:         if successful:
!                    the length of the copied string, not including the zero
!                    that is put on the end; can be zero
!                  if not successful:
!                    PCRE_ERROR_NOMEMORY (-6) buffer too small
!                    PCRE_ERROR_NOSUBSTRING (-7) no such captured substring
! */
! 
! int
! pcre_copy_substring(const char *subject, int *ovector, int stringcount,
! 		    int stringnumber, char *buffer, int size)
! {
!   int yield;
!   if (stringnumber < 0 || stringnumber >= stringcount)
!     return PCRE_ERROR_NOSUBSTRING;
!   stringnumber *= 2;
!   yield = ovector[stringnumber + 1] - ovector[stringnumber];
!   if (size < yield + 1)
!     return PCRE_ERROR_NOMEMORY;
!   memcpy(buffer, subject + ovector[stringnumber], yield);
!   buffer[yield] = 0;
!   return yield;
! }
! 
! 
! 
! /*************************************************
! *      Copy all captured strings to new store    *
! *************************************************/
! 
! /* This function gets one chunk of store and builds a list of pointers and all
! of the captured substrings in it. A NULL pointer is put on the end of the list.
! 
! Arguments:
!   subject        the subject string that was matched
!   ovector        pointer to the offsets table
!   stringcount    the number of substrings that were captured
!                    (i.e. the yield of the pcre_exec call, unless
!                    that was zero, in which case it should be 1/3
!                    of the offset table size)
!   listptr        set to point to the list of pointers
! 
! Returns:         if successful: 0
!                  if not successful:
!                    PCRE_ERROR_NOMEMORY (-6) failed to get store
! */
! 
! int
! pcre_get_substring_list(const char *subject, int *ovector, int stringcount,
! 			const char ***listptr)
! {
!   int i;
!   int size = sizeof(char *);
!   int double_count = stringcount * 2;
!   char **stringlist;
!   char *p;
! 
!   for (i = 0; i < double_count; i += 2)
!     size += sizeof(char *) + ovector[i + 1] - ovector[i] + 1;
! 
!   stringlist = (char **) malloc(size);
!   if (stringlist == NULL)
!     return PCRE_ERROR_NOMEMORY;
! 
!   *listptr = (const char **) stringlist;
!   p = (char *) (stringlist + stringcount + 1);
! 
!   for (i = 0; i < double_count; i += 2) {
!     int len = ovector[i + 1] - ovector[i];
!     memcpy(p, subject + ovector[i], len);
!     *stringlist++ = p;
!     p += len;
!     *p++ = 0;
!   }
! 
!   *stringlist = NULL;
!   return 0;
! }
! 
! 
! 
! /*************************************************
! *   Free store obtained by get_substring_list    *
! *************************************************/
! 
! /* This function exists for the benefit of people calling PCRE from non-C
! programs that can call its functions, but not free() or free() directly.
! 
! Argument:   the result of a previous pcre_get_substring_list()
! Returns:    nothing
! */
! 
! void
! pcre_free_substring_list(const char **pointer)
! {
!   free((void *) pointer);
! }
! 
! 
! 
! /*************************************************
! *      Copy captured string to new store         *
! *************************************************/
! 
! /* This function copies a single captured substring into a piece of new
! store
! 
! Arguments:
!   subject        the subject string that was matched
!   ovector        pointer to the offsets table
!   stringcount    the number of substrings that were captured
!                    (i.e. the yield of the pcre_exec call, unless
!                    that was zero, in which case it should be 1/3
!                    of the offset table size)
!   stringnumber   the number of the required substring
!   stringptr      where to put a pointer to the substring
! 
! Returns:         if successful:
!                    the length of the string, not including the zero that
!                    is put on the end; can be zero
!                  if not successful:
!                    PCRE_ERROR_NOMEMORY (-6) failed to get store
!                    PCRE_ERROR_NOSUBSTRING (-7) substring not present
! */
! 
! int
! pcre_get_substring(const char *subject, int *ovector, int stringcount,
! 		   int stringnumber, const char **stringptr)
! {
!   int yield;
!   char *substring;
!   if (stringnumber < 0 || stringnumber >= stringcount)
!     return PCRE_ERROR_NOSUBSTRING;
!   stringnumber *= 2;
!   yield = ovector[stringnumber + 1] - ovector[stringnumber];
!   substring = (char *) malloc(yield + 1);
!   if (substring == NULL)
!     return PCRE_ERROR_NOMEMORY;
!   memcpy(substring, subject + ovector[stringnumber], yield);
!   substring[yield] = 0;
!   *stringptr = substring;
!   return yield;
! }
! 
! 
! 
! /* End of get.c */
! /*************************************************
! *      Perl-Compatible Regular Expressions       *
! *************************************************/
! 
! /*
! This is a library of functions to support regular expressions whose syntax
! and semantics are as close as possible to those of the Perl 5 language. See
! the file Tech.Notes for some information on the internals.
! 
! Written by: Philip Hazel <ph10@cam.ac.uk>
! 
!            Copyright (c) 1997-2000 University of Cambridge
! 
! -----------------------------------------------------------------------------
! Permission is granted to anyone to use this software for any purpose on any
! computer system, and to redistribute it freely, subject to the following
! restrictions:
! 
! 1. This software is distributed in the hope that it will be useful,
!    but WITHOUT ANY WARRANTY; without even the implied warranty of
!    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
! 
! 2. The origin of this software must not be misrepresented, either by
!    explicit claim or by omission.
! 
! 3. Altered versions must be plainly marked as such, and must not be
!    misrepresented as being the original software.
! 
! 4. If PCRE is embedded in any software that is released under the GNU
!    General Purpose Licence (GPL), then the terms of that licence shall
!    supersede any condition above with which it is incompatible.
! -----------------------------------------------------------------------------
! */
! 
! 
! 
! /*************************************************
! *      Set a bit and maybe its alternate case    *
! *************************************************/
! 
! /* Given a character, set its bit in the table, and also the bit for the other
! version of a letter if we are caseless.
! 
! Arguments:
!   start_bits    points to the bit map
!   c             is the character
!   caseless      the caseless flag
!   cd            the block with char table pointers
! 
! Returns:        nothing
! */
! 
! static void
! set_bit(uschar * start_bits, int c, BOOL caseless, compile_data * cd)
! {
!   start_bits[c / 8] |= (1 << (c & 7));
!   if (caseless && (cd->ctypes[c] & ctype_letter) != 0)
!     start_bits[cd->fcc[c] / 8] |= (1 << (cd->fcc[c] & 7));
! }
! 
! 
! 
! /*************************************************
! *          Create bitmap of starting chars       *
! *************************************************/
! 
! /* This function scans a compiled unanchored expression and attempts to build a
! bitmap of the set of initial characters. If it can't, it returns FALSE. As time
! goes by, we may be able to get more clever at doing this.
! 
! Arguments:
!   code         points to an expression
!   start_bits   points to a 32-byte table, initialized to 0
!   caseless     the current state of the caseless flag
!   cd           the block with char table pointers
! 
! Returns:       TRUE if table built, FALSE otherwise
! */
! 
! static BOOL
! set_start_bits(const uschar * code, uschar * start_bits, BOOL caseless,
! 	       compile_data * cd)
! {
!   register int c;
! 
! /* This next statement and the later reference to dummy are here in order to
! trick the optimizer of the IBM C compiler for OS/2 into generating correct
! code. Apparently IBM isn't going to fix the problem, and we would rather not
! disable optimization (in this module it actually makes a big difference, and
! the pcre module can use all the optimization it can get). */
! 
!   volatile int dummy;
! 
!   do {
!     const uschar *tcode = code + 3;
!     BOOL try_next = TRUE;
! 
!     while (try_next) {
!       try_next = FALSE;
! 
!       /* If a branch starts with a bracket or a positive lookahead assertion,
!          recurse to set bits from within them. That's all for this branch. */
  
        if ((int) *tcode >= OP_BRA || *tcode == OP_ASSERT) {
  	if (!set_start_bits(tcode, start_bits, caseless, cd))
  	  return FALSE;
        }
  
        else
--- 5054,5138 ----
  
      if (using_temporary_offsets) {
        DPRINTF(("Freeing temporary memory\n"));
!       (pcre_free) (match_block.offset_vector);
      }
  
      DPRINTF((">>>> returning %d\n", match_block.errorcode));
    }
    return match_block.errorcode;
  }
  
  /* End of pcre.c */
+ 
  /*************************************************
! *      Set a bit and maybe its alternate case    *
  *************************************************/
  
! /* Given a character, set its bit in the table, and also the bit for the other
! version of a letter if we are caseless.
  
! Arguments:
!   start_bits    points to the bit map
!   c             is the character
!   caseless      the caseless flag
!   cd            the block with char table pointers
  
! Returns:        nothing
  */
  
! static void
! set_bit(uschar * start_bits, int c, BOOL caseless, compile_data * cd)
! {
!   start_bits[c / 8] |= (1 << (c & 7));
!   if (caseless && (cd->ctypes[c] & ctype_letter) != 0)
!     start_bits[cd->fcc[c] / 8] |= (1 << (cd->fcc[c] & 7));
! }
  
  
  
  /*************************************************
! *          Create bitmap of starting chars       *
  *************************************************/
  
! /* This function scans a compiled unanchored expression and attempts to build a
! bitmap of the set of initial characters. If it can't, it returns FALSE. As time
! goes by, we may be able to get more clever at doing this.
  
! Arguments:
!   code         points to an expression
!   start_bits   points to a 32-byte table, initialized to 0
!   caseless     the current state of the caseless flag
!   cd           the block with char table pointers
! 
! Returns:       TRUE if table built, FALSE otherwise
  */
  
! static BOOL
! set_start_bits(const uschar * code, uschar * start_bits, BOOL caseless,
! 	       compile_data * cd)
  {
!   register int c;
  
! /* This next statement and the later reference to dummy are here in order to
! trick the optimizer of the IBM C compiler for OS/2 into generating correct
! code. Apparently IBM isn't going to fix the problem, and we would rather not
! disable optimization (in this module it actually makes a big difference, and
! the pcre module can use all the optimization it can get). */
  
!   volatile int dummy;
  
!   do {
!     const uschar *tcode = code + 3;
!     BOOL try_next = TRUE;
  
!     while (try_next) {
!       /* If a branch starts with a bracket or a positive lookahead assertion,
!          recurse to set bits from within them. That's all for this branch. */
  
        if ((int) *tcode >= OP_BRA || *tcode == OP_ASSERT) {
  	if (!set_start_bits(tcode, start_bits, caseless, cd))
  	  return FALSE;
+ 	try_next = FALSE;
        }
  
        else
***************
*** 5832,5843 ****
  	default:
  	  return FALSE;
  
  	  /* Skip over lookbehind and negative lookahead assertions */
  
  	case OP_ASSERT_NOT:
  	case OP_ASSERTBACK:
  	case OP_ASSERTBACK_NOT:
- 	  try_next = TRUE;
  	  do
  	    tcode += (tcode[1] << 8) + tcode[2];
  	  while (*tcode == OP_ALT);
--- 5140,5156 ----
  	default:
  	  return FALSE;
  
+ 	  /* Skip over extended extraction bracket number */
+ 
+ 	case OP_BRANUMBER:
+ 	  tcode += 3;
+ 	  break;
+ 
  	  /* Skip over lookbehind and negative lookahead assertions */
  
  	case OP_ASSERT_NOT:
  	case OP_ASSERTBACK:
  	case OP_ASSERTBACK_NOT:
  	  do
  	    tcode += (tcode[1] << 8) + tcode[2];
  	  while (*tcode == OP_ALT);
***************
*** 5849,5855 ****
  	case OP_OPT:
  	  caseless = (tcode[1] & PCRE_CASELESS) != 0;
  	  tcode += 2;
- 	  try_next = TRUE;
  	  break;
  
  	  /* BRAZERO does the bracket, but carries on. */
--- 5162,5167 ----
***************
*** 5863,5869 ****
  	    tcode += (tcode[1] << 8) + tcode[2];
  	  while (*tcode == OP_ALT);
  	  tcode += 3;
- 	  try_next = TRUE;
  	  break;
  
  	  /* Single-char * or ? sets the bit and tries the next item */
--- 5175,5180 ----
***************
*** 5874,5880 ****
  	case OP_MINQUERY:
  	  set_bit(start_bits, tcode[1], caseless, cd);
  	  tcode += 2;
- 	  try_next = TRUE;
  	  break;
  
  	  /* Single-char upto sets the bit and tries the next */
--- 5185,5190 ----
***************
*** 5883,5889 ****
  	case OP_MINUPTO:
  	  set_bit(start_bits, tcode[3], caseless, cd);
  	  tcode += 4;
- 	  try_next = TRUE;
  	  break;
  
  	  /* At least one single char sets the bit and stops */
--- 5193,5198 ----
***************
*** 5897,5902 ****
--- 5206,5212 ----
  	case OP_PLUS:
  	case OP_MINPLUS:
  	  set_bit(start_bits, tcode[1], caseless, cd);
+ 	  try_next = FALSE;
  	  break;
  
  	  /* Single character type sets the bits and stops */
***************
*** 5904,5934 ****
--- 5214,5250 ----
  	case OP_NOT_DIGIT:
  	  for (c = 0; c < 32; c++)
  	    start_bits[c] |= ~cd->cbits[c + cbit_digit];
+ 	  try_next = FALSE;
  	  break;
  
  	case OP_DIGIT:
  	  for (c = 0; c < 32; c++)
  	    start_bits[c] |= cd->cbits[c + cbit_digit];
+ 	  try_next = FALSE;
  	  break;
  
  	case OP_NOT_WHITESPACE:
  	  for (c = 0; c < 32; c++)
  	    start_bits[c] |= ~cd->cbits[c + cbit_space];
+ 	  try_next = FALSE;
  	  break;
  
  	case OP_WHITESPACE:
  	  for (c = 0; c < 32; c++)
  	    start_bits[c] |= cd->cbits[c + cbit_space];
+ 	  try_next = FALSE;
  	  break;
  
  	case OP_NOT_WORDCHAR:
  	  for (c = 0; c < 32; c++)
  	    start_bits[c] |= ~cd->cbits[c + cbit_word];
+ 	  try_next = FALSE;
  	  break;
  
  	case OP_WORDCHAR:
  	  for (c = 0; c < 32; c++)
  	    start_bits[c] |= cd->cbits[c + cbit_word];
+ 	  try_next = FALSE;
  	  break;
  
  	  /* One or more character type fudges the pointer and restarts, knowing
***************
*** 5937,5948 ****
  	case OP_TYPEPLUS:
  	case OP_TYPEMINPLUS:
  	  tcode++;
- 	  try_next = TRUE;
  	  break;
  
  	case OP_TYPEEXACT:
  	  tcode += 3;
- 	  try_next = TRUE;
  	  break;
  
  	  /* Zero or more repeats of character types set the bits and then
--- 5253,5262 ----
***************
*** 5989,5995 ****
  	  }
  
  	  tcode += 2;
- 	  try_next = TRUE;
  	  break;
  
  	  /* Character class: set the bits and either carry on or not,
--- 5303,5308 ----
***************
*** 6007,6021 ****
  	    case OP_CRQUERY:
  	    case OP_CRMINQUERY:
  	      tcode++;
- 	      try_next = TRUE;
  	      break;
  
  	    case OP_CRRANGE:
  	    case OP_CRMINRANGE:
! 	      if (((tcode[1] << 8) + tcode[2]) == 0) {
  		tcode += 5;
! 		try_next = TRUE;
! 	      }
  	      break;
  	    }
  	  }
--- 5320,5337 ----
  	    case OP_CRQUERY:
  	    case OP_CRMINQUERY:
  	      tcode++;
  	      break;
  
  	    case OP_CRRANGE:
  	    case OP_CRMINRANGE:
! 	      if (((tcode[1] << 8) + tcode[2]) == 0)
  		tcode += 5;
! 	      else
! 		try_next = FALSE;
! 	      break;
! 
! 	    default:
! 	      try_next = FALSE;
  	      break;
  	    }
  	  }
***************
*** 6093,6099 ****
  
  /* Get an "extra" block and put the information therein. */
  
!   extra = (real_pcre_extra *) malloc(sizeof(real_pcre_extra));
  
    if (extra == NULL) {
      *errorptr = "failed to get memory";
--- 5409,5415 ----
  
  /* Get an "extra" block and put the information therein. */
  
!   extra = (real_pcre_extra *) (pcre_malloc) (sizeof(real_pcre_extra));
  
    if (extra == NULL) {
      *errorptr = "failed to get memory";
***************
*** 6107,6109 ****
--- 5423,5569 ----
  }
  
  /* End of study.c */
+ 
+ 
+ /*************************************************
+ *           Create PCRE character tables         *
+ *************************************************/
+ 
+ /* This function builds a set of character tables for use by PCRE and returns
+ a pointer to them. They are build using the ctype functions, and consequently
+ their contents will depend upon the current locale setting. When compiled as
+ part of the library, the store is obtained via pcre_malloc(), but when compiled
+ inside dftables, use malloc().
+ 
+ Arguments:   none
+ Returns:     pointer to the contiguous block of data
+ */
+ 
+ const unsigned char *
+ pcre_maketables(void)
+ {
+   unsigned char *yield, *p;
+   int i;
+ 
+ #ifndef DFTABLES
+   yield = (unsigned char *) (pcre_malloc) (tables_length);
+ #else
+   yield = (unsigned char *) malloc(tables_length);
+ #endif
+ 
+   if (yield == NULL)
+     return NULL;
+   p = yield;
+ 
+ /* First comes the lower casing table */
+ 
+   for (i = 0; i < 256; i++)
+     *p++ = tolower(i);
+ 
+ /* Next the case-flipping table */
+ 
+   for (i = 0; i < 256; i++)
+     *p++ = islower(i) ? toupper(i) : tolower(i);
+ 
+ /* Then the character class tables. Don't try to be clever and save effort
+ on exclusive ones - in some locales things may be different. */
+ 
+   memset(p, 0, cbit_length);
+   for (i = 0; i < 256; i++) {
+     if (isdigit(i)) {
+       p[cbit_digit + i / 8] |= 1 << (i & 7);
+       p[cbit_word + i / 8] |= 1 << (i & 7);
+     }
+     if (isupper(i)) {
+       p[cbit_upper + i / 8] |= 1 << (i & 7);
+       p[cbit_word + i / 8] |= 1 << (i & 7);
+     }
+     if (islower(i)) {
+       p[cbit_lower + i / 8] |= 1 << (i & 7);
+       p[cbit_word + i / 8] |= 1 << (i & 7);
+     }
+     if (i == '_')
+       p[cbit_word + i / 8] |= 1 << (i & 7);
+     if (isspace(i))
+       p[cbit_space + i / 8] |= 1 << (i & 7);
+     if (isxdigit(i))
+       p[cbit_xdigit + i / 8] |= 1 << (i & 7);
+     if (isgraph(i))
+       p[cbit_graph + i / 8] |= 1 << (i & 7);
+     if (isprint(i))
+       p[cbit_print + i / 8] |= 1 << (i & 7);
+     if (ispunct(i))
+       p[cbit_punct + i / 8] |= 1 << (i & 7);
+     if (iscntrl(i))
+       p[cbit_cntrl + i / 8] |= 1 << (i & 7);
+   }
+   p += cbit_length;
+ 
+ /* Finally, the character type table */
+ 
+   for (i = 0; i < 256; i++) {
+     int x = 0;
+     if (isspace(i))
+       x += ctype_space;
+     if (isalpha(i))
+       x += ctype_letter;
+     if (isdigit(i))
+       x += ctype_digit;
+     if (isxdigit(i))
+       x += ctype_xdigit;
+     if (isalnum(i) || i == '_')
+       x += ctype_word;
+     if (strchr("*+?{^.$|()[", i) != 0)
+       x += ctype_meta;
+     *p++ = x;
+   }
+ 
+   return yield;
+ }
+ 
+ /* End of maketables.c */
+ 
+ /*************************************************
+ *      Copy captured string to given buffer      *
+ *************************************************/
+ 
+ /* This function copies a single captured substring into a given buffer.
+ Note that we use memcpy() rather than strncpy() in case there are binary zeros
+ in the string.
+ 
+ Arguments:
+   subject        the subject string that was matched
+   ovector        pointer to the offsets table
+   stringcount    the number of substrings that were captured
+                    (i.e. the yield of the pcre_exec call, unless
+                    that was zero, in which case it should be 1/3
+                    of the offset table size)
+   stringnumber   the number of the required substring
+   buffer         where to put the substring
+   size           the size of the buffer
+ 
+ Returns:         if successful:
+                    the length of the copied string, not including the zero
+                    that is put on the end; can be zero
+                  if not successful:
+                    PCRE_ERROR_NOMEMORY (-6) buffer too small
+                    PCRE_ERROR_NOSUBSTRING (-7) no such captured substring
+ */
+ 
+ int
+ pcre_copy_substring(const char *subject, int *ovector, int stringcount,
+ 		    int stringnumber, char *buffer, int size)
+ {
+   int yield;
+   if (stringnumber < 0 || stringnumber >= stringcount)
+     return PCRE_ERROR_NOSUBSTRING;
+   stringnumber *= 2;
+   yield = ovector[stringnumber + 1] - ovector[stringnumber];
+   if (size < yield + 1)
+     return PCRE_ERROR_NOMEMORY;
+   memcpy(buffer, subject + ovector[stringnumber], yield);
+   buffer[yield] = 0;
+   return yield;
+ }
+ 
+ /* End of get.c */
*** 1_7_4.187/hdrs/pcre.h Sun, 25 Feb 2001 13:37:15 -0600 dunemush (pennmush/d/38_pcre.h 1.3.1.2.1.1.1.5 660)
--- 1_7_4.188(w)/hdrs/pcre.h Mon, 03 Dec 2001 10:09:26 -0600 dunemush (pennmush/d/38_pcre.h 1.3.1.2.1.1.1.6 660)
***************
*** 1,8 ****
- /*************************************************
- *      Perl-Compatible Regular Expressions       *
- *************************************************/
- 
- 
  /* This is a library of functions to support regular expressions whose syntax
  and semantics are as close as possible to those of the Perl 5 language. See
  the file Tech.Notes for some information on the internals.
--- 1,3 ----
***************
*** 34,40 ****
  
  /***** ALTERED VERSION ******/
  /* This file combines pcre.h and internal.h into a single header for
!  * use in PennMUSH, and removes some things we handle ourselves.
   * Also tries to avoid infinitly-long backtracking.
   * Modified by Javelin <dunemush@pennmush.org> and Raevnos
   * <raevnos@pennmush.org>
--- 29,36 ----
  
  /***** ALTERED VERSION ******/
  /* This file combines pcre.h and internal.h into a single header for
!  * use in PennMUSH, and removes some things we handle ourselves or never
!  * used to save space..
   * Also tries to avoid infinitly-long backtracking.
   * Modified by Javelin <dunemush@pennmush.org> and Raevnos
   * <raevnos@pennmush.org>
***************
*** 43,53 ****
  /* This header contains definitions that are shared between the different
  modules, but which are not relevant to the outside. */
  
- /*************************************************
- *       Perl-Compatible Regular Expressions      *
- *************************************************/
- 
- /* Copyright (c) 1997-2000 University of Cambridge */
  
  #ifndef _PCRE_H
  #define _PCRE_H
--- 39,44 ----
***************
*** 55,63 ****
  /* The file pcre.h is build by "configure". Do not edit it; instead
  make changes to pcre.in. */
  
! #define PCRE_MAJOR 3
! #define PCRE_MINOR 4
! #define PCRE_DATE  22-Aug-2000
  
  /* Win32 uses DLL by default */
  
--- 46,54 ----
  /* The file pcre.h is build by "configure". Do not edit it; instead
  make changes to pcre.in. */
  
! #define PCRE_MAJOR          3
! #define PCRE_MINOR          7
! #define PCRE_DATE           29-Oct-2001
  
  /* Win32 uses DLL by default */
  
***************
*** 81,95 ****
  #include <stdio.h>
  #include <stdlib.h>
  #include <string.h>
- #include <stdlib.h>
  #include "confmagic.h"
  
- /* Allow for C++ users */
- 
- #ifdef __cplusplus
- extern "C" {
- #endif
- 
  /* Options */
  
  #define PCRE_CASELESS        0x0001
--- 72,79 ----
***************
*** 128,206 ****
  
  /* Types */
  
!   typedef void pcre;
!   typedef void pcre_extra;
! 
! /* Store get and free functions. These can be set to alternative malloc/free
! functions if required. Some magic is required for Win32 DLL; it is null on
! other OS. */
  
!   PCRE_DL_IMPORT extern void *(*pcre_malloc) (size_t);
!   PCRE_DL_IMPORT extern void (*pcre_free) (void *);
  
  #undef PCRE_DL_IMPORT
  
  /* Functions */
  
!   extern pcre *pcre_compile(const char *, int, const char **, int *,
! 			    const unsigned char *);
!   extern int pcre_copy_substring(const char *, int *, int, int, char *, int);
!   extern int pcre_exec(const pcre *, const pcre_extra *, const char *,
! 		       int, int, int, int *, int);
!   extern void pcre_free_substring(const char *);
!   extern void pcre_free_substring_list(const char **);
!   extern int pcre_get_substring(const char *, int *, int, int, const char **);
!   extern int pcre_get_substring_list(const char *, int *, int, const char ***);
!   extern int pcre_info(const pcre *, int *, int *);
!   extern int pcre_fullinfo(const pcre *, const pcre_extra *, int, void *);
!   extern unsigned const char *pcre_maketables(void);
!   extern pcre_extra *pcre_study(const pcre *, int, const char **);
!   extern const char *pcre_version(void);
  
- #ifdef __cplusplus
- }				/* extern "C" */
- #endif
- #endif				/* End of pcre.h */
- /* Get the definitions provided by running "configure" *//* In case there is no definition of offsetof() provided - though any proper
-    Standard C system should have one. */
  #ifndef offsetof
  #define offsetof(p_type,field) ((size_t)&(((p_type *)0)->field))
  #endif
  /* These are the public options that can change during matching. */
  #define PCRE_IMS (PCRE_CASELESS|PCRE_MULTILINE|PCRE_DOTALL)
  /* Private options flags start at the most significant end of the four bytes,
  but skip the top bit so we can use ints for convenience without getting tangled
  with negative values. The public options defined in pcre.h start at the least
  significant end. Make sure they don't overlap, though now that we have expanded
  to four bytes there is plenty of space. */
  #define PCRE_FIRSTSET      0x40000000	/* first_char is set */
  #define PCRE_REQCHSET      0x20000000	/* req_char is set */
  #define PCRE_STARTLINE     0x10000000	/* start after \n for multiline */
  #define PCRE_INGROUP       0x08000000	/* compiling inside a group */
  #define PCRE_ICHANGED      0x04000000	/* i option changes within regex */
  /* Options for the "extra" block produced by pcre_study(). */
  #define PCRE_STUDY_MAPPED   0x01	/* a map of starting chars exists */
  /* Masks for identifying the public options which are permitted at compile
  time, run time or study time, respectively. */
  #define PUBLIC_OPTIONS \
    (PCRE_CASELESS|PCRE_EXTENDED|PCRE_ANCHORED|PCRE_MULTILINE| \
     PCRE_DOTALL|PCRE_DOLLAR_ENDONLY|PCRE_EXTRA|PCRE_UNGREEDY|PCRE_UTF8)
  #define PUBLIC_EXEC_OPTIONS \
    (PCRE_ANCHORED|PCRE_NOTBOL|PCRE_NOTEOL|PCRE_NOTEMPTY)
  #define PUBLIC_STUDY_OPTIONS 0	/* None defined */
  /* Magic number to provide a small check against being handed junk. */
  #define MAGIC_NUMBER  0x50435245UL	/* 'PCRE' */
! /* Miscellaneous definitions */ typedef int BOOL;
  
  #define FALSE   0
  #define TRUE    1
  
  /* These are escaped items that aren't just an encoding of a particular data
  value such as \n. They must have non-zero values, as check_escape() returns
  their negation. Also, they must appear in the same order as in the opcode
  definitions below, up to ESC_z. The final one must be ESC_REF as subsequent
  values are used for \1, \2, \3, etc. There is a test in the code for an escape
! greater than ESC_b and less than ESC_X to detect the types that may be
  repeated. If any new escapes are put in-between that don't consume a character,
  that code will have to change. */
  
--- 112,223 ----
  
  /* Types */
  
! struct real_pcre;		/* declaration; the definition is private  */
! struct real_pcre_extra;		/* declaration; the definition is private */
  
! typedef struct real_pcre pcre;
! typedef struct real_pcre_extra pcre_extra;
  
  #undef PCRE_DL_IMPORT
  
  /* Functions */
  
! extern pcre *pcre_compile(const char *, int, const char **, int *,
! 			  const unsigned char *);
! extern int pcre_copy_substring(const char *, int *, int, int, char *, int);
! extern int pcre_exec(const pcre *, const pcre_extra *, const char *,
! 		     int, int, int, int *, int);
! extern const unsigned char *pcre_maketables(void);
! extern pcre_extra *pcre_study(const pcre *, int, const char **);
! 
! 
! /* Standard C headers plus the external interface definition */
! 
! 
! /* In case there is no definition of offsetof() provided - though any proper
! Standard C system should have one. */
  
  #ifndef offsetof
  #define offsetof(p_type,field) ((size_t)&(((p_type *)0)->field))
  #endif
+ 
  /* These are the public options that can change during matching. */
+ 
  #define PCRE_IMS (PCRE_CASELESS|PCRE_MULTILINE|PCRE_DOTALL)
+ 
  /* Private options flags start at the most significant end of the four bytes,
  but skip the top bit so we can use ints for convenience without getting tangled
  with negative values. The public options defined in pcre.h start at the least
  significant end. Make sure they don't overlap, though now that we have expanded
  to four bytes there is plenty of space. */
+ 
  #define PCRE_FIRSTSET      0x40000000	/* first_char is set */
  #define PCRE_REQCHSET      0x20000000	/* req_char is set */
  #define PCRE_STARTLINE     0x10000000	/* start after \n for multiline */
  #define PCRE_INGROUP       0x08000000	/* compiling inside a group */
  #define PCRE_ICHANGED      0x04000000	/* i option changes within regex */
+ 
  /* Options for the "extra" block produced by pcre_study(). */
+ 
  #define PCRE_STUDY_MAPPED   0x01	/* a map of starting chars exists */
+ 
  /* Masks for identifying the public options which are permitted at compile
  time, run time or study time, respectively. */
+ 
  #define PUBLIC_OPTIONS \
    (PCRE_CASELESS|PCRE_EXTENDED|PCRE_ANCHORED|PCRE_MULTILINE| \
     PCRE_DOTALL|PCRE_DOLLAR_ENDONLY|PCRE_EXTRA|PCRE_UNGREEDY|PCRE_UTF8)
+ 
  #define PUBLIC_EXEC_OPTIONS \
    (PCRE_ANCHORED|PCRE_NOTBOL|PCRE_NOTEOL|PCRE_NOTEMPTY)
+ 
  #define PUBLIC_STUDY_OPTIONS 0	/* None defined */
+ 
  /* Magic number to provide a small check against being handed junk. */
+ 
  #define MAGIC_NUMBER  0x50435245UL	/* 'PCRE' */
! 
! /* Miscellaneous definitions */
! 
! typedef int BOOL;
  
  #define FALSE   0
  #define TRUE    1
  
+ #ifndef NEWLINE
+ #define NEWLINE '\n'
+ #endif
+ 
+ /* Escape items that are just an encoding of a particular data value. Note that
+ ESC_N is defined as yet another macro, which is set in config.h to either \n
+ (the default) or \r (which some people want). */
+ 
+ #ifndef ESC_E
+ #define ESC_E 27
+ #endif
+ 
+ #ifndef ESC_F
+ #define ESC_F '\f'
+ #endif
+ 
+ #ifndef ESC_N
+ #define ESC_N NEWLINE
+ #endif
+ 
+ #ifndef ESC_R
+ #define ESC_R '\r'
+ #endif
+ 
+ #ifndef ESC_T
+ #define ESC_T '\t'
+ #endif
+ 
  /* These are escaped items that aren't just an encoding of a particular data
  value such as \n. They must have non-zero values, as check_escape() returns
  their negation. Also, they must appear in the same order as in the opcode
  definitions below, up to ESC_z. The final one must be ESC_REF as subsequent
  values are used for \1, \2, \3, etc. There is a test in the code for an escape
! greater than ESC_b and less than ESC_Z to detect the types that may be
  repeated. If any new escapes are put in-between that don't consume a character,
  that code will have to change. */
  
***************
*** 297,315 ****
  
    OP_ONCE,			/* Once matched, don't back up into the subpattern */
    OP_COND,			/* Conditional group */
!   OP_CREF,			/* Used to hold an extraction string number */
  
    OP_BRAZERO,			/* These two must remain together and in this */
    OP_BRAMINZERO,		/* order. */
  
    OP_BRA			/* This and greater values are used for brackets that
! 				   extract substrings. */
  };
  
! /* The highest extraction number. This is limited by the number of opcodes
! left after OP_BRA, i.e. 255 - OP_BRA. We actually set it somewhat lower. */
  
! #define EXTRACT_MAX  99
  
  /* The texts of compile-time error messages are defined as macros here so that
  they can be accessed by the POSIX wrapper and converted into error codes.  Yes,
--- 314,339 ----
  
    OP_ONCE,			/* Once matched, don't back up into the subpattern */
    OP_COND,			/* Conditional group */
!   OP_CREF,			/* Used to hold an extraction string number (cond ref) */
  
    OP_BRAZERO,			/* These two must remain together and in this */
    OP_BRAMINZERO,		/* order. */
  
+   OP_BRANUMBER,			/* Used for extracting brackets whose number is greater
+ 				   than can fit into an opcode. */
+ 
    OP_BRA			/* This and greater values are used for brackets that
! 				   extract substrings up to a basic limit. After that,
! 				   use is made of OP_BRANUMBER. */
  };
  
! /* The highest extraction number before we have to start using additional
! bytes. (Originally PCRE didn't have support for extraction counts highter than
! this number.) The value is limited by the number of opcodes left after OP_BRA,
! i.e. 255 - OP_BRA. We actually set it a bit lower to leave room for additional
! opcodes. */
  
! #define EXTRACT_BASIC_MAX  150
  
  /* The texts of compile-time error messages are defined as macros here so that
  they can be accessed by the POSIX wrapper and converted into error codes.  Yes,
***************
*** 328,340 ****
  #define ERR10 "operand of unlimited repeat could match the empty string"
  #define ERR11 "internal error: unexpected repeat"
  #define ERR12 "unrecognized character after (?"
! #define ERR13 "too many capturing parenthesized sub-patterns"
  #define ERR14 "missing )"
  #define ERR15 "back reference to non-existent subpattern"
  #define ERR16 "erroffset passed as NULL"
  #define ERR17 "unknown option bit(s) set"
  #define ERR18 "missing ) after comment"
! #define ERR19 "too many sets of parentheses"
  #define ERR20 "regular expression too large"
  #define ERR21 "failed to get memory"
  #define ERR22 "unmatched parentheses"
--- 352,364 ----
  #define ERR10 "operand of unlimited repeat could match the empty string"
  #define ERR11 "internal error: unexpected repeat"
  #define ERR12 "unrecognized character after (?"
! #define ERR13 "unused error"
  #define ERR14 "missing )"
  #define ERR15 "back reference to non-existent subpattern"
  #define ERR16 "erroffset passed as NULL"
  #define ERR17 "unknown option bit(s) set"
  #define ERR18 "missing ) after comment"
! #define ERR19 "parentheses nested too deeply"
  #define ERR20 "regular expression too large"
  #define ERR21 "failed to get memory"
  #define ERR22 "unmatched parentheses"
***************
*** 369,376 ****
    size_t size;
    const unsigned char *tables;
    unsigned long int options;
!   uschar top_bracket;
!   uschar top_backref;
    uschar first_char;
    uschar req_char;
    uschar code[1];
--- 393,400 ----
    size_t size;
    const unsigned char *tables;
    unsigned long int options;
!   unsigned short int top_bracket;
!   unsigned short int top_backref;
    uschar first_char;
    uschar req_char;
    uschar code[1];
***************
*** 452,454 ****
--- 476,480 ----
  #define tables_length (ctypes_offset + 256)
  
  /* End of internal.h */
+ 
+ #endif				/* End of pcre.h */