flight5bhandler.go 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778
  1. // SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>
  2. // SPDX-License-Identifier: MIT
  3. package dtls
  4. import (
  5. "context"
  6. "github.com/pion/dtls/v2/pkg/crypto/prf"
  7. "github.com/pion/dtls/v2/pkg/protocol"
  8. "github.com/pion/dtls/v2/pkg/protocol/alert"
  9. "github.com/pion/dtls/v2/pkg/protocol/handshake"
  10. "github.com/pion/dtls/v2/pkg/protocol/recordlayer"
  11. )
  12. func flight5bParse(_ context.Context, _ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
  13. _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence-1, state.cipherSuite,
  14. handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, false, false},
  15. )
  16. if !ok {
  17. // No valid message received. Keep reading
  18. return 0, nil, nil
  19. }
  20. if _, ok = msgs[handshake.TypeFinished].(*handshake.MessageFinished); !ok {
  21. return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, nil
  22. }
  23. // Other party may re-transmit the last flight. Keep state to be flight5b.
  24. return flight5b, nil, nil
  25. }
  26. func flight5bGenerate(_ context.Context, _ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) { //nolint:gocognit
  27. var pkts []*packet
  28. pkts = append(pkts,
  29. &packet{
  30. record: &recordlayer.RecordLayer{
  31. Header: recordlayer.Header{
  32. Version: protocol.Version1_2,
  33. },
  34. Content: &protocol.ChangeCipherSpec{},
  35. },
  36. })
  37. if len(state.localVerifyData) == 0 {
  38. plainText := cache.pullAndMerge(
  39. handshakeCachePullRule{handshake.TypeClientHello, cfg.initialEpoch, true, false},
  40. handshakeCachePullRule{handshake.TypeServerHello, cfg.initialEpoch, false, false},
  41. handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, false, false},
  42. )
  43. var err error
  44. state.localVerifyData, err = prf.VerifyDataClient(state.masterSecret, plainText, state.cipherSuite.HashFunc())
  45. if err != nil {
  46. return nil, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
  47. }
  48. }
  49. pkts = append(pkts,
  50. &packet{
  51. record: &recordlayer.RecordLayer{
  52. Header: recordlayer.Header{
  53. Version: protocol.Version1_2,
  54. Epoch: 1,
  55. },
  56. Content: &handshake.Handshake{
  57. Message: &handshake.MessageFinished{
  58. VerifyData: state.localVerifyData,
  59. },
  60. },
  61. },
  62. shouldEncrypt: true,
  63. resetLocalSequenceNumber: true,
  64. })
  65. return pkts, nil, nil
  66. }