Skip to content

Commit 2e9d407

Browse files
authored
Merge pull request #1156 from wangyd1988/release-1.7-yd
When netpol is added to a workload, the workload's POD can be accessed using service
2 parents aaedbd3 + 6fb7d26 commit 2e9d407

File tree

4 files changed

+269
-49
lines changed

4 files changed

+269
-49
lines changed

pkg/controller/controller.go

+1
Original file line numberDiff line numberDiff line change
@@ -263,6 +263,7 @@ func NewController(config *Configuration) *Controller {
263263
})
264264

265265
serviceInformer.Informer().AddEventHandler(cache.ResourceEventHandlerFuncs{
266+
AddFunc: controller.enqueueAddService,
266267
DeleteFunc: controller.enqueueDeleteService,
267268
UpdateFunc: controller.enqueueUpdateService,
268269
})

pkg/controller/network_policy.go

+214-38
Original file line numberDiff line numberDiff line change
@@ -202,9 +202,58 @@ func (c *Controller) handleUpdateNp(key string) error {
202202
return err
203203
}
204204

205+
// set svc addreess_set
206+
svcAsNameIPv4 := strings.Replace(fmt.Sprintf("%s.%s.service.%s", np.Name, np.Namespace, kubeovnv1.ProtocolIPv4), "-", ".", -1)
207+
svcAsNameIPv6 := strings.Replace(fmt.Sprintf("%s.%s.service.%s", np.Name, np.Namespace, kubeovnv1.ProtocolIPv6), "-", ".", -1)
208+
svcIpv4s, svcIpv6s, err := c.fetchSelectedSvc(np.Namespace, &np.Spec.PodSelector)
209+
if err != nil {
210+
klog.Errorf("failed to fetchSelectedSvc svcIPs result %v", err)
211+
return err
212+
}
213+
for _, cidrBlock := range strings.Split(subnet.Spec.CIDRBlock, ",") {
214+
protocol := util.CheckProtocol(cidrBlock)
215+
svcAsName := svcAsNameIPv4
216+
svcIPs := svcIpv4s
217+
if protocol == kubeovnv1.ProtocolIPv6 {
218+
svcAsName = svcAsNameIPv6
219+
svcIPs = svcIpv6s
220+
}
221+
if err := c.ovnClient.CreateAddressSet(svcAsName, np.Namespace, np.Name, "service"); err != nil {
222+
klog.Errorf("failed to create address_set %s, %v", svcAsNameIPv4, err)
223+
return err
224+
}
225+
if err := c.ovnClient.SetAddressesToAddressSet(svcIPs, svcAsName); err != nil {
226+
klog.Errorf("failed to set netpol svc, %v", err)
227+
return err
228+
}
229+
}
230+
231+
// before update or add ingress info,we should first delete acl and address_set
232+
if err := c.ovnClient.DeleteACL(pgName, "to-lport"); err != nil {
233+
klog.Errorf("failed to delete np %s ingress acls, %v", key, err)
234+
return err
235+
}
236+
237+
ingressAsNames, err := c.ovnClient.ListAddressSet(np.Namespace, np.Name, "ingress")
238+
if err != nil {
239+
klog.Errorf("failed to list ingress address_set, %v", err)
240+
return err
241+
}
242+
for _, ingressAsName := range ingressAsNames {
243+
if err := c.ovnClient.DeleteAddressSet(ingressAsName); err != nil {
244+
klog.Errorf("failed to delete np %s address set, %v", key, err)
245+
return err
246+
}
247+
}
248+
205249
if hasIngressRule(np) {
206250
for _, cidrBlock := range strings.Split(subnet.Spec.CIDRBlock, ",") {
207251
protocol := util.CheckProtocol(cidrBlock)
252+
svcAsName := svcAsNameIPv4
253+
if protocol == kubeovnv1.ProtocolIPv6 {
254+
svcAsName = svcAsNameIPv6
255+
}
256+
208257
for idx, npr := range np.Spec.Ingress {
209258
// A single address set must contain addresses of the same type and the name must be unique within table, so IPv4 and IPv6 address set should be different
210259
ingressAllowAsName := fmt.Sprintf("%s.%s.%d", ingressAllowAsNamePrefix, protocol, idx)
@@ -250,7 +299,7 @@ func (c *Controller) handleUpdateNp(key string) error {
250299
}
251300

252301
if len(allows) != 0 || len(excepts) != 0 {
253-
if err := c.ovnClient.CreateIngressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, ingressAllowAsName, ingressExceptAsName, protocol, npr.Ports); err != nil {
302+
if err := c.ovnClient.CreateIngressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, ingressAllowAsName, ingressExceptAsName, protocol, npr.Ports, svcAsName); err != nil {
254303
klog.Errorf("failed to create ingress acls for np %s, %v", key, err)
255304
return err
256305
}
@@ -269,7 +318,7 @@ func (c *Controller) handleUpdateNp(key string) error {
269318
return err
270319
}
271320
ingressPorts := []netv1.NetworkPolicyPort{}
272-
if err := c.ovnClient.CreateIngressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, ingressAllowAsName, ingressExceptAsName, protocol, ingressPorts); err != nil {
321+
if err := c.ovnClient.CreateIngressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, ingressAllowAsName, ingressExceptAsName, protocol, ingressPorts, svcAsName); err != nil {
273322
klog.Errorf("failed to create ingress acls for np %s, %v", key, err)
274323
return err
275324
}
@@ -299,28 +348,33 @@ func (c *Controller) handleUpdateNp(key string) error {
299348
}
300349
}
301350
}
302-
} else {
303-
if err := c.ovnClient.DeleteACL(pgName, "to-lport"); err != nil {
304-
klog.Errorf("failed to delete np %s ingress acls, %v", key, err)
305-
return err
306-
}
351+
}
307352

