Reimplement rtc::ToString and rtc::FromString without streams.

Bug: webrtc:8982
Change-Id: I3977435b035fdebef449732301d6e77fc899e7ba
Reviewed-on: https://webrtc-review.googlesource.com/86941
Commit-Queue: Jonas Olsson <jonasolsson@webrtc.org>
Reviewed-by: Karl Wiberg <kwiberg@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#24319}
This commit is contained in:
Jonas Olsson 2018-07-05 11:59:48 +02:00 committed by Commit Bot
parent dc1133ff84
commit 6b1985de95
20 changed files with 326 additions and 167 deletions

View file

@ -99,7 +99,7 @@ class TypedIntId : public StatsReport::IdBase {
std::string ToString() const override { std::string ToString() const override {
return std::string(InternalTypeToString(type_)) + kSeparator + return std::string(InternalTypeToString(type_)) + kSeparator +
rtc::ToString<int>(id_); rtc::ToString(id_);
} }
protected: protected:
@ -165,7 +165,7 @@ class ComponentId : public StatsReport::IdBase {
std::string ret(prefix); std::string ret(prefix);
ret += content_name_; ret += content_name_;
ret += '-'; ret += '-';
ret += rtc::ToString<>(component_); ret += rtc::ToString(component_);
return ret; return ret;
} }
@ -190,7 +190,7 @@ class CandidatePairId : public ComponentId {
std::string ToString() const override { std::string ToString() const override {
std::string ret(ComponentId::ToString("Conn-")); std::string ret(ComponentId::ToString("Conn-"));
ret += '-'; ret += '-';
ret += rtc::ToString<>(index_); ret += rtc::ToString(index_);
return ret; return ret;
} }

View file

@ -30,7 +30,7 @@ class FakeConstraints : public webrtc::MediaConstraintsInterface {
template <class T> template <class T>
void AddMandatory(const std::string& key, const T& value) { void AddMandatory(const std::string& key, const T& value) {
mandatory_.push_back(Constraint(key, rtc::ToString<T>(value))); mandatory_.push_back(Constraint(key, rtc::ToString(value)));
} }
template <class T> template <class T>
@ -45,12 +45,12 @@ class FakeConstraints : public webrtc::MediaConstraintsInterface {
} }
} }
} }
mandatory_.push_back(Constraint(key, rtc::ToString<T>(value))); mandatory_.push_back(Constraint(key, rtc::ToString(value)));
} }
template <class T> template <class T>
void AddOptional(const std::string& key, const T& value) { void AddOptional(const std::string& key, const T& value) {
optional_.push_back(Constraint(key, rtc::ToString<T>(value))); optional_.push_back(Constraint(key, rtc::ToString(value)));
} }
void SetMandatoryMinAspectRatio(double ratio) { void SetMandatoryMinAspectRatio(double ratio) {

View file

@ -17,9 +17,9 @@
using rtc::ToString; using rtc::ToString;
std::string int2str(int i) { std::string int2str(int i) {
return ToString<int>(i); return ToString(i);
} }
std::string size_t2str(size_t i) { std::string size_t2str(size_t i) {
return ToString<size_t>(i); return ToString(i);
} }

View file

@ -867,7 +867,7 @@ void P2PTransportChannel::OnUnknownAddress(
// The foundation of the candidate is set to an arbitrary value, different // The foundation of the candidate is set to an arbitrary value, different
// from the foundation for all other remote candidates. // from the foundation for all other remote candidates.
remote_candidate.set_foundation( remote_candidate.set_foundation(
rtc::ToString<uint32_t>(rtc::ComputeCrc32(remote_candidate.id()))); rtc::ToString(rtc::ComputeCrc32(remote_candidate.id())));
} }
// RFC5245, the agent constructs a pair whose local candidate is equal to // RFC5245, the agent constructs a pair whose local candidate is equal to

View file

@ -208,7 +208,7 @@ static std::string ComputeFoundation(const std::string& type,
const rtc::SocketAddress& base_address) { const rtc::SocketAddress& base_address) {
std::ostringstream ost; std::ostringstream ost;
ost << type << base_address.ipaddr().ToString() << protocol << relay_protocol; ost << type << base_address.ipaddr().ToString() << protocol << relay_protocol;
return rtc::ToString<uint32_t>(rtc::ComputeCrc32(ost.str())); return rtc::ToString(rtc::ComputeCrc32(ost.str()));
} }
CandidateStats::CandidateStats() = default; CandidateStats::CandidateStats() = default;

View file

