OLD | NEW |
---|---|
1 /* | 1 /* |
2 * libjingle | 2 * libjingle |
3 * Copyright 2004 Google Inc. | 3 * Copyright 2004 Google Inc. |
4 * | 4 * |
5 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
6 * modification, are permitted provided that the following conditions are met: | 6 * modification, are permitted provided that the following conditions are met: |
7 * | 7 * |
8 * 1. Redistributions of source code must retain the above copyright notice, | 8 * 1. Redistributions of source code must retain the above copyright notice, |
9 * this list of conditions and the following disclaimer. | 9 * this list of conditions and the following disclaimer. |
10 * 2. Redistributions in binary form must reproduce the above copyright notice, | 10 * 2. Redistributions in binary form must reproduce the above copyright notice, |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
91 return false; | 91 return false; |
92 } | 92 } |
93 | 93 |
94 const MediaContentDescription* mdesc = | 94 const MediaContentDescription* mdesc = |
95 static_cast<const MediaContentDescription*>(content->description); | 95 static_cast<const MediaContentDescription*>(content->description); |
96 return mdesc && mdesc->type() == media_type; | 96 return mdesc && mdesc->type() == media_type; |
97 } | 97 } |
98 | 98 |
99 static bool CreateCryptoParams(int tag, const std::string& cipher, | 99 static bool CreateCryptoParams(int tag, const std::string& cipher, |
100 CryptoParams *out) { | 100 CryptoParams *out) { |
101 int key_len; | |
102 int salt_len; | |
103 if (!rtc::SrtpCryptoSuiteParams( | |
104 rtc::SrtpCryptoSuiteFromName(cipher), &key_len, &salt_len)) { | |
105 return false; | |
106 } | |
107 | |
108 int master_key_base64_len = (key_len + salt_len) * 4 / 3; | |
109 | |
101 std::string key; | 110 std::string key; |
102 key.reserve(SRTP_MASTER_KEY_BASE64_LEN); | 111 key.reserve(master_key_base64_len); |
103 | 112 |
104 if (!rtc::CreateRandomString(SRTP_MASTER_KEY_BASE64_LEN, &key)) { | 113 if (!rtc::CreateRandomString(master_key_base64_len, &key)) { |
105 return false; | 114 return false; |
106 } | 115 } |
107 out->tag = tag; | 116 out->tag = tag; |
108 out->cipher_suite = cipher; | 117 out->cipher_suite = cipher; |
109 out->key_params = kInline; | 118 out->key_params = kInline; |
110 out->key_params += key; | 119 out->key_params += key; |
111 return true; | 120 return true; |
112 } | 121 } |
113 | 122 |
114 #ifdef HAVE_SRTP | 123 #ifdef HAVE_SRTP |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
155 for (CryptoParamsVec::const_iterator it = cryptos.begin(); | 164 for (CryptoParamsVec::const_iterator it = cryptos.begin(); |
156 it != cryptos.end(); ++it) { | 165 it != cryptos.end(); ++it) { |
157 if (crypto.Matches(*it)) { | 166 if (crypto.Matches(*it)) { |
158 *out = *it; | 167 *out = *it; |
159 return true; | 168 return true; |
160 } | 169 } |
161 } | 170 } |
162 return false; | 171 return false; |
163 } | 172 } |
164 | 173 |
165 // For audio, HMAC 32 is prefered because of the low overhead. | 174 void FilterGcmCiphers(std::vector<int>* crypto_suites) { |
pthatcher1
2015/12/18 20:31:31
Can you break this up to be a bit more generic and
joachim
2015/12/19 15:26:23
Done. Implemented functions in sslstreamadapter (w
| |
175 for (std::vector<int>::iterator it = crypto_suites->begin(); | |
176 it != crypto_suites->end(); ) { | |
177 if (*it == rtc::SRTP_AEAD_AES_256_GCM || | |
178 *it == rtc::SRTP_AEAD_AES_128_GCM) { | |
179 it = crypto_suites->erase(it); | |
180 } else { | |
181 ++it; | |
182 } | |
183 } | |
184 } | |
pthatcher1
2015/12/18 20:31:31
Then you can just remove this function and replace
joachim
2015/12/19 15:26:23
Done.
| |
185 | |
186 void FilterGcmCipherNames(std::vector<std::string>* crypto_suites) { | |
187 for (std::vector<std::string>::iterator it = crypto_suites->begin(); | |
188 it != crypto_suites->end(); ) { | |
189 if (*it == rtc::CS_AEAD_AES_256_GCM || | |
190 *it == rtc::CS_AEAD_AES_128_GCM) { | |
191 it = crypto_suites->erase(it); | |
192 } else { | |
193 ++it; | |
194 } | |
195 } | |
196 } | |
pthatcher1
2015/12/18 20:31:32
Similarly here:
cipher_names.erase(std::remove_if
joachim
2015/12/19 15:26:23
Done.
| |
197 | |
198 // For audio, HMAC 32 is prefered over HMAC 80 because of the low overhead. | |
166 void GetSupportedAudioCryptoSuites(std::vector<int>* crypto_suites) { | 199 void GetSupportedAudioCryptoSuites(std::vector<int>* crypto_suites) { |
167 #ifdef HAVE_SRTP | 200 #ifdef HAVE_SRTP |
201 crypto_suites->push_back(rtc::SRTP_AEAD_AES_256_GCM); | |
202 crypto_suites->push_back(rtc::SRTP_AEAD_AES_128_GCM); | |
168 crypto_suites->push_back(rtc::SRTP_AES128_CM_SHA1_32); | 203 crypto_suites->push_back(rtc::SRTP_AES128_CM_SHA1_32); |
169 crypto_suites->push_back(rtc::SRTP_AES128_CM_SHA1_80); | 204 crypto_suites->push_back(rtc::SRTP_AES128_CM_SHA1_80); |
170 #endif | 205 #endif |
171 } | 206 } |
172 | 207 |
173 void GetSupportedAudioCryptoSuiteNames( | 208 void GetSupportedAudioCryptoSuiteNames( |
174 std::vector<std::string>* crypto_suite_names) { | 209 std::vector<std::string>* crypto_suite_names) { |
175 GetSupportedCryptoSuiteNames(GetSupportedAudioCryptoSuites, | 210 GetSupportedCryptoSuiteNames(GetSupportedAudioCryptoSuites, |
176 crypto_suite_names); | 211 crypto_suite_names); |
177 } | 212 } |
(...skipping 13 matching lines...) Expand all Loading... | |
191 } | 226 } |
192 | 227 |
193 void GetSupportedDataCryptoSuiteNames( | 228 void GetSupportedDataCryptoSuiteNames( |
194 std::vector<std::string>* crypto_suite_names) { | 229 std::vector<std::string>* crypto_suite_names) { |
195 GetSupportedCryptoSuiteNames(GetSupportedDataCryptoSuites, | 230 GetSupportedCryptoSuiteNames(GetSupportedDataCryptoSuites, |
196 crypto_suite_names); | 231 crypto_suite_names); |
197 } | 232 } |
198 | 233 |
199 void GetDefaultSrtpCryptoSuites(std::vector<int>* crypto_suites) { | 234 void GetDefaultSrtpCryptoSuites(std::vector<int>* crypto_suites) { |
200 #ifdef HAVE_SRTP | 235 #ifdef HAVE_SRTP |
236 crypto_suites->push_back(rtc::SRTP_AEAD_AES_256_GCM); | |
237 crypto_suites->push_back(rtc::SRTP_AEAD_AES_128_GCM); | |
201 crypto_suites->push_back(rtc::SRTP_AES128_CM_SHA1_80); | 238 crypto_suites->push_back(rtc::SRTP_AES128_CM_SHA1_80); |
202 #endif | 239 #endif |
203 } | 240 } |
204 | 241 |
205 void GetDefaultSrtpCryptoSuiteNames( | 242 void GetDefaultSrtpCryptoSuiteNames( |
206 std::vector<std::string>* crypto_suite_names) { | 243 std::vector<std::string>* crypto_suite_names) { |
207 GetSupportedCryptoSuiteNames(GetDefaultSrtpCryptoSuites, crypto_suite_names); | 244 GetSupportedCryptoSuiteNames(GetDefaultSrtpCryptoSuites, crypto_suite_names); |
208 } | 245 } |
209 | 246 |
210 // For video support only 80-bit SHA1 HMAC. For audio 32-bit HMAC is | 247 // Support any GCM cipher (if enabled through options). For video support only |
211 // tolerated unless bundle is enabled because it is low overhead. Pick the | 248 // 80-bit SHA1 HMAC. For audio 32-bit HMAC is tolerated unless bundle is enabled |
212 // crypto in the list that is supported. | 249 // because it is low overhead. |
250 // Pick the crypto in the list that is supported. | |
213 static bool SelectCrypto(const MediaContentDescription* offer, | 251 static bool SelectCrypto(const MediaContentDescription* offer, |
214 bool bundle, | 252 bool bundle, |
253 const MediaSessionOptions& options, | |
215 CryptoParams *crypto) { | 254 CryptoParams *crypto) { |
216 bool audio = offer->type() == MEDIA_TYPE_AUDIO; | 255 bool audio = offer->type() == MEDIA_TYPE_AUDIO; |
217 const CryptoParamsVec& cryptos = offer->cryptos(); | 256 const CryptoParamsVec& cryptos = offer->cryptos(); |
218 | 257 |
219 for (CryptoParamsVec::const_iterator i = cryptos.begin(); | 258 for (CryptoParamsVec::const_iterator i = cryptos.begin(); |
220 i != cryptos.end(); ++i) { | 259 i != cryptos.end(); ++i) { |
221 if (rtc::CS_AES_CM_128_HMAC_SHA1_80 == i->cipher_suite || | 260 if ((options.enable_gcm_ciphers && |
261 (rtc::CS_AEAD_AES_256_GCM == i->cipher_suite || | |
262 rtc::CS_AEAD_AES_128_GCM == i->cipher_suite)) || | |
pthatcher1
2015/12/18 20:31:31
IsGcmCipherName or IsGcmCryptoSuite would be usefu
joachim
2015/12/19 15:26:23
Done.
| |
263 rtc::CS_AES_CM_128_HMAC_SHA1_80 == i->cipher_suite || | |
222 (rtc::CS_AES_CM_128_HMAC_SHA1_32 == i->cipher_suite && audio && | 264 (rtc::CS_AES_CM_128_HMAC_SHA1_32 == i->cipher_suite && audio && |
223 !bundle)) { | 265 !bundle)) { |
pthatcher1
2015/12/18 20:31:32
Actually this, method seems to duplicate a lot wit
joachim
2015/12/19 15:26:23
Done.
| |
224 return CreateCryptoParams(i->tag, i->cipher_suite, crypto); | 266 return CreateCryptoParams(i->tag, i->cipher_suite, crypto); |
225 } | 267 } |
226 } | 268 } |
227 return false; | 269 return false; |
228 } | 270 } |
229 | 271 |
230 static const StreamParams* FindFirstStreamParamsByCname( | 272 static const StreamParams* FindFirstStreamParamsByCname( |
231 const StreamParamsVec& params_vec, | 273 const StreamParamsVec& params_vec, |
232 const std::string& cname) { | 274 const std::string& cname) { |
233 for (StreamParamsVec::const_iterator it = params_vec.begin(); | 275 for (StreamParamsVec::const_iterator it = params_vec.begin(); |
(...skipping 810 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1044 | 1086 |
1045 answer->set_rtcp_mux(options.rtcp_mux_enabled && offer->rtcp_mux()); | 1087 answer->set_rtcp_mux(options.rtcp_mux_enabled && offer->rtcp_mux()); |
1046 // TODO(deadbeef): Once we're sure this works correctly, enable it in | 1088 // TODO(deadbeef): Once we're sure this works correctly, enable it in |
1047 // CreateAnswer. | 1089 // CreateAnswer. |
1048 // if (answer->type() == cricket::MEDIA_TYPE_VIDEO) { | 1090 // if (answer->type() == cricket::MEDIA_TYPE_VIDEO) { |
1049 // answer->set_rtcp_reduced_size(offer->rtcp_reduced_size()); | 1091 // answer->set_rtcp_reduced_size(offer->rtcp_reduced_size()); |
1050 // } | 1092 // } |
1051 | 1093 |
1052 if (sdes_policy != SEC_DISABLED) { | 1094 if (sdes_policy != SEC_DISABLED) { |
1053 CryptoParams crypto; | 1095 CryptoParams crypto; |
1054 if (SelectCrypto(offer, bundle_enabled, &crypto)) { | 1096 if (SelectCrypto(offer, bundle_enabled, options, &crypto)) { |
1055 if (current_cryptos) { | 1097 if (current_cryptos) { |
1056 FindMatchingCrypto(*current_cryptos, crypto, &crypto); | 1098 FindMatchingCrypto(*current_cryptos, crypto, &crypto); |
1057 } | 1099 } |
1058 answer->AddCrypto(crypto); | 1100 answer->AddCrypto(crypto); |
1059 } | 1101 } |
1060 } | 1102 } |
1061 | 1103 |
1062 if (answer->cryptos().empty() && | 1104 if (answer->cryptos().empty() && |
1063 (offer->crypto_required() == CT_SDES || sdes_policy == SEC_REQUIRED)) { | 1105 (offer->crypto_required() == CT_SDES || sdes_policy == SEC_REQUIRED)) { |
1064 return false; | 1106 return false; |
(...skipping 491 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1556 const AudioCodecs& audio_codecs, | 1598 const AudioCodecs& audio_codecs, |
1557 StreamParamsVec* current_streams, | 1599 StreamParamsVec* current_streams, |
1558 SessionDescription* desc) const { | 1600 SessionDescription* desc) const { |
1559 cricket::SecurePolicy sdes_policy = | 1601 cricket::SecurePolicy sdes_policy = |
1560 IsDtlsActive(CN_AUDIO, current_description) ? | 1602 IsDtlsActive(CN_AUDIO, current_description) ? |
1561 cricket::SEC_DISABLED : secure(); | 1603 cricket::SEC_DISABLED : secure(); |
1562 | 1604 |
1563 scoped_ptr<AudioContentDescription> audio(new AudioContentDescription()); | 1605 scoped_ptr<AudioContentDescription> audio(new AudioContentDescription()); |
1564 std::vector<std::string> crypto_suites; | 1606 std::vector<std::string> crypto_suites; |
1565 GetSupportedAudioCryptoSuiteNames(&crypto_suites); | 1607 GetSupportedAudioCryptoSuiteNames(&crypto_suites); |
1608 if (!options.enable_gcm_ciphers) { | |
pthatcher1
2015/12/18 20:31:32
Instead of filtering, can we pass options into Get
joachim
2015/12/19 15:26:23
Done.
| |
1609 FilterGcmCipherNames(&crypto_suites); | |
1610 } | |
1566 if (!CreateMediaContentOffer( | 1611 if (!CreateMediaContentOffer( |
1567 options, | 1612 options, |
1568 audio_codecs, | 1613 audio_codecs, |
1569 sdes_policy, | 1614 sdes_policy, |
1570 GetCryptos(GetFirstAudioContentDescription(current_description)), | 1615 GetCryptos(GetFirstAudioContentDescription(current_description)), |
1571 crypto_suites, | 1616 crypto_suites, |
1572 audio_rtp_extensions, | 1617 audio_rtp_extensions, |
1573 add_legacy_, | 1618 add_legacy_, |
1574 current_streams, | 1619 current_streams, |
1575 audio.get())) { | 1620 audio.get())) { |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1610 const VideoCodecs& video_codecs, | 1655 const VideoCodecs& video_codecs, |
1611 StreamParamsVec* current_streams, | 1656 StreamParamsVec* current_streams, |
1612 SessionDescription* desc) const { | 1657 SessionDescription* desc) const { |
1613 cricket::SecurePolicy sdes_policy = | 1658 cricket::SecurePolicy sdes_policy = |
1614 IsDtlsActive(CN_VIDEO, current_description) ? | 1659 IsDtlsActive(CN_VIDEO, current_description) ? |
1615 cricket::SEC_DISABLED : secure(); | 1660 cricket::SEC_DISABLED : secure(); |
1616 | 1661 |
1617 scoped_ptr<VideoContentDescription> video(new VideoContentDescription()); | 1662 scoped_ptr<VideoContentDescription> video(new VideoContentDescription()); |
1618 std::vector<std::string> crypto_suites; | 1663 std::vector<std::string> crypto_suites; |
1619 GetSupportedVideoCryptoSuiteNames(&crypto_suites); | 1664 GetSupportedVideoCryptoSuiteNames(&crypto_suites); |
1665 if (!options.enable_gcm_ciphers) { | |
1666 FilterGcmCipherNames(&crypto_suites); | |
1667 } | |
pthatcher1
2015/12/18 20:31:32
Instead of filtering, can we pass options into Get
joachim
2015/12/19 15:26:23
Done.
| |
1620 if (!CreateMediaContentOffer( | 1668 if (!CreateMediaContentOffer( |
1621 options, | 1669 options, |
1622 video_codecs, | 1670 video_codecs, |
1623 sdes_policy, | 1671 sdes_policy, |
1624 GetCryptos(GetFirstVideoContentDescription(current_description)), | 1672 GetCryptos(GetFirstVideoContentDescription(current_description)), |
1625 crypto_suites, | 1673 crypto_suites, |
1626 video_rtp_extensions, | 1674 video_rtp_extensions, |
1627 add_legacy_, | 1675 add_legacy_, |
1628 current_streams, | 1676 current_streams, |
1629 video.get())) { | 1677 video.get())) { |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1680 // get SDES crypto suites for RTP-based data channels. | 1728 // get SDES crypto suites for RTP-based data channels. |
1681 sdes_policy = cricket::SEC_DISABLED; | 1729 sdes_policy = cricket::SEC_DISABLED; |
1682 // Unlike SetMediaProtocol below, we need to set the protocol | 1730 // Unlike SetMediaProtocol below, we need to set the protocol |
1683 // before we call CreateMediaContentOffer. Otherwise, | 1731 // before we call CreateMediaContentOffer. Otherwise, |
1684 // CreateMediaContentOffer won't know this is SCTP and will | 1732 // CreateMediaContentOffer won't know this is SCTP and will |
1685 // generate SSRCs rather than SIDs. | 1733 // generate SSRCs rather than SIDs. |
1686 data->set_protocol( | 1734 data->set_protocol( |
1687 secure_transport ? kMediaProtocolDtlsSctp : kMediaProtocolSctp); | 1735 secure_transport ? kMediaProtocolDtlsSctp : kMediaProtocolSctp); |
1688 } else { | 1736 } else { |
1689 GetSupportedDataCryptoSuiteNames(&crypto_suites); | 1737 GetSupportedDataCryptoSuiteNames(&crypto_suites); |
1738 if (!options.enable_gcm_ciphers) { | |
1739 FilterGcmCipherNames(&crypto_suites); | |
1740 } | |
1690 } | 1741 } |
1691 | 1742 |
1692 if (!CreateMediaContentOffer( | 1743 if (!CreateMediaContentOffer( |
1693 options, | 1744 options, |
1694 *data_codecs, | 1745 *data_codecs, |
1695 sdes_policy, | 1746 sdes_policy, |
1696 GetCryptos(GetFirstDataContentDescription(current_description)), | 1747 GetCryptos(GetFirstDataContentDescription(current_description)), |
1697 crypto_suites, | 1748 crypto_suites, |
1698 RtpHeaderExtensions(), | 1749 RtpHeaderExtensions(), |
1699 add_legacy_, | 1750 add_legacy_, |
(...skipping 272 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1972 GetFirstMediaContentDescription(sdesc, MEDIA_TYPE_VIDEO)); | 2023 GetFirstMediaContentDescription(sdesc, MEDIA_TYPE_VIDEO)); |
1973 } | 2024 } |
1974 | 2025 |
1975 const DataContentDescription* GetFirstDataContentDescription( | 2026 const DataContentDescription* GetFirstDataContentDescription( |
1976 const SessionDescription* sdesc) { | 2027 const SessionDescription* sdesc) { |
1977 return static_cast<const DataContentDescription*>( | 2028 return static_cast<const DataContentDescription*>( |
1978 GetFirstMediaContentDescription(sdesc, MEDIA_TYPE_DATA)); | 2029 GetFirstMediaContentDescription(sdesc, MEDIA_TYPE_DATA)); |
1979 } | 2030 } |
1980 | 2031 |
1981 } // namespace cricket | 2032 } // namespace cricket |
OLD | NEW |