| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (c) 2014 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2014 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 |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 52 } riff; | 52 } riff; |
| 53 FmtSubchunk fmt; | 53 FmtSubchunk fmt; |
| 54 struct { | 54 struct { |
| 55 ChunkHeader header; | 55 ChunkHeader header; |
| 56 } data; | 56 } data; |
| 57 }; | 57 }; |
| 58 static_assert(sizeof(WavHeader) == kWavHeaderSize, "no padding in header"); | 58 static_assert(sizeof(WavHeader) == kWavHeaderSize, "no padding in header"); |
| 59 | 59 |
| 60 } // namespace | 60 } // namespace |
| 61 | 61 |
| 62 bool CheckWavParameters(int num_channels, | 62 bool CheckWavParameters(size_t num_channels, |
| 63 int sample_rate, | 63 int sample_rate, |
| 64 WavFormat format, | 64 WavFormat format, |
| 65 size_t bytes_per_sample, | 65 size_t bytes_per_sample, |
| 66 size_t num_samples) { | 66 size_t num_samples) { |
| 67 // num_channels, sample_rate, and bytes_per_sample must be positive, must fit | 67 // num_channels, sample_rate, and bytes_per_sample must be positive, must fit |
| 68 // in their respective fields, and their product must fit in the 32-bit | 68 // in their respective fields, and their product must fit in the 32-bit |
| 69 // ByteRate field. | 69 // ByteRate field. |
| 70 if (num_channels <= 0 || sample_rate <= 0 || bytes_per_sample == 0) | 70 if (num_channels == 0 || sample_rate <= 0 || bytes_per_sample == 0) |
| 71 return false; | 71 return false; |
| 72 if (static_cast<uint64_t>(sample_rate) > std::numeric_limits<uint32_t>::max()) | 72 if (static_cast<uint64_t>(sample_rate) > std::numeric_limits<uint32_t>::max()) |
| 73 return false; | 73 return false; |
| 74 if (static_cast<uint64_t>(num_channels) > | 74 if (num_channels > std::numeric_limits<uint16_t>::max()) |
| 75 std::numeric_limits<uint16_t>::max()) | |
| 76 return false; | 75 return false; |
| 77 if (static_cast<uint64_t>(bytes_per_sample) * 8 > | 76 if (static_cast<uint64_t>(bytes_per_sample) * 8 > |
| 78 std::numeric_limits<uint16_t>::max()) | 77 std::numeric_limits<uint16_t>::max()) |
| 79 return false; | 78 return false; |
| 80 if (static_cast<uint64_t>(sample_rate) * num_channels * bytes_per_sample > | 79 if (static_cast<uint64_t>(sample_rate) * num_channels * bytes_per_sample > |
| 81 std::numeric_limits<uint32_t>::max()) | 80 std::numeric_limits<uint32_t>::max()) |
| 82 return false; | 81 return false; |
| 83 | 82 |
| 84 // format and bytes_per_sample must agree. | 83 // format and bytes_per_sample must agree. |
| 85 switch (format) { | 84 switch (format) { |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 129 } | 128 } |
| 130 #else | 129 #else |
| 131 #error "Write be-to-le conversion functions" | 130 #error "Write be-to-le conversion functions" |
| 132 #endif | 131 #endif |
| 133 | 132 |
| 134 static inline uint32_t RiffChunkSize(size_t bytes_in_payload) { | 133 static inline uint32_t RiffChunkSize(size_t bytes_in_payload) { |
| 135 return static_cast<uint32_t>( | 134 return static_cast<uint32_t>( |
| 136 bytes_in_payload + kWavHeaderSize - sizeof(ChunkHeader)); | 135 bytes_in_payload + kWavHeaderSize - sizeof(ChunkHeader)); |
| 137 } | 136 } |
| 138 | 137 |
| 139 static inline uint32_t ByteRate(int num_channels, int sample_rate, | 138 static inline uint32_t ByteRate(size_t num_channels, int sample_rate, |
| 140 size_t bytes_per_sample) { | 139 size_t bytes_per_sample) { |
| 141 return static_cast<uint32_t>(num_channels * sample_rate * bytes_per_sample); | 140 return static_cast<uint32_t>(num_channels * sample_rate * bytes_per_sample); |
| 142 } | 141 } |
| 143 | 142 |
| 144 static inline uint16_t BlockAlign(int num_channels, size_t bytes_per_sample) { | 143 static inline uint16_t BlockAlign(size_t num_channels, |
| 144 size_t bytes_per_sample) { |
| 145 return static_cast<uint16_t>(num_channels * bytes_per_sample); | 145 return static_cast<uint16_t>(num_channels * bytes_per_sample); |
| 146 } | 146 } |
| 147 | 147 |
| 148 void WriteWavHeader(uint8_t* buf, | 148 void WriteWavHeader(uint8_t* buf, |
| 149 int num_channels, | 149 size_t num_channels, |
| 150 int sample_rate, | 150 int sample_rate, |
| 151 WavFormat format, | 151 WavFormat format, |
| 152 size_t bytes_per_sample, | 152 size_t bytes_per_sample, |
| 153 size_t num_samples) { | 153 size_t num_samples) { |
| 154 RTC_CHECK(CheckWavParameters(num_channels, sample_rate, format, | 154 RTC_CHECK(CheckWavParameters(num_channels, sample_rate, format, |
| 155 bytes_per_sample, num_samples)); | 155 bytes_per_sample, num_samples)); |
| 156 | 156 |
| 157 WavHeader header; | 157 WavHeader header; |
| 158 const size_t bytes_in_payload = bytes_per_sample * num_samples; | 158 const size_t bytes_in_payload = bytes_per_sample * num_samples; |
| 159 | 159 |
| (...skipping 14 matching lines...) Expand all Loading... |
| 174 | 174 |
| 175 WriteFourCC(&header.data.header.ID, 'd', 'a', 't', 'a'); | 175 WriteFourCC(&header.data.header.ID, 'd', 'a', 't', 'a'); |
| 176 WriteLE32(&header.data.header.Size, static_cast<uint32_t>(bytes_in_payload)); | 176 WriteLE32(&header.data.header.Size, static_cast<uint32_t>(bytes_in_payload)); |
| 177 | 177 |
| 178 // Do an extra copy rather than writing everything to buf directly, since buf | 178 // Do an extra copy rather than writing everything to buf directly, since buf |
| 179 // might not be correctly aligned. | 179 // might not be correctly aligned. |
| 180 memcpy(buf, &header, kWavHeaderSize); | 180 memcpy(buf, &header, kWavHeaderSize); |
| 181 } | 181 } |
| 182 | 182 |
| 183 bool ReadWavHeader(ReadableWav* readable, | 183 bool ReadWavHeader(ReadableWav* readable, |
| 184 int* num_channels, | 184 size_t* num_channels, |
| 185 int* sample_rate, | 185 int* sample_rate, |
| 186 WavFormat* format, | 186 WavFormat* format, |
| 187 size_t* bytes_per_sample, | 187 size_t* bytes_per_sample, |
| 188 size_t* num_samples) { | 188 size_t* num_samples) { |
| 189 WavHeader header; | 189 WavHeader header; |
| 190 if (readable->Read(&header, kWavHeaderSize - sizeof(header.data)) != | 190 if (readable->Read(&header, kWavHeaderSize - sizeof(header.data)) != |
| 191 kWavHeaderSize - sizeof(header.data)) | 191 kWavHeaderSize - sizeof(header.data)) |
| 192 return false; | 192 return false; |
| 193 | 193 |
| 194 const uint32_t fmt_size = ReadLE32(header.fmt.header.Size); | 194 const uint32_t fmt_size = ReadLE32(header.fmt.header.Size); |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 234 if (ReadLE16(header.fmt.BlockAlign) != | 234 if (ReadLE16(header.fmt.BlockAlign) != |
| 235 BlockAlign(*num_channels, *bytes_per_sample)) | 235 BlockAlign(*num_channels, *bytes_per_sample)) |
| 236 return false; | 236 return false; |
| 237 | 237 |
| 238 return CheckWavParameters(*num_channels, *sample_rate, *format, | 238 return CheckWavParameters(*num_channels, *sample_rate, *format, |
| 239 *bytes_per_sample, *num_samples); | 239 *bytes_per_sample, *num_samples); |
| 240 } | 240 } |
| 241 | 241 |
| 242 | 242 |
| 243 } // namespace webrtc | 243 } // namespace webrtc |
| OLD | NEW |