| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
| 5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
| 6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
| 7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
| 8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
| 9 */ | 9 */ |
| 10 | 10 |
| 11 #include "webrtc/modules/rtp_rtcp/source/vp8_partition_aggregator.h" | 11 #include "webrtc/modules/rtp_rtcp/source/vp8_partition_aggregator.h" |
| 12 | 12 |
| 13 #include <assert.h> | 13 #include <assert.h> |
| 14 #include <stdlib.h> // NULL | 14 #include <stdlib.h> // nullptr |
| 15 | 15 |
| 16 #include <algorithm> | 16 #include <algorithm> |
| 17 #include <limits> | 17 #include <limits> |
| 18 | 18 |
| 19 namespace webrtc { | 19 namespace webrtc { |
| 20 | 20 |
| 21 PartitionTreeNode::PartitionTreeNode(PartitionTreeNode* parent, | 21 PartitionTreeNode::PartitionTreeNode(PartitionTreeNode* parent, |
| 22 const size_t* size_vector, | 22 const size_t* size_vector, |
| 23 size_t num_partitions, | 23 size_t num_partitions, |
| 24 size_t this_size) | 24 size_t this_size) |
| 25 : parent_(parent), | 25 : parent_(parent), |
| 26 this_size_(this_size), | 26 this_size_(this_size), |
| 27 size_vector_(size_vector), | 27 size_vector_(size_vector), |
| 28 num_partitions_(num_partitions), | 28 num_partitions_(num_partitions), |
| 29 max_parent_size_(0), | 29 max_parent_size_(0), |
| 30 min_parent_size_(std::numeric_limits<int>::max()), | 30 min_parent_size_(std::numeric_limits<int>::max()), |
| 31 packet_start_(false) { | 31 packet_start_(false) { |
| 32 // If |this_size_| > INT_MAX, Cost() and CreateChildren() won't work properly. | 32 // If |this_size_| > INT_MAX, Cost() and CreateChildren() won't work properly. |
| 33 assert(this_size_ <= static_cast<size_t>(std::numeric_limits<int>::max())); | 33 assert(this_size_ <= static_cast<size_t>(std::numeric_limits<int>::max())); |
| 34 children_[kLeftChild] = NULL; | 34 children_[kLeftChild] = nullptr; |
| 35 children_[kRightChild] = NULL; | 35 children_[kRightChild] = nullptr; |
| 36 } | 36 } |
| 37 | 37 |
| 38 PartitionTreeNode* PartitionTreeNode::CreateRootNode(const size_t* size_vector, | 38 PartitionTreeNode* PartitionTreeNode::CreateRootNode(const size_t* size_vector, |
| 39 size_t num_partitions) { | 39 size_t num_partitions) { |
| 40 PartitionTreeNode* root_node = new PartitionTreeNode( | 40 PartitionTreeNode* root_node = new PartitionTreeNode( |
| 41 NULL, &size_vector[1], num_partitions - 1, size_vector[0]); | 41 nullptr, &size_vector[1], num_partitions - 1, size_vector[0]); |
| 42 root_node->set_packet_start(true); | 42 root_node->set_packet_start(true); |
| 43 return root_node; | 43 return root_node; |
| 44 } | 44 } |
| 45 | 45 |
| 46 PartitionTreeNode::~PartitionTreeNode() { | 46 PartitionTreeNode::~PartitionTreeNode() { |
| 47 delete children_[kLeftChild]; | 47 delete children_[kLeftChild]; |
| 48 delete children_[kRightChild]; | 48 delete children_[kRightChild]; |
| 49 } | 49 } |
| 50 | 50 |
| 51 int PartitionTreeNode::Cost(size_t penalty) { | 51 int PartitionTreeNode::Cost(size_t penalty) { |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 85 std::min(min_parent_size_, this_size_int())); | 85 std::min(min_parent_size_, this_size_int())); |
| 86 // "Right" child starts a new packet. | 86 // "Right" child starts a new packet. |
| 87 children_[kRightChild]->set_packet_start(true); | 87 children_[kRightChild]->set_packet_start(true); |
| 88 children_created = true; | 88 children_created = true; |
| 89 } | 89 } |
| 90 } | 90 } |
| 91 return children_created; | 91 return children_created; |
| 92 } | 92 } |
| 93 | 93 |
| 94 size_t PartitionTreeNode::NumPackets() { | 94 size_t PartitionTreeNode::NumPackets() { |
| 95 if (parent_ == NULL) { | 95 if (parent_ == nullptr) { |
| 96 // Root node is a "right" child by definition. | 96 // Root node is a "right" child by definition. |
| 97 return 1; | 97 return 1; |
| 98 } | 98 } |
| 99 if (parent_->children_[kLeftChild] == this) { | 99 if (parent_->children_[kLeftChild] == this) { |
| 100 // This is a "left" child. | 100 // This is a "left" child. |
| 101 return parent_->NumPackets(); | 101 return parent_->NumPackets(); |
| 102 } else { | 102 } else { |
| 103 // This is a "right" child. | 103 // This is a "right" child. |
| 104 return 1 + parent_->NumPackets(); | 104 return 1 + parent_->NumPackets(); |
| 105 } | 105 } |
| 106 } | 106 } |
| 107 | 107 |
| 108 PartitionTreeNode* PartitionTreeNode::GetOptimalNode(size_t max_size, | 108 PartitionTreeNode* PartitionTreeNode::GetOptimalNode(size_t max_size, |
| 109 size_t penalty) { | 109 size_t penalty) { |
| 110 CreateChildren(max_size); | 110 CreateChildren(max_size); |
| 111 PartitionTreeNode* left = children_[kLeftChild]; | 111 PartitionTreeNode* left = children_[kLeftChild]; |
| 112 PartitionTreeNode* right = children_[kRightChild]; | 112 PartitionTreeNode* right = children_[kRightChild]; |
| 113 if ((left == NULL) && (right == NULL)) { | 113 if ((left == nullptr) && (right == nullptr)) { |
| 114 // This is a solution node; return it. | 114 // This is a solution node; return it. |
| 115 return this; | 115 return this; |
| 116 } else if (left == NULL) { | 116 } else if (left == nullptr) { |
| 117 // One child empty, return the other. | 117 // One child empty, return the other. |
| 118 return right->GetOptimalNode(max_size, penalty); | 118 return right->GetOptimalNode(max_size, penalty); |
| 119 } else if (right == NULL) { | 119 } else if (right == nullptr) { |
| 120 // One child empty, return the other. | 120 // One child empty, return the other. |
| 121 return left->GetOptimalNode(max_size, penalty); | 121 return left->GetOptimalNode(max_size, penalty); |
| 122 } else { | 122 } else { |
| 123 PartitionTreeNode* first; | 123 PartitionTreeNode* first; |
| 124 PartitionTreeNode* second; | 124 PartitionTreeNode* second; |
| 125 if (left->Cost(penalty) <= right->Cost(penalty)) { | 125 if (left->Cost(penalty) <= right->Cost(penalty)) { |
| 126 first = left; | 126 first = left; |
| 127 second = right; | 127 second = right; |
| 128 } else { | 128 } else { |
| 129 first = right; | 129 first = right; |
| 130 second = left; | 130 second = left; |
| 131 } | 131 } |
| 132 first = first->GetOptimalNode(max_size, penalty); | 132 first = first->GetOptimalNode(max_size, penalty); |
| 133 if (second->Cost(penalty) <= first->Cost(penalty)) { | 133 if (second->Cost(penalty) <= first->Cost(penalty)) { |
| 134 second = second->GetOptimalNode(max_size, penalty); | 134 second = second->GetOptimalNode(max_size, penalty); |
| 135 // Compare cost estimate for "second" with actual cost for "first". | 135 // Compare cost estimate for "second" with actual cost for "first". |
| 136 if (second->Cost(penalty) < first->Cost(penalty)) { | 136 if (second->Cost(penalty) < first->Cost(penalty)) { |
| 137 return second; | 137 return second; |
| 138 } | 138 } |
| 139 } | 139 } |
| 140 return first; | 140 return first; |
| 141 } | 141 } |
| 142 } | 142 } |
| 143 | 143 |
| 144 Vp8PartitionAggregator::Vp8PartitionAggregator( | 144 Vp8PartitionAggregator::Vp8PartitionAggregator( |
| 145 const RTPFragmentationHeader& fragmentation, | 145 const RTPFragmentationHeader& fragmentation, |
| 146 size_t first_partition_idx, | 146 size_t first_partition_idx, |
| 147 size_t last_partition_idx) | 147 size_t last_partition_idx) |
| 148 : root_(NULL), | 148 : root_(nullptr), |
| 149 num_partitions_(last_partition_idx - first_partition_idx + 1), | 149 num_partitions_(last_partition_idx - first_partition_idx + 1), |
| 150 size_vector_(new size_t[num_partitions_]), | 150 size_vector_(new size_t[num_partitions_]), |
| 151 largest_partition_size_(0) { | 151 largest_partition_size_(0) { |
| 152 assert(last_partition_idx >= first_partition_idx); | 152 assert(last_partition_idx >= first_partition_idx); |
| 153 assert(last_partition_idx < fragmentation.fragmentationVectorSize); | 153 assert(last_partition_idx < fragmentation.fragmentationVectorSize); |
| 154 for (size_t i = 0; i < num_partitions_; ++i) { | 154 for (size_t i = 0; i < num_partitions_; ++i) { |
| 155 size_vector_[i] = | 155 size_vector_[i] = |
| 156 fragmentation.fragmentationLength[i + first_partition_idx]; | 156 fragmentation.fragmentationLength[i + first_partition_idx]; |
| 157 largest_partition_size_ = | 157 largest_partition_size_ = |
| 158 std::max(largest_partition_size_, size_vector_[i]); | 158 std::max(largest_partition_size_, size_vector_[i]); |
| (...skipping 18 matching lines...) Expand all Loading... |
| 177 Vp8PartitionAggregator::FindOptimalConfiguration(size_t max_size, | 177 Vp8PartitionAggregator::FindOptimalConfiguration(size_t max_size, |
| 178 size_t penalty) { | 178 size_t penalty) { |
| 179 assert(root_); | 179 assert(root_); |
| 180 assert(max_size >= largest_partition_size_); | 180 assert(max_size >= largest_partition_size_); |
| 181 PartitionTreeNode* opt = root_->GetOptimalNode(max_size, penalty); | 181 PartitionTreeNode* opt = root_->GetOptimalNode(max_size, penalty); |
| 182 ConfigVec config_vector(num_partitions_, 0); | 182 ConfigVec config_vector(num_partitions_, 0); |
| 183 PartitionTreeNode* temp_node = opt; | 183 PartitionTreeNode* temp_node = opt; |
| 184 size_t packet_index = opt->NumPackets(); | 184 size_t packet_index = opt->NumPackets(); |
| 185 for (size_t i = num_partitions_; i > 0; --i) { | 185 for (size_t i = num_partitions_; i > 0; --i) { |
| 186 assert(packet_index > 0); | 186 assert(packet_index > 0); |
| 187 assert(temp_node != NULL); | 187 assert(temp_node != nullptr); |
| 188 config_vector[i - 1] = packet_index - 1; | 188 config_vector[i - 1] = packet_index - 1; |
| 189 if (temp_node->packet_start()) | 189 if (temp_node->packet_start()) |
| 190 --packet_index; | 190 --packet_index; |
| 191 temp_node = temp_node->parent(); | 191 temp_node = temp_node->parent(); |
| 192 } | 192 } |
| 193 return config_vector; | 193 return config_vector; |
| 194 } | 194 } |
| 195 | 195 |
| 196 void Vp8PartitionAggregator::CalcMinMax(const ConfigVec& config, | 196 void Vp8PartitionAggregator::CalcMinMax(const ConfigVec& config, |
| 197 int* min_size, | 197 int* min_size, |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 259 best_cost = cost; | 259 best_cost = cost; |
| 260 } | 260 } |
| 261 } | 261 } |
| 262 assert(num_fragments > 0); | 262 assert(num_fragments > 0); |
| 263 // TODO(mflodman) Assert disabled since it's falsely triggered, see issue 293. | 263 // TODO(mflodman) Assert disabled since it's falsely triggered, see issue 293. |
| 264 // assert(large_partition_size / num_fragments + 1 <= max_payload_size); | 264 // assert(large_partition_size / num_fragments + 1 <= max_payload_size); |
| 265 return num_fragments; | 265 return num_fragments; |
| 266 } | 266 } |
| 267 | 267 |
| 268 } // namespace webrtc | 268 } // namespace webrtc |
| OLD | NEW |