From 69d735ea0aa42e63d9c4f8068ff075b96c201ea9 Mon Sep 17 00:00:00 2001 From: Tom Eastep Date: Thu, 10 May 2012 11:19:23 -0700 Subject: [PATCH] Make TPROXY actually work! Signed-off-by: Tom Eastep --- Shorewall/Perl/Shorewall/Config.pm | 2 +- Shorewall/Perl/Shorewall/Providers.pm | 67 ++++++++++--------- Shorewall/Perl/Shorewall/Tc.pm | 63 +++++++---------- Shorewall/manpages/shorewall-providers.xml | 13 ++++ Shorewall/manpages/shorewall-tcrules.xml | 37 ++++------ Shorewall6/manpages/shorewall6-providers.xml | 13 ++++ Shorewall6/manpages/shorewall6-tcrules.xml | 31 +++------ docs/PacketMarking.xml | 4 ++ docs/Shorewall_Squid_Usage.xml | 46 ++++++++----- docs/images/MarkGeometry.dia | Bin 2328 -> 2496 bytes docs/images/MarkGeometry.png | Bin 18155 -> 19852 bytes 11 files changed, 144 insertions(+), 132 deletions(-) diff --git a/Shorewall/Perl/Shorewall/Config.pm b/Shorewall/Perl/Shorewall/Config.pm index d41ae9613..c3460773d 100644 --- a/Shorewall/Perl/Shorewall/Config.pm +++ b/Shorewall/Perl/Shorewall/Config.pm @@ -4097,7 +4097,7 @@ sub get_configuration( $$$ ) { fatal_error 'Invalid Packet Mark layout' if $config{ZONE_BITS} + $globals{ZONE_OFFSET} > 30; $globals{EXCLUSION_MASK} = 1 << ( $globals{ZONE_OFFSET} + $config{ZONE_BITS} ); - $globals{TPROXY_MASK} = $globals{EXCLUSION_MASK} << 1; + $globals{TPROXY_MARK} = $globals{EXCLUSION_MASK} << 1; $globals{PROVIDER_MIN} = 1 << $config{PROVIDER_OFFSET}; $globals{TC_MAX} = make_mask( $config{TC_BITS} ); diff --git a/Shorewall/Perl/Shorewall/Providers.pm b/Shorewall/Perl/Shorewall/Providers.pm index 187a63638..2e1b057aa 100644 --- a/Shorewall/Perl/Shorewall/Providers.pm +++ b/Shorewall/Perl/Shorewall/Providers.pm @@ -396,8 +396,8 @@ sub process_a_provider() { $gateway = ''; } - my ( $loose, $track, $balance , $default, $default_balance, $optional, $mtu, $local , $load ) = - (0, $config{TRACK_PROVIDERS}, 0 , 0, $config{USE_DEFAULT_RT} ? 1 : 0, interface_is_optional( $interface ), '' , 0 , 0 ); + my ( $loose, $track, $balance , $default, $default_balance, $optional, $mtu, $tproxy , $load ) = + (0, $config{TRACK_PROVIDERS}, 0 , 0, $config{USE_DEFAULT_RT} ? 1 : 0, interface_is_optional( $interface ), '' , 0 , 0 ); unless ( $options eq '-' ) { for my $option ( split_list $options, 'option' ) { @@ -434,10 +434,10 @@ sub process_a_provider() { } elsif ( $option eq 'fallback' ) { $default = -1; $default_balance = 0; - } elsif ( $option eq 'local' ) { - $local = 1; - $track = 0 if $config{TRACK_PROVIDERS}; - $default_balance = 0 if $config{USE_DEFAULT_RT}; + } elsif ( $option eq 'tproxy' ) { + $tproxy = 1; + $track = 0 if $config{TRACK_PROVIDERS}; + $default_balance = 0 if $config{USE_DEFAULT_RT}; } elsif ( $option =~ /^load=(0?\.\d{1,8})/ ) { $load = $1; require_capability 'STATISTIC_MATCH', "load=$load", 's'; @@ -455,11 +455,12 @@ sub process_a_provider() { $maxload += $load; } - if ( $local ) { - fatal_error "GATEWAY not valid with 'local' provider" unless $gatewaycase eq 'none'; - fatal_error "'track' not valid with 'local'" if $track; - fatal_error "DUPLICATE not valid with 'local'" if $duplicate ne '-'; - fatal_error "MARK required with 'local'" unless $mark; + if ( $tproxy ) { + fatal_error "GATEWAY not valid with 'tproxy' provider" unless $gatewaycase eq 'none'; + fatal_error "'track' not valid with 'tproxy'" if $track; + fatal_error "DUPLICATE not valid with 'tproxy'" if $duplicate ne '-'; + fatal_error "MARK not allowed with 'tproxy'" if $mark ne '-'; + $mark = $globals{TPROXY_MARK}; } my $val = 0; @@ -471,24 +472,29 @@ sub process_a_provider() { require_capability( 'MANGLE_ENABLED' , 'Provider marks' , '' ); - $val = numeric_value $mark; + if ( $tproxy ) { + $val = $globals{TPROXY_MARK}; + $pref = 1; + } else { + $val = numeric_value $mark; - fatal_error "Invalid Mark Value ($mark)" unless defined $val && $val; + fatal_error "Invalid Mark Value ($mark)" unless defined $val && $val; - verify_mark $mark; + verify_mark $mark; - fatal_error "Invalid Mark Value ($mark)" unless ( $val & $globals{PROVIDER_MASK} ) == $val; + fatal_error "Invalid Mark Value ($mark)" unless ( $val & $globals{PROVIDER_MASK} ) == $val; - fatal_error "Provider MARK may not be specified when PROVIDER_BITS=0" unless $config{PROVIDER_BITS}; + fatal_error "Provider MARK may not be specified when PROVIDER_BITS=0" unless $config{PROVIDER_BITS}; - for my $providerref ( values %providers ) { - fatal_error "Duplicate mark value ($mark)" if numeric_value( $providerref->{mark} ) == $val; + for my $providerref ( values %providers ) { + fatal_error "Duplicate mark value ($mark)" if numeric_value( $providerref->{mark} ) == $val; + } + + $lastmark = $val; + + $pref = 10000 + $number - 1; } - $pref = 10000 + $number - 1; - - $lastmark = $val; - } unless ( $loose ) { @@ -526,7 +532,7 @@ sub process_a_provider() { loose => $loose , duplicate => $duplicate , address => $address , - local => $local , + tproxy => $tproxy , load => $load , rules => [] , routes => [] , @@ -578,7 +584,7 @@ sub add_a_provider( $$ ) { my $loose = $providerref->{loose}; my $duplicate = $providerref->{duplicate}; my $address = $providerref->{address}; - my $local = $providerref->{local}; + my $tproxy = $providerref->{tproxy}; my $load = $providerref->{load}; my $dev = chain_base $physical; @@ -600,7 +606,7 @@ sub add_a_provider( $$ ) { $provider_interfaces{$interface} = $table; if ( $gatewaycase eq 'none' ) { - if ( $local ) { + if ( $tproxy ) { emit 'run_ip route add local ' . ALLIP . " dev $physical table $number"; } else { emit "run_ip route add default dev $physical table $number"; @@ -632,12 +638,13 @@ CEOF setup_interface_proc( $interface ); if ( $mark ne '-' ) { - my $mask = have_capability 'FWMARK_RT_MASK' ? '/' . in_hex $globals{PROVIDER_MASK} : ''; + my $hexmark = in_hex( $mark ); + my $mask = have_capability 'FWMARK_RT_MASK' ? '/' . in_hex( $globals{ $tproxy ? 'TPROXY_MARK' : 'PROVIDER_MASK' } ) : ''; - emit ( "qt \$IP -$family rule del fwmark ${mark}${mask}" ) if $config{DELETE_THEN_ADD}; + emit ( "qt \$IP -$family rule del fwmark ${hexmark}${mask}" ) if $config{DELETE_THEN_ADD}; - emit ( "run_ip rule add fwmark ${mark}${mask} pref $pref table $number", - "echo \"qt \$IP -$family rule del fwmark ${mark}${mask}\" >> \${VARDIR}/undo_${table}_routing" + emit ( "run_ip rule add fwmark ${hexmark}${mask} pref $pref table $number", + "echo \"qt \$IP -$family rule del fwmark ${hexmark}${mask}\" >> \${VARDIR}/undo_${table}_routing" ); } @@ -697,7 +704,7 @@ CEOF qq( qt \$IP -6 rule add from all table ) . DEFAULT_TABLE . qq( prio 32767\n) , qq(fi) ) if $family == F_IPV6; - unless ( $local ) { + unless ( $tproxy ) { emit ''; if ( $loose ) { diff --git a/Shorewall/Perl/Shorewall/Tc.pm b/Shorewall/Perl/Shorewall/Tc.pm index 6da363341..ed880fa75 100644 --- a/Shorewall/Perl/Shorewall/Tc.pm +++ b/Shorewall/Perl/Shorewall/Tc.pm @@ -163,18 +163,16 @@ my @tcclasses; my %tcclasses; my %restrictions = ( tcpre => PREROUTE_RESTRICT , + tproxy => PREROUTE_RESTRICT , tcpost => POSTROUTE_RESTRICT , tcfor => NO_RESTRICT , tcin => INPUT_RESTRICT , - tcout => OUTPUT_RESTRICT ); + tcout => OUTPUT_RESTRICT , + ); my $family; -# -# Variables supporting DIVERT -# -my $divert; #Next chain sequence number -my %diversions; #Map of marks -> chains. We use a hash rather than an array because mark values can be huge +my $divertref; # DIVERT chain # # Rather than initializing globals in an INIT block or during declaration, @@ -187,18 +185,17 @@ my %diversions; #Map of marks -> chains. We use a hash rather than an array # able to re-initialize its dependent modules' state. # sub initialize( $ ) { - $family = shift; - %classids = (); - @tcdevices = (); - %tcdevices = (); - @tcclasses = (); - %tcclasses = (); - %diversions = (); - @devnums = (); - $devnum = 0; - $sticky = 0; - $ipp2p = 0; - $divert = 0; + $family = shift; + %classids = (); + @tcdevices = (); + %tcdevices = (); + @tcclasses = (); + %tcclasses = (); + @devnums = (); + $devnum = 0; + $sticky = 0; + $ipp2p = 0; + $divertref = 0; } sub process_tc_rule( ) { @@ -305,30 +302,18 @@ sub process_tc_rule( ) { }, DIVERT => sub() { fatal_error "Invalid DIVERT specification( $cmd/$rest )" if $rest; - fatal_error "DIVERT requires TC_EXPERT=Yes" unless $config{TC_EXPERT}; - $chain = 'tcpre'; + $chain = 'tproxy'; - $cmd =~ /DIVERT\((.+?)\)$/; + $mark = in_hex( $globals{TPROXY_MARK} ) . '/' . in_hex( $globals{TPROXY_MARK} ); - $mark = $1; - - fatal_error "Invalid DIVERT specification( $cmd )" unless defined $mark; - - my $val = numeric_value( $mark ); - - validate_mark $val . '/' . in_hex( $globals{PROVIDER_MASK} ); - - my $divertref = $diversions{$val}; - unless ( $divertref ) { - $divertref = $diversions{$val} = new_chain( 'mangle', 'DIVERT' . ( $divert ? $divert : '' ) ); - $divert++; - add_ijump( $divertref , j => 'MARK', targetopts => '--set-mark ' . in_hex( $val ) . '/' . in_hex( $globals{PROVIDER_MASK} ) ); + $divertref = new_chain( 'mangle', 'divert' ); + add_ijump( $divertref , j => 'MARK', targetopts => "--set-mark $mark" ); add_ijump( $divertref , j => 'ACCEPT' ); } - $target = $divertref->{name}; + $target = 'divert'; $matches = '! --tcp-flags FIN,SYN,RST,ACK SYN -m socket --transparent '; }, @@ -337,7 +322,7 @@ sub process_tc_rule( ) { fatal_error "Invalid TPROXY specification( $cmd/$rest )" if $rest; - $chain = 'tcpre'; + $chain = 'tproxy'; $cmd =~ /TPROXY\((.+?)\)$/; @@ -345,7 +330,7 @@ sub process_tc_rule( ) { fatal_error "Invalid TPROXY specification( $cmd )" unless defined $params; - ( $mark, my $port, my $ip, my $bad ) = split ',', $params; + ( my $port, my $ip, my $bad ) = split ',', $params; fatal_error "Invalid TPROXY specification( $cmd )" if defined $bad; @@ -368,7 +353,7 @@ sub process_tc_rule( ) { $target .= ' --tproxy-mark'; - $mark = "$mark/" . in_hex( $globals{PROVIDER_MASK} ); + $mark = in_hex( $globals{TPROXY_MARK} ) . '/' . in_hex( $globals{TPROXY_MARK} ); }, TTL => sub() { fatal_error "TTL is not supported in IPv6 - use HL instead" if $family == F_IPV6; @@ -1958,6 +1943,7 @@ sub setup_tc() { ensure_mangle_chain 'tcfor'; ensure_mangle_chain 'tcpost'; ensure_mangle_chain 'tcin'; + ensure_mangle_chain 'tproxy'; } my @mark_part; @@ -1975,6 +1961,7 @@ sub setup_tc() { } } + add_ijump $mangle_table->{PREROUTING} , j => 'tproxy' if $mangle_table->{tproxy}{referenced}; add_ijump $mangle_table->{PREROUTING} , j => 'tcpre', @mark_part; add_ijump $mangle_table->{OUTPUT} , j => 'tcout', @mark_part; diff --git a/Shorewall/manpages/shorewall-providers.xml b/Shorewall/manpages/shorewall-providers.xml index bf4d5be78..337a472a0 100644 --- a/Shorewall/manpages/shorewall-providers.xml +++ b/Shorewall/manpages/shorewall-providers.xml @@ -270,6 +270,19 @@ shorewall.conf. + + + tproxy + + + Added in Shorewall 4.5.4. Used for supporting the TPROXY + action in shorewall-tcrules(5). See http://www.shorewall.net/Shorewall_Squid_Usage.html. + When specified, the MARK, DUPLICATE and GATEWAY columns should + be empty, INTERFACE should be set to 'lo' and + should be the only OPTION. + + diff --git a/Shorewall/manpages/shorewall-tcrules.xml b/Shorewall/manpages/shorewall-tcrules.xml index 770a44d0c..299ea104a 100644 --- a/Shorewall/manpages/shorewall-tcrules.xml +++ b/Shorewall/manpages/shorewall-tcrules.xml @@ -408,36 +408,29 @@ SAME $FW 0.0.0.0/0 tcp 80,443 - DIVERT(mark) + DIVERT - Added in Shorewall 4.5.3. A DIVERT rule should preceed - each TPROXY rule and should specify the same - mark value. DIVERT avoids sending - packets to the TPROXY target once a socket connection to Squid3 - has been established by TPROXY. DIVERT marks the packet with the - specified mark and exempts it from - any rules that follow. + Added in Shorewall 4.5.3. Two DIVERT rule should preceed + the TPROXY rule and should select DEST PORT tcp 80 and SOURCE + PORT tcp 80 respectively (assuming that tcp port 80 is being + proxied). DIVERT avoids sending packets to the TPROXY target + once a socket connection to Squid3 has been established by + TPROXY. DIVERT marks the packet with a unique mark and exempts + it from any rules that follow. TPROXY(mark[,[port][,[address]]]) + role="bold">TPROXY([port][,address]) Transparently redirects a packet without altering the IP - header. Requires a local provider to be defined in shorewall-providers(5). - There are three parameters to TPROXY - only the first - (mark) is required: + There are three parameters to TPROXY - neither is + required: - - mark - the MARK value - corresponding to the local provider in shorewall-providers(5). - - port - the port on which the proxy server is listening. If omitted, the original @@ -451,12 +444,6 @@ SAME $FW 0.0.0.0/0 tcp 80,443 request arrives. - - - A DIVERT rule specifying the same - mark value and other column values - should preceed each TPROXY rule. - diff --git a/Shorewall6/manpages/shorewall6-providers.xml b/Shorewall6/manpages/shorewall6-providers.xml index 99c3b6f57..96d5cff99 100644 --- a/Shorewall6/manpages/shorewall6-providers.xml +++ b/Shorewall6/manpages/shorewall6-providers.xml @@ -245,6 +245,19 @@ column is assumed. + + + tproxy + + + Added in Shorewall 4.5.4. Used for supporting the TPROXY + action in shorewall-tcrules(5). See http://www.shorewall.net/Shorewall_Squid_Usage.html. + When specified, the MARK, DUPLICATE and GATEWAY columns should + be empty, INTERFACE should be set to 'lo' and + should be the only OPTION. + + diff --git a/Shorewall6/manpages/shorewall6-tcrules.xml b/Shorewall6/manpages/shorewall6-tcrules.xml index ada019d7d..d16945e3e 100644 --- a/Shorewall6/manpages/shorewall6-tcrules.xml +++ b/Shorewall6/manpages/shorewall6-tcrules.xml @@ -305,21 +305,20 @@ SAME $FW 0.0.0.0/0 tcp 80,443 - DIVERT(mark) + DIVERT - Added in Shorewall 4.5.3. A DIVERT rule should preceed - each TPROXY rule and should specify the same - mark value. DIVERT avoids sending - packets to the TPROXY target once a socket connection to Squid3 - has been established by TPROXY. DIVERT marks the packet with the - specified mark and exempts it from - any rules that follow. + Added in Shorewall 4.5.3. Two DIVERT rule should preceed + the TPROXY rule and should select DEST PORT tcp 80 and SOURCE + PORT tcp 80 respectively (assuming that tcp port 80 is being + proxied). DIVERT avoids sending packets to the TPROXY target + once a socket connection to Squid3 has been established by + TPROXY. DIVERT marks the packet with a unique mark and exempts + it from any rules that follow. TPROXY(mark][,[port][,[address]]]) + role="bold">TPROXY([port][,[address]]]) Transparently redirects a packet without altering the IP header. Requires a local provider to be defined in (mark) is required: - - mark - the MARK value - corresponding to the local provider in shorewall6-providers(5). - - port - the port on which the proxy server is listening. If omitted, the original @@ -348,12 +341,6 @@ SAME $FW 0.0.0.0/0 tcp 80,443 request arrives. - - - A DIVERT rule specifying the same - mark value and other column values - should preceed each TPROXY rule. - diff --git a/docs/PacketMarking.xml b/docs/PacketMarking.xml index 6c8e4815b..d05f85d5d 100644 --- a/docs/PacketMarking.xml +++ b/docs/PacketMarking.xml @@ -398,6 +398,10 @@ tcp 6 19 TIME_WAIT src=206.124.146.176 dst=192.136.34.98 sport=58597 dport= shorewall update (shorewall6 update) command will set the above options based on the settings of WIDE_TC_MARKS and HIGH_ROUTE_MARKS. + + In Shorewall 4.5.4, a TPROXY mark was added + for TPROXY support. It is a single bit wide and is to the immediate left + of the exclusion mark.
diff --git a/docs/Shorewall_Squid_Usage.xml b/docs/Shorewall_Squid_Usage.xml index 92e6f8851..1efbac6b8 100644 --- a/docs/Shorewall_Squid_Usage.xml +++ b/docs/Shorewall_Squid_Usage.xml @@ -312,15 +312,25 @@ ACCEPT $FW net tcp 80,443
Transparent with TPROXY - Shorewall 4.4.7 contains support for TPROXY. TPROXY differs from - REDIRECT in that it does not modify the IP header. Because the IP header - stays intact, TPROXY requires policy routing to direct the packets to the - proxy server running on the firewall. This approach requires TPROXY - support in your kernel and iptables and Squid 3. See Shorewall 4.5.4 contains support for TPROXY. TPROXY differs from + REDIRECT in that it does not modify the IP header and requires Squid 3 or + later. Because the IP header stays intact, TPROXY requires policy routing + to direct the packets to the proxy server running on the firewall. This + approach requires TPROXY support in your kernel and iptables and Squid 3. + See http://wiki.squid-cache.org/Features/Tproxy4. + + Support for the TPROXY action in shorewall-tcrules(5) and the + option in shorewall-providers(5) has been + available since Shoreall 4.4.7. That support required additional rules + to be added in the 'start' extention script to make it work + reliable. + + The following configuration works with Squid running on the firewall - itself (assume that Squid is listening on port 3128). + itself (assume that Squid is listening on port 3129 for TPROXY + connections). /etc/shorewall/interfaces: @@ -330,21 +340,25 @@ ACCEPT $FW net tcp 80,443 /etc/shorewall/providers: #NAME NUMBER MARK DUPLICATE INTERFACE GATEWAY OPTIONS COPY -Tproxy 1 1 - lo - local +Tproxy 1 - - lo - tproxy + + + Notice that the MARK, DUPLICATE and GATEWAY columns are empty and + that the only option is . + /etc/shorewall/tcrules (assume loc interface is eth1): - MARK SOURCE DEST PROTO PORT(S) -DIVERT(1) eth1 0.0.0.0/0 tcp 80 -TPROXY(1,3128) eth1 0.0.0.0/0 tcp 80 + MARK SOURCE DEST PROTO DEST SOURCE + PORT(S) PORT(S) +DIVERT - 0.0.0.0/0 tcp 80 +DIVERT - 0.0.0.0/0 tcp - 80 +TPROXY(3129) eth1 0.0.0.0/0 tcp 80 - - The DIVERT action was added in Shorewall 4.5.3; user's running - earlier versions of Shorewall will need to use the start extension script to add the - DIVERT logic mentioned in the Squid article linked above. - + The DIVERT rules are used to avoid unnecessary invocation of TPROXY + for request packets after the connection is established and to direct + response packets back to Squid3. /etc/shorewall/rules: diff --git a/docs/images/MarkGeometry.dia b/docs/images/MarkGeometry.dia index c8528dedcf140819ccb50d336cc3618c1435b3c0..f41ca2e8f17f95de8e408a086e028fec86826c90 100644 GIT binary patch literal 2496 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 K<3~?Zr2qgk8_?kZ literal 2328 zcmV+z3Fr17iwFP!000021MOW~Z{s!=e$THEJTJR|hvroz>n6p{?hLlrwo`O6edvoJ z+lr$dSqfz3_OicyNlG5yq{NX-CrYRw0p!s9MEdaX`wkE3AAh==$KFktEuu6z?I8er zUYJbMX_U-Pdtc8#y%)Wo&Q5-uM!^s2ca{ZnPrV~q=)2S2Wu9OCFc{q4-h%jk5#(tG z;^-PI!omN7I1UD?(4cpA;(6;8OoKeoua&O`d7ee%>pb+5U>=_K#=+#yiy&U?(}3dT?<4N1qj#1?(}xG|Mv0nQZlh^_Il8mdT}AEpmTJF=7ST8k ztDZhe@`F`>f0*jGKON)2S8s1=4MlCWQ^Zt+EM!lgB4*doG+aDlW}9VdYPu|o4IbOZWeYOnl&OON9PlRUav-mUdXI{t4s$;-xm$%AAXWK-|G z_aVLOt$2uHA<^`-_Ze<>)^_t$Wy%lk^ww3nGAROl*5~Tab|36|kUE6%cpD&7O$d@% z9Iik##*h#ISs!sAnxTbpI3G>YEZL$K@wvU)4-Hm> zZjVuT9^U0^!w{9j5VakK7y^RT$iRTx9ESo(PPm3akPR^cKKHS{6%02VEV=HHM<$=G zGIgJ^w#fb0H0kL^ykww|?tU$N;r3lPFc{UWlbkqQ07U5Hayv-^Fj8KH9@3ojU4_I%3ZfzvZo6AqUWY z{8srsxs2a33eXYax2+rI;|afqwiZYVVuz;!!B4y>;5@V z9&_tNW~~IxaFTYn6s+MurU({RinF*Cup5eV^x^08FHUhDDHdLBmX2+`Z&cERsjOLTszi*l@e3N!p}4Z^Blg8K9c?S_;9GlI;AypJ)! z2ol?Zth$YrqKqQwn}SFRC(4{Cd()!KKR~cY=+Lkl=a#ofEMXuty39w#E$_sZt>6Fn z{O8aA`uNA_^QTW=KAt;$b|fZLX`PM;by1)lB6ZrVQYd2(cJ z))1Xn>Y_Xo2RM+&hm4v`n#RjS`yR@}7&Eyz)HlcSK*se78pecL7HGAttSBlKrz?vh zw{GSn+8dW>t+TQT0j$i<;8u^+Sm7YXw1YvI`}$VGPH8l^f_B7{HmZ%&k)aMsG~7CO zny^BzD{Ej@UDXmt=zXrkHCXP}(40oAw?yZcx_1Z=Zk={r9ARqv%v1$Zo&rRGB*!>1 zwPmyR*>O(+Bvh`hR#F#^KpN7!=@f%I2fOsRt7xI=sHzb@Q) zsmBfKRvV_E%yQql7q>E1dq8gr$cZPODCQqU7DfQ};DW+!c1wGTUiYOIzHf>Q<= zZS|!#?nI!j)05Uoz?cHuX8_p@UKk9j*K&pg11J?9=|t4xBM7 z$*gCwuV7HIz`}8NQrQ3c{M$#DzJAO_l}e*@?5Bg->!fv>r~riZ36K`OlY$_KAcca3 yPtednQUHY%+-WhV#db~5`J!j_Ma6v_+=toONpYioXIU^mJNZ8`F1=FzlmGxYnT1dQ diff --git a/docs/images/MarkGeometry.png b/docs/images/MarkGeometry.png index fd921ee87d0a010e2d14a74bf3fdfd454ef0ecd2..70cdbe112390ee750a2c236ebd656ad631a7bf2a 100644 GIT binary patch literal 19852 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 }V zbQJ;LPEZRb7J2!5vV&}OmL1I{oYgd$ zY5My5dU~V?yP1m`_zIz7+CvW~Cmh7;+S--pc6NPByZeWS5n*A9IL4ergB{T^G0rgG zhxm2S5cr(+@lhAV#|s+@A=7%NsGKAQ17%Cg0=*Jcn?yz?L@s9n0NkN~W+!^F$bVeO zJ4q_Oefhx8IcuyfXL@9E|o-gjG;*s=xp1J}nExR&~mxCA&_MS~LfL!LUVz z)|Irv!cYO0m;uOhl1xXC#Fu+BBQC2i?@2~+%qD+)mf}$SMpim|V8tmsENpD!0BADU zra|Qhc$)6STzz#Gb+R#~MREoO;kbbm0^fo2G@Z3ps$kf~*?DZk1ySv~l`^<;9pP`# zF0SI~iRwxI-KkgP01W0EWupXs%uG*T%y-90T&J$%vyImXPvCJzlJa|HGTc{R}{;UZ8I0))7uoEaR96f+WkTxz?TSL76pd+ z$p+83kLGb*s?fbsQlgCO0_g(Uye)>a;>jRh0v}RVR!&zi19%JAx5L!_@dLECV4C{{ z${r$Z*rGR?AAj(rCl$jio7uA;M|aI>^si?2(_sg_mo|p7Z*Kkw@c?j@M=Fc)5$=sq zBM65+?D!rN1T@p9pp$$>q-3;iY7<~=P>W$|FKu)Oh)^s09`N-!Kki_my`2?dt#l literal 18155 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 PK~w1aN>X`uAHDb=?9~TU