Re: [RFC] ignore ftp_epsv off for IPv6

From: Amos Jeffries <squid3_at_treenet.co.nz>
Date: Wed, 29 Jan 2014 20:30:12 +1300

On 29/01/2014 6:40 p.m., Alex Rousskov wrote:
> On 01/28/2014 09:29 PM, Amos Jeffries wrote:
>> On 29/01/2014 9:24 a.m., Alex Rousskov wrote:
>>> On 01/25/2014 06:05 PM, Amos Jeffries wrote:
>>>> "off" should never be abused to mean half-off.
>
>>> The problem here is that the directive itself was misnamed IMO. It
>>> should have been ftp_epsv_for_ipv4 or similar.
>
>> It is named correctly for its scope of "whether to send EPSV command in
>> FTP".
>
> OK, then its scope is wrong. There should not be an option to enable or
> disable a required command; EPSV (or EPRT) are required for IPv6 servers
> to work.
>

The "(or EPRT)" is important. The scope is right.

>>> However, what should Squid do when it is talking to an IPv6 server and
>>> ftp_epsv is "off" or "ipv4"? Does it really make sense to write more
>>> code to handle that essentially misconfigured (but inherited from the
>>> old configs) case? I doubt...
>
>
>> When talking to an IPv6 server with ftp_epsv "off" or "ipv4" the
>> expected behaviour is that Squid uses active-FTP immediately (EPRT
>> command) without even trying the passive connection first.
>
> I assume EPRT is similarly disabled, of course. The two options ought to
> be treated the same for the purpose of this discussion.
>

So this is one of those instances you mentioned in the -n discussion
where Squid can be badly configured but a smart admin does not do so and
we should be allowing configuration rather than denying it.

NP: a smart admin may actually disable both if the network was gatewayed
over software which dies on both. The clients could not contact
IPv6-only servers, but that is the smart admins intent. Fail-fast on
IPv6 rather than trying slow-ish things and killing the gateway router
on the way.

>
>>> How about this alternative:
>>>
>>> 1. Add ftp_epsv_for_ipv4 on/off.
>>> 2. Deprecate ftp_epsv in favor of the newly added ftp_epsv_for_ipv4.
>>> 3. Treat ftp_epsv on/off as ftp_epsv_for_ipv4 on/off.
>>>
>>> This would avoid writing useless code to handle misconfigurations
>>> because it would be impossible to misconfigure Squid in this area.
>
>
>> It is not an isolated command, but one of a set of 5 connection
>> possibilities. The commands permutations are attempted as follows, any
>> one command may be skipped by a matching squid.conf directive, first to
>> succeed wins:
>>
>> * contacting IPv4 server
>>
>> EPSV ALL
>> - skipped when ftp_passive off, ftp_epsv_all off, ftp_epsv_all ipv6
>> - default is skip due to broken NATs and lack of failover possibilities.
>>
>> EPSV <port>
>> - skipped when ftp_passive off, ftp_epsv off, ftp_epsv ipv6
>> - default to attempt since failover is easy and IPv6 benefits
>> outweight the RTT cost.
>>
>> PASV
>> - skipped when ftp_passive off
>> - default to attempt due to RFC requirements
>>
>> EPRT <ipv4>
>> - skipped when ftp_eprt off
>> - default to attempt since failover is easy and IPv6 benefits
>> outweight the RTT cost.
>>
>> PORT <ipv4>
>>
>> Send Failed connection error to client
>>
>>
>> * contacting IPv6 server
>>
>> EPSV ALL
>> - skipped when ftp_passive off, ftp_epsv_all off, ftp_epsv_all ipv4
>> - default is skip due to broken NATs and lack of failover possibilities.
>>
>> EPSV <port>
>> - skipped when ftp_passive off, ftp_epsv off, ftp_epsv ipv4
>> - default to attempt
>>
>> PASV
>> - not possible. always skipped.
>>
>> EPRT <ipv6>
>> - skipped when ftp_eprt off
>> - default to attempt (unless patched by RHEL to send EPSV again)
>>
>> PORT
>> - not possible. always skipped.
>>
>> Send Failed connection error to client
>
>
> The current approach does not work well in practice because, while it
> looks reasonable when IPv4 and IPv6 actions are documented separately,
> the [necessarily single] configuration breaks either IPv4 or IPv6 servers:
>
> If ftp_epsv is on (default):
>
> contacting an IPv4 server may break because the network breaks EPSV.
>
> If ftp_epsv is off:
>
> contacting IPv6 servers breaks because they need EPSV.
>
>
> (I am omitting the cases of ESPV ALL and EPRT for clarity, they do not
> add value to the current discussion).

They *do* add value. Since EPRT may be working perfectly and nullify
your second example of when "ftp_epsv off".

Also note that by "break" you mean:
  IPv6 connectivity to IPv6-only servers over a faulty router is not
possible.

So, what can we possibly do that would not make that broken? IPv4
connectivity to IPv4-enabled servers is still possible. Which is the
scope of your change, yes? to selectively disable the EPSV command being
sent depending on IPv4 or IPv6.

>
> I suspect the initial attempt-based algorithm was developed for PASV and
> PORT only, where it makes sense. It was wrong to add similar EPSV and
> EPRT configuration to that IPv4-specific algorithm because a single
> ftp_epsv option setting does work for a mix of IPv4 and IPv6 servers.

The algorithm is baked into RFC 2428. See section 2 about the meaning of
that 1-digit <net-prt> parameteron EPSV; 1 = IPv4 wanted, 2 = IPv6. The
server accepts or rejects with 522 and a list of supported protocols
which can be tried on the followup attempt.
 Only IPv4/IPv6 are defined by that RFC, however there is a note that
the RFC 1639 set may be used in future.

The data connection to an FTP server is not necessarily going to be the
same protocol as the ctrl channel connection due to dual-stack servers
in IPv6.

In theory only EPSV/EPRT should ever be needed. In practice, for
IPv4-enabled servers all 4 commands should still work fine and for older
servers where EPSV is not supported we can only get a data connection by
treating PASV/PORT as a last-ditch protocol attempt when a rejection
occurs to all attempted EPSV/EPRT or with no list of supported protocols.

Amos
Received on Wed Jan 29 2014 - 07:30:23 MST

This archive was generated by hypermail 2.2.0 : Wed Jan 29 2014 - 12:00:14 MST