1.34
====
- bugfix:  fixed taint mode logging error for verbose --showconfig and --stdoutlog
	   options and newer perl versions.
- bugfix:  check_* functions use print/getline instead of send/recv for large 
	   --dumpcache output (thanks to Alexandre Simon)
- code:    log_* routines added to allow the same plugins for postfwd1 and postfwd2
- code:    added more information when using --debug=cleanup
- docs:    documentation updates
- feature: new sendmail(sendmail-path::from::to::subject::body) action.
           Please take a look at the manual, especially about
           it's limitations, before using it!
    ------------------------------------------------------------
     # alert
     action=sendmail(/usr/sbin/sendmail::from@example.org::to@example.org::Subject::Text)
    ------------------------------------------------------------


1.33
====
- feature: new compare operators *
        ====================================================================
         *ITEM > VALUE                true if ITEM > VALUE
         *ITEM < VALUE                true if ITEM < VALUE
        ====================================================================
- bugfix:  fixed bug when computing scores with more than 1 digit after the "." (n.nn)
- bugfix:  fixed bug when computing negative values with the set action
- bugfix:  ITEMS plugins returning zero values were handled incorrectly
- bugfix:  max command recursion was not reset for each rule


1.32
====
- feature: new option --save_rates=<file> allows to load and save
	   rate limit counters to disk on program start and termination.
	   this allows rate limit persistence during restarts and reboots
	   (requires perl module 'Storable')
- feature: the --debugitem="sender=example\.org$" option
           allows verbose logging for particular requests
- feature: the debug() action allows verbose logging for certain
           rules:
    ------------------------------------------------------------
     id=R01
        client_address=1.1.1.1
        action=debug(on)
     id=R02
     ...
     id=R42
        action=debug(off)
    ------------------------------------------------------------
- feature: nested commands are possible now, e.g.:
    ------------------------------------------------------------
     # throttle
     action=rate(client_address/10/60/wait(3))
    ------------------------------------------------------------
- feature: new mail(server/helo/from/to/subject/body) action.
           Please take a look at the manual, especially about
           it's limitations, before using it!
    ------------------------------------------------------------
     # alert
     action=size(recipient_domain/100000000/86400/mail(mailhost/helo/from/to/subject/text))
    ------------------------------------------------------------

1.31
====
- feature: single cache items can be wiped using --delcache <item>
	   or --delrate <item> options. use --dumpcache to identify
- feature: sasl_username is logged if available
	   (thanks to Bernhard Schmidt)
- code:    rate limit action is executed, if the first request exceeds the limit
- code:    exceeded ratecounters will not be kept permanently anymore. this
	   allows further requests to pass, if they are below the limit
- code:	   rate limits are evaluated at ruleset stage now, which leads to
	   much more comprehensible behaviour. due to this change the request
	   cache is now disabled, if rate limits are used. use the
	   --fast_limit_evaluation option to revert to the former mode.

1.30
====
- feature: new parser enhancement allows to omit the trailing "\" for multi-line rules,
	   if the following lines are prefixed by whitespace characters:
		--------------------------------------
		 id=RCPTCOUNT
		    protocol_state  == END-OF-MESSAGE
		    client_address  != 10.1.1.0/24
		    recipient_count >= 100
		    action=REJECT too many recipients
		--------------------------------------
- feature: new plugin interface (BETA)
- feature: Time::HiRes is used if available
- feature: new $$ratecount variable for rate() actions
- feature: ported --dumpstats and --dumpcache option from postfwd2
- bugfix:  fixed program usage statistics (--summary)
- docs:    documentation updates

1.22
=====
- feature: new option --keep_rates
- feature: queueid is logged when available
- bugfix:  rate limits using the same item and the same limits
           did not work correctly (thanks to Yves Blusseau):
		id=INT01; INT_DOMAIN==1; \
			action=rate(sender/100/60/450 4.7.1 too much for internal domains)
		id=EXT01; EXT_DOMAIN==1; \
			action=rate(sender/100/60/450 4.7.1 too much for external domains)
- bugfix:  small fix for cleanup of old rate limits
- docs:    documentation updates and fixes (thanks to Vincent Lefevre)

1.21
=====
- feature: postfwd supports multiple rate limits to the same items now.
	   this means that the following will now work as expected:
		id=R001; recipient_count>=100; action=rate(sender/3/3600/WARN state RED)
		id=R002; recipient_count>=100; action=rate(sender/2/3600/WARN state YELLOW)
		id=R003; recipient_count>=100; action=rate(sender/1/3600/WARN state GREEN)
- code:    ported command-line option --facility from postfwd2
- docs:    documentation updates and fixes (thanks to Vincent Lefevre)

