From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from firstgate.proxmox.com (firstgate.proxmox.com [212.224.123.68]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by lists.proxmox.com (Postfix) with ESMTPS id 083E17B6FF for ; Wed, 12 May 2021 21:05:39 +0200 (CEST) Received: from firstgate.proxmox.com (localhost [127.0.0.1]) by firstgate.proxmox.com (Proxmox) with ESMTP id E205A10E39 for ; Wed, 12 May 2021 21:05:08 +0200 (CEST) Received: from proxmox-new.maurer-it.com (proxmox-new.maurer-it.com [94.136.29.106]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by firstgate.proxmox.com (Proxmox) with ESMTPS id 236E110E2D for ; Wed, 12 May 2021 21:05:07 +0200 (CEST) Received: from proxmox-new.maurer-it.com (localhost.localdomain [127.0.0.1]) by proxmox-new.maurer-it.com (Proxmox) with ESMTP id DC1C846556 for ; Wed, 12 May 2021 21:05:06 +0200 (CEST) From: Stoiko Ivanov To: pve-devel@lists.proxmox.com Date: Wed, 12 May 2021 21:04:52 +0200 Message-Id: <20210512190452.22885-1-s.ivanov@proxmox.com> X-Mailer: git-send-email 2.20.1 MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-SPAM-LEVEL: Spam detection results: 0 AWL 0.007 Adjusted score from AWL reputation of From: address KAM_DMARC_STATUS 0.01 Test Rule for DKIM or SPF Failure with Strict Alignment SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_PASS -0.001 SPF: sender matches SPF record Subject: [pve-devel] [PATCH proxmox-acme] fix #3390: standalone: explicitly bind to '::' X-BeenThere: pve-devel@lists.proxmox.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Proxmox VE development discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 12 May 2021 19:05:39 -0000 This patch follows 2f8be3bfda203065b22e60862e5f98d831a46921 from pve-common: Instead of not specifying a listen address, we first try to bind on '::', which usually accepts connections for both ipv4 and ipv6, and fall back to '0.0.0.0' if this fails (if ipv6 is disabled via kernel commandline). The arguments are the same for HTTP::Daemon as for IO::Socket::IP, since the former has IO::Socket::IP as base. Additionally, by setting 'V6Only' explicitly to '0', the listening socket will also accept ipv4 connections, even if the sysctl 'net.ipv6.bindv6only' is set to 1 - the sysctl provides a default value, which can be overridden by a socket-option (see ipv6(7) - IPV6_ONLY). setting this option results in the following setsockopt-call being added: setsockopt(3, SOL_IPV6, IPV6_V6ONLY, [0], 4) = 0 AFAICT the socket option is available and overridable on Linux > 2.4 see [0] for an explanation of why this might not be wanted Overriding the default setting set by an admin might be debateable, but considering that the http-listener for the ACME challenge is rather short-lived I think this is justified. The only other option would be to create 2 listening sockets and binding on both - which would mean reorganizing our perl-deamons to deal with multiple listen sockets. quickly tested on a publicly reachable test-machine of mine with: * ipv6.domain.test (only AAAA record) * ip46.domain.test (both AAAA and A) * ipv4.domain.test (only A record) with: * sysctl net.ipv6.bindv6only=1 (for all 3 domains) * disabling ipv6 via kernel-commandline (only ipv4 tested) * disabling ipv6 via sysctl (only ipv4 tested) * only configuring an ipv6 address (only ipv6 tested) [0] https://man.openbsd.org/inet6.4 Signed-off-by: Stoiko Ivanov --- src/PVE/ACME/StandAlone.pm | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/PVE/ACME/StandAlone.pm b/src/PVE/ACME/StandAlone.pm index 0e2ece6..c054c5a 100644 --- a/src/PVE/ACME/StandAlone.pm +++ b/src/PVE/ACME/StandAlone.pm @@ -35,10 +35,14 @@ sub setup { my $challenge = $self->extract_challenge($auth->{challenges}); my $key_auth = $acme->key_authorization($challenge->{token}); - my $server = HTTP::Daemon->new( + my %sockopts = ( LocalPort => 80, ReuseAddr => 1, - ) or die "Failed to initialize HTTP daemon\n"; + ); + my $server = HTTP::Daemon->new( LocalHost => '::', V6Only => 0, %sockopts) // + HTTP::Daemon->new( LocalHost => '0.0.0.0', %sockopts) + or die "Failed to initialize HTTP daemon\n"; + my $pid = fork() // die "Failed to fork HTTP daemon - $!\n"; if ($pid) { $data->{server} = $server; -- 2.20.1