Skip to content

Commit

Permalink
only save new profile/activity when sets are updated
Browse files Browse the repository at this point in the history
Signed-off-by: Matthias Bertschy <[email protected]>
  • Loading branch information
matthyx committed Nov 15, 2023
1 parent d9c6b09 commit d94a5b7
Show file tree
Hide file tree
Showing 3 changed files with 99 additions and 85 deletions.
163 changes: 87 additions & 76 deletions pkg/applicationprofilemanager/v1/applicationprofile_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -169,108 +169,119 @@ func (am *ApplicationProfileManager) saveProfile(ctx context.Context, watchedCon
return
}

// get syscalls from IG
observedSyscalls, err := am.syscallPeekFunc(watchedContainer.NsMntId)
if err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to get syscalls", helpers.Error(err))
}
// activity sets
syscalls := mapset.NewSet[string]()
var addedActivities int
syscalls := mapset.NewSet[string](observedSyscalls...)
// existing activity
existingActivity, _ := am.storageClient.GetApplicationActivity(slug, namespace)
if existingActivity != nil {
syscalls.Append(existingActivity.Spec.Syscalls...)
existingActivity, _ := am.storageClient.GetApplicationActivity(namespace, slug)
if existingActivity != nil && existingActivity.Spec.Syscalls != nil {
addedActivities += syscalls.Append(existingActivity.Spec.Syscalls...)
} else {
addedActivities += 1
}
// new activity
newActivity := &v1beta1.ApplicationActivity{
ObjectMeta: metav1.ObjectMeta{
Name: slug,
Annotations: map[string]string{
instanceidhandler.WlidMetadataKey: watchedContainer.Wlid,
instanceidhandler.StatusMetadataKey: "",
if addedActivities > 0 {
newActivity := &v1beta1.ApplicationActivity{
ObjectMeta: metav1.ObjectMeta{
Name: slug,
Annotations: map[string]string{
instanceidhandler.WlidMetadataKey: watchedContainer.Wlid,
instanceidhandler.StatusMetadataKey: "",
},
Labels: utils.GetLabels(watchedContainer, true),
},
Labels: utils.GetLabels(watchedContainer, true),
},
}
// add syscalls
newSyscalls, err := am.syscallPeekFunc(watchedContainer.NsMntId)
if err == nil {
syscalls.Append(newSyscalls...)
} else {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to get syscalls", helpers.Error(err))
}
newActivity.Spec.Syscalls = syscalls.ToSlice()
if err := am.storageClient.CreateApplicationActivity(newActivity, namespace); err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to save application activity", helpers.Error(err))
}
// add syscalls
newActivity.Spec.Syscalls = syscalls.ToSlice()
// save application activity
if err := am.storageClient.CreateApplicationActivity(newActivity, namespace); err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to save application activity", helpers.Error(err))
}
logger.L().Debug("ApplicationProfileManager - saved application activity", helpers.String("slug", slug), helpers.String("container ID", watchedContainer.ContainerID), helpers.String("k8s workload", watchedContainer.K8sContainerID))
}

// profile sets
var addedProfiles int
capabilities := am.capabilitiesSets.Get(watchedContainer.K8sContainerID)
execs := am.execSets.Get(watchedContainer.K8sContainerID)
opens := am.openSets.Get(watchedContainer.K8sContainerID)
// existing profile
existingProfile, _ := am.storageClient.GetApplicationProfile(slug, namespace)
existingProfile, _ := am.storageClient.GetApplicationProfile(namespace, slug)
existingProfileContainer := utils.GetApplicationProfileContainer(existingProfile, watchedContainer.ContainerType, watchedContainer.ContainerIndex)
if existingProfile != nil {
capabilities.Append(existingProfileContainer.Capabilities...)
if existingProfileContainer != nil {
addedProfiles += capabilities.Append(existingProfileContainer.Capabilities...)
for _, exec := range existingProfileContainer.Execs {
if _, exist := execs[exec.Path]; !exist {
execs[exec.Path] = mapset.NewSet[string]()
}
execs[exec.Path].Append(exec.Args...)
addedProfiles += execs[exec.Path].Append(exec.Args...)
}
for _, open := range existingProfileContainer.Opens {
if _, exist := opens[open.Path]; !exist {
opens[open.Path] = mapset.NewSet[string]()
}
opens[open.Path].Append(open.Flags...)
addedProfiles += opens[open.Path].Append(open.Flags...)
}
} else {
addedProfiles += 1
}
// new profile
newProfile := &v1beta1.ApplicationProfile{
ObjectMeta: metav1.ObjectMeta{
Name: slug,
Annotations: map[string]string{
instanceidhandler.WlidMetadataKey: watchedContainer.Wlid,
instanceidhandler.StatusMetadataKey: "",
if addedProfiles > 0 {
newProfile := &v1beta1.ApplicationProfile{
ObjectMeta: metav1.ObjectMeta{
Name: slug,
Annotations: map[string]string{
instanceidhandler.WlidMetadataKey: watchedContainer.Wlid,
instanceidhandler.StatusMetadataKey: "",
},
Labels: utils.GetLabels(watchedContainer, true),
},
Labels: utils.GetLabels(watchedContainer, true),
},
}
newProfileContainer := v1beta1.ApplicationProfileContainer{
Name: watchedContainer.InstanceID.GetContainerName(),
}
// add capabilities
newProfileContainer.Capabilities = capabilities.ToSlice()
sort.Strings(newProfileContainer.Capabilities)
// add execs
newProfileContainer.Execs = make([]v1beta1.ExecCalls, 0)
for path, exec := range execs {
args := exec.ToSlice()
sort.Strings(args)
newProfileContainer.Execs = append(newProfileContainer.Execs, v1beta1.ExecCalls{
Path: path,
Args: args,
})
}
// add opens
newProfileContainer.Opens = make([]v1beta1.OpenCalls, 0)
for path, open := range opens {
flags := open.ToSlice()
sort.Strings(flags)
newProfileContainer.Opens = append(newProfileContainer.Opens, v1beta1.OpenCalls{
Path: path,
Flags: flags,
})
}
// insert application profile container
utils.InsertApplicationProfileContainer(newProfile, watchedContainer.ContainerType, watchedContainer.ContainerIndex, newProfileContainer)
// save application profile
if err := am.storageClient.CreateApplicationProfile(newProfile, namespace); err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to save application profile", helpers.Error(err))
}
logger.L().Debug("ApplicationProfileManager - saved application profile", helpers.String("slug", slug), helpers.String("container ID", watchedContainer.ContainerID), helpers.String("k8s workload", watchedContainer.K8sContainerID), helpers.Interface("profile", newProfile))
// profile summary
summary := &v1beta1.ApplicationProfileSummary{
ObjectMeta: newProfile.ObjectMeta,
}
if err := am.storageClient.CreateApplicationProfileSummary(summary, namespace); err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to save application profile summary", helpers.Error(err))
}
newProfileContainer := &v1beta1.ApplicationProfileContainer{
Name: watchedContainer.InstanceID.GetContainerName(),
}
// add capabilities
newProfileContainer.Capabilities = capabilities.ToSlice()
sort.Strings(newProfileContainer.Capabilities)
// add execs
newProfileContainer.Execs = make([]v1beta1.ExecCalls, 0)
for path, exec := range execs {
args := exec.ToSlice()
sort.Strings(args)
newProfileContainer.Execs = append(newProfileContainer.Execs, v1beta1.ExecCalls{
Path: path,
Args: args,
})
}
// add opens
newProfileContainer.Opens = make([]v1beta1.OpenCalls, 0)
for path, open := range opens {
flags := open.ToSlice()
sort.Strings(flags)
newProfileContainer.Opens = append(newProfileContainer.Opens, v1beta1.OpenCalls{
Path: path,
Flags: flags,
})
}
// insert application profile container
utils.InsertApplicationProfileContainer(newProfile, watchedContainer.ContainerType, watchedContainer.ContainerIndex, newProfileContainer)
// save application profile
if err := am.storageClient.CreateApplicationProfile(newProfile, namespace); err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to save application profile", helpers.Error(err))
}
logger.L().Debug("ApplicationProfileManager - saved application profile", helpers.String("slug", slug), helpers.String("container ID", watchedContainer.ContainerID), helpers.String("k8s workload", watchedContainer.K8sContainerID))
// profile summary
summary := &v1beta1.ApplicationProfileSummary{
ObjectMeta: newProfile.ObjectMeta,
}
if err := am.storageClient.CreateApplicationProfileSummary(summary, namespace); err != nil {
logger.L().Ctx(ctx).Error("ApplicationProfileManager - failed to save application profile summary", helpers.Error(err))
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,10 +68,10 @@ func TestApplicationProfileManager(t *testing.T) {
assert.Equal(t, 2, len(storageClient.ApplicationActivities))
sort.Strings(storageClient.ApplicationActivities[0].Spec.Syscalls)
assert.Equal(t, []string{"dup", "listen", "open"}, storageClient.ApplicationActivities[0].Spec.Syscalls)
assert.Equal(t, 2, len(storageClient.ApplicationProfiles))
assert.Equal(t, 1, len(storageClient.ApplicationProfiles))
sort.Strings(storageClient.ApplicationProfiles[0].Spec.Containers[0].Capabilities)
assert.Equal(t, []string{"NET_BIND_SERVICE", "NET_BROADCAST"}, storageClient.ApplicationProfiles[0].Spec.Containers[1].Capabilities)
assert.Equal(t, []v1beta1.ExecCalls{{Path: "/bin/bash", Args: []string{"-c", "ls"}, Envs: []string(nil)}}, storageClient.ApplicationProfiles[0].Spec.Containers[1].Execs)
assert.Equal(t, []v1beta1.OpenCalls{{Path: "/etc/passwd", Flags: []string{"O_RDONLY"}}}, storageClient.ApplicationProfiles[0].Spec.Containers[1].Opens)
assert.Equal(t, 2, len(storageClient.ApplicationProfileSummaries))
assert.Equal(t, 1, len(storageClient.ApplicationProfileSummaries))
}
17 changes: 10 additions & 7 deletions pkg/utils/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -138,31 +138,34 @@ func GetLabels(watchedContainer *WatchedContainerData, stripContainer bool) map[
return labels
}

func GetApplicationProfileContainer(profile *v1beta1.ApplicationProfile, containerType ContainerType, containerIndex int) v1beta1.ApplicationProfileContainer {
func GetApplicationProfileContainer(profile *v1beta1.ApplicationProfile, containerType ContainerType, containerIndex int) *v1beta1.ApplicationProfileContainer {
if profile == nil {
return nil
}
switch containerType {
case Container:
if len(profile.Spec.Containers) > containerIndex {
return profile.Spec.Containers[containerIndex]
return &profile.Spec.Containers[containerIndex]
}
case InitContainer:
if len(profile.Spec.InitContainers) > containerIndex {
return profile.Spec.InitContainers[containerIndex]
return &profile.Spec.InitContainers[containerIndex]
}
}
return v1beta1.ApplicationProfileContainer{}
return nil
}

func InsertApplicationProfileContainer(profile *v1beta1.ApplicationProfile, containerType ContainerType, containerIndex int, profileContainer v1beta1.ApplicationProfileContainer) {
func InsertApplicationProfileContainer(profile *v1beta1.ApplicationProfile, containerType ContainerType, containerIndex int, profileContainer *v1beta1.ApplicationProfileContainer) {
switch containerType {
case Container:
if len(profile.Spec.Containers) <= containerIndex {
profile.Spec.Containers = append(profile.Spec.Containers, make([]v1beta1.ApplicationProfileContainer, containerIndex-len(profile.Spec.Containers)+1)...)
}
profile.Spec.Containers[containerIndex] = profileContainer
profile.Spec.Containers[containerIndex] = *profileContainer
case InitContainer:
if len(profile.Spec.InitContainers) <= containerIndex {
profile.Spec.InitContainers = append(profile.Spec.InitContainers, make([]v1beta1.ApplicationProfileContainer, containerIndex-len(profile.Spec.InitContainers)+1)...)
}
profile.Spec.InitContainers[containerIndex] = profileContainer
profile.Spec.InitContainers[containerIndex] = *profileContainer
}
}

0 comments on commit d94a5b7

Please sign in to comment.