1.20
=====
- code:    changed the default umask for the server socket to 0111
           to support out-of-the-box postfix setup. Use the
           --umask setting to change this
- bugfix:  rbl check could fail on multiple dnsbl answers
- bugfix:  rbl checks disabled for ipv6 addresses, cidr compare
	   will switch to default (regex/string)

1.19
=====
- code:    Rate limit code rewritten
- code:    new --umask setting allows to set filepermissions for pidfiles
	   and unix domain sockets. Default is 0117 (owner and group rw).

1.18
=====
- bugfix:  Fixed bug when comparing sender and recipient addresses, like
	   "sender=$$recipient". This affects only postfwd version 1.17.

1.17
=====
- bugfix:  Invalid characters in variable substitutions were not correctly catched when
           the '=' operator was used, like "client_name=$$helo_name". If you can not
           upgrade for some reason change your rule to "client_name=~$$helo_name"
- code:    Net::DNS errors will now be handled gracefully
- code:    default for options --dns_max_ns_a_lookups and --dns_max_mx_a_lookups of 100

1.16
=====
- bugfix:  this is a bugfix release for 1.15. anyone affected is encouraged to upgrade.
	   detail: the default behavior for the '=' operator with numeric items
	   (size, recipient_count, ...) changed with version 1.15 to '==' (equals to).
	   now these items are compared '>=' (greater than) again.
	   note: if you are using 1.15 and you are not able upgrade for some reason,
	   please change '=' to '>=' in your ruleset where you mean 'greater than'.

1.15
=====
- feature: items may now be retrieved from files using "item=file:/some/where"
	   more information in the postfwd manual (FILES section)
- feature: helo_address, and sender_(ns|mx)_addrs can now be csv items
- feature: new rcpt() command counts recipients for rate limits (thanks to Sahil Tandon)
- code:    redirect syslog to stdout for --kill, --reload and --showconfig
- code:    option --reload (HUP signal) now reloads config, if the file is unchanged
- code:	   configuration parser improvements:
	   * rules without defined action will be skipped at configuration stage
	   * undefined ACLs will now be detected and skipped at configuration stage
	   * parser timeout skips loading a rule after 4s, to prevent problems with
	     large files or loops. use --config_timeout to override
- bugfix:  documentation fixed (missing "action=" in ask() examples)

1.14
=====
- feature: new compare operators *
        ====================================================================
         ITEM == VALUE                true if ITEM equals VALUE
         ITEM => VALUE                true if ITEM >= VALUE
         ITEM =< VALUE                true if ITEM <= VALUE
         ITEM =~ VALUE                true if ITEM ~= /^VALUE$/i
         *ITEM != VALUE               false if ITEM equals VALUE
         *ITEM !> VALUE               false if ITEM >= VALUE
         *ITEM !< VALUE               false if ITEM <= VALUE
         *ITEM !~ VALUE               false if ITEM ~= /^VALUE$/i
         ITEM =  VALUE                default behaviour (see ITEMS section)
        ====================================================================
- feature: added --nodaemon option
- code:    non dns items first: if a rule contains dns and non dns items, the
	   lookups will only be done if all non dns items matched
- bugfix:  empty pcre with empty sender_(ns|mx)_names was parsed incorrectly.
	   this bug affects postfwd versions 1.12 - 1.13
- bugfix:  negated pcre items with '~=' operator were parsed incorrectly.
	   this bug affects postfwd version 1.13

1.13
=====
- feature: enabled dns cache for sender(ns|mx) and helo address
- feature: new options --dns_max_ns_lookups and --dns_max_mx_lookups
- bugfix:  workaround: Net::Server died if a unix domain socket
	   filename without a dot ('.') was used (B. Frauendienst)

1.12
=====
- feature: new items sender_ns_names and sender_ns_addrs
- feature: new items sender_mx_names and sender_mx_addrs
- feature: new item helo_address, please see docs for more
- feature: added --proto switch, to enable the use of unix domain sockets
	   (thanks to Bernhard Frauendienst)
- feature: added command-line options --kill and --reload
	   (of course you can still use TERM and HUP signals)
- feature: dnsbl txt lookups only for dnsbls with at least one a record.
	   use --dns_async_txt for the old behaviour (see docs for more).
- code:    small performance improvement (5-10%) for pcre (~= or =~) items
- bugfix:  network 0.0.0.0/0 did not work as expected on all platforms
- bugfix:  postfwd tried to chop() an uninitialized value when sending
	   garbage (non policy delegation protocol requests) to it.

1.11
=====
- feature: the ask() action allows to delegate the policy decision to another
           policy service (like postgrey). a new parameter allows to specify
           answer patterns which should be ignored by postfwd. please look
           at the 'ACTIONS' section in the manual (postfwd2 -m) for details.
