mirror of
https://github.com/vdukhovni/postfix
synced 2025-08-29 13:18:12 +00:00
postfix-2.8-20110103
This commit is contained in:
parent
fdd520cf24
commit
19c1ec2275
@ -16337,5 +16337,15 @@ Apologies for any names omitted.
|
||||
TLS <=> plaintext for postscreen(8). One tlsproxy(8) process
|
||||
can translate traffic for multiple remote SMTP clients.
|
||||
With early testing feedback from Victor Duchovni and Christian
|
||||
Roessner. Files: util/nbbio.c, tlsproxy/starttlsd.c,
|
||||
tlsproxy/starttlsd_state.c.
|
||||
Roessner. Files: util/nbbio.[hc], tlsproxy/*.[hc],
|
||||
postscreen/postscreen_starttlsd.c, postscreen/postscreen_smtpd.c.
|
||||
|
||||
20101103
|
||||
|
||||
Cleanup: missing tls_level support in tlsproxy (it has no
|
||||
way to send plaintext, but perhaps an informative error
|
||||
message is in order anyway). File: tlsproxy/tlsproxy.c.
|
||||
|
||||
Cleanup: simplified the handling of throttled output (i.e.
|
||||
output that can't be sent because the receiver tries to be
|
||||
nasty). File: postscreen/postscreen_send.c.
|
||||
|
@ -4,7 +4,12 @@ Wish list:
|
||||
|
||||
anvil rate limit for sasl_username.
|
||||
|
||||
encapsulate nbbio buffer access and update by tlsproxy.
|
||||
Encapsulate nbbio buffer access and update by tlsproxy.
|
||||
|
||||
Full-duplex support for tlsproxy(8). This requires updating
|
||||
events(3) and nbbio(3).
|
||||
|
||||
Register automagic destructor for object attached to VSTREAM.
|
||||
|
||||
smtpd xclient option for sasl_username.
|
||||
|
||||
|
@ -60,98 +60,101 @@ POSTSCREEN(8) POSTSCREEN(8)
|
||||
<a href="http://tools.ietf.org/html/rfc3207">RFC 3207</a> (STARTTLS command)
|
||||
<a href="http://tools.ietf.org/html/rfc3461">RFC 3461</a> (SMTP DSN Extension)
|
||||
<a href="http://tools.ietf.org/html/rfc3463">RFC 3463</a> (Enhanced Status Codes)
|
||||
<a href="http://tools.ietf.org/html/rfc5321">RFC 5321</a> (SMTP protocol, including multi-line 220 greetings)
|
||||
<a href="http://tools.ietf.org/html/rfc5321">RFC 5321</a> (SMTP protocol, including multi-line 220 banners)
|
||||
|
||||
<b>DIAGNOSTICS</b>
|
||||
Problems and transactions are logged to <b>syslogd</b>(8).
|
||||
|
||||
<b>BUGS</b>
|
||||
The <a href="postscreen.8.html"><b>postscreen</b>(8)</a> built-in SMTP protocol engine currently
|
||||
does not announce support for AUTH, XCLIENT or XFORWARD.
|
||||
Support for AUTH may be added in the future. In the mean
|
||||
The <a href="postscreen.8.html"><b>postscreen</b>(8)</a> server does not yet implement the
|
||||
<b><a href="postconf.5.html#soft_bounce">soft_bounce</a></b> feature.
|
||||
|
||||
The <a href="postscreen.8.html"><b>postscreen</b>(8)</a> built-in SMTP protocol engine currently
|
||||
does not announce support for AUTH, XCLIENT or XFORWARD.
|
||||
Support for AUTH may be added in the future. In the mean
|
||||
time, if you need to make these services available on port
|
||||
25, then do not enable the optional "after 220 server
|
||||
25, then do not enable the optional "after 220 server
|
||||
greeting" tests.
|
||||
|
||||
The optional "after 220 server greeting" tests involve
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a>'s built-in SMTP protocol engine. When these
|
||||
The optional "after 220 server greeting" tests involve
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a>'s built-in SMTP protocol engine. When these
|
||||
tests succeed, <a href="postscreen.8.html"><b>postscreen</b>(8)</a> adds the client to the tempo-
|
||||
rary whitelist but it cannot not hand off the "live" con-
|
||||
nection to a Postfix SMTP server process in the middle of
|
||||
a session. Instead, <a href="postscreen.8.html"><b>postscreen</b>(8)</a> defers attempts to
|
||||
deliver mail with a 4XX status, and waits for the client
|
||||
to disconnect. The next time a good client connects, it
|
||||
will be allowed to talk to a Postfix SMTP server process
|
||||
to deliver mail. <a href="postscreen.8.html"><b>postscreen</b>(8)</a> mitigates the impact of
|
||||
this limitation by giving such tests a long expiration
|
||||
rary whitelist but it cannot not hand off the "live" con-
|
||||
nection to a Postfix SMTP server process in the middle of
|
||||
a session. Instead, <a href="postscreen.8.html"><b>postscreen</b>(8)</a> defers attempts to
|
||||
deliver mail with a 4XX status, and waits for the client
|
||||
to disconnect. The next time a good client connects, it
|
||||
will be allowed to talk to a Postfix SMTP server process
|
||||
to deliver mail. <a href="postscreen.8.html"><b>postscreen</b>(8)</a> mitigates the impact of
|
||||
this limitation by giving such tests a long expiration
|
||||
time.
|
||||
|
||||
<b>CONFIGURATION PARAMETERS</b>
|
||||
Changes to <a href="postconf.5.html">main.cf</a> are not picked up automatically, as
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> processes may run for several hours. Use
|
||||
Changes to <a href="postconf.5.html">main.cf</a> are not picked up automatically, as
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> processes may run for several hours. Use
|
||||
the command "postfix reload" after a configuration change.
|
||||
|
||||
The text below provides only a parameter summary. See
|
||||
The text below provides only a parameter summary. See
|
||||
<a href="postconf.5.html"><b>postconf</b>(5)</a> for more details including examples.
|
||||
|
||||
NOTE: Some <a href="postscreen.8.html"><b>postscreen</b>(8)</a> parameters implement stress-
|
||||
dependent behavior. This is supported only when the
|
||||
default parameter value is stress-dependent (that is, it
|
||||
looks like ${stress?X}${stress:Y}, or it is the $<i>name</i> of
|
||||
dependent behavior. This is supported only when the
|
||||
default parameter value is stress-dependent (that is, it
|
||||
looks like ${stress?X}${stress:Y}, or it is the $<i>name</i> of
|
||||
an smtpd parameter with a stress-dependent default).
|
||||
Other parameters always evaluate as if the <b>stress</b> parame-
|
||||
Other parameters always evaluate as if the <b>stress</b> parame-
|
||||
ter value is the empty string.
|
||||
|
||||
<b>COMPATIBILITY CONTROLS</b>
|
||||
<b><a href="postconf.5.html#postscreen_discard_ehlo_keyword_address_maps">postscreen_discard_ehlo_keyword_address_maps</a> ($<a href="postconf.5.html#smtpd_discard_ehlo_keyword_address_maps">smtpd_dis</a>-</b>
|
||||
<b><a href="postconf.5.html#smtpd_discard_ehlo_keyword_address_maps">card_ehlo_keyword_address_maps</a>)</b>
|
||||
Lookup tables, indexed by the remote SMTP client
|
||||
address, with case insensitive lists of EHLO key-
|
||||
words (pipelining, starttls, auth, etc.) that the
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> server will not send in the EHLO
|
||||
Lookup tables, indexed by the remote SMTP client
|
||||
address, with case insensitive lists of EHLO key-
|
||||
words (pipelining, starttls, auth, etc.) that the
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> server will not send in the EHLO
|
||||
response to a remote SMTP client.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_discard_ehlo_keywords">postscreen_discard_ehlo_keywords</a> ($<a href="postconf.5.html#smtpd_discard_ehlo_keywords">smtpd_discard_ehlo_key</a>-</b>
|
||||
<b><a href="postconf.5.html#smtpd_discard_ehlo_keywords">words</a>)</b>
|
||||
A case insensitive list of EHLO keywords (pipelin-
|
||||
ing, starttls, auth, etc.) that the <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
server will not send in the EHLO response to a
|
||||
A case insensitive list of EHLO keywords (pipelin-
|
||||
ing, starttls, auth, etc.) that the <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
server will not send in the EHLO response to a
|
||||
remote SMTP client.
|
||||
|
||||
<b>TRIAGE PARAMETERS</b>
|
||||
<b><a href="postconf.5.html#postscreen_bare_newline_action">postscreen_bare_newline_action</a> (ignore)</b>
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client sends a bare newline character, that is, a
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client sends a bare newline character, that is, a
|
||||
newline not preceded by carriage return.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_bare_newline_enable">postscreen_bare_newline_enable</a> (no)</b>
|
||||
Enable "bare newline" SMTP protocol tests in the
|
||||
Enable "bare newline" SMTP protocol tests in the
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> server.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_blacklist_action">postscreen_blacklist_action</a> (ignore)</b>
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client is permanently blacklisted with the
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client is permanently blacklisted with the
|
||||
<a href="postconf.5.html#postscreen_blacklist_networks">postscreen_blacklist_networks</a> parameter.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_blacklist_networks">postscreen_blacklist_networks</a> (empty)</b>
|
||||
Network addresses that are permanently blacklisted;
|
||||
see the <a href="postconf.5.html#postscreen_blacklist_action">postscreen_blacklist_action</a> parameter for
|
||||
see the <a href="postconf.5.html#postscreen_blacklist_action">postscreen_blacklist_action</a> parameter for
|
||||
possible actions.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_disable_vrfy_command">postscreen_disable_vrfy_command</a> ($<a href="postconf.5.html#disable_vrfy_command">disable_vrfy_command</a>)</b>
|
||||
Disable the SMTP VRFY command in the <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
Disable the SMTP VRFY command in the <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
daemon.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_dnsbl_action">postscreen_dnsbl_action</a> (ignore)</b>
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client's combined DNSBL score is equal to or
|
||||
greater than a threshold (as defined with the
|
||||
greater than a threshold (as defined with the
|
||||
<a href="postconf.5.html#postscreen_dnsbl_sites">postscreen_dnsbl_sites</a> and <a href="postconf.5.html#postscreen_dnsbl_threshold">postscreen_dnsbl_thresh</a>-
|
||||
<a href="postconf.5.html#postscreen_dnsbl_threshold">old</a> parameters).
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_dnsbl_reply_map">postscreen_dnsbl_reply_map</a> (empty)</b>
|
||||
A mapping from actual DNSBL domain name which
|
||||
includes a secret password, to the DNSBL domain
|
||||
A mapping from actual DNSBL domain name which
|
||||
includes a secret password, to the DNSBL domain
|
||||
name that postscreen will reply with when it
|
||||
rejects mail.
|
||||
|
||||
@ -160,16 +163,16 @@ POSTSCREEN(8) POSTSCREEN(8)
|
||||
weight factors.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_dnsbl_threshold">postscreen_dnsbl_threshold</a> (1)</b>
|
||||
The inclusive lower bound for blocking an SMTP
|
||||
The inclusive lower bound for blocking an SMTP
|
||||
client, based on its combined DNSBL score as
|
||||
defined with the <a href="postconf.5.html#postscreen_dnsbl_sites">postscreen_dnsbl_sites</a> parameter.
|
||||
defined with the <a href="postconf.5.html#postscreen_dnsbl_sites">postscreen_dnsbl_sites</a> parameter.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_forbidden_commands">postscreen_forbidden_commands</a> ($<a href="postconf.5.html#smtpd_forbidden_commands">smtpd_forbidden_commands</a>)</b>
|
||||
List of commands that the <a href="postscreen.8.html"><b>postscreen</b>(8)</a> server con-
|
||||
siders in violation of the SMTP protocol.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_greet_action">postscreen_greet_action</a> (ignore)</b>
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client speaks before its turn within the time spec-
|
||||
ified with the <a href="postconf.5.html#postscreen_greet_wait">postscreen_greet_wait</a> parameter.
|
||||
|
||||
@ -177,151 +180,151 @@ POSTSCREEN(8) POSTSCREEN(8)
|
||||
The <i>text</i> in the optional "220-<i>text</i>..." server
|
||||
response that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> sends ahead of the real
|
||||
Postfix SMTP server's "220 text..." response, in an
|
||||
attempt to confuse bad SMTP clients so that they
|
||||
attempt to confuse bad SMTP clients so that they
|
||||
speak before their turn (pre-greet).
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_greet_wait">postscreen_greet_wait</a> (${stress?2}${stress:6}s)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will wait for
|
||||
an SMTP client to send a command before its turn,
|
||||
and for DNS blocklist lookup results to arrive
|
||||
(default: up to 2 seconds under stress, up to 6
|
||||
an SMTP client to send a command before its turn,
|
||||
and for DNS blocklist lookup results to arrive
|
||||
(default: up to 2 seconds under stress, up to 6
|
||||
seconds otherwise).
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_helo_required">postscreen_helo_required</a> ($<a href="postconf.5.html#smtpd_helo_required">smtpd_helo_required</a>)</b>
|
||||
Require that a remote SMTP client sends HELO or
|
||||
Require that a remote SMTP client sends HELO or
|
||||
EHLO before commencing a MAIL transaction.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_non_smtp_command_action">postscreen_non_smtp_command_action</a> (drop)</b>
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client sends non-SMTP commands as specified with
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client sends non-SMTP commands as specified with
|
||||
the <a href="postconf.5.html#postscreen_forbidden_commands">postscreen_forbidden_commands</a> parameter.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_non_smtp_command_enable">postscreen_non_smtp_command_enable</a> (no)</b>
|
||||
Enable "non-SMTP command" tests in the
|
||||
Enable "non-SMTP command" tests in the
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> server.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_pipelining_action">postscreen_pipelining_action</a> (enforce)</b>
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client sends multiple commands instead of sending
|
||||
one command and waiting for the server to respond.
|
||||
The action that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> takes when an SMTP
|
||||
client sends multiple commands instead of sending
|
||||
one command and waiting for the server to respond.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_pipelining_enable">postscreen_pipelining_enable</a> (no)</b>
|
||||
Enable "pipelining" SMTP protocol tests in the
|
||||
Enable "pipelining" SMTP protocol tests in the
|
||||
<a href="postscreen.8.html"><b>postscreen</b>(8)</a> server.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_whitelist_networks">postscreen_whitelist_networks</a> ($<a href="postconf.5.html#mynetworks">mynetworks</a>)</b>
|
||||
Network addresses that are permanently whitelisted,
|
||||
and that will not be subjected to <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
and that will not be subjected to <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
checks.
|
||||
|
||||
<b><a href="postconf.5.html#smtpd_service_name">smtpd_service_name</a> (smtpd)</b>
|
||||
The internal service that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> forwards
|
||||
The internal service that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> forwards
|
||||
allowed connections to.
|
||||
|
||||
<b>CACHE CONTROLS</b>
|
||||
<b><a href="postconf.5.html#postscreen_cache_cleanup_interval">postscreen_cache_cleanup_interval</a> (12h)</b>
|
||||
The amount of time between <a href="postscreen.8.html"><b>postscreen</b>(8)</a> cache
|
||||
The amount of time between <a href="postscreen.8.html"><b>postscreen</b>(8)</a> cache
|
||||
cleanup runs.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_cache_map">postscreen_cache_map</a> (btree:$<a href="postconf.5.html#data_directory">data_directory</a>/ps_cache)</b>
|
||||
Persistent storage for the <a href="postscreen.8.html"><b>postscreen</b>(8)</a> server
|
||||
Persistent storage for the <a href="postscreen.8.html"><b>postscreen</b>(8)</a> server
|
||||
decisions.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_cache_retention_time">postscreen_cache_retention_time</a> (7d)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache an
|
||||
expired temporary whitelist entry before it is
|
||||
expired temporary whitelist entry before it is
|
||||
removed.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_bare_newline_ttl">postscreen_bare_newline_ttl</a> (30d)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful "bare newline" SMTP pro-
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful "bare newline" SMTP pro-
|
||||
tocol test.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_dnsbl_ttl">postscreen_dnsbl_ttl</a> (1h)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful DNS blocklist test.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_greet_ttl">postscreen_greet_ttl</a> (1d)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful PREGREET test.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_non_smtp_command_ttl">postscreen_non_smtp_command_ttl</a> (30d)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful "non_smtp_command" SMTP
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful "non_smtp_command" SMTP
|
||||
protocol test.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_pipelining_ttl">postscreen_pipelining_ttl</a> (30d)</b>
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful "pipelining" SMTP proto-
|
||||
The amount of time that <a href="postscreen.8.html"><b>postscreen</b>(8)</a> will cache
|
||||
results from a successful "pipelining" SMTP proto-
|
||||
col test.
|
||||
|
||||
<b>RESOURCE CONTROLS</b>
|
||||
<b><a href="postconf.5.html#line_length_limit">line_length_limit</a> (2048)</b>
|
||||
Upon input, long lines are chopped up into pieces
|
||||
of at most this length; upon delivery, long lines
|
||||
Upon input, long lines are chopped up into pieces
|
||||
of at most this length; upon delivery, long lines
|
||||
are reconstructed.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_client_connection_count_limit">postscreen_client_connection_count_limit</a></b>
|
||||
<b>($<a href="postconf.5.html#smtpd_client_connection_count_limit">smtpd_client_connection_count_limit</a>)</b>
|
||||
How many simultaneous connections any client is
|
||||
How many simultaneous connections any client is
|
||||
allowed to have with the <a href="postscreen.8.html"><b>postscreen</b>(8)</a> daemon.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_command_count_limit">postscreen_command_count_limit</a> (20)</b>
|
||||
The limit on the total number of commands per SMTP
|
||||
session for <a href="postscreen.8.html"><b>postscreen</b>(8)</a>'s built-in SMTP protocol
|
||||
The limit on the total number of commands per SMTP
|
||||
session for <a href="postscreen.8.html"><b>postscreen</b>(8)</a>'s built-in SMTP protocol
|
||||
engine.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_command_time_limit">postscreen_command_time_limit</a> (${stress?10}${stress:300}s)</b>
|
||||
The command "read" time limit for <a href="postscreen.8.html"><b>postscreen</b>(8)</a>'s
|
||||
The command "read" time limit for <a href="postscreen.8.html"><b>postscreen</b>(8)</a>'s
|
||||
built-in SMTP protocol engine.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_post_queue_limit">postscreen_post_queue_limit</a> ($<a href="postconf.5.html#default_process_limit">default_process_limit</a>)</b>
|
||||
The number of clients that can be waiting for ser-
|
||||
The number of clients that can be waiting for ser-
|
||||
vice from a real SMTP server process.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_pre_queue_limit">postscreen_pre_queue_limit</a> ($<a href="postconf.5.html#default_process_limit">default_process_limit</a>)</b>
|
||||
The number of non-whitelisted clients that can be
|
||||
waiting for a decision whether they will receive
|
||||
The number of non-whitelisted clients that can be
|
||||
waiting for a decision whether they will receive
|
||||
service from a real SMTP server process.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_watchdog_timeout">postscreen_watchdog_timeout</a> (10s)</b>
|
||||
How much time a <a href="postscreen.8.html"><b>postscreen</b>(8)</a> process may take to
|
||||
respond to an SMTP client command or to perform a
|
||||
How much time a <a href="postscreen.8.html"><b>postscreen</b>(8)</a> process may take to
|
||||
respond to an SMTP client command or to perform a
|
||||
cache operation before it is terminated by a built-
|
||||
in watchdog timer.
|
||||
|
||||
<b>STARTTLS CONTROLS</b>
|
||||
<b><a href="postconf.5.html#postscreen_tls_security_level">postscreen_tls_security_level</a> ($<a href="postconf.5.html#smtpd_tls_security_level">smtpd_tls_security_level</a>)</b>
|
||||
The SMTP TLS security level for the <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
server; when a non-empty value is specified, this
|
||||
The SMTP TLS security level for the <a href="postscreen.8.html"><b>postscreen</b>(8)</a>
|
||||
server; when a non-empty value is specified, this
|
||||
overrides the obsolete parameters
|
||||
<a href="postconf.5.html#postscreen_use_tls">postscreen_use_tls</a> and <a href="postconf.5.html#postscreen_enforce_tls">postscreen_enforce_tls</a>.
|
||||
|
||||
<b>OBSOLETE STARTTLS SUPPORT CONTROLS</b>
|
||||
These parameters are supported for compatibility with
|
||||
These parameters are supported for compatibility with
|
||||
<a href="smtpd.8.html"><b>smtpd</b>(8)</a> legacy parameters.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_use_tls">postscreen_use_tls</a> ($<a href="postconf.5.html#smtpd_use_tls">smtpd_use_tls</a>)</b>
|
||||
Opportunistic TLS: announce STARTTLS support to
|
||||
SMTP clients, but do not require that clients use
|
||||
Opportunistic TLS: announce STARTTLS support to
|
||||
SMTP clients, but do not require that clients use
|
||||
TLS encryption.
|
||||
|
||||
<b><a href="postconf.5.html#postscreen_enforce_tls">postscreen_enforce_tls</a> ($<a href="postconf.5.html#smtpd_enforce_tls">smtpd_enforce_tls</a>)</b>
|
||||
Mandatory TLS: announce STARTTLS support to SMTP
|
||||
clients, and require that clients use TLS encryp-
|
||||
Mandatory TLS: announce STARTTLS support to SMTP
|
||||
clients, and require that clients use TLS encryp-
|
||||
tion.
|
||||
|
||||
<b>MISCELLANEOUS CONTROLS</b>
|
||||
<b><a href="postconf.5.html#config_directory">config_directory</a> (see 'postconf -d' output)</b>
|
||||
The default location of the Postfix <a href="postconf.5.html">main.cf</a> and
|
||||
The default location of the Postfix <a href="postconf.5.html">main.cf</a> and
|
||||
<a href="master.5.html">master.cf</a> configuration files.
|
||||
|
||||
<b><a href="postconf.5.html#delay_logging_resolution_limit">delay_logging_resolution_limit</a> (2)</b>
|
||||
The maximal number of digits after the decimal
|
||||
The maximal number of digits after the decimal
|
||||
point when logging sub-second delay values.
|
||||
|
||||
<b><a href="postconf.5.html#command_directory">command_directory</a> (see 'postconf -d' output)</b>
|
||||
The location of all postfix administrative com-
|
||||
The location of all postfix administrative com-
|
||||
mands.
|
||||
|
||||
<b><a href="postconf.5.html#ipc_timeout">ipc_timeout</a> (3600s)</b>
|
||||
@ -329,24 +332,24 @@ POSTSCREEN(8) POSTSCREEN(8)
|
||||
over an internal communication channel.
|
||||
|
||||
<b><a href="postconf.5.html#max_idle">max_idle</a> (100s)</b>
|
||||
The maximum amount of time that an idle Postfix
|
||||
daemon process waits for an incoming connection
|
||||
The maximum amount of time that an idle Postfix
|
||||
daemon process waits for an incoming connection
|
||||
before terminating voluntarily.
|
||||
|
||||
<b><a href="postconf.5.html#process_id">process_id</a> (read-only)</b>
|
||||
The process ID of a Postfix command or daemon
|
||||
The process ID of a Postfix command or daemon
|
||||
process.
|
||||
|
||||
<b><a href="postconf.5.html#process_name">process_name</a> (read-only)</b>
|
||||
The process name of a Postfix command or daemon
|
||||
The process name of a Postfix command or daemon
|
||||
process.
|
||||
|
||||
<b><a href="postconf.5.html#syslog_facility">syslog_facility</a> (mail)</b>
|
||||
The syslog facility of Postfix logging.
|
||||
|
||||
<b><a href="postconf.5.html#syslog_name">syslog_name</a> (see 'postconf -d' output)</b>
|
||||
The mail system name that is prepended to the
|
||||
process name in syslog records, so that "smtpd"
|
||||
The mail system name that is prepended to the
|
||||
process name in syslog records, so that "smtpd"
|
||||
becomes, for example, "postfix/smtpd".
|
||||
|
||||
<b>SEE ALSO</b>
|
||||
@ -359,12 +362,12 @@ POSTSCREEN(8) POSTSCREEN(8)
|
||||
<a href="POSTSCREEN_README.html">POSTSCREEN_README</a>, Postfix Postscreen Howto
|
||||
|
||||
<b>LICENSE</b>
|
||||
The Secure Mailer license must be distributed with this
|
||||
The Secure Mailer license must be distributed with this
|
||||
software.
|
||||
|
||||
<b>HISTORY</b>
|
||||
Many ideas in <a href="postscreen.8.html"><b>postscreen</b>(8)</a> were explored in earlier work
|
||||
by Michael Tokarev, in OpenBSD spamd, and in MailChannels
|
||||
Many ideas in <a href="postscreen.8.html"><b>postscreen</b>(8)</a> were explored in earlier work
|
||||
by Michael Tokarev, in OpenBSD spamd, and in MailChannels
|
||||
Traffic Control.
|
||||
|
||||
<b>AUTHOR(S)</b>
|
||||
|
@ -63,7 +63,7 @@ RFC 2920 (SMTP Pipelining)
|
||||
RFC 3207 (STARTTLS command)
|
||||
RFC 3461 (SMTP DSN Extension)
|
||||
RFC 3463 (Enhanced Status Codes)
|
||||
RFC 5321 (SMTP protocol, including multi-line 220 greetings)
|
||||
RFC 5321 (SMTP protocol, including multi-line 220 banners)
|
||||
.SH DIAGNOSTICS
|
||||
.ad
|
||||
.fi
|
||||
@ -71,6 +71,9 @@ Problems and transactions are logged to \fBsyslogd\fR(8).
|
||||
.SH BUGS
|
||||
.ad
|
||||
.fi
|
||||
The \fBpostscreen\fR(8) server does not yet implement
|
||||
the \fBsoft_bounce\fR feature.
|
||||
|
||||
The \fBpostscreen\fR(8) built-in SMTP protocol engine
|
||||
currently does not announce support for AUTH, XCLIENT or
|
||||
XFORWARD.
|
||||
|
@ -20,7 +20,7 @@
|
||||
* Patches change both the patchlevel and the release date. Snapshots have no
|
||||
* patchlevel; they change the release date only.
|
||||
*/
|
||||
#define MAIL_RELEASE_DATE "20110102"
|
||||
#define MAIL_RELEASE_DATE "20110103"
|
||||
#define MAIL_VERSION_NUMBER "2.8"
|
||||
|
||||
#ifdef SNAPSHOT
|
||||
|
@ -180,6 +180,7 @@ postscreen_send.o: ../../include/dict_cache.h
|
||||
postscreen_send.o: ../../include/events.h
|
||||
postscreen_send.o: ../../include/htable.h
|
||||
postscreen_send.o: ../../include/iostuff.h
|
||||
postscreen_send.o: ../../include/mail_params.h
|
||||
postscreen_send.o: ../../include/match_list.h
|
||||
postscreen_send.o: ../../include/match_ops.h
|
||||
postscreen_send.o: ../../include/msg.h
|
||||
|
@ -53,10 +53,13 @@
|
||||
/* RFC 3207 (STARTTLS command)
|
||||
/* RFC 3461 (SMTP DSN Extension)
|
||||
/* RFC 3463 (Enhanced Status Codes)
|
||||
/* RFC 5321 (SMTP protocol, including multi-line 220 greetings)
|
||||
/* RFC 5321 (SMTP protocol, including multi-line 220 banners)
|
||||
/* DIAGNOSTICS
|
||||
/* Problems and transactions are logged to \fBsyslogd\fR(8).
|
||||
/* BUGS
|
||||
/* The \fBpostscreen\fR(8) server does not yet implement
|
||||
/* the \fBsoft_bounce\fR feature.
|
||||
/*
|
||||
/* The \fBpostscreen\fR(8) built-in SMTP protocol engine
|
||||
/* currently does not announce support for AUTH, XCLIENT or
|
||||
/* XFORWARD.
|
||||
@ -542,9 +545,10 @@ static void psc_service(VSTREAM *smtp_client_stream,
|
||||
if (getpeername(vstream_fileno(smtp_client_stream), (struct sockaddr *)
|
||||
& addr_storage, &addr_storage_len) < 0) {
|
||||
msg_warn("getpeername: %m -- dropping this connection");
|
||||
psc_send_reply(vstream_fileno(smtp_client_stream),
|
||||
"unknown_address", "unknown_port",
|
||||
"421 4.3.2 No system resources\r\n");
|
||||
/* Best effort - if this non-blocking write(2) fails, so be it. */
|
||||
(void) write(vstream_fileno(smtp_client_stream),
|
||||
"421 4.3.2 No system resources\r\n",
|
||||
sizeof("421 4.3.2 No system resources\r\n") - 1);
|
||||
PSC_SERVICE_DISCONNECT_AND_RETURN(smtp_client_stream);
|
||||
}
|
||||
|
||||
@ -558,9 +562,10 @@ static void psc_service(VSTREAM *smtp_client_stream,
|
||||
msg_warn("cannot convert client address/port to string: %s"
|
||||
" -- dropping this connection",
|
||||
MAI_STRERROR(aierr));
|
||||
psc_send_reply(vstream_fileno(smtp_client_stream),
|
||||
"unknown_address", "unknown_port",
|
||||
"421 4.3.2 No system resources\r\n");
|
||||
/* Best effort - if this non-blocking write(2) fails, so be it. */
|
||||
(void) write(vstream_fileno(smtp_client_stream),
|
||||
"421 4.3.2 No system resources\r\n",
|
||||
sizeof("421 4.3.2 No system resources\r\n") - 1);
|
||||
PSC_SERVICE_DISCONNECT_AND_RETURN(smtp_client_stream);
|
||||
}
|
||||
if (strncasecmp("::ffff:", smtp_client_addr.buf, 7) == 0)
|
||||
|
@ -44,6 +44,7 @@ typedef struct {
|
||||
char *smtp_client_port; /* client port */
|
||||
int client_concurrency; /* per-client */
|
||||
const char *final_reply; /* cause for hanging up */
|
||||
VSTRING *send_buf; /* pending output */
|
||||
/* Test context. */
|
||||
struct timeval start_time; /* start of current test */
|
||||
const char *test_name; /* name of current test */
|
||||
@ -438,12 +439,8 @@ extern void psc_hangup_event(PSC_STATE *);
|
||||
/*
|
||||
* postscreen_send.c
|
||||
*/
|
||||
#define PSC_SEND_REPLY(state, text) \
|
||||
psc_send_reply(vstream_fileno((state)->smtp_client_stream), \
|
||||
(state)->smtp_client_addr, \
|
||||
(state)->smtp_client_port, \
|
||||
(text))
|
||||
extern int psc_send_reply(int, const char *, const char *, const char *);
|
||||
#define PSC_SEND_REPLY psc_send_reply /* legacy macro */
|
||||
extern int psc_send_reply(PSC_STATE *, const char *);
|
||||
extern void psc_send_socket(PSC_STATE *);
|
||||
|
||||
/*
|
||||
|
@ -6,13 +6,12 @@
|
||||
/* SYNOPSIS
|
||||
/* #include <postscreen.h>
|
||||
/*
|
||||
/* int psc_send_reply(client_fd, client_addr, client_port, text)
|
||||
/* int client_fd;
|
||||
/* const char *client_addr;
|
||||
/* const char *client_port;
|
||||
/* int psc_send_reply(state, text)
|
||||
/* PSC_STATE *state;
|
||||
/* const char *text;
|
||||
/*
|
||||
/* int PSC_SEND_REPLY(state, text)
|
||||
/* PSC_STATE *state;
|
||||
/* const char *text;
|
||||
/*
|
||||
/* void psc_send_socket(state)
|
||||
@ -23,9 +22,8 @@
|
||||
/* a warning (except EPIPE) with the client address and port,
|
||||
/* and returns a non-zero result (all errors including EPIPE).
|
||||
/*
|
||||
/* PSC_SEND_REPLY() is a convenience wrapper for psc_send_reply().
|
||||
/* It is an unsafe macro that evaluates its arguments multiple
|
||||
/* times.
|
||||
/* PSC_SEND_REPLY() is a legacy wrapper for psc_send_reply().
|
||||
/* It will eventually be replaced by its expansion.
|
||||
/*
|
||||
/* psc_send_socket() sends the specified socket to the real
|
||||
/* Postfix SMTP server. The socket is delivered in the background.
|
||||
@ -57,6 +55,10 @@
|
||||
#include <iostuff.h>
|
||||
#include <connect.h>
|
||||
|
||||
/* Global library. */
|
||||
|
||||
#include <mail_params.h>
|
||||
|
||||
/* Application-specific. */
|
||||
|
||||
#include <postscreen.h>
|
||||
@ -67,28 +69,53 @@
|
||||
*/
|
||||
#define PSC_SEND_SOCK_CONNECT_TIMEOUT 1
|
||||
#define PSC_SEND_SOCK_NOTIFY_TIMEOUT 100
|
||||
#define PSC_SEND_TEXT_TIMEOUT 1
|
||||
|
||||
/* psc_send_reply - send reply to remote SMTP client */
|
||||
|
||||
int psc_send_reply(int smtp_client_fd, const char *smtp_client_addr,
|
||||
const char *smtp_client_port, const char *text)
|
||||
int psc_send_reply(PSC_STATE *state, const char *text)
|
||||
{
|
||||
int start;
|
||||
int ret;
|
||||
|
||||
if (msg_verbose)
|
||||
msg_info("> [%s]:%s: %.*s", smtp_client_addr, smtp_client_port,
|
||||
(int) strlen(text) - 2, text);
|
||||
msg_info("> [%s]:%s: %.*s", state->smtp_client_addr,
|
||||
state->smtp_client_port, (int) strlen(text) - 2, text);
|
||||
|
||||
/*
|
||||
* XXX Need to make sure that the TCP send buffer is large enough for any
|
||||
* response, so that a nasty client can't cause this process to block.
|
||||
* Append the new text to earlier text that could not be sent because the
|
||||
* output was throttled.
|
||||
*/
|
||||
ret = (write_buf(smtp_client_fd, text, strlen(text),
|
||||
PSC_SEND_TEXT_TIMEOUT) < 0);
|
||||
if (ret != 0 && errno != EPIPE)
|
||||
msg_warn("write [%s]:%s: %m", smtp_client_addr, smtp_client_port);
|
||||
return (ret);
|
||||
start = VSTRING_LEN(state->send_buf);
|
||||
vstring_strcat(state->send_buf, text);
|
||||
|
||||
/*
|
||||
* XXX For soft_bounce support, it is not sufficient to fix replies here.
|
||||
* We also need to fix the REJECT messages that are logged by the dummy
|
||||
* SMTP engine. Those messages are set with the PSC_DROP_SESSION_STATE
|
||||
* and PSC_ENFORCE_SESSION_STATE macros, and we should not mess up all
|
||||
* the code that invokes those macros.
|
||||
*/
|
||||
#if 0
|
||||
if (var_soft_bounce) {
|
||||
if (text[0] == '5')
|
||||
STR(state->send_buf)[start + 0] = '4';
|
||||
if (text[4] == '5')
|
||||
STR(state->send_buf)[start + 4] = '4';
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Do a best effort sending text, but don't block when the output is
|
||||
* throttled by a hostile peer.
|
||||
*/
|
||||
ret = write(vstream_fileno(state->smtp_client_stream),
|
||||
STR(state->send_buf), LEN(state->send_buf));
|
||||
if (ret > 0)
|
||||
vstring_truncate(state->send_buf, ret - LEN(state->send_buf));
|
||||
if (ret < 0 && errno != EAGAIN && errno != EPIPE)
|
||||
msg_warn("write [%s]:%s: %m", state->smtp_client_addr,
|
||||
state->smtp_client_port);
|
||||
return (ret < 0 && errno != EAGAIN);
|
||||
}
|
||||
|
||||
/* psc_send_socket_close_event - file descriptor has arrived or timeout */
|
||||
|
@ -260,7 +260,8 @@ static int psc_helo_cmd(PSC_STATE *state, char *args)
|
||||
|
||||
/* psc_smtpd_format_ehlo_reply - format EHLO response */
|
||||
|
||||
static void psc_smtpd_format_ehlo_reply(VSTRING *buf, int discard_mask)
|
||||
static void psc_smtpd_format_ehlo_reply(VSTRING *buf, int discard_mask
|
||||
/*, const char *sasl_mechanism_list */)
|
||||
{
|
||||
const char *myname = "psc_smtpd_format_ehlo_reply";
|
||||
int saved_len = 0;
|
||||
@ -1063,6 +1064,9 @@ void psc_smtpd_init(void)
|
||||
case TLS_LEV_SECURE:
|
||||
case TLS_LEV_VERIFY:
|
||||
case TLS_LEV_FPRINT:
|
||||
msg_warn("%s: unsupported TLS level \"%s\", using \"encrypt\"",
|
||||
VAR_PSC_TLS_LEVEL, var_psc_tls_level);
|
||||
/* FALLTHROUGH */
|
||||
case TLS_LEV_ENCRYPT:
|
||||
var_psc_enforce_tls = var_psc_use_tls = 1;
|
||||
break;
|
||||
|
@ -153,6 +153,7 @@ PSC_STATE *psc_new_session_state(VSTREAM *stream,
|
||||
state->smtp_server_fd = (-1);
|
||||
state->smtp_client_addr = mystrdup(addr);
|
||||
state->smtp_client_port = mystrdup(port);
|
||||
state->send_buf = vstring_alloc(100);
|
||||
state->test_name = "TEST NAME HERE";
|
||||
state->dnsbl_reply = 0;
|
||||
state->final_reply = "421 4.3.2 Service currently unavailable\r\n";
|
||||
@ -212,6 +213,8 @@ void psc_free_session_state(PSC_STATE *state)
|
||||
close(state->smtp_server_fd);
|
||||
psc_post_queue_length--;
|
||||
}
|
||||
if (state->send_buf != 0)
|
||||
state->send_buf = vstring_free(state->send_buf);
|
||||
myfree(state->smtp_client_addr);
|
||||
myfree(state->smtp_client_port);
|
||||
if (state->dnsbl_reply)
|
||||
|
@ -293,6 +293,7 @@ int var_tlsp_watchdog;
|
||||
static TLS_APPL_STATE *tlsp_server_ctx;
|
||||
static int ask_client_cert;
|
||||
static int enforce_tls;
|
||||
static int tlsp_tls_enforce_tls;
|
||||
|
||||
/*
|
||||
* SLMs.
|
||||
@ -625,9 +626,13 @@ static void tlsp_ciphertext_event(int event, char *context)
|
||||
if (event == EVENT_READ || event == EVENT_WRITE) {
|
||||
tlsp_strategy(state);
|
||||
} else {
|
||||
msg_warn("read/write %s for %s",
|
||||
event == EVENT_TIME ? "timeout" : "error",
|
||||
state->remote_endpt);
|
||||
if (event == EVENT_TIME && state->ssl_last_err == SSL_ERROR_NONE)
|
||||
msg_warn("deadlock on plaintext stream for %s",
|
||||
state->remote_endpt);
|
||||
else
|
||||
msg_warn("read/write %s for %s",
|
||||
event == EVENT_TIME ? "timeout" : "error",
|
||||
state->remote_endpt);
|
||||
tlsp_state_free(state);
|
||||
}
|
||||
}
|
||||
@ -645,8 +650,6 @@ static void tlsp_start_tls(TLSP_STATE *state)
|
||||
* going to sanitize this because doing so surely will break things in
|
||||
* unexpected ways.
|
||||
*/
|
||||
state->tls_use_tls = var_tlsp_use_tls | var_tlsp_enforce_tls;
|
||||
state->tls_enforce_tls = var_tlsp_enforce_tls;
|
||||
|
||||
/*
|
||||
* Perform the before-handshake portion of the per-session initalization.
|
||||
@ -680,7 +683,7 @@ static void tlsp_start_tls(TLSP_STATE *state)
|
||||
log_level = var_tlsp_tls_loglevel,
|
||||
timeout = 0, /* unused */
|
||||
requirecert = (var_tlsp_tls_req_ccert
|
||||
&& state->tls_enforce_tls),
|
||||
&& tlsp_tls_enforce_tls),
|
||||
serverid = state->service,
|
||||
namaddr = state->remote_endpt,
|
||||
cipher_grade = cipher_grade,
|
||||
@ -894,7 +897,39 @@ static void pre_jail_init(char *unused_name, char **unused_argv)
|
||||
* The code in this routine is pasted literally from smtpd(8). I am not
|
||||
* going to sanitize this because doing so surely will break things in
|
||||
* unexpected ways.
|
||||
*
|
||||
*/
|
||||
if (*var_tlsp_tls_level) {
|
||||
switch (tls_level_lookup(var_tlsp_tls_level)) {
|
||||
default:
|
||||
msg_fatal("Invalid TLS level \"%s\"", var_tlsp_tls_level);
|
||||
/* NOTREACHED */
|
||||
break;
|
||||
case TLS_LEV_SECURE:
|
||||
case TLS_LEV_VERIFY:
|
||||
case TLS_LEV_FPRINT:
|
||||
msg_warn("%s: unsupported TLS level \"%s\", using \"encrypt\"",
|
||||
VAR_TLSP_TLS_LEVEL, var_tlsp_tls_level);
|
||||
/* FALLTHROUGH */
|
||||
case TLS_LEV_ENCRYPT:
|
||||
var_tlsp_enforce_tls = var_tlsp_use_tls = 1;
|
||||
break;
|
||||
case TLS_LEV_MAY:
|
||||
var_tlsp_enforce_tls = 0;
|
||||
var_tlsp_use_tls = 1;
|
||||
break;
|
||||
case TLS_LEV_NONE:
|
||||
var_tlsp_enforce_tls = var_tlsp_use_tls = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
tlsp_tls_enforce_tls = var_tlsp_enforce_tls;
|
||||
if (!(var_tlsp_use_tls || var_tlsp_enforce_tls)) {
|
||||
msg_warn("TLS service is requested, but disabled with %s or %s",
|
||||
VAR_TLSP_TLS_LEVEL, VAR_TLSP_USE_TLS);
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* Load TLS keys before dropping privileges.
|
||||
*
|
||||
* Can't use anonymous ciphers if we want client certificates. Must use
|
||||
|
@ -33,8 +33,6 @@ typedef struct {
|
||||
char *remote_endpt; /* printable remote endpoint */
|
||||
TLS_SESS_STATE *tls_context; /* llibtls state */
|
||||
int ssl_last_err; /* TLS I/O state */
|
||||
int tls_use_tls; /* legacy libtls API */
|
||||
int tls_enforce_tls; /* legacy libtls API */
|
||||
} TLSP_STATE;
|
||||
|
||||
#define TLSP_FLAG_DO_HANDSHAKE (1<<0)
|
||||
|
@ -173,7 +173,8 @@
|
||||
/* arguments more than once. The result is NOT null-terminated.
|
||||
/*
|
||||
/* vstring_truncate() truncates the named string to the specified
|
||||
/* length. The operation has no effect when the string is shorter.
|
||||
/* length. If length is negative, the trailing portion is kept.
|
||||
/* The operation has no effect when the string is shorter.
|
||||
/* The string is not null-terminated.
|
||||
/*
|
||||
/* VSTRING_RESET() is a macro that resets the write position of its
|
||||
@ -393,8 +394,13 @@ void vstring_ctl(VSTRING *vp,...)
|
||||
|
||||
VSTRING *vstring_truncate(VSTRING *vp, ssize_t len)
|
||||
{
|
||||
if (len < 0)
|
||||
msg_panic("vstring_truncate: bad length %ld", (long) len);
|
||||
ssize_t move;
|
||||
|
||||
if (len < 0) {
|
||||
len = (-len);
|
||||
if ((move = VSTRING_LEN(vp) - len) > 0)
|
||||
memmove(vstring_str(vp), vstring_str(vp) + move, len);
|
||||
}
|
||||
if (len < VSTRING_LEN(vp))
|
||||
VSTRING_AT_OFFSET(vp, len);
|
||||
return (vp);
|
||||
|
Loading…
x
Reference in New Issue
Block a user