mirror of
https://chromium.googlesource.com/libyuv/libyuv
synced 2025-12-06 16:56:55 +08:00
Fix odd length HammingDistance
If length of HammingDistance was not a multiple of 4, the result was incorrect. The old tests did not catch this so a new test is done to count 1s. Bug: libyuv:740 Test: LibYUVCompareTest.TestHammingDistance Change-Id: I93db5437821c597f1f162ac263d4a594bb83231f Reviewed-on: https://chromium-review.googlesource.com/699614 Reviewed-by: richard winterton <rrwinterton@gmail.com> Reviewed-by: Cheng Wang <wangcheng@google.com> Reviewed-by: Frank Barchard <fbarchard@google.com> Commit-Queue: Frank Barchard <fbarchard@google.com>
This commit is contained in:
parent
fecd741794
commit
1734712a6f
@ -1,6 +1,6 @@
|
|||||||
Name: libyuv
|
Name: libyuv
|
||||||
URL: http://code.google.com/p/libyuv/
|
URL: http://code.google.com/p/libyuv/
|
||||||
Version: 1672
|
Version: 1673
|
||||||
License: BSD
|
License: BSD
|
||||||
License File: LICENSE
|
License File: LICENSE
|
||||||
|
|
||||||
|
|||||||
@ -11,6 +11,6 @@
|
|||||||
#ifndef INCLUDE_LIBYUV_VERSION_H_
|
#ifndef INCLUDE_LIBYUV_VERSION_H_
|
||||||
#define INCLUDE_LIBYUV_VERSION_H_
|
#define INCLUDE_LIBYUV_VERSION_H_
|
||||||
|
|
||||||
#define LIBYUV_VERSION 1672
|
#define LIBYUV_VERSION 1673
|
||||||
|
|
||||||
#endif // INCLUDE_LIBYUV_VERSION_H_
|
#endif // INCLUDE_LIBYUV_VERSION_H_
|
||||||
|
|||||||
@ -115,8 +115,9 @@ uint64 ComputeHammingDistance(const uint8* src_a,
|
|||||||
const uint8* src_b,
|
const uint8* src_b,
|
||||||
int count) {
|
int count) {
|
||||||
const int kBlockSize = 65536;
|
const int kBlockSize = 65536;
|
||||||
|
const int kSimdSize = 64;
|
||||||
// SIMD for multiple of 64, and C for remainder
|
// SIMD for multiple of 64, and C for remainder
|
||||||
int remainder = count & (kBlockSize - 1) & ~63;
|
int remainder = count & (kBlockSize - 1) & ~(kSimdSize - 1);
|
||||||
uint64 diff = 0;
|
uint64 diff = 0;
|
||||||
int i;
|
int i;
|
||||||
uint32 (*HammingDistance)(const uint8* src_a, const uint8* src_b, int count) =
|
uint32 (*HammingDistance)(const uint8* src_a, const uint8* src_b, int count) =
|
||||||
@ -159,7 +160,7 @@ uint64 ComputeHammingDistance(const uint8* src_a,
|
|||||||
src_a += remainder;
|
src_a += remainder;
|
||||||
src_b += remainder;
|
src_b += remainder;
|
||||||
}
|
}
|
||||||
remainder = count & 31;
|
remainder = count & (kSimdSize - 1);
|
||||||
if (remainder) {
|
if (remainder) {
|
||||||
diff += HammingDistance_C(src_a, src_b, remainder);
|
diff += HammingDistance_C(src_a, src_b, remainder);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -18,7 +18,7 @@ extern "C" {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if ORIGINAL_OPT
|
#if ORIGINAL_OPT
|
||||||
uint32 HammingDistance_C(const uint8* src_a, const uint8* src_b, int count) {
|
uint32 HammingDistance_C1(const uint8* src_a, const uint8* src_b, int count) {
|
||||||
uint32 diff = 0u;
|
uint32 diff = 0u;
|
||||||
|
|
||||||
int i;
|
int i;
|
||||||
@ -58,6 +58,16 @@ uint32 HammingDistance_C(const uint8* src_a, const uint8* src_b, int count) {
|
|||||||
src_a += 4;
|
src_a += 4;
|
||||||
src_b += 4;
|
src_b += 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (; i < count; ++i) {
|
||||||
|
uint32 x = *src_a ^ *src_b;
|
||||||
|
uint32 u = x - ((x >> 1) & 0x55);
|
||||||
|
u = ((u >> 2) & 0x33) + (u & 0x33);
|
||||||
|
diff += (u + (u >> 4)) & 0x0f;
|
||||||
|
src_a += 1;
|
||||||
|
src_b += 1;
|
||||||
|
}
|
||||||
|
|
||||||
return diff;
|
return diff;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -316,6 +316,23 @@ TEST_F(LibYUVCompareTest, BenchmarkHammingDistance) {
|
|||||||
free_aligned_buffer_page_end(src_b);
|
free_aligned_buffer_page_end(src_b);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_F(LibYUVCompareTest, TestHammingDistance) {
|
||||||
|
align_buffer_page_end(src_a, benchmark_width_ * benchmark_height_);
|
||||||
|
align_buffer_page_end(src_b, benchmark_width_ * benchmark_height_);
|
||||||
|
memset(src_a, 255u, benchmark_width_ * benchmark_height_);
|
||||||
|
memset(src_b, 0, benchmark_width_ * benchmark_height_);
|
||||||
|
|
||||||
|
uint64 h1 = 0;
|
||||||
|
for (int i = 0; i < benchmark_iterations_; ++i) {
|
||||||
|
h1 = ComputeHammingDistance(src_a, src_b,
|
||||||
|
benchmark_width_ * benchmark_height_);
|
||||||
|
}
|
||||||
|
EXPECT_EQ(benchmark_width_ * benchmark_height_ * 8ULL, h1);
|
||||||
|
|
||||||
|
free_aligned_buffer_page_end(src_a);
|
||||||
|
free_aligned_buffer_page_end(src_b);
|
||||||
|
}
|
||||||
|
|
||||||
TEST_F(LibYUVCompareTest, BenchmarkSumSquareError_Opt) {
|
TEST_F(LibYUVCompareTest, BenchmarkSumSquareError_Opt) {
|
||||||
const int kMaxWidth = 4096 * 3;
|
const int kMaxWidth = 4096 * 3;
|
||||||
align_buffer_page_end(src_a, kMaxWidth);
|
align_buffer_page_end(src_a, kMaxWidth);
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user