@ -995,7 +995,7 @@ void RTCStatsCollector::ProduceDataChannelStats_s(
pc_->sctp_data_channels()) { pc_->sctp_data_channels()) {
std::unique_ptr<RTCDataChannelStats> data_channel_stats( std::unique_ptr<RTCDataChannelStats> data_channel_stats(
new RTCDataChannelStats( new RTCDataChannelStats(
"RTCDataChannel_" + rtc::ToString<>(data_channel->id()), "RTCDataChannel_" + rtc::ToString(data_channel->id()),
timestamp_us)); timestamp_us));
data_channel_stats->label = data_channel->label(); data_channel_stats->label = data_channel->label();
data_channel_stats->protocol = data_channel->protocol(); data_channel_stats->protocol = data_channel->protocol();

View file

@ -586,12 +586,12 @@ class RTCStatsCollectorTest : public testing::Test {
graph.sender = stats_->SetupLocalTrackAndSender( graph.sender = stats_->SetupLocalTrackAndSender(
cricket::MEDIA_TYPE_VIDEO, "LocalVideoTrackID", 3, false); cricket::MEDIA_TYPE_VIDEO, "LocalVideoTrackID", 3, false);
graph.sender_track_id = "RTCMediaStreamTrack_sender_" + graph.sender_track_id = "RTCMediaStreamTrack_sender_" +
rtc::ToString<>(graph.sender->AttachmentId()); rtc::ToString(graph.sender->AttachmentId());
// track (receiver) and stream (remote stream) // track (receiver) and stream (remote stream)
graph.receiver = stats_->SetupRemoteTrackAndReceiver( graph.receiver = stats_->SetupRemoteTrackAndReceiver(
cricket::MEDIA_TYPE_VIDEO, "RemoteVideoTrackID", "RemoteStreamId", 4); cricket::MEDIA_TYPE_VIDEO, "RemoteVideoTrackID", "RemoteStreamId", 4);
graph.receiver_track_id = "RTCMediaStreamTrack_receiver_" + graph.receiver_track_id = "RTCMediaStreamTrack_receiver_" +
rtc::ToString<>(graph.receiver->AttachmentId()); rtc::ToString(graph.receiver->AttachmentId());
graph.remote_stream_id = "RTCMediaStream_RemoteStreamId"; graph.remote_stream_id = "RTCMediaStream_RemoteStreamId";
// peer-connection // peer-connection
graph.peer_connection_id = "RTCPeerConnection"; graph.peer_connection_id = "RTCPeerConnection";
@ -1121,7 +1121,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCIceCandidatePairStats) {
report->timestamp_us()); report->timestamp_us());
expected_pair.transport_id = expected_pair.transport_id =
"RTCTransport_transport_" + "RTCTransport_transport_" +
rtc::ToString<>(cricket::ICE_CANDIDATE_COMPONENT_RTP); rtc::ToString(cricket::ICE_CANDIDATE_COMPONENT_RTP);
expected_pair.local_candidate_id = "RTCIceCandidate_" + local_candidate->id(); expected_pair.local_candidate_id = "RTCIceCandidate_" + local_candidate->id();
expected_pair.remote_candidate_id = expected_pair.remote_candidate_id =
"RTCIceCandidate_" + remote_candidate->id(); "RTCIceCandidate_" + remote_candidate->id();
@ -1853,7 +1853,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCTransportStats) {
RTCTransportStats expected_rtp_transport( RTCTransportStats expected_rtp_transport(
"RTCTransport_transport_" + "RTCTransport_transport_" +
rtc::ToString<>(cricket::ICE_CANDIDATE_COMPONENT_RTP), rtc::ToString(cricket::ICE_CANDIDATE_COMPONENT_RTP),
report->timestamp_us()); report->timestamp_us());
expected_rtp_transport.bytes_sent = 42; expected_rtp_transport.bytes_sent = 42;
expected_rtp_transport.bytes_received = 1337; expected_rtp_transport.bytes_received = 1337;
@ -1883,7 +1883,7 @@ TEST_F(RTCStatsCollectorTest, CollectRTCTransportStats) {
RTCTransportStats expected_rtcp_transport( RTCTransportStats expected_rtcp_transport(
"RTCTransport_transport_" + "RTCTransport_transport_" +
rtc::ToString<>(cricket::ICE_CANDIDATE_COMPONENT_RTCP), rtc::ToString(cricket::ICE_CANDIDATE_COMPONENT_RTCP),
report->timestamp_us()); report->timestamp_us());
expected_rtcp_transport.bytes_sent = 1337; expected_rtcp_transport.bytes_sent = 1337;
expected_rtcp_transport.bytes_received = 42; expected_rtcp_transport.bytes_received = 42;

View file

@ -582,7 +582,7 @@ StatsReport* StatsCollector::PrepareReport(bool local,
StatsReport::Id id(StatsReport::NewIdWithDirection( StatsReport::Id id(StatsReport::NewIdWithDirection(
local ? StatsReport::kStatsReportTypeSsrc local ? StatsReport::kStatsReportTypeSsrc
: StatsReport::kStatsReportTypeRemoteSsrc, : StatsReport::kStatsReportTypeRemoteSsrc,
rtc::ToString<uint32_t>(ssrc), direction)); rtc::ToString(ssrc), direction));
StatsReport* report = reports_.Find(id); StatsReport* report = reports_.Find(id);
// Use the ID of the track that is currently mapped to the SSRC, if any. // Use the ID of the track that is currently mapped to the SSRC, if any.
@ -1004,8 +1004,8 @@ void StatsCollector::ExtractSenderInfo() {
continue; continue;
} }
const StatsReport::Id stats_id = StatsReport::NewIdWithDirection( const StatsReport::Id stats_id = StatsReport::NewIdWithDirection(
StatsReport::kStatsReportTypeSsrc, StatsReport::kStatsReportTypeSsrc, rtc::ToString(sender->ssrc()),
rtc::ToString<uint32_t>(sender->ssrc()), StatsReport::kSend); StatsReport::kSend);
StatsReport* report = reports_.FindOrAddNew(stats_id); StatsReport* report = reports_.FindOrAddNew(stats_id);
report->AddInt(StatsReport::kStatsValueNameFrameWidthInput, report->AddInt(StatsReport::kStatsValueNameFrameWidthInput,
stats.input_width); stats.input_width);
@ -1051,9 +1051,8 @@ void StatsCollector::UpdateStatsFromExistingLocalAudioTracks(
for (const auto& it : local_audio_tracks_) { for (const auto& it : local_audio_tracks_) {
AudioTrackInterface* track = it.first; AudioTrackInterface* track = it.first;
uint32_t ssrc = it.second; uint32_t ssrc = it.second;
StatsReport* report = StatsReport* report = GetReport(StatsReport::kStatsReportTypeSsrc,
GetReport(StatsReport::kStatsReportTypeSsrc, rtc::ToString(ssrc), StatsReport::kSend);
rtc::ToString<uint32_t>(ssrc), StatsReport::kSend);
if (report == NULL) { if (report == NULL) {
// This can happen if a local audio track is added to a stream on the // This can happen if a local audio track is added to a stream on the
// fly and the report has not been set up yet. Do nothing in this case. // fly and the report has not been set up yet. Do nothing in this case.

View file

@ -283,69 +283,67 @@ void VerifyVoiceReceiverInfoReport(const StatsReport* report,
std::string value_in_report; std::string value_in_report;
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAudioOutputLevel, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAudioOutputLevel,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.audio_level), value_in_report); EXPECT_EQ(rtc::ToString(info.audio_level), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameBytesReceived, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameBytesReceived,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int64_t>(info.bytes_rcvd), value_in_report); EXPECT_EQ(rtc::ToString(info.bytes_rcvd), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameJitterReceived, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameJitterReceived,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.jitter_ms), value_in_report); EXPECT_EQ(rtc::ToString(info.jitter_ms), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameJitterBufferMs, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameJitterBufferMs,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.jitter_buffer_ms), value_in_report); EXPECT_EQ(rtc::ToString(info.jitter_buffer_ms), value_in_report);
EXPECT_TRUE(GetValue(report, EXPECT_TRUE(GetValue(report,
StatsReport::kStatsValueNamePreferredJitterBufferMs, StatsReport::kStatsValueNamePreferredJitterBufferMs,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.jitter_buffer_preferred_ms), EXPECT_EQ(rtc::ToString(info.jitter_buffer_preferred_ms), value_in_report);
value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameCurrentDelayMs, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameCurrentDelayMs,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.delay_estimate_ms), value_in_report); EXPECT_EQ(rtc::ToString(info.delay_estimate_ms), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameExpandRate, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameExpandRate,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>(info.expand_rate), value_in_report); EXPECT_EQ(rtc::ToString(info.expand_rate), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameSpeechExpandRate, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameSpeechExpandRate,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>(info.speech_expand_rate), value_in_report); EXPECT_EQ(rtc::ToString(info.speech_expand_rate), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAccelerateRate, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAccelerateRate,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>(info.accelerate_rate), value_in_report); EXPECT_EQ(rtc::ToString(info.accelerate_rate), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePreemptiveExpandRate, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePreemptiveExpandRate,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>(info.preemptive_expand_rate), value_in_report); EXPECT_EQ(rtc::ToString(info.preemptive_expand_rate), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameSecondaryDecodedRate, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameSecondaryDecodedRate,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>(info.secondary_decoded_rate), value_in_report); EXPECT_EQ(rtc::ToString(info.secondary_decoded_rate), value_in_report);
EXPECT_TRUE(GetValue(report, EXPECT_TRUE(GetValue(report,
StatsReport::kStatsValueNameSecondaryDiscardedRate, StatsReport::kStatsValueNameSecondaryDiscardedRate,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>(info.secondary_discarded_rate), EXPECT_EQ(rtc::ToString(info.secondary_discarded_rate), value_in_report);
value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePacketsReceived, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePacketsReceived,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.packets_rcvd), value_in_report); EXPECT_EQ(rtc::ToString(info.packets_rcvd), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingCTSG, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingCTSG,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_calls_to_silence_generator), EXPECT_EQ(rtc::ToString(info.decoding_calls_to_silence_generator),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingCTN, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingCTN,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_calls_to_neteq), value_in_report); EXPECT_EQ(rtc::ToString(info.decoding_calls_to_neteq), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingNormal, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingNormal,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_normal), value_in_report); EXPECT_EQ(rtc::ToString(info.decoding_normal), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingPLC, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingPLC,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_plc), value_in_report); EXPECT_EQ(rtc::ToString(info.decoding_plc), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingCNG, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingCNG,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_cng), value_in_report); EXPECT_EQ(rtc::ToString(info.decoding_cng), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingPLCCNG, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingPLCCNG,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_plc_cng), value_in_report); EXPECT_EQ(rtc::ToString(info.decoding_plc_cng), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingMutedOutput, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameDecodingMutedOutput,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(info.decoding_muted_output), value_in_report); EXPECT_EQ(rtc::ToString(info.decoding_muted_output), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameCodecName, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameCodecName,
&value_in_report)); &value_in_report));
} }
@ -358,26 +356,26 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
EXPECT_EQ(sinfo.codec_name, value_in_report); EXPECT_EQ(sinfo.codec_name, value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameBytesSent, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameBytesSent,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int64_t>(sinfo.bytes_sent), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.bytes_sent), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePacketsSent, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePacketsSent,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(sinfo.packets_sent), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.packets_sent), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePacketsLost, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNamePacketsLost,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(sinfo.packets_lost), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.packets_lost), value_in_report);
EXPECT_TRUE( EXPECT_TRUE(
GetValue(report, StatsReport::kStatsValueNameRtt, &value_in_report)); GetValue(report, StatsReport::kStatsValueNameRtt, &value_in_report));
EXPECT_EQ(rtc::ToString<int>(sinfo.rtt_ms), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.rtt_ms), value_in_report);
EXPECT_TRUE( EXPECT_TRUE(
GetValue(report, StatsReport::kStatsValueNameRtt, &value_in_report)); GetValue(report, StatsReport::kStatsValueNameRtt, &value_in_report));
EXPECT_EQ(rtc::ToString<int>(sinfo.rtt_ms), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.rtt_ms), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameJitterReceived, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameJitterReceived,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(sinfo.jitter_ms), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.jitter_ms), value_in_report);
if (sinfo.apm_statistics.delay_median_ms) { if (sinfo.apm_statistics.delay_median_ms) {
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameEchoDelayMedian, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameEchoDelayMedian,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(*sinfo.apm_statistics.delay_median_ms), EXPECT_EQ(rtc::ToString(*sinfo.apm_statistics.delay_median_ms),
value_in_report); value_in_report);
} else { } else {
EXPECT_FALSE(GetValue(report, StatsReport::kStatsValueNameEchoDelayMedian, EXPECT_FALSE(GetValue(report, StatsReport::kStatsValueNameEchoDelayMedian,
@ -386,8 +384,7 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
if (sinfo.apm_statistics.delay_standard_deviation_ms) { if (sinfo.apm_statistics.delay_standard_deviation_ms) {
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameEchoDelayStdDev, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameEchoDelayStdDev,
&value_in_report)); &value_in_report));
EXPECT_EQ( EXPECT_EQ(rtc::ToString(*sinfo.apm_statistics.delay_standard_deviation_ms),
rtc::ToString<int>(*sinfo.apm_statistics.delay_standard_deviation_ms),
value_in_report); value_in_report);
} else { } else {
EXPECT_FALSE(GetValue(report, StatsReport::kStatsValueNameEchoDelayStdDev, EXPECT_FALSE(GetValue(report, StatsReport::kStatsValueNameEchoDelayStdDev,
@ -396,7 +393,7 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
if (sinfo.apm_statistics.echo_return_loss) { if (sinfo.apm_statistics.echo_return_loss) {
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameEchoReturnLoss, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameEchoReturnLoss,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(*sinfo.apm_statistics.echo_return_loss), EXPECT_EQ(rtc::ToString(*sinfo.apm_statistics.echo_return_loss),
value_in_report); value_in_report);
} else { } else {
EXPECT_FALSE(GetValue(report, StatsReport::kStatsValueNameEchoReturnLoss, EXPECT_FALSE(GetValue(report, StatsReport::kStatsValueNameEchoReturnLoss,
@ -406,8 +403,7 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
EXPECT_TRUE(GetValue(report, EXPECT_TRUE(GetValue(report,
StatsReport::kStatsValueNameEchoReturnLossEnhancement, StatsReport::kStatsValueNameEchoReturnLossEnhancement,
&value_in_report)); &value_in_report));
EXPECT_EQ( EXPECT_EQ(rtc::ToString(*sinfo.apm_statistics.echo_return_loss_enhancement),
rtc::ToString<int>(*sinfo.apm_statistics.echo_return_loss_enhancement),
value_in_report); value_in_report);
} else { } else {
EXPECT_FALSE(GetValue(report, EXPECT_FALSE(GetValue(report,
@ -418,8 +414,7 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
EXPECT_TRUE(GetValue(report, EXPECT_TRUE(GetValue(report,
StatsReport::kStatsValueNameResidualEchoLikelihood, StatsReport::kStatsValueNameResidualEchoLikelihood,
&value_in_report)); &value_in_report));
EXPECT_EQ( EXPECT_EQ(rtc::ToString(*sinfo.apm_statistics.residual_echo_likelihood),
rtc::ToString<float>(*sinfo.apm_statistics.residual_echo_likelihood),
value_in_report); value_in_report);
} else { } else {
EXPECT_FALSE(GetValue(report, EXPECT_FALSE(GetValue(report,
@ -430,7 +425,7 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
EXPECT_TRUE(GetValue( EXPECT_TRUE(GetValue(
report, StatsReport::kStatsValueNameResidualEchoLikelihoodRecentMax, report, StatsReport::kStatsValueNameResidualEchoLikelihoodRecentMax,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<float>( EXPECT_EQ(rtc::ToString(
*sinfo.apm_statistics.residual_echo_likelihood_recent_max), *sinfo.apm_statistics.residual_echo_likelihood_recent_max),
value_in_report); value_in_report);
} else { } else {
@ -440,7 +435,7 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
} }
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAudioInputLevel, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAudioInputLevel,
&value_in_report)); &value_in_report));
EXPECT_EQ(rtc::ToString<int>(sinfo.audio_level), value_in_report); EXPECT_EQ(rtc::ToString(sinfo.audio_level), value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameTypingNoiseState, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameTypingNoiseState,
&value_in_report)); &value_in_report));
std::string typing_detected = sinfo.typing_noise_detected ? "true" : "false"; std::string typing_detected = sinfo.typing_noise_detected ? "true" : "false";
@ -449,46 +444,41 @@ void VerifyVoiceSenderInfoReport(const StatsReport* report,
StatsReport::kStatsValueNameAnaBitrateActionCounter, StatsReport::kStatsValueNameAnaBitrateActionCounter,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.bitrate_action_counter); ASSERT_TRUE(sinfo.ana_statistics.bitrate_action_counter);
EXPECT_EQ( EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.bitrate_action_counter),
rtc::ToString<uint32_t>(*sinfo.ana_statistics.bitrate_action_counter),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue(report, EXPECT_TRUE(GetValue(report,
StatsReport::kStatsValueNameAnaChannelActionCounter, StatsReport::kStatsValueNameAnaChannelActionCounter,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.channel_action_counter); ASSERT_TRUE(sinfo.ana_statistics.channel_action_counter);
EXPECT_EQ( EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.channel_action_counter),
rtc::ToString<uint32_t>(*sinfo.ana_statistics.channel_action_counter),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAnaDtxActionCounter, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAnaDtxActionCounter,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.dtx_action_counter); ASSERT_TRUE(sinfo.ana_statistics.dtx_action_counter);
EXPECT_EQ(rtc::ToString<uint32_t>(*sinfo.ana_statistics.dtx_action_counter), EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.dtx_action_counter),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAnaFecActionCounter, EXPECT_TRUE(GetValue(report, StatsReport::kStatsValueNameAnaFecActionCounter,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.fec_action_counter); ASSERT_TRUE(sinfo.ana_statistics.fec_action_counter);
EXPECT_EQ(rtc::ToString<uint32_t>(*sinfo.ana_statistics.fec_action_counter), EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.fec_action_counter),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue( EXPECT_TRUE(GetValue(
report, StatsReport::kStatsValueNameAnaFrameLengthIncreaseCounter, report, StatsReport::kStatsValueNameAnaFrameLengthIncreaseCounter,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.frame_length_increase_counter); ASSERT_TRUE(sinfo.ana_statistics.frame_length_increase_counter);
EXPECT_EQ(rtc::ToString<uint32_t>( EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.frame_length_increase_counter),
*sinfo.ana_statistics.frame_length_increase_counter),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue( EXPECT_TRUE(GetValue(
report, StatsReport::kStatsValueNameAnaFrameLengthDecreaseCounter, report, StatsReport::kStatsValueNameAnaFrameLengthDecreaseCounter,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.frame_length_decrease_counter); ASSERT_TRUE(sinfo.ana_statistics.frame_length_decrease_counter);
EXPECT_EQ(rtc::ToString<uint32_t>( EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.frame_length_decrease_counter),
*sinfo.ana_statistics.frame_length_decrease_counter),
value_in_report); value_in_report);
EXPECT_TRUE(GetValue(report, EXPECT_TRUE(GetValue(report,
StatsReport::kStatsValueNameAnaUplinkPacketLossFraction, StatsReport::kStatsValueNameAnaUplinkPacketLossFraction,
&value_in_report)); &value_in_report));
ASSERT_TRUE(sinfo.ana_statistics.uplink_packet_loss_fraction); ASSERT_TRUE(sinfo.ana_statistics.uplink_packet_loss_fraction);
EXPECT_EQ( EXPECT_EQ(rtc::ToString(*sinfo.ana_statistics.uplink_packet_loss_fraction),
rtc::ToString<float>(*sinfo.ana_statistics.uplink_packet_loss_fraction),
value_in_report); value_in_report);
} }
@ -591,7 +581,7 @@ class StatsCollectorTest : public testing::Test {
EXPECT_EQ(audio_track->id(), track_id); EXPECT_EQ(audio_track->id(), track_id);
std::string ssrc_id = std::string ssrc_id =
ExtractSsrcStatsValue(*reports, StatsReport::kStatsValueNameSsrc); ExtractSsrcStatsValue(*reports, StatsReport::kStatsValueNameSsrc);
EXPECT_EQ(rtc::ToString<uint32_t>(kSsrcOfTrack), ssrc_id); EXPECT_EQ(rtc::ToString(kSsrcOfTrack), ssrc_id);
std::string media_type = std::string media_type =
ExtractSsrcStatsValue(*reports, StatsReport::kStatsValueNameMediaType); ExtractSsrcStatsValue(*reports, StatsReport::kStatsValueNameMediaType);
@ -617,7 +607,7 @@ class StatsCollectorTest : public testing::Test {
EXPECT_EQ(audio_track->id(), track_id); EXPECT_EQ(audio_track->id(), track_id);
ssrc_id = ssrc_id =
ExtractSsrcStatsValue(track_reports, StatsReport::kStatsValueNameSsrc); ExtractSsrcStatsValue(track_reports, StatsReport::kStatsValueNameSsrc);
EXPECT_EQ(rtc::ToString<uint32_t>(kSsrcOfTrack), ssrc_id); EXPECT_EQ(rtc::ToString(kSsrcOfTrack), ssrc_id);
if (!voice_info.senders.empty()) { if (!voice_info.senders.empty()) {
VerifyVoiceSenderInfoReport(track_report, voice_info.senders[0]); VerifyVoiceSenderInfoReport(track_report, voice_info.senders[0]);
} }
@ -823,7 +813,7 @@ TEST_F(StatsCollectorTest, ExtractDataInfo) {
EXPECT_EQ(kDataChannelLabel, EXPECT_EQ(kDataChannelLabel,
ExtractStatsValue(StatsReport::kStatsReportTypeDataChannel, reports, ExtractStatsValue(StatsReport::kStatsReportTypeDataChannel, reports,
StatsReport::kStatsValueNameLabel)); StatsReport::kStatsValueNameLabel));
EXPECT_EQ(rtc::ToString<int64_t>(kDataChannelId), EXPECT_EQ(rtc::ToString(kDataChannelId),
ExtractStatsValue(StatsReport::kStatsReportTypeDataChannel, reports, ExtractStatsValue(StatsReport::kStatsReportTypeDataChannel, reports,
StatsReport::kStatsValueNameDataChannelId)); StatsReport::kStatsValueNameDataChannelId));
EXPECT_EQ(kConnectingString, EXPECT_EQ(kConnectingString,
@ -1054,7 +1044,7 @@ TEST_P(StatsCollectorTrackTest, TrackAndSsrcObjectExistAfterUpdateSsrcStats) {
std::string ssrc_id = std::string ssrc_id =
ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameSsrc); ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameSsrc);
EXPECT_EQ(rtc::ToString<uint32_t>(kSsrcOfTrack), ssrc_id); EXPECT_EQ(rtc::ToString(kSsrcOfTrack), ssrc_id);
std::string track_id = std::string track_id =
ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameTrackId); ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameTrackId);
@ -1190,7 +1180,7 @@ TEST_P(StatsCollectorTrackTest, ReportsFromRemoteTrack) {
std::string ssrc_id = std::string ssrc_id =
ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameSsrc); ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameSsrc);
EXPECT_EQ(rtc::ToString<uint32_t>(kSsrcOfTrack), ssrc_id); EXPECT_EQ(rtc::ToString(kSsrcOfTrack), ssrc_id);
std::string track_id = std::string track_id =
ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameTrackId); ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameTrackId);
@ -1573,7 +1563,7 @@ TEST_P(StatsCollectorTrackTest, GetStatsAfterRemoveAudioStream) {
EXPECT_EQ(kLocalTrackId, track_id); EXPECT_EQ(kLocalTrackId, track_id);
std::string ssrc_id = std::string ssrc_id =
ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameSsrc); ExtractSsrcStatsValue(reports, StatsReport::kStatsValueNameSsrc);
EXPECT_EQ(rtc::ToString<uint32_t>(kSsrcOfTrack), ssrc_id); EXPECT_EQ(rtc::ToString(kSsrcOfTrack), ssrc_id);
// Verifies the values in the track report, no value will be changed by the // Verifies the values in the track report, no value will be changed by the
// AudioTrackInterface::GetSignalValue() and // AudioTrackInterface::GetSignalValue() and

View file

@ -449,7 +449,7 @@ TEST_F(VideoCapturerTrackSourceTest, ScreencastResolutionWithConstraint) {
TEST_F(VideoCapturerTrackSourceTest, MandatorySubOneFpsConstraints) { TEST_F(VideoCapturerTrackSourceTest, MandatorySubOneFpsConstraints) {
FakeConstraints constraints; FakeConstraints constraints;
constraints.AddMandatory(MediaConstraintsInterface::kMaxFrameRate, 0.5); constraints.AddMandatory(MediaConstraintsInterface::kMaxFrameRate, 0);
CreateVideoCapturerSource(&constraints); CreateVideoCapturerSource(&constraints);
EXPECT_EQ_WAIT(MediaSourceInterface::kEnded, state_observer_->state(), EXPECT_EQ_WAIT(MediaSourceInterface::kEnded, state_observer_->state(),
@ -459,7 +459,7 @@ TEST_F(VideoCapturerTrackSourceTest, MandatorySubOneFpsConstraints) {
TEST_F(VideoCapturerTrackSourceTest, OptionalSubOneFpsConstraints) { TEST_F(VideoCapturerTrackSourceTest, OptionalSubOneFpsConstraints) {
FakeConstraints constraints; FakeConstraints constraints;
constraints.AddOptional(MediaConstraintsInterface::kMaxFrameRate, 0.5); constraints.AddOptional(MediaConstraintsInterface::kMaxFrameRate, 0);
CreateVideoCapturerSource(&constraints); CreateVideoCapturerSource(&constraints);
EXPECT_EQ_WAIT(MediaSourceInterface::kLive, state_observer_->state(), EXPECT_EQ_WAIT(MediaSourceInterface::kLive, state_observer_->state(),

View file

@ -1282,7 +1282,7 @@ void BuildMediaDescription(const ContentInfo* content_info,
video_desc->codecs().begin(); video_desc->codecs().begin();
it != video_desc->codecs().end(); ++it) { it != video_desc->codecs().end(); ++it) {
fmt.append(" "); fmt.append(" ");
fmt.append(rtc::ToString<int>(it->id)); fmt.append(rtc::ToString(it->id));
} }
} else if (media_type == cricket::MEDIA_TYPE_AUDIO) { } else if (media_type == cricket::MEDIA_TYPE_AUDIO) {
const AudioContentDescription* audio_desc = media_desc->as_audio(); const AudioContentDescription* audio_desc = media_desc->as_audio();
@ -1290,7 +1290,7 @@ void BuildMediaDescription(const ContentInfo* content_info,
audio_desc->codecs().begin(); audio_desc->codecs().begin();
it != audio_desc->codecs().end(); ++it) { it != audio_desc->codecs().end(); ++it) {
fmt.append(" "); fmt.append(" ");
fmt.append(rtc::ToString<int>(it->id)); fmt.append(rtc::ToString(it->id));
} }
} else if (media_type == cricket::MEDIA_TYPE_DATA) { } else if (media_type == cricket::MEDIA_TYPE_DATA) {
const DataContentDescription* data_desc = media_desc->as_data(); const DataContentDescription* data_desc = media_desc->as_data();
@ -1308,7 +1308,7 @@ void BuildMediaDescription(const ContentInfo* content_info,
} }
} }
fmt.append(rtc::ToString<int>(sctp_port)); fmt.append(rtc::ToString(sctp_port));
} else { } else {
fmt.append(kDefaultSctpmapProtocol); fmt.append(kDefaultSctpmapProtocol);
} }
@ -1317,7 +1317,7 @@ void BuildMediaDescription(const ContentInfo* content_info,
data_desc->codecs().begin(); data_desc->codecs().begin();
it != data_desc->codecs().end(); ++it) { it != data_desc->codecs().end(); ++it) {
fmt.append(" "); fmt.append(" ");
fmt.append(rtc::ToString<int>(it->id)); fmt.append(rtc::ToString(it->id));
} }
} }
} }
@ -1596,7 +1596,7 @@ void BuildRtpContentAttributes(const MediaContentDescription* media_desc,
std::vector<uint32_t>::const_iterator ssrc = std::vector<uint32_t>::const_iterator ssrc =
track->ssrc_groups[i].ssrcs.begin(); track->ssrc_groups[i].ssrcs.begin();
for (; ssrc != track->ssrc_groups[i].ssrcs.end(); ++ssrc) { for (; ssrc != track->ssrc_groups[i].ssrcs.end(); ++ssrc) {
os << kSdpDelimiterSpace << rtc::ToString<uint32_t>(*ssrc); os << kSdpDelimiterSpace << rtc::ToString(*ssrc);
} }
AddLine(os.str(), message); AddLine(os.str(), message);
} }

View file

@ -1713,7 +1713,7 @@ class WebRtcSdpTest : public testing::Test {
int expected_value) { int expected_value) {
cricket::CodecParameterMap::const_iterator found = params.find(name); cricket::CodecParameterMap::const_iterator found = params.find(name);
ASSERT_TRUE(found != params.end()); ASSERT_TRUE(found != params.end());
EXPECT_EQ(found->second, rtc::ToString<int>(expected_value)); EXPECT_EQ(found->second, rtc::ToString(expected_value));
} }
void TestDeserializeCodecParams(const CodecParams& params, void TestDeserializeCodecParams(const CodecParams& params,

View file

@ -314,6 +314,8 @@ rtc_source_set("timeutils") {
rtc_source_set("stringutils") { rtc_source_set("stringutils") {
sources = [ sources = [
"string_to_number.cc",
"string_to_number.h",
"stringencode.cc", "stringencode.cc",
"stringencode.h", "stringencode.h",
"strings/string_builder.cc", "strings/string_builder.cc",
@ -323,8 +325,10 @@ rtc_source_set("stringutils") {
] ]
deps = [ deps = [
":checks", ":checks",
":macromagic",
":safe_minmax", ":safe_minmax",
"../api:array_view", "../api:array_view",
"//third_party/abseil-cpp/absl/types:optional",
] ]
} }
@ -428,8 +432,6 @@ rtc_source_set("rtc_base_approved_generic") {
"rate_statistics.h", "rate_statistics.h",
"ratetracker.cc", "ratetracker.cc",
"ratetracker.h", "ratetracker.h",
"string_to_number.cc",
"string_to_number.h",
"swap_queue.h", "swap_queue.h",
"template_util.h", "template_util.h",
"timestampaligner.cc", "timestampaligner.cc",

View file

@ -165,7 +165,8 @@ bool OptionsFile::SetIntValue(const std::string& option, int value) {
if (!IsLegalName(option)) { if (!IsLegalName(option)) {
return false; return false;
} }
return ToString(value, &options_[option]); options_[option] = ToString(value);
return true;
} }
bool OptionsFile::RemoveValue(const std::string& option) { bool OptionsFile::RemoveValue(const std::string& option) {

View file

@ -48,5 +48,41 @@ absl::optional<unsigned_type> ParseUnsigned(const char* str, int base) {
return absl::nullopt; return absl::nullopt;
} }
template <typename T>
T StrToT(const char* str, char** str_end);
template <>
inline float StrToT(const char* str, char** str_end) {
return std::strtof(str, str_end);
}
template <>
inline double StrToT(const char* str, char** str_end) {
return std::strtod(str, str_end);
}
template <>
inline long double StrToT(const char* str, char** str_end) {
return std::strtold(str, str_end);
}
template <typename T>
absl::optional<T> ParseFloatingPoint(const char* str) {
RTC_DCHECK(str);
if (*str == '\0')
return absl::nullopt;
char* end = nullptr;
errno = 0;
const T value = StrToT<T>(str, &end);
if (end && *end == '\0' && errno == 0) {
return value;
}
return absl::nullopt;
}
template absl::optional<float> ParseFloatingPoint(const char* str);
template absl::optional<double> ParseFloatingPoint(const char* str);
template absl::optional<long double> ParseFloatingPoint(const char* str);
} // namespace string_to_number_internal } // namespace string_to_number_internal
} // namespace rtc } // namespace rtc

View file

@ -48,6 +48,9 @@ using signed_type = long long; // NOLINT(runtime/int)
absl::optional<signed_type> ParseSigned(const char* str, int base); absl::optional<signed_type> ParseSigned(const char* str, int base);
absl::optional<unsigned_type> ParseUnsigned(const char* str, int base); absl::optional<unsigned_type> ParseUnsigned(const char* str, int base);
template <typename T>
absl::optional<T> ParseFloatingPoint(const char* str);
} // namespace string_to_number_internal } // namespace string_to_number_internal
template <typename T> template <typename T>
@ -88,6 +91,17 @@ StringToNumber(const char* str, int base = 10) {
return absl::nullopt; return absl::nullopt;
} }
template <typename T>
typename std::enable_if<std::is_floating_point<T>::value,
absl::optional<T>>::type
StringToNumber(const char* str, int base = 10) {
static_assert(
std::numeric_limits<T>::max() <= std::numeric_limits<long double>::max(),
"StringToNumber only supports floating-point numbers as large "
"as long double");
return string_to_number_internal::ParseFloatingPoint<T>(str);
}
// The std::string overloads only exists if there is a matching const char* // The std::string overloads only exists if there is a matching const char*
// version. // version.
template <typename T> template <typename T>

View file

@ -13,6 +13,7 @@
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include "rtc_base/arraysize.h"
#include "rtc_base/checks.h" #include "rtc_base/checks.h"
#include "rtc_base/stringutils.h" #include "rtc_base/stringutils.h"
@ -410,4 +411,90 @@ size_t split(const std::string& source,
return fields->size(); return fields->size();
} }
std::string ToString(const bool b) {
return b ? "true" : "false";
}
std::string ToString(const char* const s) {
return std::string(s);
}
std::string ToString(const std::string s) {
return s;
}
std::string ToString(const short s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%hd", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const unsigned short s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%hu", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const int s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%d", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const unsigned int s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%u", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const long int s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%ld", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const unsigned long int s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%lu", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const long long int s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%lld", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const unsigned long long int s) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%llu", s);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const double d) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%g", d);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
std::string ToString(const void* const p) {
char buf[32];
const int len = std::snprintf(&buf[0], arraysize(buf), "%p", p);
RTC_DCHECK_LE(len, arraysize(buf));
return std::string(&buf[0], len);
}
bool FromString(const std::string& s, bool* b) {
if (s == "false") {
*b = false;
return true;
}
if (s == "true") {
*b = true;
return true;
}
return false;
}
} // namespace rtc } // namespace rtc

View file

@ -16,6 +16,7 @@
#include <vector> #include <vector>
#include "rtc_base/checks.h" #include "rtc_base/checks.h"
#include "rtc_base/string_to_number.h"
namespace rtc { namespace rtc {
@ -147,32 +148,40 @@ bool tokenize_first(const std::string& source,
std::string* rest); std::string* rest);
// Convert arbitrary values to/from a string. // Convert arbitrary values to/from a string.
// TODO(jonasolsson): Remove these when absl::StrCat becomes available.
std::string ToString(bool b);
template <class T> std::string ToString(const char* s);
static bool ToString(const T& t, std::string* s) { std::string ToString(std::string t);
RTC_DCHECK(s);
std::ostringstream oss;
oss << std::boolalpha << t;
*s = oss.str();
return !oss.fail();
}
template <class T> std::string ToString(short s);
std::string ToString(unsigned short s);
std::string ToString(int s);
std::string ToString(unsigned int s);
std::string ToString(long int s);
std::string ToString(unsigned long int s);
std::string ToString(long long int s);
std::string ToString(unsigned long long int s);
std::string ToString(double t);
std::string ToString(const void* p);
template <typename T,
typename std::enable_if<std::is_arithmetic<T>::value &&
!std::is_same<T, bool>::value,
int>::type = 0>
static bool FromString(const std::string& s, T* t) { static bool FromString(const std::string& s, T* t) {
RTC_DCHECK(t); RTC_DCHECK(t);
std::istringstream iss(s); absl::optional<T> result = StringToNumber<T>(s);
iss >> std::boolalpha >> *t;
return !iss.fail(); if (result)
*t = *result;
return result.has_value();
} }
// Inline versions of the string conversion routines. bool FromString(const std::string& s, bool* b);
template <typename T>
static inline std::string ToString(const T& val) {
std::string str;
ToString(val, &str);
return str;
}
template <typename T> template <typename T>
static inline T FromString(const std::string& str) { static inline T FromString(const std::string& str) {
@ -181,13 +190,6 @@ static inline T FromString(const std::string& str) {
return val; return val;
} }
template <typename T>
static inline T FromString(const T& defaultValue, const std::string& str) {
T val(defaultValue);
FromString(str, &val);
return val;
}
////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////
} // namespace rtc } // namespace rtc

View file

@ -13,6 +13,8 @@
#include "rtc_base/gunit.h" #include "rtc_base/gunit.h"
#include "rtc_base/stringutils.h" #include "rtc_base/stringutils.h"
#include <sstream> // no-presubmit-check TODO(webrtc:8982)
namespace rtc { namespace rtc {
class HexEncodeTest : public testing::Test { class HexEncodeTest : public testing::Test {
@ -351,53 +353,79 @@ TEST(SplitTest, CompareSubstrings) {
ASSERT_STREQ("", fields.at(0).c_str()); ASSERT_STREQ("", fields.at(0).c_str());
} }
TEST(BoolTest, DecodeValid) { TEST(ToString, SanityCheck) {
bool value; EXPECT_EQ(ToString(true), "true");
EXPECT_TRUE(FromString("true", &value)); EXPECT_EQ(ToString(false), "false");
EXPECT_TRUE(value);
EXPECT_TRUE(FromString("true,", &value));
EXPECT_TRUE(value);
EXPECT_TRUE(FromString("true , true", &value));
EXPECT_TRUE(value);
EXPECT_TRUE(FromString("true ,\n false", &value));
EXPECT_TRUE(value);
EXPECT_TRUE(FromString(" true \n", &value));
EXPECT_TRUE(value);
EXPECT_TRUE(FromString("false", &value)); const char* c = "message";
EXPECT_FALSE(value); EXPECT_EQ(ToString(c), c);
EXPECT_TRUE(FromString(" false ", &value)); EXPECT_EQ(ToString(std::string(c)), c);
EXPECT_FALSE(value);
EXPECT_TRUE(FromString(" false, ", &value));
EXPECT_FALSE(value);
EXPECT_TRUE(FromString<bool>("true\n")); EXPECT_EQ(ToString(short{-123}), "-123");
EXPECT_FALSE(FromString<bool>("false\n")); EXPECT_EQ(ToString((unsigned short)123), "123");
EXPECT_EQ(ToString(int{-123}), "-123");
EXPECT_EQ(ToString((unsigned int)123), "123");
EXPECT_EQ(ToString((long int)-123), "-123");
EXPECT_EQ(ToString((unsigned long int)123), "123");
EXPECT_EQ(ToString((long long int)-123), "-123");
EXPECT_EQ(ToString((unsigned long long int)123), "123");
int i = 10;
int* p = &i;
std::ostringstream s; // no-presubmit-check TODO(webrtc:8982)
s << p;
EXPECT_EQ(s.str(), ToString(p));
EXPECT_EQ(ToString(0.5), "0.5");
} }
TEST(BoolTest, DecodeInvalid) { template <typename T>
bool value; void ParsesTo(std::string s, T t) {
EXPECT_FALSE(FromString("True", &value)); T value;
EXPECT_FALSE(FromString("TRUE", &value)); EXPECT_TRUE(FromString(s, &value));
EXPECT_FALSE(FromString("False", &value)); EXPECT_EQ(value, t);
EXPECT_FALSE(FromString("FALSE", &value));
EXPECT_FALSE(FromString("0", &value));
EXPECT_FALSE(FromString("1", &value));
EXPECT_FALSE(FromString("0,", &value));
EXPECT_FALSE(FromString("1,", &value));
EXPECT_FALSE(FromString("1,0", &value));
EXPECT_FALSE(FromString("1.", &value));
EXPECT_FALSE(FromString("1.0", &value));
EXPECT_FALSE(FromString("", &value));
EXPECT_FALSE(FromString<bool>("false\nfalse"));
} }
TEST(BoolTest, RoundTrip) { TEST(FromString, DecodeValid) {
bool value; ParsesTo("true", true);
EXPECT_TRUE(FromString(ToString(true), &value)); ParsesTo("false", false);
EXPECT_TRUE(value);
EXPECT_TRUE(FromString(ToString(false), &value)); ParsesTo("105", 105);
EXPECT_FALSE(value); ParsesTo("0.25", 0.25);
}
template <typename T>
void FailsToParse(std::string s) {
T value;
EXPECT_FALSE(FromString(s, &value)) << "[" << s << "]";
}
TEST(FromString, DecodeInvalid) {
FailsToParse<bool>("True");
FailsToParse<bool>("0");
FailsToParse<bool>("yes");
FailsToParse<int>("0.5");
FailsToParse<int>("XIV");
FailsToParse<double>("");
FailsToParse<double>(" ");
FailsToParse<int>("1 2");
}
template <typename T>
void RoundTrip(T t) {
std::string s = ToString(t);
T value;
EXPECT_TRUE(FromString(s, &value));
EXPECT_EQ(value, t);
}
TEST(FromString, RoundTrip) {
RoundTrip<int>(123);
RoundTrip(false);
RoundTrip(true);
RoundTrip(0.5);
RoundTrip(-15l);
} }
} // namespace rtc } // namespace rtc

View file

@ -26,9 +26,9 @@ std::string VectorToString(const std::vector<T>& vector) {
if (vector.empty()) if (vector.empty())
return "[]"; return "[]";
std::ostringstream oss; std::ostringstream oss;
oss << "[" << rtc::ToString<T>(vector[0]); oss << "[" << rtc::ToString(vector[0]);
for (size_t i = 1; i < vector.size(); ++i) { for (size_t i = 1; i < vector.size(); ++i) {
oss << "," << rtc::ToString<T>(vector[i]); oss << "," << rtc::ToString(vector[i]);
} }
oss << "]"; oss << "]";
return oss.str(); return oss.str();
@ -41,9 +41,9 @@ std::string VectorOfStringsToString(const std::vector<T>& strings) {
if (strings.empty()) if (strings.empty())
return "[]"; return "[]";
std::ostringstream oss; std::ostringstream oss;
oss << "[\"" << rtc::ToString<T>(strings[0]) << '\"'; oss << "[\"" << rtc::ToString(strings[0]) << '\"';
for (size_t i = 1; i < strings.size(); ++i) { for (size_t i = 1; i < strings.size(); ++i) {
oss << ",\"" << rtc::ToString<T>(strings[i]) << '\"'; oss << ",\"" << rtc::ToString(strings[i]) << '\"';
} }
oss << "]"; oss << "]";
return oss.str(); return oss.str();