diff --git a/KubeArmor/core/containerPolicy_fuzz_test.go b/KubeArmor/core/containerPolicy_fuzz_test.go index dc2a5a90f9..21eddcf888 100644 --- a/KubeArmor/core/containerPolicy_fuzz_test.go +++ b/KubeArmor/core/containerPolicy_fuzz_test.go @@ -5,6 +5,8 @@ package core import ( "context" "testing" + "encoding/json" + tp "github.com/kubearmor/KubeArmor/KubeArmor/types" "github.com/kubearmor/KubeArmor/KubeArmor/policy" pb "github.com/kubearmor/KubeArmor/protobuf" @@ -13,78 +15,146 @@ import ( func FuzzContainerPolicy(f *testing.F) { Data1 := &pb.Policy{ Policy: []byte(` - apiVersion: security.kubearmor.com/v1 - kind: KubeArmorPolicy - metadata: - name: ksp-group-1-proc-path-block - namespace: multiubuntu - spec: - selector: - matchLabels: - group: group-1 - process: - matchPaths: - - path: /bin/sleep - action: - Block +{ + "type": "ContainerPolicy", + "object": { + "apiVersion": "security.kubearmor.com/v1", + "kind": "KubeArmorPolicy", + "metadata": { + "name": "ksp-group-1-proc-path-block", + "namespace": "multiubuntu" + }, + "spec": { + "selector": { + "matchLabels": { + "group": "group-1" + } + }, + "process": { + "matchPaths": [ + { + "path": "/bin/sleep" + } + ] + }, + "action": "Block" + } + } +} + + `), } //ksp-group-2-allow-file-path-from-source-path.yaml Data2 := &pb.Policy{ Policy: []byte(` - apiVersion: security.kubearmor.com/v1 -kind: KubeArmorPolicy -metadata: - name: ksp-group-2-allow-file-path-from-source-path - namespace: multiubuntu -spec: - severity: 5 - message: "allow /bin/cat to access /secret.txt" - selector: - matchLabels: - group: group-2 - process: - matchDirectories: - - dir: /bin/ - recursive: true - file: - matchPaths: - - path: /secret.txt - fromSource: - - path: /bin/cat - - path: /dev/tty - - path: /lib/terminfo/x/xterm - matchDirectories: - - dir: /pts/ - recursive: true - - dir: /proc/ - recursive: true - - dir: /dev/ - recursive: true - - dir: /lib/x86_64-linux-gnu/ - - dir: /bin/ - action: - Allow +{ + "type": "ContainerPolicy", + "object": { + "apiVersion": "security.kubearmor.com/v1", + "kind": "KubeArmorPolicy", + "metadata": { + "name": "ksp-group-2-allow-file-path-from-source-path", + "namespace": "multiubuntu" + }, + "spec": { + "severity": 5, + "message": "allow /bin/cat to access /secret.txt", + "selector": { + "matchLabels": { + "group": "group-2" + } + }, + "process": { + "matchDirectories": [ + { + "dir": "/bin/", + "recursive": true + } + ] + }, + "file": { + "matchPaths": [ + { + "path": "/secret.txt", + "fromSource": [ + { + "path": "/bin/cat" + } + ] + }, + { + "path": "/dev/tty" + }, + { + "path": "/lib/terminfo/x/xterm" + } + ], + "matchDirectories": [ + { + "dir": "/pts/", + "recursive": true + }, + { + "dir": "/proc/", + "recursive": true + }, + { + "dir": "/dev/", + "recursive": true + }, + { + "dir": "/lib/x86_64-linux-gnu/" + }, + { + "dir": "/bin/" + } + ] + }, + "action": "Allow" + } + } +} + + `), } + Data3 := &pb.Policy{ Policy: []byte(` - apiVersion: security.kubearmor.com/v1 -kind: KubeArmorPolicy -metadata: - name: ksp-ubuntu-1-allow-net-tcp-from-source - namespace: multiubuntu -spec: - severity: 8 - selector: - matchLabels: - container: ubuntu-1 - network: - matchProtocols: - - protocol: tcp - fromSource: - - path: /usr/bin/curl - action: Allow +{ + "type": "ContainerPolicy", + "object": { + "apiVersion": "security.kubearmor.com/v1", + "kind": "KubeArmorPolicy", + "metadata": { + "name": "ksp-ubuntu-1-allow-net-tcp-from-source", + "namespace": "multiubuntu" + }, + "spec": { + "severity": 8, + "selector": { + "matchLabels": { + "container": "ubuntu-1" + } + }, + "network": { + "matchProtocols": [ + { + "protocol": "tcp", + "fromSource": [ + { + "path": "/usr/bin/curl" + } + ] + } + ] + }, + "action": "Allow" + } + } +} + `), } @@ -101,12 +171,24 @@ spec: policy := &pb.Policy{ Policy: data, } + policyEvent := tp.K8sKubeArmorPolicyEvent{} + if err := json.Unmarshal(data, &policyEvent); err != nil { + // Skip invalid JSON requests that may be generated during fuzz + t.Skip("invalid json") + } res, err := p.ContainerPolicy(context.Background(), policy) if err != nil { t.Errorf("Unexpected error: %v", err) } - if res.Status != pb.PolicyStatus_Invalid && res.Status != pb.PolicyStatus_Applied && res.Status != pb.PolicyStatus_Modified { - t.Errorf("Unexpected status: %v, %v", res.Status, data) + if res.Status != pb.PolicyStatus_Applied && res.Status != pb.PolicyStatus_Modified { + if policyEvent.Object.Metadata.Name == "" && res.Status == pb.PolicyStatus_Invalid{ + t.Skip("no name metadata") + } + if len(policyEvent.Object.Spec.Selector.MatchLabels) == 0 && res.Status == pb.PolicyStatus_Invalid{ + t.Skip("No labels to match found on policy.") + } + + t.Errorf("Unexpected status: %v", res.Status) } }) } diff --git a/KubeArmor/core/hostPolicy_fuzz_test.go b/KubeArmor/core/hostPolicy_fuzz_test.go index 57c4371ca6..900318b77f 100644 --- a/KubeArmor/core/hostPolicy_fuzz_test.go +++ b/KubeArmor/core/hostPolicy_fuzz_test.go @@ -7,35 +7,58 @@ import ( "github.com/kubearmor/KubeArmor/KubeArmor/policy" pb "github.com/kubearmor/KubeArmor/protobuf" "testing" + "encoding/json" + tp "github.com/kubearmor/KubeArmor/KubeArmor/types" + ) func FuzzHostPolicy(f *testing.F) { data := &pb.Policy{ Policy: []byte(` -apiVersion: security.kubearmor.com/v1 -kind: KubeArmorHostPolicy -metadata: - name: hsp-cve-2019-14271 -spec: - tags: ["CVE-2019-14271","docker-cp","libraries","docker-tar","root-code-execution"] - message: "Alert! Docker Binary Has Been Executed." - nodeSelector: - matchLabels: - kubernetes.io/hostname: gke-ubuntu #change with your hostname - process: - severity: 2 - matchPaths: - - path: /usr/bin/docker - - path: /usr/sbin/chroot - - path: /usr/lib/tar - - path: /usr/lib/chmod - action: Block - file: - severity: 3 - matchDirectories: - - dir: /lib/x86_64-linux-gnu/ - - dir: /var/log/ - action: Block +{ + "type": "HostPolicy", + "object": { + "apiVersion": "security.kubearmor.com/v1", + "kind": "KubeArmorHostPolicy", + "metadata": { + "name": "hsp-cve-2019-14271" + }, + "spec": { + "tags": [ + "CVE-2019-14271", + "docker-cp", + "libraries", + "docker-tar", + "root-code-execution" + ], + "message": "Alert! Docker Binary Has Been Executed.", + "nodeSelector": { + "matchLabels": { + "kubernetes.io/hostname": "gke-ubuntu" + } + }, + "process": { + "severity": 2, + "matchPaths": [ + { "path": "/usr/bin/docker" }, + { "path": "/usr/sbin/chroot" }, + { "path": "/usr/lib/tar" }, + { "path": "/usr/lib/chmod" } + ], + "action": "Block" + }, + "file": { + "severity": 3, + "matchDirectories": [ + { "dir": "/lib/x86_64-linux-gnu/" }, + { "dir": "/var/log/" } + ], + "action": "Block" + } + } +} + + `), } dm := NewKubeArmorDaemon() @@ -48,12 +71,21 @@ spec: policy := &pb.Policy{ Policy: data, } + policyEvent := tp.K8sKubeArmorPolicyEvent{} + if err := json.Unmarshal(data, &policyEvent); err != nil { + // Skip invalid JSON requests that may be generated during fuzz + t.Skip("invalid json") + } res, err := p.HostPolicy(context.Background(), policy) if err != nil { t.Errorf("Unexpected error: %v", err) } - if res.Status != pb.PolicyStatus_Invalid && res.Status != pb.PolicyStatus_Applied { - t.Errorf("Unexpected status: %v, %v", res.Status, data) + if len(policyEvent.Object.Spec.Selector.MatchLabels) == 0 && res.Status == pb.PolicyStatus_Invalid{ + t.Skip("No labels to match found on policy.") + } + + if res.Status != pb.PolicyStatus_Applied { + t.Errorf("Unexpected status: %v", res.Status) } }) } diff --git a/KubeArmor/policy/policy.go b/KubeArmor/policy/policy.go index 68f2fa9e3d..10852c1a23 100644 --- a/KubeArmor/policy/policy.go +++ b/KubeArmor/policy/policy.go @@ -43,15 +43,16 @@ func (p *PolicyServer) ContainerPolicy(c context.Context, data *pb.Policy) (*pb. res.Status = pb.PolicyStatus_Invalid kg.Warn("Empty Container Policy Event") } - + return res, nil + } else { kg.Warn("Invalid Container Policy Event") res.Status = pb.PolicyStatus_Invalid + return res, err } - return res, nil } // HostPolicy accepts host policy event on gRPC service and updates host security policies. It responds with 1 if success else 0. @@ -78,11 +79,12 @@ func (p *PolicyServer) HostPolicy(c context.Context, data *pb.Policy) (*pb.Respo res.Status = pb.PolicyStatus_Invalid } + return res, nil } else { kg.Warn("Invalid Host Policy Event") res.Status = pb.PolicyStatus_Invalid + return res, err } - return res, nil }