1// Copyright 2017 The Go Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style 3// license that can be found in the LICENSE file. 4 5//go:build boringcrypto 6 7package tls 8 9import ( 10 "crypto/ecdsa" 11 "crypto/elliptic" 12 "crypto/internal/boring/fipstls" 13 "crypto/rand" 14 "crypto/rsa" 15 "crypto/x509" 16 "crypto/x509/pkix" 17 "encoding/pem" 18 "fmt" 19 "internal/obscuretestdata" 20 "math/big" 21 "net" 22 "runtime" 23 "strings" 24 "testing" 25 "time" 26) 27 28func TestBoringServerProtocolVersion(t *testing.T) { 29 test := func(t *testing.T, name string, v uint16, msg string) { 30 t.Run(name, func(t *testing.T) { 31 serverConfig := testConfig.Clone() 32 serverConfig.MinVersion = VersionSSL30 33 clientConfig := testConfig.Clone() 34 clientConfig.MinVersion = v 35 clientConfig.MaxVersion = v 36 _, _, err := testHandshake(t, clientConfig, serverConfig) 37 if msg == "" { 38 if err != nil { 39 t.Fatalf("got error: %v, expected success", err) 40 } 41 } else { 42 if err == nil { 43 t.Fatalf("got success, expected error") 44 } 45 if !strings.Contains(err.Error(), msg) { 46 t.Fatalf("got error %v, expected %q", err, msg) 47 } 48 } 49 }) 50 } 51 52 test(t, "VersionTLS10", VersionTLS10, "") 53 test(t, "VersionTLS11", VersionTLS11, "") 54 test(t, "VersionTLS12", VersionTLS12, "") 55 test(t, "VersionTLS13", VersionTLS13, "") 56 57 t.Run("fipstls", func(t *testing.T) { 58 fipstls.Force() 59 defer fipstls.Abandon() 60 test(t, "VersionTLS10", VersionTLS10, "supported versions") 61 test(t, "VersionTLS11", VersionTLS11, "supported versions") 62 test(t, "VersionTLS12", VersionTLS12, "") 63 test(t, "VersionTLS13", VersionTLS13, "supported versions") 64 }) 65} 66 67func isBoringVersion(v uint16) bool { 68 return v == VersionTLS12 69} 70 71func isBoringCipherSuite(id uint16) bool { 72 switch id { 73 case TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 74 TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, 75 TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 76 TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384, 77 TLS_RSA_WITH_AES_128_GCM_SHA256, 78 TLS_RSA_WITH_AES_256_GCM_SHA384: 79 return true 80 } 81 return false 82} 83 84func isBoringCurve(id CurveID) bool { 85 switch id { 86 case CurveP256, CurveP384, CurveP521: 87 return true 88 } 89 return false 90} 91 92func isECDSA(id uint16) bool { 93 for _, suite := range cipherSuites { 94 if suite.id == id { 95 return suite.flags&suiteECSign == suiteECSign 96 } 97 } 98 panic(fmt.Sprintf("unknown cipher suite %#x", id)) 99} 100 101func isBoringSignatureScheme(alg SignatureScheme) bool { 102 switch alg { 103 default: 104 return false 105 case PKCS1WithSHA256, 106 ECDSAWithP256AndSHA256, 107 PKCS1WithSHA384, 108 ECDSAWithP384AndSHA384, 109 PKCS1WithSHA512, 110 ECDSAWithP521AndSHA512, 111 PSSWithSHA256, 112 PSSWithSHA384, 113 PSSWithSHA512: 114 // ok 115 } 116 return true 117} 118 119func TestBoringServerCipherSuites(t *testing.T) { 120 serverConfig := testConfig.Clone() 121 serverConfig.CipherSuites = allCipherSuites() 122 serverConfig.Certificates = make([]Certificate, 1) 123 124 for _, id := range allCipherSuites() { 125 if isECDSA(id) { 126 serverConfig.Certificates[0].Certificate = [][]byte{testECDSACertificate} 127 serverConfig.Certificates[0].PrivateKey = testECDSAPrivateKey 128 } else { 129 serverConfig.Certificates[0].Certificate = [][]byte{testRSACertificate} 130 serverConfig.Certificates[0].PrivateKey = testRSAPrivateKey 131 } 132 serverConfig.BuildNameToCertificate() 133 t.Run(fmt.Sprintf("suite=%#x", id), func(t *testing.T) { 134 clientHello := &clientHelloMsg{ 135 vers: VersionTLS12, 136 random: make([]byte, 32), 137 cipherSuites: []uint16{id}, 138 compressionMethods: []uint8{compressionNone}, 139 supportedCurves: defaultCurvePreferences(), 140 supportedPoints: []uint8{pointFormatUncompressed}, 141 } 142 143 testClientHello(t, serverConfig, clientHello) 144 t.Run("fipstls", func(t *testing.T) { 145 fipstls.Force() 146 defer fipstls.Abandon() 147 msg := "" 148 if !isBoringCipherSuite(id) { 149 msg = "no cipher suite supported by both client and server" 150 } 151 testClientHelloFailure(t, serverConfig, clientHello, msg) 152 }) 153 }) 154 } 155} 156 157func TestBoringServerCurves(t *testing.T) { 158 serverConfig := testConfig.Clone() 159 serverConfig.Certificates = make([]Certificate, 1) 160 serverConfig.Certificates[0].Certificate = [][]byte{testECDSACertificate} 161 serverConfig.Certificates[0].PrivateKey = testECDSAPrivateKey 162 serverConfig.BuildNameToCertificate() 163 164 for _, curveid := range defaultCurvePreferences() { 165 t.Run(fmt.Sprintf("curve=%d", curveid), func(t *testing.T) { 166 clientConfig := testConfig.Clone() 167 clientConfig.CurvePreferences = []CurveID{curveid} 168 if curveid == x25519Kyber768Draft00 { 169 // x25519Kyber768Draft00 is not supported standalone. 170 clientConfig.CurvePreferences = append(clientConfig.CurvePreferences, X25519) 171 } 172 if _, _, err := testHandshake(t, clientConfig, serverConfig); err != nil { 173 t.Fatalf("got error: %v, expected success", err) 174 } 175 176 // With fipstls forced, bad curves should be rejected. 177 t.Run("fipstls", func(t *testing.T) { 178 fipstls.Force() 179 defer fipstls.Abandon() 180 _, _, err := testHandshake(t, clientConfig, serverConfig) 181 if err != nil && isBoringCurve(curveid) { 182 t.Fatalf("got error: %v, expected success", err) 183 } else if err == nil && !isBoringCurve(curveid) { 184 t.Fatalf("got success, expected error") 185 } 186 }) 187 }) 188 } 189} 190 191func boringHandshake(t *testing.T, clientConfig, serverConfig *Config) (clientErr, serverErr error) { 192 c, s := localPipe(t) 193 client := Client(c, clientConfig) 194 server := Server(s, serverConfig) 195 done := make(chan error, 1) 196 go func() { 197 done <- client.Handshake() 198 c.Close() 199 }() 200 serverErr = server.Handshake() 201 s.Close() 202 clientErr = <-done 203 return 204} 205 206func TestBoringServerSignatureAndHash(t *testing.T) { 207 defer func() { 208 testingOnlyForceClientHelloSignatureAlgorithms = nil 209 }() 210 211 for _, sigHash := range defaultSupportedSignatureAlgorithms { 212 t.Run(fmt.Sprintf("%v", sigHash), func(t *testing.T) { 213 serverConfig := testConfig.Clone() 214 serverConfig.Certificates = make([]Certificate, 1) 215 216 testingOnlyForceClientHelloSignatureAlgorithms = []SignatureScheme{sigHash} 217 218 sigType, _, _ := typeAndHashFromSignatureScheme(sigHash) 219 switch sigType { 220 case signaturePKCS1v15, signatureRSAPSS: 221 serverConfig.CipherSuites = []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256} 222 serverConfig.Certificates[0].Certificate = [][]byte{testRSA2048Certificate} 223 serverConfig.Certificates[0].PrivateKey = testRSA2048PrivateKey 224 case signatureEd25519: 225 serverConfig.CipherSuites = []uint16{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256} 226 serverConfig.Certificates[0].Certificate = [][]byte{testEd25519Certificate} 227 serverConfig.Certificates[0].PrivateKey = testEd25519PrivateKey 228 case signatureECDSA: 229 serverConfig.CipherSuites = []uint16{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256} 230 serverConfig.Certificates[0].Certificate = [][]byte{testECDSACertificate} 231 serverConfig.Certificates[0].PrivateKey = testECDSAPrivateKey 232 } 233 serverConfig.BuildNameToCertificate() 234 // PKCS#1 v1.5 signature algorithms can't be used standalone in TLS 235 // 1.3, and the ECDSA ones bind to the curve used. 236 serverConfig.MaxVersion = VersionTLS12 237 238 clientErr, serverErr := boringHandshake(t, testConfig, serverConfig) 239 if clientErr != nil { 240 t.Fatalf("expected handshake with %#x to succeed; client error: %v; server error: %v", sigHash, clientErr, serverErr) 241 } 242 243 // With fipstls forced, bad curves should be rejected. 244 t.Run("fipstls", func(t *testing.T) { 245 fipstls.Force() 246 defer fipstls.Abandon() 247 clientErr, _ := boringHandshake(t, testConfig, serverConfig) 248 if isBoringSignatureScheme(sigHash) { 249 if clientErr != nil { 250 t.Fatalf("expected handshake with %#x to succeed; err=%v", sigHash, clientErr) 251 } 252 } else { 253 if clientErr == nil { 254 t.Fatalf("expected handshake with %#x to fail, but it succeeded", sigHash) 255 } 256 } 257 }) 258 }) 259 } 260} 261 262func TestBoringClientHello(t *testing.T) { 263 // Test that no matter what we put in the client config, 264 // the client does not offer non-FIPS configurations. 265 fipstls.Force() 266 defer fipstls.Abandon() 267 268 c, s := net.Pipe() 269 defer c.Close() 270 defer s.Close() 271 272 clientConfig := testConfig.Clone() 273 // All sorts of traps for the client to avoid. 274 clientConfig.MinVersion = VersionSSL30 275 clientConfig.MaxVersion = VersionTLS13 276 clientConfig.CipherSuites = allCipherSuites() 277 clientConfig.CurvePreferences = defaultCurvePreferences() 278 279 go Client(c, clientConfig).Handshake() 280 srv := Server(s, testConfig) 281 msg, err := srv.readHandshake(nil) 282 if err != nil { 283 t.Fatal(err) 284 } 285 hello, ok := msg.(*clientHelloMsg) 286 if !ok { 287 t.Fatalf("unexpected message type %T", msg) 288 } 289 290 if !isBoringVersion(hello.vers) { 291 t.Errorf("client vers=%#x, want %#x (TLS 1.2)", hello.vers, VersionTLS12) 292 } 293 for _, v := range hello.supportedVersions { 294 if !isBoringVersion(v) { 295 t.Errorf("client offered disallowed version %#x", v) 296 } 297 } 298 for _, id := range hello.cipherSuites { 299 if !isBoringCipherSuite(id) { 300 t.Errorf("client offered disallowed suite %#x", id) 301 } 302 } 303 for _, id := range hello.supportedCurves { 304 if !isBoringCurve(id) { 305 t.Errorf("client offered disallowed curve %d", id) 306 } 307 } 308 for _, sigHash := range hello.supportedSignatureAlgorithms { 309 if !isBoringSignatureScheme(sigHash) { 310 t.Errorf("client offered disallowed signature-and-hash %v", sigHash) 311 } 312 } 313} 314 315func TestBoringCertAlgs(t *testing.T) { 316 // NaCl, arm and wasm time out generating keys. Nothing in this test is architecture-specific, so just don't bother on those. 317 if runtime.GOOS == "nacl" || runtime.GOARCH == "arm" || runtime.GOOS == "js" { 318 t.Skipf("skipping on %s/%s because key generation takes too long", runtime.GOOS, runtime.GOARCH) 319 } 320 321 // Set up some roots, intermediate CAs, and leaf certs with various algorithms. 322 // X_Y is X signed by Y. 323 R1 := boringCert(t, "R1", boringRSAKey(t, 2048), nil, boringCertCA|boringCertFIPSOK) 324 R2 := boringCert(t, "R2", boringRSAKey(t, 512), nil, boringCertCA) 325 326 M1_R1 := boringCert(t, "M1_R1", boringECDSAKey(t, elliptic.P256()), R1, boringCertCA|boringCertFIPSOK) 327 M2_R1 := boringCert(t, "M2_R1", boringECDSAKey(t, elliptic.P224()), R1, boringCertCA) 328 329 I_R1 := boringCert(t, "I_R1", boringRSAKey(t, 3072), R1, boringCertCA|boringCertFIPSOK) 330 I_R2 := boringCert(t, "I_R2", I_R1.key, R2, boringCertCA|boringCertFIPSOK) 331 I_M1 := boringCert(t, "I_M1", I_R1.key, M1_R1, boringCertCA|boringCertFIPSOK) 332 I_M2 := boringCert(t, "I_M2", I_R1.key, M2_R1, boringCertCA|boringCertFIPSOK) 333 334 L1_I := boringCert(t, "L1_I", boringECDSAKey(t, elliptic.P384()), I_R1, boringCertLeaf|boringCertFIPSOK) 335 L2_I := boringCert(t, "L2_I", boringRSAKey(t, 1024), I_R1, boringCertLeaf) 336 337 // client verifying server cert 338 testServerCert := func(t *testing.T, desc string, pool *x509.CertPool, key interface{}, list [][]byte, ok bool) { 339 clientConfig := testConfig.Clone() 340 clientConfig.RootCAs = pool 341 clientConfig.InsecureSkipVerify = false 342 clientConfig.ServerName = "example.com" 343 344 serverConfig := testConfig.Clone() 345 serverConfig.Certificates = []Certificate{{Certificate: list, PrivateKey: key}} 346 serverConfig.BuildNameToCertificate() 347 348 clientErr, _ := boringHandshake(t, clientConfig, serverConfig) 349 350 if (clientErr == nil) == ok { 351 if ok { 352 t.Logf("%s: accept", desc) 353 } else { 354 t.Logf("%s: reject", desc) 355 } 356 } else { 357 if ok { 358 t.Errorf("%s: BAD reject (%v)", desc, clientErr) 359 } else { 360 t.Errorf("%s: BAD accept", desc) 361 } 362 } 363 } 364 365 // server verifying client cert 366 testClientCert := func(t *testing.T, desc string, pool *x509.CertPool, key interface{}, list [][]byte, ok bool) { 367 clientConfig := testConfig.Clone() 368 clientConfig.ServerName = "example.com" 369 clientConfig.Certificates = []Certificate{{Certificate: list, PrivateKey: key}} 370 371 serverConfig := testConfig.Clone() 372 serverConfig.ClientCAs = pool 373 serverConfig.ClientAuth = RequireAndVerifyClientCert 374 375 _, serverErr := boringHandshake(t, clientConfig, serverConfig) 376 377 if (serverErr == nil) == ok { 378 if ok { 379 t.Logf("%s: accept", desc) 380 } else { 381 t.Logf("%s: reject", desc) 382 } 383 } else { 384 if ok { 385 t.Errorf("%s: BAD reject (%v)", desc, serverErr) 386 } else { 387 t.Errorf("%s: BAD accept", desc) 388 } 389 } 390 } 391 392 // Run simple basic test with known answers before proceeding to 393 // exhaustive test with computed answers. 394 r1pool := x509.NewCertPool() 395 r1pool.AddCert(R1.cert) 396 testServerCert(t, "basic", r1pool, L2_I.key, [][]byte{L2_I.der, I_R1.der}, true) 397 testClientCert(t, "basic (client cert)", r1pool, L2_I.key, [][]byte{L2_I.der, I_R1.der}, true) 398 fipstls.Force() 399 testServerCert(t, "basic (fips)", r1pool, L2_I.key, [][]byte{L2_I.der, I_R1.der}, false) 400 testClientCert(t, "basic (fips, client cert)", r1pool, L2_I.key, [][]byte{L2_I.der, I_R1.der}, false) 401 fipstls.Abandon() 402 403 if t.Failed() { 404 t.Fatal("basic test failed, skipping exhaustive test") 405 } 406 407 if testing.Short() { 408 t.Logf("basic test passed; skipping exhaustive test in -short mode") 409 return 410 } 411 412 for l := 1; l <= 2; l++ { 413 leaf := L1_I 414 if l == 2 { 415 leaf = L2_I 416 } 417 for i := 0; i < 64; i++ { 418 reachable := map[string]bool{leaf.parentOrg: true} 419 reachableFIPS := map[string]bool{leaf.parentOrg: leaf.fipsOK} 420 list := [][]byte{leaf.der} 421 listName := leaf.name 422 addList := func(cond int, c *boringCertificate) { 423 if cond != 0 { 424 list = append(list, c.der) 425 listName += "," + c.name 426 if reachable[c.org] { 427 reachable[c.parentOrg] = true 428 } 429 if reachableFIPS[c.org] && c.fipsOK { 430 reachableFIPS[c.parentOrg] = true 431 } 432 } 433 } 434 addList(i&1, I_R1) 435 addList(i&2, I_R2) 436 addList(i&4, I_M1) 437 addList(i&8, I_M2) 438 addList(i&16, M1_R1) 439 addList(i&32, M2_R1) 440 441 for r := 1; r <= 3; r++ { 442 pool := x509.NewCertPool() 443 rootName := "," 444 shouldVerify := false 445 shouldVerifyFIPS := false 446 addRoot := func(cond int, c *boringCertificate) { 447 if cond != 0 { 448 rootName += "," + c.name 449 pool.AddCert(c.cert) 450 if reachable[c.org] { 451 shouldVerify = true 452 } 453 if reachableFIPS[c.org] && c.fipsOK { 454 shouldVerifyFIPS = true 455 } 456 } 457 } 458 addRoot(r&1, R1) 459 addRoot(r&2, R2) 460 rootName = rootName[1:] // strip leading comma 461 testServerCert(t, listName+"->"+rootName[1:], pool, leaf.key, list, shouldVerify) 462 testClientCert(t, listName+"->"+rootName[1:]+"(client cert)", pool, leaf.key, list, shouldVerify) 463 fipstls.Force() 464 testServerCert(t, listName+"->"+rootName[1:]+" (fips)", pool, leaf.key, list, shouldVerifyFIPS) 465 testClientCert(t, listName+"->"+rootName[1:]+" (fips, client cert)", pool, leaf.key, list, shouldVerifyFIPS) 466 fipstls.Abandon() 467 } 468 } 469 } 470} 471 472const ( 473 boringCertCA = iota 474 boringCertLeaf 475 boringCertFIPSOK = 0x80 476) 477 478func boringRSAKey(t *testing.T, size int) *rsa.PrivateKey { 479 k, err := rsa.GenerateKey(rand.Reader, size) 480 if err != nil { 481 t.Fatal(err) 482 } 483 return k 484} 485 486func boringECDSAKey(t *testing.T, curve elliptic.Curve) *ecdsa.PrivateKey { 487 k, err := ecdsa.GenerateKey(curve, rand.Reader) 488 if err != nil { 489 t.Fatal(err) 490 } 491 return k 492} 493 494type boringCertificate struct { 495 name string 496 org string 497 parentOrg string 498 der []byte 499 cert *x509.Certificate 500 key interface{} 501 fipsOK bool 502} 503 504func boringCert(t *testing.T, name string, key interface{}, parent *boringCertificate, mode int) *boringCertificate { 505 org := name 506 parentOrg := "" 507 if i := strings.Index(org, "_"); i >= 0 { 508 org = org[:i] 509 parentOrg = name[i+1:] 510 } 511 tmpl := &x509.Certificate{ 512 SerialNumber: big.NewInt(1), 513 Subject: pkix.Name{ 514 Organization: []string{org}, 515 }, 516 NotBefore: time.Unix(0, 0), 517 NotAfter: time.Unix(0, 0), 518 519 KeyUsage: x509.KeyUsageKeyEncipherment | x509.KeyUsageDigitalSignature, 520 ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth, x509.ExtKeyUsageClientAuth}, 521 BasicConstraintsValid: true, 522 } 523 if mode&^boringCertFIPSOK == boringCertLeaf { 524 tmpl.DNSNames = []string{"example.com"} 525 } else { 526 tmpl.IsCA = true 527 tmpl.KeyUsage |= x509.KeyUsageCertSign 528 } 529 530 var pcert *x509.Certificate 531 var pkey interface{} 532 if parent != nil { 533 pcert = parent.cert 534 pkey = parent.key 535 } else { 536 pcert = tmpl 537 pkey = key 538 } 539 540 var pub interface{} 541 switch k := key.(type) { 542 case *rsa.PrivateKey: 543 pub = &k.PublicKey 544 case *ecdsa.PrivateKey: 545 pub = &k.PublicKey 546 default: 547 t.Fatalf("invalid key %T", key) 548 } 549 550 der, err := x509.CreateCertificate(rand.Reader, tmpl, pcert, pub, pkey) 551 if err != nil { 552 t.Fatal(err) 553 } 554 cert, err := x509.ParseCertificate(der) 555 if err != nil { 556 t.Fatal(err) 557 } 558 559 fipsOK := mode&boringCertFIPSOK != 0 560 return &boringCertificate{name, org, parentOrg, der, cert, key, fipsOK} 561} 562 563// A self-signed test certificate with an RSA key of size 2048, for testing 564// RSA-PSS with SHA512. SAN of example.golang. 565var ( 566 testRSA2048Certificate []byte 567 testRSA2048PrivateKey *rsa.PrivateKey 568) 569 570func init() { 571 block, _ := pem.Decode(obscuretestdata.Rot13([]byte(` 572-----ORTVA PREGVSVPNGR----- 573ZVVP/mPPNrrtNjVONtVENYUUK/xu4+4mZH9QnemORpDjQDLWXbMVuipANDRYODNj 574RwRDZN4TN1HRPuZUDJAgMFOQomNrSj0kZGNkZQRkAGN0ZQInSj0lZQRlZwxkAGN0 575ZQInZOVkRQNBOtAIONbGO0SwoJHtD28jttRvZN0TPFdTFVo3QDRONDHNN4VOQjNj 576ttRXNbVONDPs8sx0A6vrPOK4VBIVsXvgg4xTpBDYrvzPsfwddUplfZVITRgSFZ6R 5774Nl141s/7VdqJ0HgVdAo4CKuEBVQ7lQkE284kY6KoPhi/g5uC3HpruLp3uzYvlIq 578ZxMDvMJgsHHWs/1dBgZ+buAt59YEJc4q+6vK0yn1WY3RjPVpxxAwW9uDoS7Co2PF 579+RF9Lb55XNnc8XBoycpE8ZOFA38odajwsDqPKiBRBwnz2UHkXmRSK5ZN+sN0zr4P 580vbPpPEYJXy+TbA9S8sNOsbM+G+2rny4QYhB95eKE8FeBVIOu3KSBe/EIuwgKpAIS 581MXpiQg6q68I6wNXNLXz5ayw9TCcq4i+eNtZONNTwHQOBZN4TN1HqQjRO/jDRNjVS 582bQNGOtAIUFHRQQNXOtteOtRSODpQNGNZOtAIUEZONs8RNwNNZOxTN1HqRDDFZOPP 583QzI4LJ1joTHhM29fLJ5aZN0TPFdTFVo3QDROPjHNN4VONDPBbLfIpSPOuobdr3JU 584qP6I7KKKRPzawu01e8u80li0AE379aFQ3pj2Z+UXinKlfJdey5uwTIXj0igjQ81e 585I4WmQh7VsVbt5z8+DAP+7YdQMfm88iQXBefblFIBzHPtzPXSKrj+YN+rB/vDRWGe 5867rafqqBrKWRc27Rq5iJ+xzJJ3Dztyp2Tjl8jSeZQVdaeaBmON4bPaQRtgKWg0mbt 587aEjosRZNJv1nDEl5qG9XN3FC9zb5FrGSFmTTUvR4f4tUHr7wifNSS2dtgQ6+jU6f 588m9o6fukaP7t5VyOXuV7FIO/Hdg2lqW+xU1LowZpVd6ANZ5rAZXtMhWe3+mjfFtju 589TAnR 590-----RAQ PREGVSVPNGR-----`))) 591 testRSA2048Certificate = block.Bytes 592 593 block, _ = pem.Decode(obscuretestdata.Rot13([]byte(` 594-----ORTVA EFN CEVINGR XRL----- 595ZVVRcNVONNXPNDRNa/U5AQrbattI+PQyFUlbeorWOaQxP3bcta7V6du3ZeQPSEuY 596EHwBuBNZgrAK/+lXaIgSYFXwJ+Q14HGvN+8t8HqiBZF+y2jee/7rLG91UUbJUA4M 597v4fyKGWTHVzIeK1SPK/9nweGCdVGLBsF0IdrUshby9WJgFF9kZNvUWWQLlsLHTkr 598m29txiuRiJXBrFtTdsPwz5nKRsQNHwq/T6c8V30UDy7muQb2cgu1ZFfkOI+GNCaj 599AWahNbdNaNxF1vcsudQsEsUjNK6Tsx/gazcrNl7wirn10sRdmvSDLq1kGd/0ILL7 600I3QIEJFaYj7rariSrbjPtTPchM5L/Ew6KrY/djVQNDNONbVONDPAcZMvsq/it42u 601UqPiYhMnLF0E7FhaSycbKRfygTqYSfac0VsbWM/htSDOFNVVsYjZhzH6bKN1m7Hi 60298nVLI61QrCeGPQIQSOfUoAzC8WNb8JgohfRojq5mlbO7YLT2+pyxWxyJR73XdHd 603ezV+HWrlFpy2Tva7MGkOKm1JCOx9IjpajxrnKctNFVOJ23suRPZ9taLRRjnOrm5G 6046Zr8q1gUgLDi7ifXr7eb9j9/UXeEKrwdLXX1YkxusSevlI+z8YMWMa2aKBn6T3tS 605Ao8Dx1Hx5CHORAOzlZSWuG4Z/hhFd4LgZeeB2tv8D+sCuhTmp5FfuLXEOc0J4C5e 606zgIPgRSENbTONZRAOVSYeI2+UfTw0kLSnfXbi/DCr6UFGE1Uu2VMBAc+bX4bfmJR 607wOG4IpaVGzcy6gP1Jl4TpekwAtXVSMNw+1k1YHHYqbeKxhT8le0gNuT9mAlsJfFl 608CeFbiP0HIome8Wkkyn+xDIkRDDdJDkCyRIhY8xKnVQN6Ylg1Uchn2YiCNbTONADM 609p6Yd2G7+OkYkAqv2z8xMmrw5xtmOc/KqIfoSJEyroVK2XeSUfeUmG9CHx3QR1iMX 610Z6cmGg94aDuJFxQtPnj1FbuRyW3USVSjphfS1FWNp3cDrcq8ht6VLqycQZYgOw/C 611/5C6OIHgtb05R4+V/G3vLngztyDkGgyM0ExFI2yyNbTONYBKxXSK7nuCis0JxfQu 612hGshSBGCbbjtDT0RctJ0jEqPkrt/WYvp3yFQ0tfggDI2JfErpelJpknryEt10EzB 61338OobtzunS4kitfFihwBsvMGR8bX1G43Z+6AXfVyZY3LVYocH/9nWkCJl0f2QdQe 614pDWuMeyx+cmwON7Oas/HEqjkNbTNXE/PAj14Q+zeY3LYoovPKvlqdkIjki5cqMqm 6158guv3GApfJP4vTHEqpIdosHvaICqWvKr/Xnp3JTPrEWnSItoXNBkYgv1EO5ZxVut 616Q8rlhcOdx4J1Y1txekdfqw4GSykxjZljwy2R2F4LlD8COg6I04QbIEMfVXmdm+CS 617HvbaCd0PtLOPLKidvbWuCrjxBd/L5jeQOrMJ1SDX5DQ9J5Z8/5mkq4eqiWgwuoWc 618bBegiZqey6hcl9Um4OWQ3SKjISvCSR7wdrAdv0S21ivYkOCZZQ3HBQS6YY5RlYvE 6199I4kIZF8XKkit7ekfhdmZCfpIvnJHY6JAIOufQ2+92qUkFKmm5RWXD== 620-----RAQ EFN CEVINGR XRL-----`))) 621 var err error 622 testRSA2048PrivateKey, err = x509.ParsePKCS1PrivateKey(block.Bytes) 623 if err != nil { 624 panic(err) 625 } 626} 627