@@ -107,42 +107,14 @@ func Test_StandardSecurityPolicyEnforcer_From_Security_Policy_Conversion(t *test
107107 }
108108}
109109
110- // Do we correctly set up the data structures that are part of creating a new
111- // StandardSecurityPolicyEnforcer
112- func Test_StandardSecurityPolicyEnforcer_Devices_Initialization (t * testing.T ) {
113- f := func (p * generatedContainers ) bool {
114- policy := NewStandardSecurityPolicyEnforcer (p .containers , ignoredEncodedPolicyString )
115-
116- // there should be a device entry for each container
117- if len (p .containers ) != len (policy .Devices ) {
118- return false
119- }
120-
121- // in each device entry that corresponds to a container,
122- // the array should have space for all the root hashes
123- for i := 0 ; i < len (p .containers ); i ++ {
124- if len (p .containers [i ].Layers ) != len (policy .Devices [i ]) {
125- return false
126- }
127- }
128-
129- return true
130- }
131-
132- if err := quick .Check (f , & quick.Config {MaxCount : 1000 }); err != nil {
133- t .Errorf ("Test_StandardSecurityPolicyEnforcer_Devices_Initialization failed: %v" , err )
134- }
135- }
136-
137110// Verify that StandardSecurityPolicyEnforcer.EnforceDeviceMountPolicy will
138111// return an error when there's no matching root hash in the policy
139112func Test_EnforceDeviceMountPolicy_No_Matches (t * testing.T ) {
140113 f := func (p * generatedContainers ) bool {
141114 policy := NewStandardSecurityPolicyEnforcer (p .containers , ignoredEncodedPolicyString )
142115
143- r := rand .New (rand .NewSource (time .Now ().UnixNano ()))
144- target := generateMountTarget (r )
145- rootHash := generateInvalidRootHash (r )
116+ target := generateMountTarget (testRand )
117+ rootHash := generateInvalidRootHash (testRand )
146118
147119 err := policy .EnforceDeviceMountPolicy (target , rootHash )
148120
@@ -161,9 +133,8 @@ func Test_EnforceDeviceMountPolicy_Matches(t *testing.T) {
161133 f := func (p * generatedContainers ) bool {
162134 policy := NewStandardSecurityPolicyEnforcer (p .containers , ignoredEncodedPolicyString )
163135
164- r := rand .New (rand .NewSource (time .Now ().UnixNano ()))
165- target := generateMountTarget (r )
166- rootHash := selectRootHashFromContainers (p , r )
136+ target := generateMountTarget (testRand )
137+ rootHash := selectRootHashFromContainers (p , testRand )
167138
168139 err := policy .EnforceDeviceMountPolicy (target , rootHash )
169140
@@ -180,33 +151,16 @@ func Test_EnforceDeviceUmountPolicy_Removes_Device_Entries(t *testing.T) {
180151 f := func (p * generatedContainers ) bool {
181152 policy := NewStandardSecurityPolicyEnforcer (p .containers , ignoredEncodedPolicyString )
182153
183- r := rand .New (rand .NewSource (time .Now ().UnixNano ()))
184- target := generateMountTarget (r )
185- rootHash := selectRootHashFromContainers (p , r )
154+ target := generateMountTarget (testRand )
155+ rootHash := selectRootHashFromContainers (p , testRand )
186156
187157 err := policy .EnforceDeviceMountPolicy (target , rootHash )
188158 if err != nil {
189159 return false
190160 }
191161
192- // we set up an expected new data structure shape were
193- // the target has been removed, but everything else is
194- // the same
195- setupCorrectlyDone := false
196- expectedDevices := make ([][]string , len (policy .Devices ))
197- for i , container := range policy .Devices {
198- expectedDevices [i ] = make ([]string , len (container ))
199- for j , storedTarget := range container {
200- if target == storedTarget {
201- setupCorrectlyDone = true
202- } else {
203- expectedDevices [i ][j ] = storedTarget
204- }
205- }
206- }
207- if ! setupCorrectlyDone {
208- // somehow, setup failed. this should never happen without another test
209- // also failing
162+ if v , ok := policy .Devices [target ]; ! ok || v != rootHash {
163+ t .Errorf ("root hash is missing or doesn't match: actual=%q expected=%q" , v , rootHash )
210164 return false
211165 }
212166
@@ -215,7 +169,7 @@ func Test_EnforceDeviceUmountPolicy_Removes_Device_Entries(t *testing.T) {
215169 return false
216170 }
217171
218- return cmp .Equal (policy .Devices , expectedDevices )
172+ return cmp .Equal (policy .Devices , map [ string ] string {} )
219173 }
220174
221175 if err := quick .Check (f , & quick.Config {MaxCount : 1000 }); err != nil {
@@ -322,8 +276,6 @@ func Test_EnforceOverlayMountPolicy_Multiple_Instances_Same_Container(t *testing
322276 t .Fatalf ("failed with %d containers" , containersToCreate )
323277 }
324278 }
325-
326- t .Logf ("ok for %d\n " , containersToCreate )
327279 }
328280}
329281
@@ -421,7 +373,7 @@ func Test_EnforceCommandPolicy_NarrowingMatches(t *testing.T) {
421373 f := func (p * generatedContainers ) bool {
422374 // create two additional containers that "share everything"
423375 // except that they have different commands
424- testContainerOne := generateContainersContainer (testRand , 5 )
376+ testContainerOne := generateContainersContainer (testRand , 1 , 5 )
425377 testContainerTwo := * testContainerOne
426378 testContainerTwo .Command = generateCommand (testRand )
427379 // add new containers to policy before creating enforcer
@@ -535,7 +487,7 @@ func Test_EnforceEnvironmentVariablePolicy_Matches(t *testing.T) {
535487func Test_EnforceEnvironmentVariablePolicy_Re2Match (t * testing.T ) {
536488 p := generateContainers (testRand , 1 )
537489
538- container := generateContainersContainer (testRand , 1 )
490+ container := generateContainersContainer (testRand , 1 , 1 )
539491 // add a rule to re2 match
540492 re2MatchRule := EnvRuleConfig {
541493 Strategy : EnvVarRuleRegex ,
@@ -605,12 +557,11 @@ func Test_EnforceEnvironmentVariablePolicy_NotAllMatches(t *testing.T) {
605557// the container in our policy" functionality works correctly.
606558func Test_EnforceEnvironmentVariablePolicy_NarrowingMatches (t * testing.T ) {
607559 f := func (p * generatedContainers ) bool {
608- r := rand .New (rand .NewSource (time .Now ().UnixNano ()))
609560 // create two additional containers that "share everything"
610561 // except that they have different environment variables
611- testContainerOne := generateContainersContainer (r , 5 )
562+ testContainerOne := generateContainersContainer (testRand , 1 , 5 )
612563 testContainerTwo := * testContainerOne
613- testContainerTwo .EnvRules = generateEnvironmentVariableRules (r )
564+ testContainerTwo .EnvRules = generateEnvironmentVariableRules (testRand )
614565 // add new containers to policy before creating enforcer
615566 p .containers = append (p .containers , testContainerOne , & testContainerTwo )
616567
@@ -623,9 +574,9 @@ func Test_EnforceEnvironmentVariablePolicy_NarrowingMatches(t *testing.T) {
623574
624575 // mount and overlay all our containers
625576 for index , container := range p .containers {
626- containerID := generateContainerID (r )
577+ containerID := generateContainerID (testRand )
627578
628- layerPaths , err := createValidOverlayForContainer (policy , container , r )
579+ layerPaths , err := createValidOverlayForContainer (policy , container , testRand )
629580 if err != nil {
630581 return false
631582 }
@@ -668,7 +619,7 @@ func Test_EnforceEnvironmentVariablePolicy_NarrowingMatches(t *testing.T) {
668619
669620 // enforce command policy for containerOne
670621 // this will narrow our list of possible ids down
671- envVars := buildEnvironmentVariablesFromContainerRules (testContainerOne , r )
622+ envVars := buildEnvironmentVariablesFromContainerRules (testContainerOne , testRand )
672623 err := policy .enforceEnvironmentVariablePolicy (testContainerOneID , envVars )
673624 if err != nil {
674625 return false
@@ -738,6 +689,72 @@ func Test_WorkingDirectoryPolicy_NoMatches(t *testing.T) {
738689 }
739690}
740691
692+ // Consequent layers
693+ func Test_Overlay_Duplicate_Layers (t * testing.T ) {
694+ f := func (p * generatedContainers ) bool {
695+ c1 := generateContainersContainer (testRand , 5 , 5 )
696+ numLayers := len (c1 .Layers )
697+ // make sure first container has two identical layers
698+ c1 .Layers [numLayers - 3 ] = c1 .Layers [numLayers - 2 ]
699+
700+ policy := NewStandardSecurityPolicyEnforcer ([]* securityPolicyContainer {c1 }, ignoredEncodedPolicyString )
701+
702+ // generate mount targets
703+ mountTargets := make ([]string , numLayers )
704+ for i := 0 ; i < numLayers ; i ++ {
705+ mountTargets [i ] = randString (testRand , maxGeneratedMountTargetLength )
706+ }
707+
708+ // call into mount enforcement
709+ for i := 0 ; i < numLayers ; i ++ {
710+ if err := policy .EnforceDeviceMountPolicy (mountTargets [i ], c1 .Layers [i ]); err != nil {
711+ t .Errorf ("failed to enforce device mount policy: %s" , err )
712+ return false
713+ }
714+ }
715+
716+ if len (policy .Devices ) != numLayers {
717+ t .Errorf ("the number of mounted devices %v don't match the expectation: targets=%v layers=%v" ,
718+ policy .Devices , mountTargets , c1 .Layers )
719+ return false
720+ }
721+
722+ overlay := make ([]string , numLayers )
723+ for i := 0 ; i < numLayers ; i ++ {
724+ overlay [i ] = mountTargets [numLayers - i - 1 ]
725+ }
726+ containerID := randString (testRand , 32 )
727+ if err := policy .EnforceOverlayMountPolicy (containerID , overlay ); err != nil {
728+ t .Errorf ("failed to enforce overlay mount policy: %s" , err )
729+ return false
730+ }
731+
732+ // validate the state of the ContainerIndexToContainerIds mapping
733+ if containerIDs , ok := policy .ContainerIndexToContainerIds [0 ]; ! ok {
734+ t .Errorf ("container index to containerIDs mapping was not set: %v" , containerIDs )
735+ return false
736+ } else {
737+ if _ , ok := containerIDs [containerID ]; ! ok {
738+ t .Errorf ("containerID is missing from possible containerIDs set: %v" , containerIDs )
739+ return false
740+ }
741+ }
742+
743+ for _ , mountTarget := range mountTargets {
744+ if err := policy .EnforceDeviceUnmountPolicy (mountTarget ); err != nil {
745+ t .Errorf ("failed to enforce unmount policy: %s" , err )
746+ return false
747+ }
748+ }
749+
750+ return true
751+ }
752+
753+ if err := quick .Check (f , & quick.Config {MaxCount : 1 }); err != nil {
754+ t .Errorf ("failed to run stuff: %s" , err )
755+ }
756+ }
757+
741758//
742759// Setup and "fixtures" follow...
743760//
@@ -844,21 +861,21 @@ func generateContainers(r *rand.Rand, upTo int32) *generatedContainers {
844861
845862 numContainers := (int )(atLeastOneAtMost (r , upTo ))
846863 for i := 0 ; i < numContainers ; i ++ {
847- containers = append (containers , generateContainersContainer (r , maxLayersInGeneratedContainer ))
864+ containers = append (containers , generateContainersContainer (r , 1 , maxLayersInGeneratedContainer ))
848865 }
849866
850867 return & generatedContainers {
851868 containers : containers ,
852869 }
853870}
854871
855- func generateContainersContainer (r * rand.Rand , size int32 ) * securityPolicyContainer {
872+ func generateContainersContainer (r * rand.Rand , minNumberOfLayers , maxNumberOfLayers int32 ) * securityPolicyContainer {
856873 c := securityPolicyContainer {}
857874 c .Command = generateCommand (r )
858875 c .EnvRules = generateEnvironmentVariableRules (r )
859876 c .WorkingDir = randVariableString (r , maxGeneratedCommandLength )
860- layers := int (atLeastOneAtMost (r , size ))
861- for i := 0 ; i < layers ; i ++ {
877+ numLayers := int (atLeastNAtMostM (r , minNumberOfLayers , maxNumberOfLayers ))
878+ for i := 0 ; i < numLayers ; i ++ {
862879 c .Layers = append (c .Layers , generateRootHash (r ))
863880 }
864881
@@ -1072,21 +1089,27 @@ func randVariableString(r *rand.Rand, maxLen int32) string {
10721089 return randString (r , atLeastOneAtMost (r , maxLen ))
10731090}
10741091
1075- func randString (r * rand.Rand , len int32 ) string {
1076- var s strings.Builder
1077- for i := 0 ; i < (int )(len ); i ++ {
1078- s .WriteRune (0x00ff & r .Int31n (256 ))
1092+ func randString (r * rand.Rand , length int32 ) string {
1093+ charset := "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
1094+ sb := strings.Builder {}
1095+ sb .Grow (int (length ))
1096+ for i := 0 ; i < (int )(length ); i ++ {
1097+ sb .WriteByte (charset [r .Intn (len (charset ))])
10791098 }
10801099
1081- return s .String ()
1100+ return sb .String ()
10821101}
10831102
10841103func randMinMax (r * rand.Rand , min int32 , max int32 ) int32 {
10851104 return r .Int31n (max - min + 1 ) + min
10861105}
10871106
1107+ func atLeastNAtMostM (r * rand.Rand , min , max int32 ) int32 {
1108+ return randMinMax (r , min , max )
1109+ }
1110+
10881111func atLeastOneAtMost (r * rand.Rand , most int32 ) int32 {
1089- return randMinMax (r , 1 , most )
1112+ return atLeastNAtMostM (r , 1 , most )
10901113}
10911114
10921115func atMost (r * rand.Rand , most int32 ) int32 {
0 commit comments