New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Reduce the amount of repeating code in CT #25356
Conversation
The switch in ct_lookup4 is almost identical to ct_extract_ports4. Reuse the existing function with a slight modification. Signed-off-by: Maxim Mikityanskiy <maxim@isovalent.com>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good, thanks!
Nit: In 2nd commit, some comment blocks could be re-wrapped now that they have less left-indent.
ICMP_FRAG_NEEDED handling in snat_v4_rev_nat is pretty self-contained, and three indentation levels can easily be saved by moving this code into a separate function with just slight modifications. Signed-off-by: Maxim Mikityanskiy <maxim@isovalent.com>
Done. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💯 on the ct_extract_ports4()
patch!
I'm less convinced that the ICMP_FRAG_NEEDED
patch is truly making it easier to understand things, but not feeling strongly about it either. But should we give the ICMPV6_PKT_TOOBIG
part the same treatment then?
struct ipv4_ct_tuple tuple = {}; | ||
struct ipv4_nat_entry *state; | ||
struct iphdr iphdr; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just for context - when initially adding this code (a short while back), there was concern whether we should share the CT tuple (for processing the inner & outer packet), or have it cleanly separated. And how it would impact complexity.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, I wasn't aware of this context. What was the conclusion of that discussion? Shall I pass a pointer to tuple_buf to this function to reuse the one from the caller? Or there wasn't a clear conclusion?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What was the conclusion of that discussion?
We tried to share it as much as possible - but I don't think there was a final experiment on the latest code whether having it fully split up would trigger the verifier. So if we can do a clean split and still pass the verifier, I think that would be preferable.
/* Switch back to the outer header. */ | ||
tuple.nexthdr = IPPROTO_ICMP; | ||
|
||
return snat_v4_rewrite_ingress(ctx, &tuple, state, off); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm slightly concerned that this part (how we NAT the outer headers) will over time drift apart from what we do in the "main" path. How bad would it be to only handle the inner SNAT here, and return to the main function for handling the outer SNAT?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You mean just this function call return snat_v4_rewrite_ingress(ctx, &tuple, state, off);
? I don't see what can drift here, rewriting the outer headers is already contained in a separate function, so that it can be reused from two different flows.
I can return 0 from here and goto rewrite_ingress
in the caller on non-errors, but that's going to be uglier, and I don't see much point. Please tell me what you think.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You mean just this function call
return snat_v4_rewrite_ingress(ctx, &tuple, state, off);
? I don't see what can drift here, rewriting the outer headers is already contained in a separate function, so that it can be reused from two different flows.
The bad scenario would be that at some point we only modify the main path, without realizing that there's a second user buried somewhere else.
I can return 0 from here and
goto rewrite_ingress
in the caller on non-errors, but that's going to be uglier, and I don't see much point. Please tell me what you think.
Then let's not change it and keep your current approach :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should we give the ICMPV6_PKT_TOOBIG part the same treatment then?
Good idea, I didn't notice IPv6 had a similar flow, because I mainly worked on IPv4 code for my bugfix. Let me do that too.
BTW, why don't we have ICMPV6_PKT_TOOBIG in snat_v6_nat, but only have it in revNAT?
/* Switch back to the outer header. */ | ||
tuple.nexthdr = IPPROTO_ICMP; | ||
|
||
return snat_v4_rewrite_ingress(ctx, &tuple, state, off); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You mean just this function call return snat_v4_rewrite_ingress(ctx, &tuple, state, off);
? I don't see what can drift here, rewriting the outer headers is already contained in a separate function, so that it can be reused from two different flows.
I can return 0 from here and goto rewrite_ingress
in the caller on non-errors, but that's going to be uglier, and I don't see much point. Please tell me what you think.
struct ipv4_ct_tuple tuple = {}; | ||
struct ipv4_nat_entry *state; | ||
struct iphdr iphdr; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, I wasn't aware of this context. What was the conclusion of that discussion? Shall I pass a pointer to tuple_buf to this function to reuse the one from the caller? Or there wasn't a clear conclusion?
ICMPV6_PKT_TOOBIG handling in snat_v4_rev_nat is pretty self-contained, and two indentation levels can easily be saved by moving this code into a separate function with just slight modifications. Signed-off-by: Maxim Mikityanskiy <maxim@isovalent.com>
Good question, I don't see it being discussed in #25054. |
/test |
Ah! The read-to-merge label was added by mlh. /cc @julianwiedmann Not sure if you all your review comments were addressed (looks that way), please double check. |
All good, thanks! If it's green, merge we must. |
Pure refactoring, no behavioral change.