In 28.0.0, Docker appended to the FORWARD chain - breaking other
applications that had appended their own rules that needed to execute
after Docker's rules.
Move most of Docker's rules out of the filter-FORWARD chain into a
new DOCKER-FORWARD chain, so that Docker can append to DOCKER-FORWARD
without affecting the order of rules in the FORWARD chain.
After daemon startup inserts jumps to DOCKER-USER and DOCKER-FORWARD,
the bridge driver will not touch the FORWARD chain again. DOCKER-INGRESS
is still added to the FORWARD chain, if used, as it was in 27.x and
earlier.
Signed-off-by: Rob Murray <rob.murray@docker.com>
| ... | ... |
@@ -30,6 +30,7 @@ import ( |
| 30 | 30 |
"github.com/docker/docker/integration-cli/cli" |
| 31 | 31 |
"github.com/docker/docker/integration-cli/cli/build" |
| 32 | 32 |
"github.com/docker/docker/integration-cli/daemon" |
| 33 |
+ "github.com/docker/docker/libnetwork/drivers/bridge" |
|
| 33 | 34 |
"github.com/docker/docker/libnetwork/iptables" |
| 34 | 35 |
"github.com/docker/docker/opts" |
| 35 | 36 |
"github.com/docker/docker/testutil" |
| ... | ... |
@@ -718,7 +719,7 @@ func (s *DockerDaemonSuite) TestDaemonICCPing(c *testing.T) {
|
| 718 | 718 |
d.StartWithBusybox(testutil.GetContext(c), c, "--bridge", bridgeName, "--icc=false") |
| 719 | 719 |
defer d.Restart(c) |
| 720 | 720 |
|
| 721 |
- result := icmd.RunCommand("sh", "-c", "iptables -vL FORWARD | grep DROP")
|
|
| 721 |
+ result := icmd.RunCommand("sh", "-c", "iptables -vL "+bridge.DockerForwardChain+" | grep DROP")
|
|
| 722 | 722 |
result.Assert(c, icmd.Success) |
| 723 | 723 |
|
| 724 | 724 |
// strip whitespace and newlines to verify we only found a single DROP |
| ... | ... |
@@ -769,7 +770,7 @@ func (s *DockerDaemonSuite) TestDaemonICCLinkExpose(c *testing.T) {
|
| 769 | 769 |
d.StartWithBusybox(testutil.GetContext(c), c, "--bridge", bridgeName, "--icc=false") |
| 770 | 770 |
defer d.Restart(c) |
| 771 | 771 |
|
| 772 |
- result := icmd.RunCommand("sh", "-c", "iptables -vL FORWARD | grep DROP")
|
|
| 772 |
+ result := icmd.RunCommand("sh", "-c", "iptables -vL "+bridge.DockerForwardChain+" | grep DROP")
|
|
| 773 | 773 |
result.Assert(c, icmd.Success) |
| 774 | 774 |
|
| 775 | 775 |
// strip whitespace and newlines to verify we only found a single DROP |
| ... | ... |
@@ -11,10 +11,7 @@ Table `filter`: |
| 11 | 11 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 12 | 12 |
num pkts bytes target prot opt in out source destination |
| 13 | 13 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 14 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 15 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 16 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 17 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 14 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 18 | 15 |
|
| 19 | 16 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 20 | 17 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -23,6 +20,13 @@ Table `filter`: |
| 23 | 23 |
num pkts bytes target prot opt in out source destination |
| 24 | 24 |
1 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 25 | 25 |
|
| 26 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 27 |
+ num pkts bytes target prot opt in out source destination |
|
| 28 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 29 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 30 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 31 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 32 |
+ |
|
| 26 | 33 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 27 | 34 |
num pkts bytes target prot opt in out source destination |
| 28 | 35 |
1 0 0 DOCKER-ISOLATION-STAGE-2 0 -- docker0 !docker0 0.0.0.0/0 0.0.0.0/0 |
| ... | ... |
@@ -43,15 +47,17 @@ Table `filter`: |
| 43 | 43 |
-P FORWARD ACCEPT |
| 44 | 44 |
-P OUTPUT ACCEPT |
| 45 | 45 |
-N DOCKER |
| 46 |
+ -N DOCKER-FORWARD |
|
| 46 | 47 |
-N DOCKER-ISOLATION-STAGE-1 |
| 47 | 48 |
-N DOCKER-ISOLATION-STAGE-2 |
| 48 | 49 |
-N DOCKER-USER |
| 49 | 50 |
-A FORWARD -j DOCKER-USER |
| 50 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 51 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 52 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 53 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 51 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 54 | 52 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 53 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 54 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 55 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 56 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 55 | 57 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| 56 | 58 |
-A DOCKER-ISOLATION-STAGE-2 -o docker0 -j DROP |
| 57 | 59 |
-A DOCKER-USER -j RETURN |
| ... | ... |
@@ -76,18 +82,29 @@ The FORWARD chain rules are numbered in the output above, they are: |
| 76 | 76 |
Docker won't add rules to the DOCKER-USER chain, it's only for user-defined rules. |
| 77 | 77 |
It's (mostly) kept at the top of the by deleting it and re-creating after each |
| 78 | 78 |
new network is created, while traffic may be running for other networks. |
| 79 |
- 2. Early ACCEPT for any RELATED,ESTABLISHED traffic to a docker bridge. This rule |
|
| 79 |
+ 2. Unconditional jump to DOCKER-FORWARD. |
|
| 80 |
+ This is set up by libnetwork, in [setupUserChain][10]. |
|
| 81 |
+ |
|
| 82 |
+Once the daemon has initialised, it doesn't touch these rules. Users are free to |
|
| 83 |
+append rules to the FORWARD chain, and they'll run after DOCKER's rules (or to |
|
| 84 |
+the DOCKER-USER chain, for rules that run before DOCKER's). |
|
| 85 |
+ |
|
| 86 |
+The DOCKER-FORWARD chain contains the first stage of Docker's filter rules. Initial |
|
| 87 |
+rules are inserted at the top of the table, then not touched. Per-network rules |
|
| 88 |
+are appended. |
|
| 89 |
+ |
|
| 90 |
+ 1. Early ACCEPT for any RELATED,ESTABLISHED traffic to a docker bridge. This rule |
|
| 80 | 91 |
matches against an `ipset` called `docker-ext-bridges-v4` (`v6` for IPv6). The |
| 81 | 92 |
set contains the CIDR address of each docker network, and it is updated as networks |
| 82 | 93 |
are created and deleted. This rule is created during driver initialisation, in |
| 83 | 94 |
`setupIPChains`. |
| 84 |
- 3. Unconditional jump to DOCKER-ISOLATION-STAGE-1. |
|
| 95 |
+ 2. Unconditional jump to DOCKER-ISOLATION-STAGE-1. |
|
| 85 | 96 |
Also created during driver initialisation, in `setupIPChains`. |
| 86 |
- 4. Jump to DOCKER, for any packet destined for any bridge network, identified by |
|
| 97 |
+ 3. Jump to DOCKER, for any packet destined for any bridge network, identified by |
|
| 87 | 98 |
matching against the `docker-ext-bridge-v[46]` set. |
| 88 | 99 |
Also created during driver initialisation, in `setupIPChains`. |
| 89 | 100 |
The DOCKER chain implements per-port/protocol filtering for each container. |
| 90 |
- 5. ACCEPT any packet leaving a network, set up when the network is created, in |
|
| 101 |
+ 4. ACCEPT any packet leaving a network, set up when the network is created, in |
|
| 91 | 102 |
`setupIPTablesInternal`. Note that this accepts any packet leaving the |
| 92 | 103 |
network that's made it through the DOCKER and isolation chains, whether the |
| 93 | 104 |
destination is external or another network. |
| ... | ... |
@@ -13,12 +13,7 @@ The filter table is: |
| 13 | 13 |
num pkts bytes target prot opt in out source destination |
| 14 | 14 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 15 | 15 |
2 0 0 DOCKER-INGRESS 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 16 |
- 3 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 17 |
- 4 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 18 |
- 5 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 19 |
- 6 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 20 |
- 7 0 0 DROP 0 -- docker_gwbridge docker_gwbridge 0.0.0.0/0 0.0.0.0/0 |
|
| 21 |
- 8 0 0 ACCEPT 0 -- docker_gwbridge !docker_gwbridge 0.0.0.0/0 0.0.0.0/0 |
|
| 16 |
+ 3 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 22 | 17 |
|
| 23 | 18 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 24 | 19 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -28,6 +23,15 @@ The filter table is: |
| 28 | 28 |
1 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 29 | 29 |
2 0 0 DROP 0 -- !docker_gwbridge docker_gwbridge 0.0.0.0/0 0.0.0.0/0 |
| 30 | 30 |
|
| 31 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 32 |
+ num pkts bytes target prot opt in out source destination |
|
| 33 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 34 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 35 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 36 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 37 |
+ 5 0 0 DROP 0 -- docker_gwbridge docker_gwbridge 0.0.0.0/0 0.0.0.0/0 |
|
| 38 |
+ 6 0 0 ACCEPT 0 -- docker_gwbridge !docker_gwbridge 0.0.0.0/0 0.0.0.0/0 |
|
| 39 |
+ |
|
| 31 | 40 |
Chain DOCKER-INGRESS (1 references) |
| 32 | 41 |
num pkts bytes target prot opt in out source destination |
| 33 | 42 |
1 0 0 ACCEPT 6 -- * * 0.0.0.0/0 0.0.0.0/0 tcp dpt:8080 |
| ... | ... |
@@ -56,20 +60,22 @@ The filter table is: |
| 56 | 56 |
-P FORWARD ACCEPT |
| 57 | 57 |
-P OUTPUT ACCEPT |
| 58 | 58 |
-N DOCKER |
| 59 |
+ -N DOCKER-FORWARD |
|
| 59 | 60 |
-N DOCKER-INGRESS |
| 60 | 61 |
-N DOCKER-ISOLATION-STAGE-1 |
| 61 | 62 |
-N DOCKER-ISOLATION-STAGE-2 |
| 62 | 63 |
-N DOCKER-USER |
| 63 | 64 |
-A FORWARD -j DOCKER-USER |
| 64 | 65 |
-A FORWARD -j DOCKER-INGRESS |
| 65 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 66 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 67 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 68 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 69 |
- -A FORWARD -i docker_gwbridge -o docker_gwbridge -j DROP |
|
| 70 |
- -A FORWARD -i docker_gwbridge ! -o docker_gwbridge -j ACCEPT |
|
| 66 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 71 | 67 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 72 | 68 |
-A DOCKER ! -i docker_gwbridge -o docker_gwbridge -j DROP |
| 69 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 70 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 71 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 72 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 73 |
+ -A DOCKER-FORWARD -i docker_gwbridge -o docker_gwbridge -j DROP |
|
| 74 |
+ -A DOCKER-FORWARD -i docker_gwbridge ! -o docker_gwbridge -j ACCEPT |
|
| 73 | 75 |
-A DOCKER-INGRESS -p tcp -m tcp --dport 8080 -j ACCEPT |
| 74 | 76 |
-A DOCKER-INGRESS -p tcp -m tcp --sport 8080 -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
| 75 | 77 |
-A DOCKER-INGRESS -j RETURN |
| ... | ... |
@@ -87,7 +93,7 @@ Note that: |
| 87 | 87 |
- There's a bridge network called `docker_gwbridge` for swarm ingress. |
| 88 | 88 |
- Its rules follow the usual pattern for a network with inter-container communication disabled. |
| 89 | 89 |
- There's an additional chain `DOCKER-INGRESS`. |
| 90 |
- - The jump to `DOCKER-INGRESS` is in the `FORWARD` chain, after the jump to `DOCKER-USER`. |
|
| 90 |
+ - The jump to `DOCKER-INGRESS` is in the `FORWARD` chain. |
|
| 91 | 91 |
|
| 92 | 92 |
And the corresponding nat table: |
| 93 | 93 |
|
| ... | ... |
@@ -26,12 +26,7 @@ The filter table is updated as follows: |
| 26 | 26 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 27 | 27 |
num pkts bytes target prot opt in out source destination |
| 28 | 28 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 29 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 30 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 31 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 32 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 33 |
- 6 0 0 ACCEPT 0 -- bridgeICC bridgeICC 0.0.0.0/0 0.0.0.0/0 |
|
| 34 |
- 7 0 0 DROP 0 -- bridgeNoICC bridgeNoICC 0.0.0.0/0 0.0.0.0/0 |
|
| 29 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 35 | 30 |
|
| 36 | 31 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 37 | 32 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -40,6 +35,15 @@ The filter table is updated as follows: |
| 40 | 40 |
num pkts bytes target prot opt in out source destination |
| 41 | 41 |
1 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 42 | 42 |
|
| 43 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 44 |
+ num pkts bytes target prot opt in out source destination |
|
| 45 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 46 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 47 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 48 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 49 |
+ 5 0 0 ACCEPT 0 -- bridgeICC bridgeICC 0.0.0.0/0 0.0.0.0/0 |
|
| 50 |
+ 6 0 0 DROP 0 -- bridgeNoICC bridgeNoICC 0.0.0.0/0 0.0.0.0/0 |
|
| 51 |
+ |
|
| 43 | 52 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 44 | 53 |
num pkts bytes target prot opt in out source destination |
| 45 | 54 |
1 0 0 DROP 0 -- * bridgeNoICC !198.51.100.0/24 0.0.0.0/0 |
| ... | ... |
@@ -64,17 +68,19 @@ The filter table is updated as follows: |
| 64 | 64 |
-P FORWARD ACCEPT |
| 65 | 65 |
-P OUTPUT ACCEPT |
| 66 | 66 |
-N DOCKER |
| 67 |
+ -N DOCKER-FORWARD |
|
| 67 | 68 |
-N DOCKER-ISOLATION-STAGE-1 |
| 68 | 69 |
-N DOCKER-ISOLATION-STAGE-2 |
| 69 | 70 |
-N DOCKER-USER |
| 70 | 71 |
-A FORWARD -j DOCKER-USER |
| 71 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 72 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 73 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 74 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 75 |
- -A FORWARD -i bridgeICC -o bridgeICC -j ACCEPT |
|
| 76 |
- -A FORWARD -i bridgeNoICC -o bridgeNoICC -j DROP |
|
| 72 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 77 | 73 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 74 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 75 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 76 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 77 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 78 |
+ -A DOCKER-FORWARD -i bridgeICC -o bridgeICC -j ACCEPT |
|
| 79 |
+ -A DOCKER-FORWARD -i bridgeNoICC -o bridgeNoICC -j DROP |
|
| 78 | 80 |
-A DOCKER-ISOLATION-STAGE-1 ! -s 198.51.100.0/24 -o bridgeNoICC -j DROP |
| 79 | 81 |
-A DOCKER-ISOLATION-STAGE-1 ! -d 198.51.100.0/24 -i bridgeNoICC -j DROP |
| 80 | 82 |
-A DOCKER-ISOLATION-STAGE-1 ! -s 192.0.2.0/24 -o bridgeICC -j DROP |
| ... | ... |
@@ -88,7 +94,7 @@ The filter table is updated as follows: |
| 88 | 88 |
|
| 89 | 89 |
By comparison with the [network with external access][1]: |
| 90 | 90 |
|
| 91 |
-- In the FORWARD chain, there is no ACCEPT rule for outgoing packets (`-i bridgeINC`). |
|
| 91 |
+- In the DOCKER-FORWARD chain, there is no ACCEPT rule for outgoing packets (`-i bridgeINC`). |
|
| 92 | 92 |
- There are no rules for this network in the DOCKER chain. |
| 93 | 93 |
- In DOCKER-ISOLATION-STAGE-1: |
| 94 | 94 |
- Rule 1 drops any packet routed to the network that does not have a source address in the network's subnet. |
| ... | ... |
@@ -96,7 +102,7 @@ By comparison with the [network with external access][1]: |
| 96 | 96 |
- There is no jump to DOCKER-ISOLATION-STAGE-2. |
| 97 | 97 |
- DOCKER-ISOLATION-STAGE-2 is unused. |
| 98 | 98 |
|
| 99 |
-The only difference between `bridgeICC` and `bridgeNoICC` is the rule in the FORWARD |
|
| 99 |
+The only difference between `bridgeICC` and `bridgeNoICC` is the rule in the DOCKER-FORWARD |
|
| 100 | 100 |
chain. To enable ICC, the rule for packets looping through the bridge is ACCEPT. For |
| 101 | 101 |
no-ICC it's DROP. |
| 102 | 102 |
|
| ... | ... |
@@ -18,11 +18,7 @@ The filter and nat tables are identical to [nat mode][0]: |
| 18 | 18 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 19 | 19 |
num pkts bytes target prot opt in out source destination |
| 20 | 20 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 21 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 22 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 23 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 24 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 25 |
- 6 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 21 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 26 | 22 |
|
| 27 | 23 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 28 | 24 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -33,6 +29,14 @@ The filter and nat tables are identical to [nat mode][0]: |
| 33 | 33 |
2 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 34 | 34 |
3 0 0 DROP 0 -- !bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
| 35 | 35 |
|
| 36 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 37 |
+ num pkts bytes target prot opt in out source destination |
|
| 38 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 39 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 40 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 41 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 42 |
+ 5 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 43 |
+ |
|
| 36 | 44 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 37 | 45 |
num pkts bytes target prot opt in out source destination |
| 38 | 46 |
1 0 0 DOCKER-ISOLATION-STAGE-2 0 -- docker0 !docker0 0.0.0.0/0 0.0.0.0/0 |
| ... | ... |
@@ -52,18 +56,20 @@ The filter and nat tables are identical to [nat mode][0]: |
| 52 | 52 |
-P FORWARD ACCEPT |
| 53 | 53 |
-P OUTPUT ACCEPT |
| 54 | 54 |
-N DOCKER |
| 55 |
+ -N DOCKER-FORWARD |
|
| 55 | 56 |
-N DOCKER-ISOLATION-STAGE-1 |
| 56 | 57 |
-N DOCKER-ISOLATION-STAGE-2 |
| 57 | 58 |
-N DOCKER-USER |
| 58 | 59 |
-A FORWARD -j DOCKER-USER |
| 59 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 60 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 61 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 62 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 63 |
- -A FORWARD -i bridge1 -j ACCEPT |
|
| 60 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 64 | 61 |
-A DOCKER -d 192.0.2.2/32 ! -i bridge1 -o bridge1 -p tcp -m tcp --dport 80 -j ACCEPT |
| 65 | 62 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 66 | 63 |
-A DOCKER ! -i bridge1 -o bridge1 -j DROP |
| 64 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 65 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 66 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 67 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 68 |
+ -A DOCKER-FORWARD -i bridge1 -j ACCEPT |
|
| 67 | 69 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| 68 | 70 |
-A DOCKER-ISOLATION-STAGE-1 -i bridge1 ! -o bridge1 -j DOCKER-ISOLATION-STAGE-2 |
| 69 | 71 |
-A DOCKER-ISOLATION-STAGE-2 -o bridge1 -j DROP |
| ... | ... |
@@ -16,11 +16,7 @@ The filter table is: |
| 16 | 16 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 17 | 17 |
num pkts bytes target prot opt in out source destination |
| 18 | 18 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 19 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 20 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 21 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 22 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 23 |
- 6 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 19 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 24 | 20 |
|
| 25 | 21 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 26 | 22 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -30,6 +26,14 @@ The filter table is: |
| 30 | 30 |
1 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 31 | 31 |
2 0 0 ACCEPT 0 -- !bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
| 32 | 32 |
|
| 33 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 34 |
+ num pkts bytes target prot opt in out source destination |
|
| 35 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 36 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 37 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 38 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 39 |
+ 5 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 40 |
+ |
|
| 33 | 41 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 34 | 42 |
num pkts bytes target prot opt in out source destination |
| 35 | 43 |
1 0 0 DOCKER-ISOLATION-STAGE-2 0 -- docker0 !docker0 0.0.0.0/0 0.0.0.0/0 |
| ... | ... |
@@ -52,17 +56,19 @@ The filter table is: |
| 52 | 52 |
-P FORWARD ACCEPT |
| 53 | 53 |
-P OUTPUT ACCEPT |
| 54 | 54 |
-N DOCKER |
| 55 |
+ -N DOCKER-FORWARD |
|
| 55 | 56 |
-N DOCKER-ISOLATION-STAGE-1 |
| 56 | 57 |
-N DOCKER-ISOLATION-STAGE-2 |
| 57 | 58 |
-N DOCKER-USER |
| 58 | 59 |
-A FORWARD -j DOCKER-USER |
| 59 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 60 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 61 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 62 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 63 |
- -A FORWARD -i bridge1 -j ACCEPT |
|
| 60 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 64 | 61 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 65 | 62 |
-A DOCKER ! -i bridge1 -o bridge1 -j ACCEPT |
| 63 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 64 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 65 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 66 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 67 |
+ -A DOCKER-FORWARD -i bridge1 -j ACCEPT |
|
| 66 | 68 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| 67 | 69 |
-A DOCKER-ISOLATION-STAGE-1 -i bridge1 ! -o bridge1 -j DOCKER-ISOLATION-STAGE-2 |
| 68 | 70 |
-A DOCKER-ISOLATION-STAGE-2 -o bridge1 -j DROP |
| ... | ... |
@@ -16,12 +16,7 @@ The filter table is: |
| 16 | 16 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 17 | 17 |
num pkts bytes target prot opt in out source destination |
| 18 | 18 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 19 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 20 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 21 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 22 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 23 |
- 6 0 0 DROP 0 -- bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
|
| 24 |
- 7 0 0 ACCEPT 0 -- bridge1 !bridge1 0.0.0.0/0 0.0.0.0/0 |
|
| 19 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 25 | 20 |
|
| 26 | 21 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 27 | 22 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -32,6 +27,15 @@ The filter table is: |
| 32 | 32 |
2 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 33 | 33 |
3 0 0 DROP 0 -- !bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
| 34 | 34 |
|
| 35 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 36 |
+ num pkts bytes target prot opt in out source destination |
|
| 37 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 38 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 39 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 40 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 41 |
+ 5 0 0 DROP 0 -- bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
|
| 42 |
+ 6 0 0 ACCEPT 0 -- bridge1 !bridge1 0.0.0.0/0 0.0.0.0/0 |
|
| 43 |
+ |
|
| 35 | 44 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 36 | 45 |
num pkts bytes target prot opt in out source destination |
| 37 | 46 |
1 0 0 DOCKER-ISOLATION-STAGE-2 0 -- docker0 !docker0 0.0.0.0/0 0.0.0.0/0 |
| ... | ... |
@@ -54,19 +58,21 @@ The filter table is: |
| 54 | 54 |
-P FORWARD ACCEPT |
| 55 | 55 |
-P OUTPUT ACCEPT |
| 56 | 56 |
-N DOCKER |
| 57 |
+ -N DOCKER-FORWARD |
|
| 57 | 58 |
-N DOCKER-ISOLATION-STAGE-1 |
| 58 | 59 |
-N DOCKER-ISOLATION-STAGE-2 |
| 59 | 60 |
-N DOCKER-USER |
| 60 | 61 |
-A FORWARD -j DOCKER-USER |
| 61 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 62 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 63 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 64 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 65 |
- -A FORWARD -i bridge1 -o bridge1 -j DROP |
|
| 66 |
- -A FORWARD -i bridge1 ! -o bridge1 -j ACCEPT |
|
| 62 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 67 | 63 |
-A DOCKER -d 192.0.2.2/32 ! -i bridge1 -o bridge1 -p tcp -m tcp --dport 80 -j ACCEPT |
| 68 | 64 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 69 | 65 |
-A DOCKER ! -i bridge1 -o bridge1 -j DROP |
| 66 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 67 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 68 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 69 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 70 |
+ -A DOCKER-FORWARD -i bridge1 -o bridge1 -j DROP |
|
| 71 |
+ -A DOCKER-FORWARD -i bridge1 ! -o bridge1 -j ACCEPT |
|
| 70 | 72 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| 71 | 73 |
-A DOCKER-ISOLATION-STAGE-1 -i bridge1 ! -o bridge1 -j DOCKER-ISOLATION-STAGE-2 |
| 72 | 74 |
-A DOCKER-ISOLATION-STAGE-2 -o bridge1 -j DROP |
| ... | ... |
@@ -19,11 +19,7 @@ The filter table is the same as with the userland proxy enabled. |
| 19 | 19 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 20 | 20 |
num pkts bytes target prot opt in out source destination |
| 21 | 21 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 22 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 23 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 24 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 25 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 26 |
- 6 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 22 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 27 | 23 |
|
| 28 | 24 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 29 | 25 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -34,6 +30,14 @@ The filter table is the same as with the userland proxy enabled. |
| 34 | 34 |
2 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 35 | 35 |
3 0 0 DROP 0 -- !bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
| 36 | 36 |
|
| 37 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 38 |
+ num pkts bytes target prot opt in out source destination |
|
| 39 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 40 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 41 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 42 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 43 |
+ 5 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 44 |
+ |
|
| 37 | 45 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 38 | 46 |
num pkts bytes target prot opt in out source destination |
| 39 | 47 |
1 0 0 DOCKER-ISOLATION-STAGE-2 0 -- docker0 !docker0 0.0.0.0/0 0.0.0.0/0 |
| ... | ... |
@@ -53,18 +57,20 @@ The filter table is the same as with the userland proxy enabled. |
| 53 | 53 |
-P FORWARD ACCEPT |
| 54 | 54 |
-P OUTPUT ACCEPT |
| 55 | 55 |
-N DOCKER |
| 56 |
+ -N DOCKER-FORWARD |
|
| 56 | 57 |
-N DOCKER-ISOLATION-STAGE-1 |
| 57 | 58 |
-N DOCKER-ISOLATION-STAGE-2 |
| 58 | 59 |
-N DOCKER-USER |
| 59 | 60 |
-A FORWARD -j DOCKER-USER |
| 60 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 61 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 62 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 63 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 64 |
- -A FORWARD -i bridge1 -j ACCEPT |
|
| 61 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 65 | 62 |
-A DOCKER -d 192.0.2.2/32 ! -i bridge1 -o bridge1 -p tcp -m tcp --dport 80 -j ACCEPT |
| 66 | 63 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 67 | 64 |
-A DOCKER ! -i bridge1 -o bridge1 -j DROP |
| 65 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 66 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 67 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 68 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 69 |
+ -A DOCKER-FORWARD -i bridge1 -j ACCEPT |
|
| 68 | 70 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| 69 | 71 |
-A DOCKER-ISOLATION-STAGE-1 -i bridge1 ! -o bridge1 -j DOCKER-ISOLATION-STAGE-2 |
| 70 | 72 |
-A DOCKER-ISOLATION-STAGE-2 -o bridge1 -j DROP |
| ... | ... |
@@ -16,11 +16,7 @@ The filter table is: |
| 16 | 16 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 17 | 17 |
num pkts bytes target prot opt in out source destination |
| 18 | 18 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 19 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 20 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 21 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 22 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 23 |
- 6 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 19 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 24 | 20 |
|
| 25 | 21 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 26 | 22 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -32,6 +28,14 @@ The filter table is: |
| 32 | 32 |
3 0 0 ACCEPT 1 -- * bridge1 0.0.0.0/0 0.0.0.0/0 |
| 33 | 33 |
4 0 0 DROP 0 -- !bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
| 34 | 34 |
|
| 35 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 36 |
+ num pkts bytes target prot opt in out source destination |
|
| 37 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 38 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 39 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 40 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 41 |
+ 5 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 42 |
+ |
|
| 35 | 43 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 36 | 44 |
num pkts bytes target prot opt in out source destination |
| 37 | 45 |
1 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 ctstate RELATED,ESTABLISHED |
| ... | ... |
@@ -56,19 +60,21 @@ The filter table is: |
| 56 | 56 |
-P FORWARD ACCEPT |
| 57 | 57 |
-P OUTPUT ACCEPT |
| 58 | 58 |
-N DOCKER |
| 59 |
+ -N DOCKER-FORWARD |
|
| 59 | 60 |
-N DOCKER-ISOLATION-STAGE-1 |
| 60 | 61 |
-N DOCKER-ISOLATION-STAGE-2 |
| 61 | 62 |
-N DOCKER-USER |
| 62 | 63 |
-A FORWARD -j DOCKER-USER |
| 63 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 64 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 65 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 66 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 67 |
- -A FORWARD -i bridge1 -j ACCEPT |
|
| 64 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 68 | 65 |
-A DOCKER -d 192.0.2.2/32 ! -i bridge1 -o bridge1 -p tcp -m tcp --dport 80 -j ACCEPT |
| 69 | 66 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 70 | 67 |
-A DOCKER -o bridge1 -p icmp -j ACCEPT |
| 71 | 68 |
-A DOCKER ! -i bridge1 -o bridge1 -j DROP |
| 69 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 70 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 71 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 72 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 73 |
+ -A DOCKER-FORWARD -i bridge1 -j ACCEPT |
|
| 72 | 74 |
-A DOCKER-ISOLATION-STAGE-1 -i bridge1 -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
| 73 | 75 |
-A DOCKER-ISOLATION-STAGE-1 -o bridge1 -j RETURN |
| 74 | 76 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| ... | ... |
@@ -15,11 +15,7 @@ The filter table is updated as follows: |
| 15 | 15 |
Chain FORWARD (policy ACCEPT 0 packets, 0 bytes) |
| 16 | 16 |
num pkts bytes target prot opt in out source destination |
| 17 | 17 |
1 0 0 DOCKER-USER 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
| 18 |
- 2 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 19 |
- 3 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 20 |
- 4 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 21 |
- 5 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 22 |
- 6 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 18 |
+ 2 0 0 DOCKER-FORWARD 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 23 | 19 |
|
| 24 | 20 |
Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes) |
| 25 | 21 |
num pkts bytes target prot opt in out source destination |
| ... | ... |
@@ -30,6 +26,14 @@ The filter table is updated as follows: |
| 30 | 30 |
2 0 0 DROP 0 -- !docker0 docker0 0.0.0.0/0 0.0.0.0/0 |
| 31 | 31 |
3 0 0 DROP 0 -- !bridge1 bridge1 0.0.0.0/0 0.0.0.0/0 |
| 32 | 32 |
|
| 33 |
+ Chain DOCKER-FORWARD (1 references) |
|
| 34 |
+ num pkts bytes target prot opt in out source destination |
|
| 35 |
+ 1 0 0 ACCEPT 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst ctstate RELATED,ESTABLISHED |
|
| 36 |
+ 2 0 0 DOCKER-ISOLATION-STAGE-1 0 -- * * 0.0.0.0/0 0.0.0.0/0 |
|
| 37 |
+ 3 0 0 DOCKER 0 -- * * 0.0.0.0/0 0.0.0.0/0 match-set docker-ext-bridges-v4 dst |
|
| 38 |
+ 4 0 0 ACCEPT 0 -- docker0 * 0.0.0.0/0 0.0.0.0/0 |
|
| 39 |
+ 5 0 0 ACCEPT 0 -- bridge1 * 0.0.0.0/0 0.0.0.0/0 |
|
| 40 |
+ |
|
| 33 | 41 |
Chain DOCKER-ISOLATION-STAGE-1 (1 references) |
| 34 | 42 |
num pkts bytes target prot opt in out source destination |
| 35 | 43 |
1 0 0 DOCKER-ISOLATION-STAGE-2 0 -- docker0 !docker0 0.0.0.0/0 0.0.0.0/0 |
| ... | ... |
@@ -52,18 +56,20 @@ The filter table is updated as follows: |
| 52 | 52 |
-P FORWARD ACCEPT |
| 53 | 53 |
-P OUTPUT ACCEPT |
| 54 | 54 |
-N DOCKER |
| 55 |
+ -N DOCKER-FORWARD |
|
| 55 | 56 |
-N DOCKER-ISOLATION-STAGE-1 |
| 56 | 57 |
-N DOCKER-ISOLATION-STAGE-2 |
| 57 | 58 |
-N DOCKER-USER |
| 58 | 59 |
-A FORWARD -j DOCKER-USER |
| 59 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 60 |
- -A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 61 |
- -A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 62 |
- -A FORWARD -i docker0 -j ACCEPT |
|
| 63 |
- -A FORWARD -i bridge1 -j ACCEPT |
|
| 60 |
+ -A FORWARD -j DOCKER-FORWARD |
|
| 64 | 61 |
-A DOCKER -d 192.0.2.2/32 ! -i bridge1 -o bridge1 -p tcp -m tcp --dport 80 -j ACCEPT |
| 65 | 62 |
-A DOCKER ! -i docker0 -o docker0 -j DROP |
| 66 | 63 |
-A DOCKER ! -i bridge1 -o bridge1 -j DROP |
| 64 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 65 |
+ -A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 66 |
+ -A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 67 |
+ -A DOCKER-FORWARD -i docker0 -j ACCEPT |
|
| 68 |
+ -A DOCKER-FORWARD -i bridge1 -j ACCEPT |
|
| 67 | 69 |
-A DOCKER-ISOLATION-STAGE-1 -i docker0 ! -o docker0 -j DOCKER-ISOLATION-STAGE-2 |
| 68 | 70 |
-A DOCKER-ISOLATION-STAGE-1 -i bridge1 ! -o bridge1 -j DOCKER-ISOLATION-STAGE-2 |
| 69 | 71 |
-A DOCKER-ISOLATION-STAGE-2 -o bridge1 -j DROP |
| ... | ... |
@@ -75,7 +81,7 @@ The filter table is updated as follows: |
| 75 | 75 |
|
| 76 | 76 |
Note that: |
| 77 | 77 |
|
| 78 |
- - In the FORWARD chain, rule 6 for outgoing traffic from the new network has been |
|
| 78 |
+ - In the DOCKER-FORWARD chain, rule 5 for outgoing traffic from the new network has been |
|
| 79 | 79 |
appended to the end of the chain. |
| 80 | 80 |
- In the DOCKER-ISOLATION chains, rules equivalent to the docker0 rules have |
| 81 | 81 |
also been inserted for the new bridge. |
| ... | ... |
@@ -193,27 +193,25 @@ var index = []section{
|
| 193 | 193 |
type iptCmdType = string |
| 194 | 194 |
|
| 195 | 195 |
const ( |
| 196 |
- iptCmdLFilter4 iptCmdType = "LFilter4" |
|
| 197 |
- iptCmdSFilter4 iptCmdType = "SFilter4" |
|
| 198 |
- iptCmdLFilterDocker4 iptCmdType = "LFilterDocker4" |
|
| 199 |
- iptCmdSFilterForward4 iptCmdType = "SFilterForward4" |
|
| 200 |
- iptCmdSFilterDocker4 iptCmdType = "SFilterDocker4" |
|
| 201 |
- iptCmdLNat4 iptCmdType = "LNat4" |
|
| 202 |
- iptCmdSNat4 iptCmdType = "SNat4" |
|
| 203 |
- iptCmdLRaw4 iptCmdType = "LRaw4" |
|
| 204 |
- iptCmdSRaw4 iptCmdType = "SRaw4" |
|
| 196 |
+ iptCmdLFilter4 iptCmdType = "LFilter4" |
|
| 197 |
+ iptCmdSFilter4 iptCmdType = "SFilter4" |
|
| 198 |
+ iptCmdLFilterDocker4 iptCmdType = "LFilterDocker4" |
|
| 199 |
+ iptCmdSFilterDocker4 iptCmdType = "SFilterDocker4" |
|
| 200 |
+ iptCmdLNat4 iptCmdType = "LNat4" |
|
| 201 |
+ iptCmdSNat4 iptCmdType = "SNat4" |
|
| 202 |
+ iptCmdLRaw4 iptCmdType = "LRaw4" |
|
| 203 |
+ iptCmdSRaw4 iptCmdType = "SRaw4" |
|
| 205 | 204 |
) |
| 206 | 205 |
|
| 207 | 206 |
var iptCmds = map[iptCmdType][]string{
|
| 208 |
- iptCmdLFilter4: {"iptables", "-nvL", "--line-numbers", "-t", "filter"},
|
|
| 209 |
- iptCmdSFilter4: {"iptables", "-S", "-t", "filter"},
|
|
| 210 |
- iptCmdSFilterForward4: {"iptables", "-S", "FORWARD"},
|
|
| 211 |
- iptCmdLFilterDocker4: {"iptables", "-nvL", "DOCKER", "--line-numbers", "-t", "filter"},
|
|
| 212 |
- iptCmdSFilterDocker4: {"iptables", "-S", "DOCKER"},
|
|
| 213 |
- iptCmdLNat4: {"iptables", "-nvL", "--line-numbers", "-t", "nat"},
|
|
| 214 |
- iptCmdSNat4: {"iptables", "-S", "-t", "nat"},
|
|
| 215 |
- iptCmdLRaw4: {"iptables", "-nvL", "--line-numbers", "-t", "raw"},
|
|
| 216 |
- iptCmdSRaw4: {"iptables", "-S", "-t", "raw"},
|
|
| 207 |
+ iptCmdLFilter4: {"iptables", "-nvL", "--line-numbers", "-t", "filter"},
|
|
| 208 |
+ iptCmdSFilter4: {"iptables", "-S", "-t", "filter"},
|
|
| 209 |
+ iptCmdLFilterDocker4: {"iptables", "-nvL", "DOCKER", "--line-numbers", "-t", "filter"},
|
|
| 210 |
+ iptCmdSFilterDocker4: {"iptables", "-S", "DOCKER"},
|
|
| 211 |
+ iptCmdLNat4: {"iptables", "-nvL", "--line-numbers", "-t", "nat"},
|
|
| 212 |
+ iptCmdSNat4: {"iptables", "-S", "-t", "nat"},
|
|
| 213 |
+ iptCmdLRaw4: {"iptables", "-nvL", "--line-numbers", "-t", "raw"},
|
|
| 214 |
+ iptCmdSRaw4: {"iptables", "-S", "-t", "raw"},
|
|
| 217 | 215 |
} |
| 218 | 216 |
|
| 219 | 217 |
func TestBridgeIptablesDoc(t *testing.T) {
|
| ... | ... |
@@ -31,18 +31,29 @@ The FORWARD chain rules are numbered in the output above, they are: |
| 31 | 31 |
Docker won't add rules to the DOCKER-USER chain, it's only for user-defined rules. |
| 32 | 32 |
It's (mostly) kept at the top of the by deleting it and re-creating after each |
| 33 | 33 |
new network is created, while traffic may be running for other networks. |
| 34 |
- 2. Early ACCEPT for any RELATED,ESTABLISHED traffic to a docker bridge. This rule |
|
| 34 |
+ 2. Unconditional jump to DOCKER-FORWARD. |
|
| 35 |
+ This is set up by libnetwork, in [setupUserChain][10]. |
|
| 36 |
+ |
|
| 37 |
+Once the daemon has initialised, it doesn't touch these rules. Users are free to |
|
| 38 |
+append rules to the FORWARD chain, and they'll run after DOCKER's rules (or to |
|
| 39 |
+the DOCKER-USER chain, for rules that run before DOCKER's). |
|
| 40 |
+ |
|
| 41 |
+The DOCKER-FORWARD chain contains the first stage of Docker's filter rules. Initial |
|
| 42 |
+rules are inserted at the top of the table, then not touched. Per-network rules |
|
| 43 |
+are appended. |
|
| 44 |
+ |
|
| 45 |
+ 1. Early ACCEPT for any RELATED,ESTABLISHED traffic to a docker bridge. This rule |
|
| 35 | 46 |
matches against an `ipset` called `docker-ext-bridges-v4` (`v6` for IPv6). The |
| 36 | 47 |
set contains the CIDR address of each docker network, and it is updated as networks |
| 37 | 48 |
are created and deleted. This rule is created during driver initialisation, in |
| 38 | 49 |
`setupIPChains`. |
| 39 |
- 3. Unconditional jump to DOCKER-ISOLATION-STAGE-1. |
|
| 50 |
+ 2. Unconditional jump to DOCKER-ISOLATION-STAGE-1. |
|
| 40 | 51 |
Also created during driver initialisation, in `setupIPChains`. |
| 41 |
- 4. Jump to DOCKER, for any packet destined for any bridge network, identified by |
|
| 52 |
+ 3. Jump to DOCKER, for any packet destined for any bridge network, identified by |
|
| 42 | 53 |
matching against the `docker-ext-bridge-v[46]` set. |
| 43 | 54 |
Also created during driver initialisation, in `setupIPChains`. |
| 44 | 55 |
The DOCKER chain implements per-port/protocol filtering for each container. |
| 45 |
- 5. ACCEPT any packet leaving a network, set up when the network is created, in |
|
| 56 |
+ 4. ACCEPT any packet leaving a network, set up when the network is created, in |
|
| 46 | 57 |
`setupIPTablesInternal`. Note that this accepts any packet leaving the |
| 47 | 58 |
network that's made it through the DOCKER and isolation chains, whether the |
| 48 | 59 |
destination is external or another network. |
| ... | ... |
@@ -20,7 +20,7 @@ Note that: |
| 20 | 20 |
- There's a bridge network called `docker_gwbridge` for swarm ingress. |
| 21 | 21 |
- Its rules follow the usual pattern for a network with inter-container communication disabled. |
| 22 | 22 |
- There's an additional chain `DOCKER-INGRESS`. |
| 23 |
- - The jump to `DOCKER-INGRESS` is in the `FORWARD` chain, after the jump to `DOCKER-USER`. |
|
| 23 |
+ - The jump to `DOCKER-INGRESS` is in the `FORWARD` chain. |
|
| 24 | 24 |
|
| 25 | 25 |
And the corresponding nat table: |
| 26 | 26 |
|
| ... | ... |
@@ -31,7 +31,7 @@ The filter table is updated as follows: |
| 31 | 31 |
|
| 32 | 32 |
By comparison with the [network with external access][1]: |
| 33 | 33 |
|
| 34 |
-- In the FORWARD chain, there is no ACCEPT rule for outgoing packets (`-i bridgeINC`). |
|
| 34 |
+- In the DOCKER-FORWARD chain, there is no ACCEPT rule for outgoing packets (`-i bridgeINC`). |
|
| 35 | 35 |
- There are no rules for this network in the DOCKER chain. |
| 36 | 36 |
- In DOCKER-ISOLATION-STAGE-1: |
| 37 | 37 |
- Rule 1 drops any packet routed to the network that does not have a source address in the network's subnet. |
| ... | ... |
@@ -39,7 +39,7 @@ By comparison with the [network with external access][1]: |
| 39 | 39 |
- There is no jump to DOCKER-ISOLATION-STAGE-2. |
| 40 | 40 |
- DOCKER-ISOLATION-STAGE-2 is unused. |
| 41 | 41 |
|
| 42 |
-The only difference between `bridgeICC` and `bridgeNoICC` is the rule in the FORWARD |
|
| 42 |
+The only difference between `bridgeICC` and `bridgeNoICC` is the rule in the DOCKER-FORWARD |
|
| 43 | 43 |
chain. To enable ICC, the rule for packets looping through the bridge is ACCEPT. For |
| 44 | 44 |
no-ICC it's DROP. |
| 45 | 45 |
|
| ... | ... |
@@ -20,7 +20,7 @@ The filter table is updated as follows: |
| 20 | 20 |
|
| 21 | 21 |
Note that: |
| 22 | 22 |
|
| 23 |
- - In the FORWARD chain, rule 6 for outgoing traffic from the new network has been |
|
| 23 |
+ - In the DOCKER-FORWARD chain, rule 5 for outgoing traffic from the new network has been |
|
| 24 | 24 |
appended to the end of the chain. |
| 25 | 25 |
- In the DOCKER-ISOLATION chains, rules equivalent to the docker0 rules have |
| 26 | 26 |
also been inserted for the new bridge. |
| ... | ... |
@@ -18,7 +18,8 @@ import ( |
| 18 | 18 |
|
| 19 | 19 |
// DockerChain: DOCKER iptable chain name |
| 20 | 20 |
const ( |
| 21 |
- DockerChain = "DOCKER" |
|
| 21 |
+ DockerChain = "DOCKER" |
|
| 22 |
+ DockerForwardChain = "DOCKER-FORWARD" |
|
| 22 | 23 |
|
| 23 | 24 |
// Isolation between bridge networks is achieved in two stages by means |
| 24 | 25 |
// of the following two chains in the filter table. The first chain matches |
| ... | ... |
@@ -79,6 +80,18 @@ func setupIPChains(config configuration, version iptables.IPVersion) (retErr err |
| 79 | 79 |
} |
| 80 | 80 |
}() |
| 81 | 81 |
|
| 82 |
+ _, err = iptable.NewChain(DockerForwardChain, iptables.Filter) |
|
| 83 |
+ if err != nil {
|
|
| 84 |
+ return fmt.Errorf("failed to create FILTER chain %s: %v", DockerForwardChain, err)
|
|
| 85 |
+ } |
|
| 86 |
+ defer func() {
|
|
| 87 |
+ if retErr != nil {
|
|
| 88 |
+ if err := iptable.RemoveExistingChain(DockerForwardChain, iptables.Filter); err != nil {
|
|
| 89 |
+ log.G(context.TODO()).Warnf("failed on removing iptables FILTER chain %s on cleanup: %v", DockerForwardChain, err)
|
|
| 90 |
+ } |
|
| 91 |
+ } |
|
| 92 |
+ }() |
|
| 93 |
+ |
|
| 82 | 94 |
_, err = iptable.NewChain(IsolationChain1, iptables.Filter) |
| 83 | 95 |
if err != nil {
|
| 84 | 96 |
return fmt.Errorf("failed to create FILTER isolation chain: %v", err)
|
| ... | ... |
@@ -121,14 +134,32 @@ func setupIPChains(config configuration, version iptables.IPVersion) (retErr err |
| 121 | 121 |
if version == iptables.IPv6 {
|
| 122 | 122 |
ipsetName = ipsetExtBridges6 |
| 123 | 123 |
} |
| 124 |
- if err := iptable.EnsureJumpRule("FORWARD", DockerChain,
|
|
| 124 |
+ // Delete rules that may have been added to the FORWARD chain by moby 28.0.0. |
|
| 125 |
+ if err := iptable.DeleteJumpRule("FORWARD", DockerChain,
|
|
| 125 | 126 |
"-m", "set", "--match-set", ipsetName, "dst"); err != nil {
|
| 126 | 127 |
return fmt.Errorf("%w (kernel module netfilter_xt_set is required)", err)
|
| 127 | 128 |
} |
| 128 |
- if err := iptable.EnsureJumpRule("FORWARD", IsolationChain1); err != nil {
|
|
| 129 |
+ if err := iptable.DeleteJumpRule("FORWARD", IsolationChain1); err != nil {
|
|
| 129 | 130 |
return err |
| 130 | 131 |
} |
| 131 |
- if err := iptable.EnsureJumpRule("FORWARD", "ACCEPT",
|
|
| 132 |
+ if err := iptable.DeleteJumpRule("FORWARD", "ACCEPT",
|
|
| 133 |
+ "-m", "set", "--match-set", ipsetName, "dst", |
|
| 134 |
+ "-m", "conntrack", "--ctstate", "RELATED,ESTABLISHED", |
|
| 135 |
+ ); err != nil {
|
|
| 136 |
+ return err |
|
| 137 |
+ } |
|
| 138 |
+ // Create rules in the DockerForward chain. |
|
| 139 |
+ if err := iptable.EnsureJumpRule("FORWARD", DockerForwardChain); err != nil {
|
|
| 140 |
+ return err |
|
| 141 |
+ } |
|
| 142 |
+ if err := iptable.EnsureJumpRule(DockerForwardChain, DockerChain, |
|
| 143 |
+ "-m", "set", "--match-set", ipsetName, "dst"); err != nil {
|
|
| 144 |
+ return err |
|
| 145 |
+ } |
|
| 146 |
+ if err := iptable.EnsureJumpRule(DockerForwardChain, IsolationChain1); err != nil {
|
|
| 147 |
+ return err |
|
| 148 |
+ } |
|
| 149 |
+ if err := iptable.EnsureJumpRule(DockerForwardChain, "ACCEPT", |
|
| 132 | 150 |
"-m", "set", "--match-set", ipsetName, "dst", |
| 133 | 151 |
"-m", "conntrack", "--ctstate", "RELATED,ESTABLISHED", |
| 134 | 152 |
); err != nil {
|
| ... | ... |
@@ -452,25 +483,32 @@ func setupNonInternalNetworkRules(ipVer iptables.IPVersion, config *networkConfi |
| 452 | 452 |
// to ACCEPT packets that weren't ICC - an extra rule was needed to enable |
| 453 | 453 |
// ICC if needed. Those rules are now combined. So, outRuleNoICC is only |
| 454 | 454 |
// needed for ICC=false, along with the DROP rule for ICC added by setIcc. |
| 455 |
- outRuleNoICC := iptables.Rule{IPVer: ipVer, Table: iptables.Filter, Chain: "FORWARD", Args: []string{
|
|
| 455 |
+ outRuleNoICC := iptables.Rule{IPVer: ipVer, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{
|
|
| 456 | 456 |
"-i", config.BridgeName, |
| 457 | 457 |
"!", "-o", config.BridgeName, |
| 458 | 458 |
"-j", "ACCEPT", |
| 459 | 459 |
}} |
| 460 |
- if config.EnableICC {
|
|
| 461 |
- // Remove the legacy rule for ICC (which didn't accept outgoing traffic), if one has been |
|
| 462 |
- // left behind by an old daemon. |
|
| 463 |
- if err := outRuleNoICC.Delete(); err != nil {
|
|
| 464 |
- return err |
|
| 460 |
+ // If there's a version of outRuleNoICC in the FORWARD chain, created by moby 28.0.0 or older, delete it. |
|
| 461 |
+ if enable {
|
|
| 462 |
+ if err := outRuleNoICC.WithChain("FORWARD").Delete(); err != nil {
|
|
| 463 |
+ return fmt.Errorf("deleting FORWARD chain outRuleNoICC: %w", err)
|
|
| 465 | 464 |
} |
| 465 |
+ } |
|
| 466 |
+ if config.EnableICC {
|
|
| 466 | 467 |
// Accept outgoing traffic to anywhere, including other containers on this bridge. |
| 467 |
- outRuleICC := iptables.Rule{IPVer: ipVer, Table: iptables.Filter, Chain: "FORWARD", Args: []string{
|
|
| 468 |
+ outRuleICC := iptables.Rule{IPVer: ipVer, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{
|
|
| 468 | 469 |
"-i", config.BridgeName, |
| 469 | 470 |
"-j", "ACCEPT", |
| 470 | 471 |
}} |
| 471 | 472 |
if err := appendOrDelChainRule(outRuleICC, "ACCEPT OUTGOING", enable); err != nil {
|
| 472 | 473 |
return err |
| 473 | 474 |
} |
| 475 |
+ // If there's a version of outRuleICC in the FORWARD chain, created by moby 28.0.0 or older, delete it. |
|
| 476 |
+ if enable {
|
|
| 477 |
+ if err := outRuleICC.WithChain("FORWARD").Delete(); err != nil {
|
|
| 478 |
+ return fmt.Errorf("deleting FORWARD chain outRuleICC: %w", err)
|
|
| 479 |
+ } |
|
| 480 |
+ } |
|
| 474 | 481 |
} else {
|
| 475 | 482 |
// Accept outgoing traffic to anywhere, apart from other containers on this bridge. |
| 476 | 483 |
// setIcc added a DROP rule for ICC traffic. |
| ... | ... |
@@ -510,8 +548,8 @@ func appendOrDelChainRule(rule iptables.Rule, ruleDescr string, append bool) err |
| 510 | 510 |
|
| 511 | 511 |
func setIcc(version iptables.IPVersion, bridgeIface string, iccEnable, internal, insert bool) error {
|
| 512 | 512 |
args := []string{"-i", bridgeIface, "-o", bridgeIface, "-j"}
|
| 513 |
- acceptRule := iptables.Rule{IPVer: version, Table: iptables.Filter, Chain: "FORWARD", Args: append(args, "ACCEPT")}
|
|
| 514 |
- dropRule := iptables.Rule{IPVer: version, Table: iptables.Filter, Chain: "FORWARD", Args: append(args, "DROP")}
|
|
| 513 |
+ acceptRule := iptables.Rule{IPVer: version, Table: iptables.Filter, Chain: DockerForwardChain, Args: append(args, "ACCEPT")}
|
|
| 514 |
+ dropRule := iptables.Rule{IPVer: version, Table: iptables.Filter, Chain: DockerForwardChain, Args: append(args, "DROP")}
|
|
| 515 | 515 |
|
| 516 | 516 |
// The accept rule is no longer required for a bridge with external connectivity, because |
| 517 | 517 |
// ICC traffic is allowed by the outgoing-packets rule created by setupIptablesInternal. |
| ... | ... |
@@ -537,6 +575,16 @@ func setIcc(version iptables.IPVersion, bridgeIface string, iccEnable, internal, |
| 537 | 537 |
log.G(context.TODO()).WithError(err).Warn("Failed to delete ICC drop rule")
|
| 538 | 538 |
} |
| 539 | 539 |
} |
| 540 |
+ |
|
| 541 |
+ // Delete rules that may have been inserted into the FORWARD chain by moby 28.0.0 or older. |
|
| 542 |
+ if insert {
|
|
| 543 |
+ if err := acceptRule.WithChain("FORWARD").Delete(); err != nil {
|
|
| 544 |
+ return fmt.Errorf("deleting FORWARD chain accept rule: %w", err)
|
|
| 545 |
+ } |
|
| 546 |
+ if err := dropRule.WithChain("FORWARD").Delete(); err != nil {
|
|
| 547 |
+ return fmt.Errorf("deleting FORWARD chain drop rule: %w", err)
|
|
| 548 |
+ } |
|
| 549 |
+ } |
|
| 540 | 550 |
return nil |
| 541 | 551 |
} |
| 542 | 552 |
|
| ... | ... |
@@ -617,6 +665,7 @@ func removeIPChains(version iptables.IPVersion) {
|
| 617 | 617 |
for _, chainInfo := range []iptables.ChainInfo{
|
| 618 | 618 |
{Name: DockerChain, Table: iptables.Nat, IPVersion: version},
|
| 619 | 619 |
{Name: DockerChain, Table: iptables.Filter, IPVersion: version},
|
| 620 |
+ {Name: DockerForwardChain, Table: iptables.Filter, IPVersion: version},
|
|
| 620 | 621 |
{Name: IsolationChain1, Table: iptables.Filter, IPVersion: version},
|
| 621 | 622 |
{Name: IsolationChain2, Table: iptables.Filter, IPVersion: version},
|
| 622 | 623 |
{Name: oldIsolationChain, Table: iptables.Filter, IPVersion: version},
|
| ... | ... |
@@ -53,18 +53,20 @@ func TestProgramIPTable(t *testing.T) {
|
| 53 | 53 |
} |
| 54 | 54 |
|
| 55 | 55 |
createTestBridge(getBasicTestConfig(), &bridgeInterface{nlh: nh}, t)
|
| 56 |
+ _, err = iptables.GetIptable(iptables.IPv4).NewChain(DockerForwardChain, iptables.Filter) |
|
| 57 |
+ assert.NilError(t, err) |
|
| 56 | 58 |
|
| 57 | 59 |
// Store various iptables chain rules we care for. |
| 58 | 60 |
rules := []struct {
|
| 59 | 61 |
rule iptables.Rule |
| 60 | 62 |
descr string |
| 61 | 63 |
}{
|
| 62 |
- {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: "FORWARD", Args: []string{"-d", "127.1.2.3", "-i", "lo", "-o", "lo", "-j", "DROP"}}, "Test Loopback"},
|
|
| 64 |
+ {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{"-d", "127.1.2.3", "-i", "lo", "-o", "lo", "-j", "DROP"}}, "Test Loopback"},
|
|
| 63 | 65 |
{iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Nat, Chain: "POSTROUTING", Args: []string{"-s", iptablesTestBridgeIP, "!", "-o", DefaultBridgeName, "-j", "MASQUERADE"}}, "NAT Test"},
|
| 64 |
- {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: "FORWARD", Args: []string{"-o", DefaultBridgeName, "-m", "conntrack", "--ctstate", "RELATED,ESTABLISHED", "-j", "ACCEPT"}}, "Test ACCEPT INCOMING"},
|
|
| 65 |
- {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: "FORWARD", Args: []string{"-i", DefaultBridgeName, "!", "-o", DefaultBridgeName, "-j", "ACCEPT"}}, "Test ACCEPT NON_ICC OUTGOING"},
|
|
| 66 |
- {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: "FORWARD", Args: []string{"-i", DefaultBridgeName, "-o", DefaultBridgeName, "-j", "ACCEPT"}}, "Test enable ICC"},
|
|
| 67 |
- {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: "FORWARD", Args: []string{"-i", DefaultBridgeName, "-o", DefaultBridgeName, "-j", "DROP"}}, "Test disable ICC"},
|
|
| 66 |
+ {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{"-o", DefaultBridgeName, "-m", "conntrack", "--ctstate", "RELATED,ESTABLISHED", "-j", "ACCEPT"}}, "Test ACCEPT INCOMING"},
|
|
| 67 |
+ {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{"-i", DefaultBridgeName, "!", "-o", DefaultBridgeName, "-j", "ACCEPT"}}, "Test ACCEPT NON_ICC OUTGOING"},
|
|
| 68 |
+ {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{"-i", DefaultBridgeName, "-o", DefaultBridgeName, "-j", "ACCEPT"}}, "Test enable ICC"},
|
|
| 69 |
+ {iptables.Rule{IPVer: iptables.IPv4, Table: iptables.Filter, Chain: DockerForwardChain, Args: []string{"-i", DefaultBridgeName, "-o", DefaultBridgeName, "-j", "DROP"}}, "Test disable ICC"},
|
|
| 68 | 70 |
} |
| 69 | 71 |
|
| 70 | 72 |
// Assert the chain rules' insertion and removal. |
| ... | ... |
@@ -138,6 +140,8 @@ func createTestBridge(config *networkConfiguration, br *bridgeInterface, t *test |
| 138 | 138 |
|
| 139 | 139 |
// Assert base function which pushes iptables chain rules on insertion and removal. |
| 140 | 140 |
func assertIPTableChainProgramming(rule iptables.Rule, descr string, t *testing.T) {
|
| 141 |
+ t.Helper() |
|
| 142 |
+ |
|
| 141 | 143 |
// Add |
| 142 | 144 |
if err := programChainRule(rule, descr, true); err != nil {
|
| 143 | 145 |
t.Fatalf("Failed to program iptable rule %s: %s", descr, err.Error())
|
| ... | ... |
@@ -4,6 +4,8 @@ import ( |
| 4 | 4 |
"fmt" |
| 5 | 5 |
"testing" |
| 6 | 6 |
|
| 7 |
+ "github.com/docker/docker/libnetwork/drivers/bridge" |
|
| 8 |
+ |
|
| 7 | 9 |
"github.com/docker/docker/internal/testutils/netnsutils" |
| 8 | 10 |
"github.com/docker/docker/libnetwork/config" |
| 9 | 11 |
"github.com/docker/docker/libnetwork/iptables" |
| ... | ... |
@@ -62,6 +64,15 @@ func TestUserChain(t *testing.T) {
|
| 62 | 62 |
fmt.Sprintf("TestUserChain_iptables-%v_append-%v_fwdinit4", tc.iptables, tc.append))
|
| 63 | 63 |
golden.Assert(t, getRules(t, iptable6, fwdChainName), |
| 64 | 64 |
fmt.Sprintf("TestUserChain_iptables-%v_append-%v_fwdinit6", tc.iptables, tc.append))
|
| 65 |
+ if tc.iptables {
|
|
| 66 |
+ golden.Assert(t, getRules(t, iptable4, bridge.DockerForwardChain), |
|
| 67 |
+ fmt.Sprintf("TestUserChain_iptables-%v_append-%v_dockerfwdinit4", tc.iptables, tc.append))
|
|
| 68 |
+ golden.Assert(t, getRules(t, iptable6, bridge.DockerForwardChain), |
|
| 69 |
+ fmt.Sprintf("TestUserChain_iptables-%v_append-%v_dockerfwdinit6", tc.iptables, tc.append))
|
|
| 70 |
+ } else {
|
|
| 71 |
+ assert.Check(t, !iptables.GetIptable(iptables.IPv4).ExistChain(bridge.DockerForwardChain, fwdChainName), |
|
| 72 |
+ "Chain %s should not exist", bridge.DockerForwardChain) |
|
| 73 |
+ } |
|
| 65 | 74 |
|
| 66 | 75 |
if tc.append {
|
| 67 | 76 |
_, err := iptable4.Raw("-A", fwdChainName, "-j", "DROP")
|
| ... | ... |
@@ -75,6 +86,15 @@ func TestUserChain(t *testing.T) {
|
| 75 | 75 |
fmt.Sprintf("TestUserChain_iptables-%v_append-%v_fwdafter4", tc.iptables, tc.append))
|
| 76 | 76 |
golden.Assert(t, getRules(t, iptable6, fwdChainName), |
| 77 | 77 |
fmt.Sprintf("TestUserChain_iptables-%v_append-%v_fwdafter6", tc.iptables, tc.append))
|
| 78 |
+ if tc.iptables {
|
|
| 79 |
+ golden.Assert(t, getRules(t, iptable4, bridge.DockerForwardChain), |
|
| 80 |
+ fmt.Sprintf("TestUserChain_iptables-%v_append-%v_dockerfwdafter4", tc.iptables, tc.append))
|
|
| 81 |
+ golden.Assert(t, getRules(t, iptable6, bridge.DockerForwardChain), |
|
| 82 |
+ fmt.Sprintf("TestUserChain_iptables-%v_append-%v_dockerfwdafter6", tc.iptables, tc.append))
|
|
| 83 |
+ } else {
|
|
| 84 |
+ assert.Check(t, !iptables.GetIptable(iptables.IPv4).ExistChain(bridge.DockerForwardChain, fwdChainName), |
|
| 85 |
+ "Chain %s should not exist", bridge.DockerForwardChain) |
|
| 86 |
+ } |
|
| 78 | 87 |
|
| 79 | 88 |
if tc.iptables {
|
| 80 | 89 |
golden.Assert(t, getRules(t, iptable4, usrChainName), |
| ... | ... |
@@ -1,4 +1,5 @@ |
| 1 |
-//go:build linux |
|
| 1 |
+// FIXME(thaJeztah): remove once we are a module; the go:build directive prevents go from downgrading language version to go1.16: |
|
| 2 |
+//go:build go1.22 && linux |
|
| 2 | 3 |
|
| 3 | 4 |
package iptables |
| 4 | 5 |
|
| ... | ... |
@@ -8,6 +9,7 @@ import ( |
| 8 | 8 |
"fmt" |
| 9 | 9 |
"net" |
| 10 | 10 |
"os/exec" |
| 11 |
+ "slices" |
|
| 11 | 12 |
"strconv" |
| 12 | 13 |
"strings" |
| 13 | 14 |
"sync" |
| ... | ... |
@@ -415,15 +417,25 @@ func (iptable IPTable) AddReturnRule(chain string) error {
|
| 415 | 415 |
|
| 416 | 416 |
// EnsureJumpRule ensures the jump rule is on top |
| 417 | 417 |
func (iptable IPTable) EnsureJumpRule(fromChain, toChain string, rule ...string) error {
|
| 418 |
+ if err := iptable.DeleteJumpRule(fromChain, toChain, rule...); err != nil {
|
|
| 419 |
+ return err |
|
| 420 |
+ } |
|
| 421 |
+ rule = append(rule, "-j", toChain) |
|
| 422 |
+ if err := iptable.RawCombinedOutput(append([]string{"-I", fromChain}, rule...)...); err != nil {
|
|
| 423 |
+ return fmt.Errorf("unable to insert jump to %s rule in %s chain: %v", toChain, fromChain, err)
|
|
| 424 |
+ } |
|
| 425 |
+ return nil |
|
| 426 |
+} |
|
| 427 |
+ |
|
| 428 |
+// DeleteJumpRule deletes a rule added by EnsureJumpRule. It's a no-op if the rule |
|
| 429 |
+// doesn't exist. |
|
| 430 |
+func (iptable IPTable) DeleteJumpRule(fromChain, toChain string, rule ...string) error {
|
|
| 418 | 431 |
rule = append(rule, "-j", toChain) |
| 419 | 432 |
if iptable.Exists(Filter, fromChain, rule...) {
|
| 420 | 433 |
if err := iptable.RawCombinedOutput(append([]string{"-D", fromChain}, rule...)...); err != nil {
|
| 421 | 434 |
return fmt.Errorf("unable to remove jump to %s rule in %s chain: %v", toChain, fromChain, err)
|
| 422 | 435 |
} |
| 423 | 436 |
} |
| 424 |
- if err := iptable.RawCombinedOutput(append([]string{"-I", fromChain}, rule...)...); err != nil {
|
|
| 425 |
- return fmt.Errorf("unable to insert jump to %s rule in %s chain: %v", toChain, fromChain, err)
|
|
| 426 |
- } |
|
| 427 | 437 |
return nil |
| 428 | 438 |
} |
| 429 | 439 |
|
| ... | ... |
@@ -447,6 +459,14 @@ func (r Rule) exec(op Action) error {
|
| 447 | 447 |
return GetIptable(r.IPVer).RawCombinedOutput(r.cmdArgs(op)...) |
| 448 | 448 |
} |
| 449 | 449 |
|
| 450 |
+// WithChain returns a version of the rule with its Chain field set to chain. |
|
| 451 |
+func (r Rule) WithChain(chain string) Rule {
|
|
| 452 |
+ wc := r |
|
| 453 |
+ wc.Args = slices.Clone(r.Args) |
|
| 454 |
+ wc.Chain = chain |
|
| 455 |
+ return wc |
|
| 456 |
+} |
|
| 457 |
+ |
|
| 450 | 458 |
// Append appends the rule to the end of the chain. If the rule already exists anywhere in the |
| 451 | 459 |
// chain, this is a no-op. |
| 452 | 460 |
func (r Rule) Append() error {
|
| 453 | 461 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
| 0 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
| 0 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
| 0 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
| ... | ... |
@@ -1,5 +1,3 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
| ... | ... |
@@ -1,5 +1,3 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
| ... | ... |
@@ -1,5 +1,3 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
| ... | ... |
@@ -1,5 +1,3 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
| 6 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
| 0 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
| 0 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
| 0 | 4 |
new file mode 100644 |
| ... | ... |
@@ -0,0 +1,4 @@ |
| 0 |
+-N DOCKER-FORWARD |
|
| 1 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 2 |
+-A DOCKER-FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 3 |
+-A DOCKER-FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
| ... | ... |
@@ -1,6 +1,4 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
|
| 6 | 4 |
-A FORWARD -j DROP |
| ... | ... |
@@ -1,6 +1,4 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
|
| 6 | 4 |
-A FORWARD -j DROP |
| ... | ... |
@@ -1,5 +1,3 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v4 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |
| ... | ... |
@@ -1,5 +1,3 @@ |
| 1 | 1 |
-P FORWARD ACCEPT |
| 2 | 2 |
-A FORWARD -j DOCKER-USER |
| 3 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT |
|
| 4 |
--A FORWARD -j DOCKER-ISOLATION-STAGE-1 |
|
| 5 |
--A FORWARD -m set --match-set docker-ext-bridges-v6 dst -j DOCKER |
|
| 3 |
+-A FORWARD -j DOCKER-FORWARD |