@@ -3,7 +3,9 @@ package verification
3
3
import (
4
4
"context"
5
5
"crypto/x509"
6
+ "errors"
6
7
"fmt"
8
+ "regexp"
7
9
"strings"
8
10
"time"
9
11
@@ -13,6 +15,10 @@ import (
13
15
"github.com/notaryproject/notation-go/registry"
14
16
)
15
17
18
+ var errExtendedAttributeNotExist = errors .New ("Extended attribute not exist" )
19
+
20
+ var semVerRegEx = regexp .MustCompile ("^(0|[1-9]\\ d*)\\ .(0|[1-9]\\ d*)\\ .(0|[1-9]\\ d*)(?:-((?:0|[1-9]\\ d*|\\ d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\\ .(?:0|[1-9]\\ d*|\\ d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\\ +([0-9a-zA-Z-]+(?:\\ .[0-9a-zA-Z-]+)*))?$" )
21
+
16
22
// isCriticalFailure checks whether a VerificationResult fails the entire signature verification workflow.
17
23
// signature verification workflow is considered failed if there is a VerificationResult with "Enforced" as the action but the result was unsuccessful
18
24
func isCriticalFailure (result * VerificationResult ) bool {
@@ -235,7 +241,10 @@ func verifyX509TrustedIdentities(certs []*x509.Certificate, trustPolicy *TrustPo
235
241
}
236
242
237
243
func (v * Verifier ) executePlugin (ctx context.Context , trustPolicy * TrustPolicy , capabilitiesToVerify []plugin.VerificationCapability , signerInfo * signature.SignerInfo , payloadInfo * signature.Payload ) (* plugin.VerifySignatureResponse , error ) {
238
- verificationPluginName := GetVerificationPlugin (signerInfo )
244
+ verificationPluginName , err := getVerificationPlugin (signerInfo )
245
+ if err != nil {
246
+ return nil , err
247
+ }
239
248
var attributesToProcess []string
240
249
extendedAttributes := make (map [string ]interface {})
241
250
@@ -298,20 +307,49 @@ func (v *Verifier) executePlugin(ctx context.Context, trustPolicy *TrustPolicy,
298
307
return response , nil
299
308
}
300
309
301
- func GetVerificationPlugin (signerInfo * signature.SignerInfo ) string {
302
- if verificationPlugin , err := signerInfo .ExtendedAttribute (VerificationPlugin ); err == nil {
303
- if name , ok := verificationPlugin .Value .(string ); ok {
304
- return name
305
- }
310
+ // extractCriticalStringExtendedAttribute extracts a critical string Extended attribute from a signer
311
+ func extractCriticalStringExtendedAttribute (signerInfo * signature.SignerInfo , key string ) (string , error ) {
312
+ attr , err := signerInfo .ExtendedAttribute (key )
313
+ // not exist
314
+ if err != nil {
315
+ return "" , errExtendedAttributeNotExist
316
+ }
317
+ // not critical
318
+ if ! attr .Critical {
319
+ return "" , fmt .Errorf ("%v is not a critical Extended attribute" , key )
320
+ }
321
+ // not string
322
+ val , ok := attr .Value .(string )
323
+ if ! ok {
324
+ return "" , fmt .Errorf ("%v from Extended attribute is not a string" , key )
306
325
}
307
- return ""
326
+ return val , nil
308
327
}
309
328
310
- func GetVerificationPluginMinVersion (signerInfo * signature.SignerInfo ) string {
311
- if verificationPluginVersion , err := signerInfo .ExtendedAttribute (VerificationPluginMinVersion ); err == nil {
312
- if version , ok := verificationPluginVersion .Value .(string ); ok {
313
- return version
314
- }
329
+ // getVerificationPlugin get plugin name from the Extended attributes
330
+ func getVerificationPlugin (signerInfo * signature.SignerInfo ) (string , error ) {
331
+ name , err := extractCriticalStringExtendedAttribute (signerInfo , VerificationPlugin )
332
+ if err != nil {
333
+ return "" , err
334
+ }
335
+ // not an empty string
336
+ if strings .TrimSpace (name ) == "" {
337
+ return "" , fmt .Errorf ("%v from Extended attribute is an empty string" , VerificationPlugin )
338
+ }
339
+ return name , nil
340
+ }
341
+
342
+ func getVerificationPluginMinVersion (signerInfo * signature.SignerInfo ) (string , error ) {
343
+ version , err := extractCriticalStringExtendedAttribute (signerInfo , VerificationPluginMinVersion )
344
+ if err != nil {
345
+ return "" , err
346
+ }
347
+ // empty version
348
+ if strings .TrimSpace (version ) == "" {
349
+ return "" , fmt .Errorf ("%v from Extended attribute is an empty string" , VerificationPluginMinVersion )
350
+ }
351
+ if ! semVerRegEx .MatchString (version ) {
352
+ return "" , fmt .Errorf ("%v from Extended attribute is not a is not valid SemVer" , VerificationPluginMinVersion )
315
353
}
316
- return ""
354
+ return version , nil
317
355
}
0 commit comments