- feature: new options --noidlestats and --norulelog
- feature: more informative --version
- feature: documentation updates


**************************************************************************************************
ATTENTION:  requirements changed - postfwd since v1.10pre8 now uses Net::DNS.
	    Net::DNS::Async and Net::CIDR::Lite are not required anymore.
NOTE:       please see the docs ('postfwd -m' or 'perldoc postfwd') for more information
**************************************************************************************************

1.10pre8b
==========
- bugfix:  fixed two warnings about logging of undefined values in verbose mode

1.10pre8a
==========
- bugfix:  item plugins have been made available as cache-id items. this fixes a minor issue with
	   --cache-rdomain-only and version 1.10pre8

1.10pre8
=========
- code:    Net::DNS::Async is no longer used. The parameters --dns_queuesize and
           --dns_retries are still valid but have no function. The option --dns_timeout
           now defaults to 14s and applies to all rules containing dns items.
- code:    Net::CIDR::Lite is not required any longer.
- feature: the new variable $$request_hits contains a list of all matching ruleids
- feature: the new variable $$dnsbltext allows access to txt records of rbls
- feature: new options --no-rulestats and --nodnslog
- feature: ttls of the dns responses override --cache-rbl-timeout when bigger, which means
           that you can set the option to 0 if you want to use the ttl of the dns answer.
- feature: new item "rhsbl_helo" allows to check helo against rhsbls
- bugfix:  disabled fallback to synchronous dns on timed out rbls, default is now
	   to disable non responding dnsbls after 11 timeouts for 1200 seconds.
	   use --dns_timeout_max and --dns_timeout_interval to adjust these settings.
- bugfix:  days=Wed now means exactly Wednesday. to use a range you may
           still specify days=Wed- days=-Wed and days=Tue-Thu
           this applies to all date and time items
- code:    --shortlog is now default behaviour (use -v to see more)
- code:    changed Net::Server behaviour to ignore syslog errors


1.10pre7c
==========
- note:    1.10pre7c does not contain any code-changes to the postfwd daemon.
           this release only fixes some issues when buidling packages.
- bugfix:  set permissions of manpage dirs to 755
- bugfix:  manpage has gone to section 8
- bugfix:  postfwd-rblcheck.pl has gone to the tools folder
- bugfix:  documentation now refers to request.sample

1.10pre7b
==========
- bugfix:  inter-section links in documentation did not work correctly
           (thanks to Alexander 'Leo' Bergolth)

1.10pre7a
==========
- bugfix:  implemented workaround for possible crash of Sys::Syslog when syslog
           daemon is unavailable (thanks to Henrik Krohns)
- bugfix:  changed syslog socktype on solaris

1.10pre7
=========
- feature: $$request_score may now be used to access a request's score
- feature: auto-deactivation of non-responding dnsbls; please see the
           new --cleanup-timeouts and --dns_timeout_max options
- feature: the set command allows some basic operations:
  =========================================================
   action=set(ITEM+=VALUE)     adds VALUE to ITEM
   action=set(ITEM-=VALUE)     substracts VALUE from ITEM
   action=set(ITEM*=VALUE)     multiplies ITEM by VALUE
   action=set(ITEM/=VALUE)     divides ITEM through VALUE
   action=set(ITEM.=VALUE)     concatenates ITEM and VALUE
   action=set(ITEM==VALUE)     sets ITEM to VALUE
   action=set(ITEM=VALUE)      default: sets ITEM to VALUE
  =========================================================
- bugfix:  fixed wrong timestamp for timed out rbls
- code:    score() command now allows integer values
- code:    setting an empty score removes it from the table
- code:    duplicate lookups within the same rule are now recognised

1.10pre6
=========
- feature: the new rate() and size() commands offer some basic rate limit controls
- feature: new cleanup options: --cleanup-rates
- feature: regexps may now be included in // characters
- feature: an empty sender address is now replaced by <>
- bugfix:  some csv-separated itemlists did not work correctly since v1.10pre1
- bugfix:  fixed a possible race condition with request cache when config was reloaded via HUP signal

1.10pre5a
=========
- bugfix:  fixed a possible race condition in rbl_read_dns() function

1.10pre5
========
- feature: new dnsbl lookup types: rhsbl_client, rhsbl_sender, rhsbl_reverse_client
- feature: new caching option --cacheid allows to increase performance and cache efficiency
- code:    cleanups will only be logged if '-v' was set or if the process took at least 1 second