308-
asNames, err := c.ovnClient.ListAddressSet(np.Namespace, np.Name, "ingress")
309-
if err != nil {
310-
klog.Errorf("failed to list address_set, %v", err)
353+
// before update or add egress info,we should first delete acl and address_set
354+
if err := c.ovnClient.DeleteACL(pgName, "from-lport"); err != nil {
355+
klog.Errorf("failed to delete np %s egress acls, %v", key, err)
356+
return err
357+
}
358+
359+
egressAsNames, err := c.ovnClient.ListAddressSet(np.Namespace, np.Name, "egress")
360+
if err != nil {
361+
klog.Errorf("failed to list egress address_set, %v", err)
362+
return err
363+
}
364+
for _, egressAsName := range egressAsNames {
365+
if err := c.ovnClient.DeleteAddressSet(egressAsName); err != nil {
366+
klog.Errorf("failed to delete np %s address set, %v", key, err)
311367
return err
312368
}
313-
for _, asName := range asNames {
314-
if err := c.ovnClient.DeleteAddressSet(asName); err != nil {
315-
klog.Errorf("failed to delete np %s address set, %v", key, err)
316-
return err
317-
}
318-
}
319369
}
320-
321370
if hasEgressRule(np) {
322371
for _, cidrBlock := range strings.Split(subnet.Spec.CIDRBlock, ",") {
323372
protocol := util.CheckProtocol(cidrBlock)
373+
svcAsName := svcAsNameIPv4
374+
if protocol == kubeovnv1.ProtocolIPv6 {
375+
svcAsName = svcAsNameIPv6
376+
}
377+
324378
for idx, npr := range np.Spec.Egress {
325379
// A single address set must contain addresses of the same type and the name must be unique within table, so IPv4 and IPv6 address set should be different
326380
egressAllowAsName := fmt.Sprintf("%s.%s.%d", egressAllowAsNamePrefix, protocol, idx)
@@ -366,7 +420,7 @@ func (c *Controller) handleUpdateNp(key string) error {
366420
}
367421

368422
if len(allows) != 0 || len(excepts) != 0 {
369-
if err := c.ovnClient.CreateEgressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, egressAllowAsName, egressExceptAsName, protocol, npr.Ports); err != nil {
423+
if err := c.ovnClient.CreateEgressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, egressAllowAsName, egressExceptAsName, protocol, npr.Ports, svcAsName); err != nil {
370424
klog.Errorf("failed to create egress acls for np %s, %v", key, err)
371425
return err
372426
}
@@ -385,7 +439,7 @@ func (c *Controller) handleUpdateNp(key string) error {
385439
return err
386440
}
387441
egressPorts := []netv1.NetworkPolicyPort{}
388-
if err := c.ovnClient.CreateEgressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, egressAllowAsName, egressExceptAsName, protocol, egressPorts); err != nil {
442+
if err := c.ovnClient.CreateEgressACL(fmt.Sprintf("%s/%s", np.Namespace, np.Name), pgName, egressAllowAsName, egressExceptAsName, protocol, egressPorts, svcAsName); err != nil {
389443
klog.Errorf("failed to create egress acls for np %s, %v", key, err)
390444
return err
391445
}
@@ -416,24 +470,8 @@ func (c *Controller) handleUpdateNp(key string) error {
416470
}
417471
}
418472
}
419-
} else {
420-
if err := c.ovnClient.DeleteACL(pgName, "from-lport"); err != nil {
421-
klog.Errorf("failed to delete np %s egress acls, %v", key, err)
422-
return err
423-
}
424-
425-
asNames, err := c.ovnClient.ListAddressSet(np.Namespace, np.Name, "egress")
426-
if err != nil {
427-
klog.Errorf("failed to list address_set, %v", err)
428-
return err
429-
}
430-
for _, asName := range asNames {
431-
if err := c.ovnClient.DeleteAddressSet(asName); err != nil {
432-
klog.Errorf("failed to delete np %s address set, %v", key, err)
433-
return err
434-
}
435-
}
436473
}
474+
437475
if err := c.ovnClient.CreateGatewayACL(pgName, subnet.Spec.Gateway, subnet.Spec.CIDRBlock); err != nil {
438476
klog.Errorf("failed to create gateway acl, %v", err)
439477
return err
@@ -453,6 +491,18 @@ func (c *Controller) handleDeleteNp(key string) error {
453491
klog.Errorf("failed to delete np %s port group, %v", key, err)
454492
}
455493

494+
svcAsNames, err := c.ovnClient.ListAddressSet(namespace, name, "service")
495+
if err != nil {
496+
klog.Errorf("failed to list svc address_set, %v", err)
497+
return err
498+
}
499+
for _, asName := range svcAsNames {
500+
if err := c.ovnClient.DeleteAddressSet(asName); err != nil {
501+
klog.Errorf("failed to delete np %s address set, %v", key, err)
502+
return err
503+
}
504+
}
505+
456506
ingressAsNames, err := c.ovnClient.ListAddressSet(namespace, name, "ingress")
457507
if err != nil {
458508
klog.Errorf("failed to list address_set, %v", err)
@@ -482,7 +532,7 @@ func (c *Controller) handleDeleteNp(key string) error {
482532
func (c *Controller) fetchSelectedPorts(namespace string, selector *metav1.LabelSelector) ([]string, error) {
483533
sel, err := metav1.LabelSelectorAsSelector(selector)
484534
if err != nil {
485-
return nil, fmt.Errorf("error createing label selector, %v", err)
535+
return nil, fmt.Errorf("error fetch label selector, %v", err)
486536
}
487537
pods, err := c.podsLister.Pods(namespace).List(sel)
488538
if err != nil {
@@ -501,6 +551,45 @@ func (c *Controller) fetchSelectedPorts(namespace string, selector *metav1.Label
501551
return ports, nil
502552
}
503553

554+
func (c *Controller) fetchSelectedSvc(namespace string, selector *metav1.LabelSelector) ([]string, []string, error) {
555+
sel, err := metav1.LabelSelectorAsSelector(selector)
556+
if err != nil {
557+
return nil, nil, fmt.Errorf("error creating label selector, %v", err)
558+
}
559+
pods, err := c.podsLister.Pods(namespace).List(sel)
560+
if err != nil {
561+
return nil, nil, fmt.Errorf("failed to list pods, %v", err)
562+
}
563+
564+
svcIpv4s := make([]string, 0)
565+
svcIpv6s := make([]string, 0)
566+
svcs, err := c.servicesLister.Services(namespace).List(labels.Everything())
567+
if err != nil {
568+
klog.Errorf("failed to list svc, %v", err)
569+
return nil, nil, err
570+
}
571+
572+
for _, pod := range pods {
573+
if !isPodAlive(pod) {
574+
continue
575+
}
576+
if !pod.Spec.HostNetwork && pod.Annotations[util.AllocatedAnnotation] == "true" {
577+
svcIpv4, err := svcMatchPods(svcs, pod, kubeovnv1.ProtocolIPv4)
578+
if err != nil {
579+
return nil, nil, err
580+
}
581+
svcIpv4s = append(svcIpv4s, svcIpv4...)
582+
583+
svcIpv6, err := svcMatchPods(svcs, pod, kubeovnv1.ProtocolIPv6)
584+
if err != nil {
585+
return nil, nil, err
586+
}
587+
svcIpv6s = append(svcIpv6s, svcIpv6...)
588+
}
589+
}
590+
return svcIpv4s, svcIpv6s, nil
591+
}
592+
504593
func hasIngressRule(np *netv1.NetworkPolicy) bool {
505594
for _, pt := range np.Spec.PolicyTypes {
506595
if strings.Contains(string(pt), string(netv1.PolicyTypeIngress)) {
@@ -530,7 +619,7 @@ func (c *Controller) fetchPolicySelectedAddresses(namespace, protocol string, np
530619
} else {
531620
sel, err := metav1.LabelSelectorAsSelector(npp.NamespaceSelector)
532621
if err != nil {
533-
return nil, nil, fmt.Errorf("error createing label selector, %v", err)
622+
return nil, nil, fmt.Errorf("error fetch label selector, %v", err)
534623
}
535624
nss, err := c.namespacesLister.List(sel)
536625
if err != nil {
@@ -554,17 +643,79 @@ func (c *Controller) fetchPolicySelectedAddresses(namespace, protocol string, np
554643
if err != nil {
555644
return nil, nil, fmt.Errorf("failed to list pod, %v", err)
556645
}
646+
svcs, err := c.servicesLister.Services(ns).List(labels.Everything())
647+
if err != nil {
648+
klog.Errorf("failed to list svc, %v", err)
649+
return nil, nil, fmt.Errorf("failed to list svc, %v", err)
650+
}
651+
557652
for _, pod := range pods {
558653
for _, podIP := range pod.Status.PodIPs {
559654
if podIP.IP != "" && util.CheckProtocol(podIP.IP) == protocol {
560655
selectedAddresses = append(selectedAddresses, podIP.IP)
656+
if len(svcs) == 0 {
657+
continue
658+
}
659+
klog.Infof("svc is %v", svcs)
660+
svcIPs, err := svcMatchPods(svcs, pod, protocol)
661+
if err != nil {
662+
return nil, nil, err
663+
}
664+
klog.Infof("svcIPs is %v", svcIPs)
665+
selectedAddresses = append(selectedAddresses, svcIPs...)
561666
}
562667
}
563668
}
564669
}
670+
565671
return selectedAddresses, nil, nil
566672
}
567673

674+
func svcMatchPods(svcs []*corev1.Service, pod *corev1.Pod, protocol string) ([]string, error) {
675+
matchSvcs := []string{}
676+
// find svc ip by pod's info
677+
for _, svc := range svcs {
678+
isMatch, err := isSvcMatchPod(svc, pod)
679+
if err != nil {
680+
return nil, err
681+
}
682+
if isMatch {
683+
clusterIPs := svc.Spec.ClusterIPs
684+
if len(clusterIPs) == 0 && svc.Spec.ClusterIP != "" && svc.Spec.ClusterIP != corev1.ClusterIPNone {
685+
clusterIPs = []string{svc.Spec.ClusterIP}
686+
}
687+
protocolClusterIPs := getProtocolSvcIp(clusterIPs, protocol)
688+
if len(protocolClusterIPs) != 0 {
689+
matchSvcs = append(matchSvcs, protocolClusterIPs...)
690+
}
691+
}
692+
}
693+
return matchSvcs, nil
694+
}
695+
func getProtocolSvcIp(clusterIPs []string, protocol string) []string {
696+
protocolClusterIPs := []string{}
697+
for _, clusterIP := range clusterIPs {
698+
if clusterIP != "" && clusterIP != corev1.ClusterIPNone && util.CheckProtocol(clusterIP) == protocol {
699+
protocolClusterIPs = append(protocolClusterIPs, clusterIP)
700+
}
701+
}
702+
return protocolClusterIPs
703+
}
704+
func isSvcMatchPod(svc *corev1.Service, pod *corev1.Pod) (bool, error) {
705+
ss := metav1.SetAsLabelSelector(svc.Spec.Selector)
706+
sel, err := metav1.LabelSelectorAsSelector(ss)
707+
if err != nil {
708+
return false, fmt.Errorf("error fetch label selector, %v", err)
709+
}
710+
if pod.Labels == nil {
711+
return false, nil
712+
}
713+
if sel.Matches(labels.Set(pod.Labels)) {
714+
return true, nil
715+
}
716+
return false, nil
717+
}
718+
568719
func (c *Controller) podMatchNetworkPolicies(pod *corev1.Pod) []string {
569720
podNs, _ := c.namespacesLister.Get(pod.Namespace)
570721
nps, _ := c.npsLister.NetworkPolicies(corev1.NamespaceAll).List(labels.Everything())
@@ -577,6 +728,31 @@ func (c *Controller) podMatchNetworkPolicies(pod *corev1.Pod) []string {
577728
return match
578729
}
579730

731+
func (c *Controller) svcMatchNetworkPolicies(svc *corev1.Service) ([]string, error) {
732+
// find all match pod
733+
pods, err := c.podsLister.Pods(svc.Namespace).List(labels.Everything())
734+
if err != nil {
735+
return nil, fmt.Errorf("failed to list pods, %v", err)
736+
}
737+
738+
// find all match netpol
739+
nps, err := c.npsLister.NetworkPolicies(corev1.NamespaceAll).List(labels.Everything())
740+
if err != nil {
741+
return nil, fmt.Errorf("failed to list netpols, %v", err)
742+
}
743+
match := []string{}
744+
for _, pod := range pods {
745+
podNs, _ := c.namespacesLister.Get(pod.Namespace)
746+
for _, np := range nps {
747+
if isPodMatchNetworkPolicy(pod, *podNs, np, np.Namespace) {
748+
match = append(match, fmt.Sprintf("%s/%s", np.Namespace, np.Name))
749+
}
750+
}
751+
}
752+
klog.Infof("match svc is %v", match)
753+
return match, nil
754+
}
755+
580756
func isPodMatchNetworkPolicy(pod *corev1.Pod, podNs corev1.Namespace, policy *netv1.NetworkPolicy, policyNs string) bool {
581757
sel, _ := metav1.LabelSelectorAsSelector(&policy.Spec.PodSelector)
582758
if pod.Labels == nil {

0 commit comments

Comments
 (0)