1.10pre4
========
- feature: new date items 'days=Sun-Sat' and 'months=Jan-Dec'
- feature: all date/time items may now be csv-separated lists
- feature: the set command can now have multiple, csv-separated arguments
- feature: enhanced use of rblcount and rhsblcount (see doc)
- feature: new caching options --cache-no-sender,--cache-rbl-timeout and --cache-rbl-default
- feature: new cleanup options: --cleanup-requests and --cleanup-rbls
- code:    cache cleanups are now performed on interval basis (not per request)
           which should decrease load on busy systems.
- code:    warning on multiple definitions of id, action, rblcount and rhsblcount is issued
- bugfix:  date items may now contain whitespaces (e.g. days = Fri - Sat)

1.10pre3
========
- feature: all hits for a rule are now logged in the final message
- feature: option --shortlog disables logging for some postfwd actions
- feature: introduced set() command, which enables setting of variables, which then can be
           compared to the ruleset to gain performance on repeated item lists (see doc).
- feature: introduced new command-line switches --dns_queuesize, --dns_retries and dns_retries
           to influence the behaviour of DNS lookups
- code:    restructured code (~+15% speed compared to v1.03, with nodns ruleset)

1.10pre2
========
- feature: DNS lookups are now parallelized per rule. this increases the performance of dnsbl
           items (and any other future dns based check) significantly. implementation (per rule):
           1.) send dns queries, 2.) process other non-dns items, 3.) evaluate dns results
           As a downside of this approach the parser does not wait for dns queries anymore, which
           could result in increased load. you might use the sleep() command to get some delay ;-)

1.10pre1
========
- feature: the way how request items are compared to the ruleset can now be influenced.
  ===============================================================
   ITEM==VALUE                     true if ITEM equals VALUE
   ITEM>=VALUE                     true if ITEM >= VALUE
   ITEM<=VALUE                     true if ITEM <= VALUE
   ITEM~=VALUE                     true if ITEM ~= /^VALUE$/i
   ITEM=VALUE                      old default behaviour
  ===============================================================
- feature: the score() command now allows some basic arithmetic operations (+-*/=)
           e.g. action=score(*2) will double the current score
- feature: you can now refer to request attributes in actions, which will e.g. allow the following:
           id=R001; rbl=zen.spamhaus.org; \
		action=554 5.7.1 see http://www.spamhaus.org/query/bl?ip=$$client_address
- feature: introduced extra request attributes sender_localpart, sender_domain,
           recipient_localpart, recipient_domain and version for use like:
             id=test01; client_name ~= $$(sender_domain)$; action=score(-0.5)
- bugfix:  the "=" character could not be used in items
- bugfix:  negation of items (!!) did not work correctly under some circumstances
- bugfix:  time was logged incorrectly during request cache cleanups in verbose mode
           (thanks to Henrik Krohns)
- code:    restructured some parts of the code for future enhancement options. a plugin interface
           was prepared and will be included in the final version. perl's -w switch is used now.
- note:    the documentation has not been fully updated yet.

1.03
====
- feature: request attributes can now be compared (e.g. to compare client_name and helo_name)
- feature: rule items can now be negated (e.g. to compare if client_name does not match helo_name)
- feature: extra verbose mode '-vv' now displays much more debug information
- feature: -L switch to redirect log output to stdout
- feature: new manual section about the parser, other updates
- bugfix:  caching did not work at end_of_data level because of different queue ids, corrected
- bugfix:  all numeric items will now match if the request attribute exceeds the corresponding
           rule item. the negation operator will lead to the opposite effect:
  =============================================================================
   ITEM=VALUE                            TYPE
  =============================================================================
   rblcount=2                            matches if rbl hits   >= 2
   recipient_count=10                    matches if recipients >= 10
   size=12345                            matches if size       >= 12345
   encryption_keysize=256                matches if keysize    >= 256
   encryption_keysize=!!256              matches if keysize    <  256
  =============================================================================

1.02
====
- bugfix:  rblcount and rhsblcount did not work correctly since V1.01, corrected

1.01
====
- feature: multiple rbl, rhsbl and client_address statements in a single rule are now possible
- feature: note() command will now log (not warn!). an empty argument suppresses logging
- feature: in verbose mode you must set -vv now to see the whole request attributes
- feature: cached dnsbl results are now only logged in verbose mode
- manual:  several minor updates

1.00
====
- feature: multiple definitions of the same item in a single rule to build groups
- feature: rules can span multiple lines by specifying a trailing "\" character
- feature: syslog_name can now be set with -l|--logname <label>
- bugfix:  fixed bug in acl parser (no "}" character could be used in ACLs)

0.99p
=====
- bugfix: size and rcpt_count were checked as minimum values
          now they are correctly interpreted as maximum.

0.99o
=====
- feature: date and time based rules
- feature: macros (please see doc)
- feature: slightly changed statistics output

0.99n
=====
- first public beta version


