Compare commits
1948 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
0ae1628f7e | ||
![]() |
d46f614ca9 | ||
![]() |
a6ff396576 | ||
![]() |
2acb7fc1d3 | ||
![]() |
3cc90a6d18 | ||
![]() |
baefd61752 | ||
![]() |
546a210259 | ||
![]() |
a08f27150d | ||
![]() |
768b018d18 | ||
![]() |
c9a459216d | ||
![]() |
be5df60801 | ||
![]() |
30a5cd80e2 | ||
![]() |
0ea4e229a7 | ||
![]() |
be4561248d | ||
![]() |
7255ff9b85 | ||
![]() |
cfc6dc8db3 | ||
![]() |
4934e52e43 | ||
![]() |
5cc8df5bcf | ||
![]() |
a4e453f668 | ||
![]() |
ac4dc51027 | ||
![]() |
000c276ffa | ||
![]() |
9336197663 | ||
![]() |
742e93f030 | ||
![]() |
c9b6c5d5ad | ||
![]() |
47f22fc5fb | ||
![]() |
cb63aefa45 | ||
![]() |
b2c6e1410f | ||
![]() |
ee37046f1b | ||
![]() |
99fa889f91 | ||
![]() |
c3ba5c521e | ||
![]() |
eae638db15 | ||
![]() |
c706c02291 | ||
![]() |
2b9c017cf0 | ||
![]() |
1d6f930517 | ||
![]() |
01b19a1c3e | ||
![]() |
4127799a91 | ||
![]() |
d636fe53af | ||
![]() |
81e78a1d5f | ||
![]() |
d467bbe11e | ||
![]() |
70b86af22e | ||
![]() |
20521c394c | ||
![]() |
e0b28ad696 | ||
![]() |
5476ab095f | ||
![]() |
fe72ba15ac | ||
![]() |
382afcab98 | ||
![]() |
e358cf0a43 | ||
![]() |
cd83802885 | ||
![]() |
39de45d3cc | ||
![]() |
db49a22cfa | ||
![]() |
debd86ec82 | ||
![]() |
8edd5051aa | ||
![]() |
25d9adb74b | ||
![]() |
872e34ae8d | ||
![]() |
7b9984b386 | ||
![]() |
239511fad8 | ||
![]() |
223f9e3671 | ||
![]() |
aa5e9c6a7c | ||
![]() |
9037a05041 | ||
![]() |
2b800d9394 | ||
![]() |
f4b1eca53e | ||
![]() |
a6fdfda44c | ||
![]() |
343ef23db0 | ||
![]() |
9c9de8a8ce | ||
![]() |
99e1784525 | ||
![]() |
1000e07609 | ||
![]() |
60a3cb9ad8 | ||
![]() |
8af243cfba | ||
![]() |
e9ea629b13 | ||
![]() |
b08a0b07d4 | ||
![]() |
2cc5c8f97c | ||
![]() |
3abdb1ca65 | ||
![]() |
c13aaf7a3e | ||
![]() |
4bff5bca92 | ||
![]() |
1ae97b4a4d | ||
![]() |
920f4ab8f8 | ||
![]() |
c101a5f5c4 | ||
![]() |
5192ce92b8 | ||
![]() |
a09acf7e19 | ||
![]() |
3cb9c5ffe9 | ||
![]() |
62c4747532 | ||
![]() |
1f82e06122 | ||
![]() |
4a20caef78 | ||
![]() |
126a3718fc | ||
![]() |
7a9a46fb53 | ||
![]() |
8b263798d0 | ||
![]() |
c5630b9e6c | ||
![]() |
52da0428be | ||
![]() |
907e966adf | ||
![]() |
726b021a12 | ||
![]() |
4038632fab | ||
![]() |
0dad4e2997 | ||
![]() |
0f9521f0a8 | ||
![]() |
ca28740570 | ||
![]() |
215bddf324 | ||
![]() |
da7a7089c6 | ||
![]() |
2640f25072 | ||
![]() |
d07a5bfbf8 | ||
![]() |
b986ba84b3 | ||
![]() |
e97804c67d | ||
![]() |
b24e377008 | ||
![]() |
f3adb45914 | ||
![]() |
5dfb01bb30 | ||
![]() |
944e83ad32 | ||
![]() |
ddb3d7a8a1 | ||
![]() |
881c8ec816 | ||
![]() |
a3f09c03b8 | ||
![]() |
0e97e70496 | ||
![]() |
5c5dc73320 | ||
![]() |
13d0955b25 | ||
![]() |
f9a13a1786 | ||
![]() |
1f41c0d37f | ||
![]() |
8276005eba | ||
![]() |
60beb781c1 | ||
![]() |
ae856e4012 | ||
![]() |
6b2cc75622 | ||
![]() |
f50ad31ec1 | ||
![]() |
f0a3979063 | ||
![]() |
b0d57f682d | ||
![]() |
9351f96069 | ||
![]() |
d8424d2890 | ||
![]() |
6f9163db95 | ||
![]() |
c257d608fc | ||
![]() |
88dc0d6062 | ||
![]() |
7b278e3072 | ||
![]() |
118a57045b | ||
![]() |
fc1302cd8b | ||
![]() |
95a71057f0 | ||
![]() |
7b5a57449b | ||
![]() |
025b138679 | ||
![]() |
312745cac4 | ||
![]() |
3223a3f892 | ||
![]() |
c12398fe81 | ||
![]() |
7987f35391 | ||
![]() |
6ed4c253a9 | ||
![]() |
0bee6de332 | ||
![]() |
7195a2eaa4 | ||
![]() |
d18477b449 | ||
![]() |
c244a86234 | ||
![]() |
e0b88b5c00 | ||
![]() |
c6fcb9bb94 | ||
![]() |
0685ec767c | ||
![]() |
ac07cc89f1 | ||
![]() |
5ac63d15dc | ||
![]() |
4d8958d8dd | ||
![]() |
6cc33c1626 | ||
![]() |
29fbddec83 | ||
![]() |
932835677f | ||
![]() |
7aa588debd | ||
![]() |
88c2386447 | ||
![]() |
09ce3177bb | ||
![]() |
3c6dc743aa | ||
![]() |
8de0404ed9 | ||
![]() |
90d54a15fb | ||
![]() |
167594414f | ||
![]() |
acac262663 | ||
![]() |
e3c6d30294 | ||
![]() |
dccb8b45bb | ||
![]() |
29b6a30cd9 | ||
![]() |
c1435e321c | ||
![]() |
93da1ba2dc | ||
![]() |
1a7b256f06 | ||
![]() |
03e043e06c | ||
![]() |
811b2e412e | ||
![]() |
edc9a46876 | ||
![]() |
4410d729d1 | ||
![]() |
11b55a0614 | ||
![]() |
46adbc4af8 | ||
![]() |
efaaf387fc | ||
![]() |
62b013abe8 | ||
![]() |
c930ea7dcd | ||
![]() |
2fa333c2ae | ||
![]() |
4e5b4b5848 | ||
![]() |
b78dad3ffa | ||
![]() |
1acc25f11b | ||
![]() |
0f3edc6625 | ||
![]() |
d8497e1fcd | ||
![]() |
c104f4cbdc | ||
![]() |
82e9c30334 | ||
![]() |
3636330490 | ||
![]() |
0fe4371cc0 | ||
![]() |
ac54d233b6 | ||
![]() |
519fed01c2 | ||
![]() |
73d1236384 | ||
![]() |
534e9af53b | ||
![]() |
79c14b83e9 | ||
![]() |
14b21b84e3 | ||
![]() |
cb16652598 | ||
![]() |
2c950e131c | ||
![]() |
41d3331d42 | ||
![]() |
efa786d464 | ||
![]() |
658eb1d675 | ||
![]() |
7edd1a6cea | ||
![]() |
848d6004a4 | ||
![]() |
fdb64ec289 | ||
![]() |
8001c5c7a8 | ||
![]() |
c59c84fc74 | ||
![]() |
de3a7e2630 | ||
![]() |
8f952bada7 | ||
![]() |
254e2f5501 | ||
![]() |
5eca3c23c3 | ||
![]() |
e14e9c9964 | ||
![]() |
b14b616d96 | ||
![]() |
ddf40ec156 | ||
![]() |
9a96b18f03 | ||
![]() |
77108f5001 | ||
![]() |
7e75e8a622 | ||
![]() |
903bc150da | ||
![]() |
884d1681f8 | ||
![]() |
2654afc16c | ||
![]() |
ea1d0a6b53 | ||
![]() |
738b829b8c | ||
![]() |
3fa713caee | ||
![]() |
cc91abb325 | ||
![]() |
a9bbff1049 | ||
![]() |
067457339b | ||
![]() |
d069f4c29d | ||
![]() |
cee96c7d85 | ||
![]() |
43caed4e42 | ||
![]() |
15b261d854 | ||
![]() |
3bfadfcd62 | ||
![]() |
f80be22a10 | ||
![]() |
6248f0c91f | ||
![]() |
3b85a5beb7 | ||
![]() |
cb9f4dc105 | ||
![]() |
b9e44842fc | ||
![]() |
7c69136494 | ||
![]() |
742ae4b24d | ||
![]() |
81d66e2cc6 | ||
![]() |
9f36419bf2 | ||
![]() |
d1e9635402 | ||
![]() |
dcbe6750e1 | ||
![]() |
6ee88546c0 | ||
![]() |
004fb91416 | ||
![]() |
7e14e0f109 | ||
![]() |
231012fdab | ||
![]() |
8fd648c78a | ||
![]() |
b8159fab38 | ||
![]() |
8f50e06012 | ||
![]() |
6fea41abee | ||
![]() |
d344ab03cc | ||
![]() |
2c2fea2c5b | ||
![]() |
5b6ae020b6 | ||
![]() |
3761254119 | ||
![]() |
9874ec07bd | ||
![]() |
c7449b482c | ||
![]() |
281f68a81f | ||
![]() |
68cc1dc422 | ||
![]() |
f95bf1db50 | ||
![]() |
97acbbb701 | ||
![]() |
9debbc2ec7 | ||
![]() |
740883897a | ||
![]() |
f87a4594fb | ||
![]() |
eedda5f924 | ||
![]() |
373e08f921 | ||
![]() |
7d19739949 | ||
![]() |
f915e6d4af | ||
![]() |
733820c509 | ||
![]() |
eb20d6f64c | ||
![]() |
b4fb99220b | ||
![]() |
fd7de8362d | ||
![]() |
b87250c56e | ||
![]() |
e1c69544b1 | ||
![]() |
8f25c3ff8f | ||
![]() |
8c0cd2bd76 | ||
![]() |
2879e0d2cc | ||
![]() |
f5b2dd2a66 | ||
![]() |
f8639b1554 | ||
![]() |
1633786bfb | ||
![]() |
bbdbee429f | ||
![]() |
32f86ce276 | ||
![]() |
bb4052b873 | ||
![]() |
c5dc3373db | ||
![]() |
e20ca4fead | ||
![]() |
7a41610581 | ||
![]() |
b25b2ca455 | ||
![]() |
bed28a55f5 | ||
![]() |
321f295632 | ||
![]() |
0226ce79e9 | ||
![]() |
55db4f033f | ||
![]() |
867b593caa | ||
![]() |
fe5d87aaeb | ||
![]() |
8a4336ed2e | ||
![]() |
1a7bf0d1f9 | ||
![]() |
117893a717 | ||
![]() |
84a7263d4c | ||
![]() |
7a245adb18 | ||
![]() |
de50e8052c | ||
![]() |
1a9c7bee88 | ||
![]() |
9ca9c12dbd | ||
![]() |
86842855d3 | ||
![]() |
a2127236ae | ||
![]() |
5203b40a2a | ||
![]() |
08a668af32 | ||
![]() |
09519a55c7 | ||
![]() |
7970cc02df | ||
![]() |
d95ddc7c71 | ||
![]() |
e4b3f03c64 | ||
![]() |
7d1bf5d12a | ||
![]() |
9f8433ffe2 | ||
![]() |
920ba82409 | ||
![]() |
fe4de1ff63 | ||
![]() |
6746ba6d01 | ||
![]() |
05e6e9ac83 | ||
![]() |
f2ad523461 | ||
![]() |
c58f01724c | ||
![]() |
028429310a | ||
![]() |
e9ad5d2aee | ||
![]() |
a40fa1f95d | ||
![]() |
94eaecaa91 | ||
![]() |
f9ecdc35ec | ||
![]() |
c1e511fd82 | ||
![]() |
a1689ed16b | ||
![]() |
f1ce050f44 | ||
![]() |
2a602f745d | ||
![]() |
14dbdd95e6 | ||
![]() |
bd1d995cd3 | ||
![]() |
3562d6b0a2 | ||
![]() |
575c1933ea | ||
![]() |
2e44f16443 | ||
![]() |
33953f310e | ||
![]() |
9f9d4f8dc9 | ||
![]() |
90ce21e519 | ||
![]() |
07b12aad77 | ||
![]() |
e83d00f584 | ||
![]() |
bdbecea1ba | ||
![]() |
65df957df6 | ||
![]() |
401e00792f | ||
![]() |
460dbc01b5 | ||
![]() |
8d0e7ac29a | ||
![]() |
298f5ca47d | ||
![]() |
8099220e6c | ||
![]() |
c22ab8ab9f | ||
![]() |
9dbefc4b57 | ||
![]() |
2e701f7c29 | ||
![]() |
5044779e77 | ||
![]() |
b409863c48 | ||
![]() |
392e0188f6 | ||
![]() |
8d70aef05f | ||
![]() |
9116e3d957 | ||
![]() |
3437fe484a | ||
![]() |
49f51af4c9 | ||
![]() |
0e94522338 | ||
![]() |
3ae909b0f9 | ||
![]() |
a60da3a2eb | ||
![]() |
d49bf26b1c | ||
![]() |
339f4dcaee | ||
![]() |
9966cc8d12 | ||
![]() |
c5f5f4ed17 | ||
![]() |
9bd3f1e30d | ||
![]() |
a0ca2a4079 | ||
![]() |
f0b4868625 | ||
![]() |
bd990cad72 | ||
![]() |
cbe62b9c2d | ||
![]() |
9639641cd4 | ||
![]() |
50fc0d896b | ||
![]() |
bc29863b96 | ||
![]() |
f49360d740 | ||
![]() |
dd4cc5b596 | ||
![]() |
0cc23242b0 | ||
![]() |
559166acfe | ||
![]() |
8b7a6ca60a | ||
![]() |
07a0bf038f | ||
![]() |
849b3c238d | ||
![]() |
c66eeab30e | ||
![]() |
55eacca945 | ||
![]() |
4bd2a59e9b | ||
![]() |
ea14a1a965 | ||
![]() |
44473e7eb9 | ||
![]() |
1aea1675c0 | ||
![]() |
3e3a568616 | ||
![]() |
05302360c9 | ||
![]() |
03c1a827ac | ||
![]() |
607e45f420 | ||
![]() |
b3c93d60c2 | ||
![]() |
8d471fcee2 | ||
![]() |
7839fb98a8 | ||
![]() |
9df11a7c52 | ||
![]() |
0d2555bd2e | ||
![]() |
becab42eee | ||
![]() |
a73cee2870 | ||
![]() |
55fc4d95af | ||
![]() |
2eddfb46a9 | ||
![]() |
f5817fa612 | ||
![]() |
8e6022844f | ||
![]() |
8c7213bc00 | ||
![]() |
1ff68ec035 | ||
![]() |
6c0011a255 | ||
![]() |
10cb17aec0 | ||
![]() |
6246d8aa76 | ||
![]() |
0665b09661 | ||
![]() |
fdb054a05d | ||
![]() |
2387024f41 | ||
![]() |
bdb8b3ad86 | ||
![]() |
62ab5e99c1 | ||
![]() |
d6e29868ac | ||
![]() |
adbb4c4d32 | ||
![]() |
a68bbcff29 | ||
![]() |
cf8039c25f | ||
![]() |
93e83fd7cf | ||
![]() |
6fbc354c97 | ||
![]() |
b383a17fa4 | ||
![]() |
eb7d431cb5 | ||
![]() |
5fe82459ec | ||
![]() |
3ba9a2c8b2 | ||
![]() |
34805d6d0d | ||
![]() |
0c84b9b703 | ||
![]() |
18b470f486 | ||
![]() |
c77822615e | ||
![]() |
cc47231187 | ||
![]() |
acb9460929 | ||
![]() |
3bf02ad74a | ||
![]() |
037e596f04 | ||
![]() |
ae35425ae6 | ||
![]() |
e0aa6b24aa | ||
![]() |
0738d90169 | ||
![]() |
512bf4e029 | ||
![]() |
4906cea027 | ||
![]() |
b58259ab55 | ||
![]() |
199971d606 | ||
![]() |
0c493cbe2b | ||
![]() |
d8c34a2552 | ||
![]() |
55c126a5d7 | ||
![]() |
401e6d48bf | ||
![]() |
bd6d82e881 | ||
![]() |
ec2fced451 | ||
![]() |
b3a36f7946 | ||
![]() |
df15220a89 | ||
![]() |
dbb8926b86 | ||
![]() |
9336e01621 | ||
![]() |
0d2e95193b | ||
![]() |
55805e2786 | ||
![]() |
577d4fa792 | ||
![]() |
580d32240f | ||
![]() |
a9248457b1 | ||
![]() |
12df840777 | ||
![]() |
eaa593d293 | ||
![]() |
8842ee0b0d | ||
![]() |
3e2770de4f | ||
![]() |
28d1c0535d | ||
![]() |
a673b4f4af | ||
![]() |
175b36cb6d | ||
![]() |
caa116c9be | ||
![]() |
2b247ae91c | ||
![]() |
288890cd43 | ||
![]() |
f70de09f2a | ||
![]() |
bc4098a8e9 | ||
![]() |
72c69e14ad | ||
![]() |
1fa3ec3023 | ||
![]() |
416b7051d7 | ||
![]() |
e8ed2bb762 | ||
![]() |
16166bfdaa | ||
![]() |
dcfae2cc64 | ||
![]() |
33c598990b | ||
![]() |
54f7d68c5c | ||
![]() |
017257a317 | ||
![]() |
963cc22cef | ||
![]() |
06d231c9fa | ||
![]() |
741bd6df4f | ||
![]() |
1b2f92ee8e | ||
![]() |
27d21a3d13 | ||
![]() |
e1ae3772da | ||
![]() |
9ca06bcdd2 | ||
![]() |
807248ec81 | ||
![]() |
5bc4c37a89 | ||
![]() |
bcbc6ed82d | ||
![]() |
e405eb06b1 | ||
![]() |
7af6c6c9ca | ||
![]() |
9311ef18b4 | ||
![]() |
d2fb834ebd | ||
![]() |
e8ed030da3 | ||
![]() |
107eb6a9d4 | ||
![]() |
e095bcce44 | ||
![]() |
18262a8576 | ||
![]() |
014976c251 | ||
![]() |
4bc1fc58b6 | ||
![]() |
6a42bdd25f | ||
![]() |
127864deb3 | ||
![]() |
b809442521 | ||
![]() |
77e51e2035 | ||
![]() |
9a71811d98 | ||
![]() |
ffa3a3c441 | ||
![]() |
98dbf31c87 | ||
![]() |
ab2bd340ac | ||
![]() |
66b6b87471 | ||
![]() |
bc4bc9b622 | ||
![]() |
6543213e87 | ||
![]() |
0f756a307d | ||
![]() |
c8678fb7f3 | ||
![]() |
67c38c92e7 | ||
![]() |
fe7b869104 | ||
![]() |
33e10dfa7e | ||
![]() |
0e55b0b0a7 | ||
![]() |
2c560c3c22 | ||
![]() |
3c700052be | ||
![]() |
fb7fc1dbda | ||
![]() |
c8f6e7b99e | ||
![]() |
f2c3d0a7a3 | ||
![]() |
3bbd62ed27 | ||
![]() |
4cae64c32c | ||
![]() |
5a40c8fde1 | ||
![]() |
a2ef180dd0 | ||
![]() |
3b8cc214ef | ||
![]() |
03e8f13337 | ||
![]() |
c493ea1a6b | ||
![]() |
786b124e20 | ||
![]() |
80992a746c | ||
![]() |
8d438dc313 | ||
![]() |
690fa6bb6e | ||
![]() |
6175f285a9 | ||
![]() |
dbbbd44304 | ||
![]() |
19c45ccd43 | ||
![]() |
535b7b915a | ||
![]() |
530e60143a | ||
![]() |
d203a91a09 | ||
![]() |
878464150b | ||
![]() |
f12e786c54 | ||
![]() |
767503504f | ||
![]() |
819c5b365d | ||
![]() |
d5094cfde8 | ||
![]() |
9e52d3910b | ||
![]() |
9d0d13e939 | ||
![]() |
28762341ac | ||
![]() |
73102d1ed2 | ||
![]() |
23eccb3ca7 | ||
![]() |
a059dc0986 | ||
![]() |
cf82f7276e | ||
![]() |
691585f6b8 | ||
![]() |
10bab1ec29 | ||
![]() |
0b08f8892f | ||
![]() |
42373b21ce | ||
![]() |
d586cdb4d4 | ||
![]() |
76a3d3fcc5 | ||
![]() |
64653fa133 | ||
![]() |
f7b276c26b | ||
![]() |
24afb5d036 | ||
![]() |
f407b30490 | ||
![]() |
b85e391ac8 | ||
![]() |
15bea62176 | ||
![]() |
7c0529728a | ||
![]() |
f357335c38 | ||
![]() |
bf8bdae913 | ||
![]() |
bc86e2c6a2 | ||
![]() |
aaa6cdcc2e | ||
![]() |
2a7c0e1c4b | ||
![]() |
cd463c7acb | ||
![]() |
310e388423 | ||
![]() |
ebb015a539 | ||
![]() |
a80bdfd081 | ||
![]() |
9d278465b5 | ||
![]() |
2aacfa1acd | ||
![]() |
ad31fe36a8 | ||
![]() |
65f1c90652 | ||
![]() |
08fda52e18 | ||
![]() |
90ed0d2f73 | ||
![]() |
c12b39626f | ||
![]() |
293734b755 | ||
![]() |
c24d911847 | ||
![]() |
baf658ec4c | ||
![]() |
c3a6943c16 | ||
![]() |
b81de66171 | ||
![]() |
5b558592f5 | ||
![]() |
4ca8f8f5e2 | ||
![]() |
535dee0fb6 | ||
![]() |
0726dd97d3 | ||
![]() |
949730e2dc | ||
![]() |
ed3a80cb5e | ||
![]() |
83e59914e5 | ||
![]() |
fa01426ade | ||
![]() |
eb4238ac70 | ||
![]() |
afee58f2c4 | ||
![]() |
30f1ff94e0 | ||
![]() |
c39cd9235e | ||
![]() |
a9bbe53dbb | ||
![]() |
d6c9bbc2b6 | ||
![]() |
761f2f5cb4 | ||
![]() |
fb40b5d7a7 | ||
![]() |
9dfa76f948 | ||
![]() |
5c95fd921e | ||
![]() |
9a2dd7e67e | ||
![]() |
0657f4732c | ||
![]() |
d7caee2170 | ||
![]() |
43cbdc216d | ||
![]() |
2c7b7424c5 | ||
![]() |
ef41c6286d | ||
![]() |
71b38a144e | ||
![]() |
3ec20445b2 | ||
![]() |
d5d2cbcc75 | ||
![]() |
7219f31904 | ||
![]() |
0e95039bd9 | ||
![]() |
6822fb2f09 | ||
![]() |
d331e7a1c0 | ||
![]() |
bc4bcca3fd | ||
![]() |
0095213790 | ||
![]() |
f4150163a2 | ||
![]() |
d49a1a5329 | ||
![]() |
7587a97551 | ||
![]() |
053bd263eb | ||
![]() |
be2ba48cac | ||
![]() |
334e9abb0b | ||
![]() |
9ab4d9df38 | ||
![]() |
03191f738e | ||
![]() |
d42e876164 | ||
![]() |
ab5704f02c | ||
![]() |
20973508da | ||
![]() |
ebf3ae1a29 | ||
![]() |
f8f64c309b | ||
![]() |
297c110dcb | ||
![]() |
d7ba519b9f | ||
![]() |
c39a05ff61 | ||
![]() |
2d0c11093e | ||
![]() |
f783e3a75d | ||
![]() |
fed52670a2 | ||
![]() |
2f5fb37dac | ||
![]() |
81f45ff798 | ||
![]() |
30d9a1916c | ||
![]() |
7c10251f22 | ||
![]() |
df9ce12259 | ||
![]() |
64c55576b7 | ||
![]() |
255241c6d0 | ||
![]() |
43b9e785ba | ||
![]() |
a0de2692fc | ||
![]() |
3e069846b9 | ||
![]() |
a74593b30c | ||
![]() |
8c42237bb2 | ||
![]() |
ece1989fa2 | ||
![]() |
34e48d6115 | ||
![]() |
ccae8da7c6 | ||
![]() |
6c21650c0e | ||
![]() |
9e4647c7ab | ||
![]() |
d14777157e | ||
![]() |
258122fdc6 | ||
![]() |
f60d1dcd3d | ||
![]() |
1787e7dbe0 | ||
![]() |
92aafefa1e | ||
![]() |
2dc0a5132d | ||
![]() |
d080c92524 | ||
![]() |
30c261b1eb | ||
![]() |
e89344d61a | ||
![]() |
f53b656207 | ||
![]() |
c9ff7b6637 | ||
![]() |
1aad50c092 | ||
![]() |
dfafd10ef5 | ||
![]() |
7c27872164 | ||
![]() |
2a5aa98a35 | ||
![]() |
e83d99d7b8 | ||
![]() |
59e065b6ed | ||
![]() |
0207f17144 | ||
![]() |
103e4e50a8 | ||
![]() |
a31461c853 | ||
![]() |
b9c1dcc5fa | ||
![]() |
7f2993f5e4 | ||
![]() |
75752ab7c0 | ||
![]() |
ab27b68693 | ||
![]() |
7a178a5631 | ||
![]() |
419ce36294 | ||
![]() |
bff5aa9827 | ||
![]() |
2c56bb97f2 | ||
![]() |
c02fdd0258 | ||
![]() |
b527b47312 | ||
![]() |
7b13d99b98 | ||
![]() |
661efeca97 | ||
![]() |
13eed991f9 | ||
![]() |
eab3f5e0cc | ||
![]() |
2c5478e383 | ||
![]() |
2f7497f341 | ||
![]() |
1426f04e91 | ||
![]() |
7d82e57f5b | ||
![]() |
bb15fd51be | ||
![]() |
7f602d6114 | ||
![]() |
e038d1610e | ||
![]() |
f64e14047d | ||
![]() |
372336d1e5 | ||
![]() |
f95686895b | ||
![]() |
b814e2d898 | ||
![]() |
48110d0f79 | ||
![]() |
0472382dbe | ||
![]() |
e15be3025b | ||
![]() |
6b9c691daf | ||
![]() |
14437d0fa6 | ||
![]() |
a153080b55 | ||
![]() |
c59d1a4dc7 | ||
![]() |
e9ccc6fe79 | ||
![]() |
77ed4414d6 | ||
![]() |
7e8357d664 | ||
![]() |
08cb7b5c68 | ||
![]() |
ca393c9726 | ||
![]() |
5009302bce | ||
![]() |
d72e20b123 | ||
![]() |
69775d2f40 | ||
![]() |
3f05a70c41 | ||
![]() |
fa85cf131c | ||
![]() |
ff184e482a | ||
![]() |
45b39750d6 | ||
![]() |
2caff16151 | ||
![]() |
1ab60466ec | ||
![]() |
c06d6649c5 | ||
![]() |
746c0eab3b | ||
![]() |
e702b68b6c | ||
![]() |
e022ce84ac | ||
![]() |
d48be6ad73 | ||
![]() |
0f8ebddec4 | ||
![]() |
15193ce51f | ||
![]() |
9bb8ce5efb | ||
![]() |
0b393ae505 | ||
![]() |
db8fa86a6c | ||
![]() |
39da7fb786 | ||
![]() |
68805583e9 | ||
![]() |
357adb68b2 | ||
![]() |
1092cc7f1a | ||
![]() |
93166c5e51 | ||
![]() |
d52cb59729 | ||
![]() |
427de67e63 | ||
![]() |
853165ba39 | ||
![]() |
d670678f26 | ||
![]() |
fa829e0e5a | ||
![]() |
c9fb719ee1 | ||
![]() |
7f20c3ac44 | ||
![]() |
22b6dc9fdf | ||
![]() |
0c61331244 | ||
![]() |
cbb83ba4aa | ||
![]() |
9578a84205 | ||
![]() |
c42517568d | ||
![]() |
39e8b8dac6 | ||
![]() |
e921c7ba8d | ||
![]() |
f6c6f37e0c | ||
![]() |
563d58ab84 | ||
![]() |
6624f20785 | ||
![]() |
8334a48d3a | ||
![]() |
76d77aa013 | ||
![]() |
6843e7c7f3 | ||
![]() |
15a47db730 | ||
![]() |
8c0ab7607e | ||
![]() |
bfd0f41f9b | ||
![]() |
787970a625 | ||
![]() |
b9577e07fc | ||
![]() |
698e56f26c | ||
![]() |
1059b5cc52 | ||
![]() |
632fe8286a | ||
![]() |
0e87b16022 | ||
![]() |
6738ad7aaf | ||
![]() |
c0490b52b1 | ||
![]() |
847394fe77 | ||
![]() |
3be14200fc | ||
![]() |
c22b17dcef | ||
![]() |
5d6c1c2d8f | ||
![]() |
bf14d468c1 | ||
![]() |
78e2da3e42 | ||
![]() |
2d6b5df657 | ||
![]() |
2758de5cb2 | ||
![]() |
ebb023deb6 | ||
![]() |
999bd6ea84 | ||
![]() |
f027908ad0 | ||
![]() |
78155b7ed5 | ||
![]() |
facb124941 | ||
![]() |
c9266b8547 | ||
![]() |
d35b627340 | ||
![]() |
5d0bef4763 | ||
![]() |
e48dfcead1 | ||
![]() |
ac211fe23e | ||
![]() |
064fc570ff | ||
![]() |
7105e66d19 | ||
![]() |
75653b7032 | ||
![]() |
3c73e587d1 | ||
![]() |
5232e35bc2 | ||
![]() |
7f4acf8700 | ||
![]() |
aa1c4cd140 | ||
![]() |
9c43d81bc2 | ||
![]() |
a83e1f1d53 | ||
![]() |
905b8ec27f | ||
![]() |
56d95b77f5 | ||
![]() |
1c666465af | ||
![]() |
62682ac8ad | ||
![]() |
85736e616e | ||
![]() |
666c543f7b | ||
![]() |
b0f1ae1475 | ||
![]() |
8836e46ffd | ||
![]() |
8c7a60e04d | ||
![]() |
e8bd534c42 | ||
![]() |
0c30b75f40 | ||
![]() |
494188505b | ||
![]() |
af08fbb444 | ||
![]() |
c782f27ead | ||
![]() |
4702bb26be | ||
![]() |
e1809501d0 | ||
![]() |
9dd992b6f0 | ||
![]() |
bde2e4aa36 | ||
![]() |
b72d3e8a25 | ||
![]() |
89a116f4cb | ||
![]() |
8ad9338e2e | ||
![]() |
4526644615 | ||
![]() |
59e461db1f | ||
![]() |
babef23a5f | ||
![]() |
56d3f1573a | ||
![]() |
4b9a848bb3 | ||
![]() |
fd216268ad | ||
![]() |
03f5e300d6 | ||
![]() |
101981b736 | ||
![]() |
adbfc4308a | ||
![]() |
c7ebe82253 | ||
![]() |
cb61ba02f4 | ||
![]() |
817f68cdcf | ||
![]() |
ad56371343 | ||
![]() |
0c9e2f4c15 | ||
![]() |
9223b947ca | ||
![]() |
682135fa60 | ||
![]() |
666e394d41 | ||
![]() |
e3fa4ae8e3 | ||
![]() |
960466939d | ||
![]() |
b578d59623 | ||
![]() |
e0d79bc7b5 | ||
![]() |
f6586b8bf8 | ||
![]() |
3158752980 | ||
![]() |
e381753926 | ||
![]() |
e1bde306c8 | ||
![]() |
807ce8fb1e | ||
![]() |
8152b0904d | ||
![]() |
dd4347e9ec | ||
![]() |
1dee320446 | ||
![]() |
df18412f32 | ||
![]() |
5322a31b18 | ||
![]() |
7d5afa227a | ||
![]() |
1a4d8f2033 | ||
![]() |
689ad89e86 | ||
![]() |
3818a3723b | ||
![]() |
3d6b0cb825 | ||
![]() |
66a96fd3de | ||
![]() |
87610ac45e | ||
![]() |
4b78c6e6f7 | ||
![]() |
125a532b34 | ||
![]() |
109faffe9b | ||
![]() |
2ac7c549e9 | ||
![]() |
4e16f70703 | ||
![]() |
5d6060b62f | ||
![]() |
6c375b9cd0 | ||
![]() |
e4e08556db | ||
![]() |
6ae8f8dbe8 | ||
![]() |
67cffc1ef6 | ||
![]() |
b0d15713be | ||
![]() |
527e0c9b1c | ||
![]() |
3c18acf452 | ||
![]() |
9b253f9f0a | ||
![]() |
2075af4b16 | ||
![]() |
80b83c73ba | ||
![]() |
777ca80f0a | ||
![]() |
a15c6a7ebf | ||
![]() |
8c3f18efa1 | ||
![]() |
26a9a4cd64 | ||
![]() |
d6423b3166 | ||
![]() |
63bdc574e5 | ||
![]() |
6bac3f80ee | ||
![]() |
75b00592c7 | ||
![]() |
5227b8200b | ||
![]() |
48c4a038eb | ||
![]() |
af3cab7b24 | ||
![]() |
4ffd8350be | ||
![]() |
0d245d42c4 | ||
![]() |
f2b1dc529f | ||
![]() |
e3cafbc8df | ||
![]() |
24d0391efb | ||
![]() |
9a05f9771a | ||
![]() |
a22bb9809e | ||
![]() |
3e08a88854 | ||
![]() |
23d60be414 | ||
![]() |
a6531cbc54 | ||
![]() |
b6321025cd | ||
![]() |
da2ad47d66 | ||
![]() |
5b44ef0c50 | ||
![]() |
a1af335f44 | ||
![]() |
b0459ec8ea | ||
![]() |
7d526c1654 | ||
![]() |
6cb3178192 | ||
![]() |
fb135ff050 | ||
![]() |
c757d6dde4 | ||
![]() |
d8c277030c | ||
![]() |
f7645138d4 | ||
![]() |
3dd993e4be | ||
![]() |
3ae458f2f3 | ||
![]() |
a876d04072 | ||
![]() |
8710c6d884 | ||
![]() |
329dabf57e | ||
![]() |
27e37e1a8a | ||
![]() |
af3ab45867 | ||
![]() |
5a8e4110c7 | ||
![]() |
37e03b1d13 | ||
![]() |
f781cc8a46 | ||
![]() |
2290898ac7 | ||
![]() |
1e3a93e72e | ||
![]() |
70b7713059 | ||
![]() |
303cb3106b | ||
![]() |
bc837b223b | ||
![]() |
78fe5ca360 | ||
![]() |
ba76b662af | ||
![]() |
fb134e759a | ||
![]() |
86d51dfbf5 | ||
![]() |
469986f963 | ||
![]() |
c2044fda1d | ||
![]() |
ce5b17f9ad | ||
![]() |
89d3dc043e | ||
![]() |
c338f3635e | ||
![]() |
ee5cb8d87f | ||
![]() |
0fa59a4baf | ||
![]() |
9ac78ae35f | ||
![]() |
e3c8f2f152 | ||
![]() |
dcdb013b55 | ||
![]() |
ab76f1f224 | ||
![]() |
67d7a6df2d | ||
![]() |
e5bdab98e9 | ||
![]() |
508ef2a6e3 | ||
![]() |
8d1bda93f4 | ||
![]() |
bd77931421 | ||
![]() |
74dc640565 | ||
![]() |
9fe510c12a | ||
![]() |
f310ddc470 | ||
![]() |
4959dd3eb3 | ||
![]() |
cf75ab6ccd | ||
![]() |
81e25512c3 | ||
![]() |
d91af5f905 | ||
![]() |
35f8515c3f | ||
![]() |
5ac88162b9 | ||
![]() |
ad011aaab8 | ||
![]() |
77a648885c | ||
![]() |
469643757f | ||
![]() |
e40e78be24 | ||
![]() |
46d8660ce3 | ||
![]() |
8582d33a0d | ||
![]() |
e0330c4810 | ||
![]() |
88d11f473c | ||
![]() |
515fed8f38 | ||
![]() |
a220b931f5 | ||
![]() |
d4595de5db | ||
![]() |
0bb31a46a4 | ||
![]() |
39972d999d | ||
![]() |
ddae8f7632 | ||
![]() |
a76b6b232c | ||
![]() |
f749905d0a | ||
![]() |
ec4afbf74a | ||
![]() |
30eeb4dc32 | ||
![]() |
6ff5de68dd | ||
![]() |
4bb99ee27e | ||
![]() |
ee1fcb0e69 | ||
![]() |
8ad23a072a | ||
![]() |
8253a27904 | ||
![]() |
b8a4b5dd8d | ||
![]() |
b0c4d87ac7 | ||
![]() |
0d1c782306 | ||
![]() |
54bcd98314 | ||
![]() |
18805eee6c | ||
![]() |
e187b27438 | ||
![]() |
88a302e743 | ||
![]() |
a377f99088 | ||
![]() |
794a5ad713 | ||
![]() |
b28fc490aa | ||
![]() |
4f917912b9 | ||
![]() |
c5f9de573f | ||
![]() |
92145006c3 | ||
![]() |
e67660cf37 | ||
![]() |
efe1982e63 | ||
![]() |
d7515b1187 | ||
![]() |
33a9394eb1 | ||
![]() |
dd88bd87db | ||
![]() |
828a1fa6de | ||
![]() |
7c0788b07f | ||
![]() |
44418c659f | ||
![]() |
b24ed95f44 | ||
![]() |
b093d998fc | ||
![]() |
eb8226b903 | ||
![]() |
864bc77e7a | ||
![]() |
d5d6a609d0 | ||
![]() |
1d86383512 | ||
![]() |
18335f193d | ||
![]() |
07f847873b | ||
![]() |
9a329b5285 | ||
![]() |
3f296533f6 | ||
![]() |
9e1d2de67c | ||
![]() |
21afafa31a | ||
![]() |
8cf6f78fce | ||
![]() |
fbba31e241 | ||
![]() |
355432b0d2 | ||
![]() |
466b667ff3 | ||
![]() |
42522ce0b7 | ||
![]() |
2b43a1ee18 | ||
![]() |
96ec8a425b | ||
![]() |
1c48915233 | ||
![]() |
0aa3677d9d | ||
![]() |
9e03eedf62 | ||
![]() |
d96ed96c0f | ||
![]() |
492d52b9cc | ||
![]() |
ae3a173352 | ||
![]() |
a929911339 | ||
![]() |
737aa5c9e4 | ||
![]() |
b55240057f | ||
![]() |
782aacc3d3 | ||
![]() |
4ebb9a36f1 | ||
![]() |
ed56ddfef8 | ||
![]() |
ada640a508 | ||
![]() |
ff7fb4b280 | ||
![]() |
bf41a982b4 | ||
![]() |
112cd95507 | ||
![]() |
31d6ba9a54 | ||
![]() |
038522e4a0 | ||
![]() |
a36017e007 | ||
![]() |
27c2185954 | ||
![]() |
c7e4917e97 | ||
![]() |
98967645a1 | ||
![]() |
a4ea7e131b | ||
![]() |
8d391a111a | ||
![]() |
8b48f68c0d | ||
![]() |
6da6a23291 | ||
![]() |
d6eeef9ee6 | ||
![]() |
9c72e85e4c | ||
![]() |
cbb991b6b8 | ||
![]() |
4f9d852759 | ||
![]() |
98666368ee | ||
![]() |
b6e1bdfc76 | ||
![]() |
21e1661b54 | ||
![]() |
a46bc0268b | ||
![]() |
e540ca7155 | ||
![]() |
ff2d220d21 | ||
![]() |
6dcd9b37ea | ||
![]() |
8aa4ee1f10 | ||
![]() |
65f4299d65 | ||
![]() |
92373a5bb2 | ||
![]() |
5aee8ea752 | ||
![]() |
c12d1d9b98 | ||
![]() |
b3a262dff3 | ||
![]() |
45daecb4f7 | ||
![]() |
e50ea014c3 | ||
![]() |
943f9ee25c | ||
![]() |
903375a48a | ||
![]() |
658e854252 | ||
![]() |
21d2273efa | ||
![]() |
eae7cf2368 | ||
![]() |
9cea3a3c4e | ||
![]() |
0c4f74d129 | ||
![]() |
14d4718043 | ||
![]() |
902d63759e | ||
![]() |
4a37e3e2a0 | ||
![]() |
f08581c1d0 | ||
![]() |
13b02a8efe | ||
![]() |
ff42e04f9c | ||
![]() |
27b34a109d | ||
![]() |
7d2f5f8e9d | ||
![]() |
de4cb716ee | ||
![]() |
8659764a07 | ||
![]() |
cf07d85809 | ||
![]() |
6df142e2ab | ||
![]() |
968a5d6bc2 | ||
![]() |
4753c23983 | ||
![]() |
ffe0f9b7fb | ||
![]() |
f3a9ae5baa | ||
![]() |
e30781ff80 | ||
![]() |
ff637d1903 | ||
![]() |
8c6fa5c5e3 | ||
![]() |
68f035026f | ||
![]() |
e254969df2 | ||
![]() |
f1a300acc4 | ||
![]() |
755b3daf90 | ||
![]() |
32d8992147 | ||
![]() |
30ea3ef283 | ||
![]() |
f695b30ac2 | ||
![]() |
c39526da8a | ||
![]() |
45048dc9dc | ||
![]() |
b9649d2407 | ||
![]() |
48c0e13286 | ||
![]() |
ea8b4a450d | ||
![]() |
a5ab38093f | ||
![]() |
42ce25821d | ||
![]() |
2693b89c19 | ||
![]() |
47174d60c8 | ||
![]() |
0afa2dad76 | ||
![]() |
146005a911 | ||
![]() |
9ec9415fd9 | ||
![]() |
4be18ab295 | ||
![]() |
ea914456af | ||
![]() |
327c9bb1da | ||
![]() |
747cf7a505 | ||
![]() |
f3c97ed32e | ||
![]() |
d204c4bf01 | ||
![]() |
de1a9c77a7 | ||
![]() |
b11a37f540 | ||
![]() |
f0279ceb92 | ||
![]() |
566f6d75bd | ||
![]() |
8bf6eaf433 | ||
![]() |
6444958f62 | ||
![]() |
36f1b183e4 | ||
![]() |
bcfd9c9750 | ||
![]() |
f6fcd3410d | ||
![]() |
188d58eaa9 | ||
![]() |
9b0d306a2f | ||
![]() |
e0d294c3af | ||
![]() |
27beada6d0 | ||
![]() |
67ac68e399 | ||
![]() |
c167345ffb | ||
![]() |
d217c87139 | ||
![]() |
e7cac13016 | ||
![]() |
b3bf91bdc6 | ||
![]() |
2adc0443dd | ||
![]() |
ff9395eb3b | ||
![]() |
b5055002d7 | ||
![]() |
3c603eadb4 | ||
![]() |
a7977ece93 | ||
![]() |
1205e3207e | ||
![]() |
6b6ff9c969 | ||
![]() |
2ba4729ef8 | ||
![]() |
5680b4517f | ||
![]() |
7b742da63e | ||
![]() |
2057d3ef75 | ||
![]() |
a2dfbbd7d6 | ||
![]() |
13918a9ccc | ||
![]() |
bde2c04fb7 | ||
![]() |
4733df333f | ||
![]() |
3210ca6d60 | ||
![]() |
105503b839 | ||
![]() |
42e5073f94 | ||
![]() |
18e8baa5c0 | ||
![]() |
31cb852a90 | ||
![]() |
2300e16675 | ||
![]() |
baef5486bf | ||
![]() |
13d4a0d011 | ||
![]() |
b9987a7c25 | ||
![]() |
3704807805 | ||
![]() |
dac3b59721 | ||
![]() |
7498fe2e54 | ||
![]() |
3fbc371e99 | ||
![]() |
8739a182c8 | ||
![]() |
1088b4f87c | ||
![]() |
4a7424adba | ||
![]() |
bcbc3929ae | ||
![]() |
6b9d130214 | ||
![]() |
4c0655f26b | ||
![]() |
1fcd5cca3c | ||
![]() |
0d88e15454 | ||
![]() |
9a66582604 | ||
![]() |
ac8f58f6ab | ||
![]() |
143b21e362 | ||
![]() |
6d225eb5f9 | ||
![]() |
a7f8bd451b | ||
![]() |
f48532e271 | ||
![]() |
0b15bf1e54 | ||
![]() |
a12ea1d5e9 | ||
![]() |
629279a45c | ||
![]() |
c64667c338 | ||
![]() |
37cdd3bfc2 | ||
![]() |
c5c31b9eb6 | ||
![]() |
c5a4376aed | ||
![]() |
3caaf21c5b | ||
![]() |
d35541fe29 | ||
![]() |
9a7625652c | ||
![]() |
76567d84ce | ||
![]() |
f7e767d8ee | ||
![]() |
2f11a65c99 | ||
![]() |
eaa6715b02 | ||
![]() |
597d1f4c03 | ||
![]() |
8477a66fc8 | ||
![]() |
cc7f0c0f3e | ||
![]() |
764b3b8090 | ||
![]() |
2574573fea | ||
![]() |
d3aebeee4e | ||
![]() |
d713ec3c46 | ||
![]() |
db2fad7516 | ||
![]() |
fcd6e4a1c2 | ||
![]() |
1b59964162 | ||
![]() |
4e23998fb4 | ||
![]() |
870cf4356c | ||
![]() |
f532504864 | ||
![]() |
ecd1eb2162 | ||
![]() |
8053dba5a1 | ||
![]() |
9586d5e682 | ||
![]() |
f7d1486f48 | ||
![]() |
1814463864 | ||
![]() |
2c3a2ad6f1 | ||
![]() |
f4653c1efc | ||
![]() |
9b729748ac | ||
![]() |
3453c8d6c4 | ||
![]() |
83a2bfd7dc | ||
![]() |
fff358fb06 | ||
![]() |
069eedb3a0 | ||
![]() |
a082c562d0 | ||
![]() |
34cce144d8 | ||
![]() |
38f440120c | ||
![]() |
af69ed20c4 | ||
![]() |
2346a6da4a | ||
![]() |
19e1ec8359 | ||
![]() |
462e29703c | ||
![]() |
d6a7489dd5 | ||
![]() |
cb9133c72f | ||
![]() |
a24e1e8027 | ||
![]() |
2231669a83 | ||
![]() |
d5de63d2be | ||
![]() |
081b39f2b7 | ||
![]() |
5048d6e7ee | ||
![]() |
f701a44305 | ||
![]() |
a3452996a1 | ||
![]() |
a10a5cb356 | ||
![]() |
5599e4275a | ||
![]() |
e2ad89092d | ||
![]() |
e6ca81ee67 | ||
![]() |
a65f1771ad | ||
![]() |
77772350f3 | ||
![]() |
08edb85bd0 | ||
![]() |
0178d974e5 | ||
![]() |
4412996d59 | ||
![]() |
a7a57d9756 | ||
![]() |
240a5a15ef | ||
![]() |
cd94d5f68e | ||
![]() |
b1a31f8066 | ||
![]() |
1e112bce37 | ||
![]() |
e8655d49f5 | ||
![]() |
3d33a462b3 | ||
![]() |
760c214519 | ||
![]() |
ee3df31d74 | ||
![]() |
ae0215f945 | ||
![]() |
8394990b27 | ||
![]() |
2ff01aa1e4 | ||
![]() |
2930903d51 | ||
![]() |
d51d3934f5 | ||
![]() |
63860ba7b8 | ||
![]() |
ef5918098d | ||
![]() |
ce2e278059 | ||
![]() |
04de501229 | ||
![]() |
bea27a5809 | ||
![]() |
657f3e9f14 | ||
![]() |
94ebdba71d | ||
![]() |
26aebd77b8 | ||
![]() |
0e8fea6c13 | ||
![]() |
ef15d38df0 | ||
![]() |
6dfeea6592 | ||
![]() |
43e0e082d1 | ||
![]() |
b68f14d0ed | ||
![]() |
54c4e0f7a5 | ||
![]() |
004fab120a | ||
![]() |
66117b97c5 | ||
![]() |
d01c9febe9 | ||
![]() |
8069f31076 | ||
![]() |
15ee8a8c45 | ||
![]() |
997e54ea43 | ||
![]() |
c614164cb6 | ||
![]() |
69b0242e9a | ||
![]() |
4758d20227 | ||
![]() |
51dc998f3a | ||
![]() |
0be513e8e8 | ||
![]() |
92ec0674fd | ||
![]() |
10a497bd38 | ||
![]() |
c530208ae3 | ||
![]() |
b35f64241f | ||
![]() |
bca4564683 | ||
![]() |
58fe1bde59 | ||
![]() |
5de0e9ed08 | ||
![]() |
7ae1e321a1 | ||
![]() |
25c1bada72 | ||
![]() |
29938b3a5a | ||
![]() |
30ef50b522 | ||
![]() |
17559cd8b5 | ||
![]() |
85ca2e8a8b | ||
![]() |
3134a52d26 | ||
![]() |
8975436466 | ||
![]() |
914b160fb5 | ||
![]() |
0b9be93205 | ||
![]() |
ee9325b0bd | ||
![]() |
2904eb5800 | ||
![]() |
58245d7050 | ||
![]() |
6b4a65e8b1 | ||
![]() |
92e33c7b31 | ||
![]() |
a5469a00a8 | ||
![]() |
cc868da526 | ||
![]() |
7a7dc9e624 | ||
![]() |
c08baa2900 | ||
![]() |
22ca468c7c | ||
![]() |
ad9dea1f6d | ||
![]() |
d68d37872c | ||
![]() |
f9d20e6df2 | ||
![]() |
0d9417de4a | ||
![]() |
a81f037f15 | ||
![]() |
e96e49c2f9 | ||
![]() |
fbbdba3b04 | ||
![]() |
bf8a49abbd | ||
![]() |
977356a72b | ||
![]() |
f34be01190 | ||
![]() |
348bdc0195 | ||
![]() |
479443a570 | ||
![]() |
c8f5a55df4 | ||
![]() |
7b0e12934e | ||
![]() |
a7a2d1653b | ||
![]() |
7ad1faa6f8 | ||
![]() |
a39b723eb3 | ||
![]() |
3252e6b63d | ||
![]() |
a02f391cbe | ||
![]() |
15afee1938 | ||
![]() |
ad2e3598d2 | ||
![]() |
a6095333a7 | ||
![]() |
9aa429a66d | ||
![]() |
d578bdad02 | ||
![]() |
9fa24f03b5 | ||
![]() |
9e19102972 | ||
![]() |
069b772915 | ||
![]() |
4ba20da8b1 | ||
![]() |
aa5a941992 | ||
![]() |
7178e68bbe | ||
![]() |
e3b2710b04 | ||
![]() |
e9b7f98c56 | ||
![]() |
5f39262dcc | ||
![]() |
b937f1c839 | ||
![]() |
eaa7cdf05d | ||
![]() |
bdb593ab20 | ||
![]() |
adb9b4eddf | ||
![]() |
f0ccaff553 | ||
![]() |
6bff6cb5a9 | ||
![]() |
863f860bfc | ||
![]() |
28a8622143 | ||
![]() |
f22b828d68 | ||
![]() |
2420f44342 | ||
![]() |
f16f08e55b | ||
![]() |
6557baf336 | ||
![]() |
ff1fef9607 | ||
![]() |
f496032686 | ||
![]() |
349c3118bd | ||
![]() |
18b54ef468 | ||
![]() |
04e9456567 | ||
![]() |
6af42f5102 | ||
![]() |
b82b574e76 | ||
![]() |
3227a9be5f | ||
![]() |
c9fbb1881a | ||
![]() |
705fc9f107 | ||
![]() |
1aa46abbdf | ||
![]() |
7ac3acf762 | ||
![]() |
b3e2eb14c5 | ||
![]() |
47b9a09120 | ||
![]() |
288d73c861 | ||
![]() |
511a207444 | ||
![]() |
2136de9374 | ||
![]() |
58ba880b94 | ||
![]() |
6fc2e57c2c | ||
![]() |
fb60204d4c | ||
![]() |
8097b49997 | ||
![]() |
6b3f4bc794 | ||
![]() |
41fac44707 | ||
![]() |
9d403d6f48 | ||
![]() |
bf15ca1091 | ||
![]() |
002cf38837 | ||
![]() |
f1600db3e4 | ||
![]() |
c824eda6cc | ||
![]() |
8e7c5a3c8d | ||
![]() |
6fed5692d2 | ||
![]() |
01d23109ab | ||
![]() |
7fde349b25 | ||
![]() |
fc83fcb7c4 | ||
![]() |
32b3d2f174 | ||
![]() |
fe432cacf8 | ||
![]() |
ddd75573a7 | ||
![]() |
3cc57e67a9 | ||
![]() |
eec92e8a5b | ||
![]() |
6e99ed72a5 | ||
![]() |
0169a985d9 | ||
![]() |
66c6b4d6fc | ||
![]() |
aefc1088a2 | ||
![]() |
67cde46dd7 | ||
![]() |
e05f4cf8f4 | ||
![]() |
d45617c702 | ||
![]() |
07ad5a15c2 | ||
![]() |
4ffdf60b85 | ||
![]() |
10164407fb | ||
![]() |
d7b220b467 | ||
![]() |
d856157388 | ||
![]() |
8ee9b855a0 | ||
![]() |
4863e07c01 | ||
![]() |
f16ea6a6eb | ||
![]() |
ff0e0a76e8 | ||
![]() |
4d50991320 | ||
![]() |
dcd6c87b80 | ||
![]() |
83dd9b36f4 | ||
![]() |
c099d6be1c | ||
![]() |
e097bb1d39 | ||
![]() |
5661cd8ff4 | ||
![]() |
f91c3bb3ab | ||
![]() |
36d732c22b | ||
![]() |
e45c1f55b4 | ||
![]() |
20c2892693 | ||
![]() |
2fac50fa0e | ||
![]() |
74f4c5cd12 | ||
![]() |
4ddde47d8c | ||
![]() |
dbed479d79 | ||
![]() |
cb9b277b2f | ||
![]() |
1935dfb294 | ||
![]() |
266868a40b | ||
![]() |
6f13620761 | ||
![]() |
e0b4c4d1ae | ||
![]() |
6d71d33d55 | ||
![]() |
05c7259525 | ||
![]() |
bf43b4c4b4 | ||
![]() |
3135b85423 | ||
![]() |
8dc1523057 | ||
![]() |
06c8713e89 | ||
![]() |
d642dd4311 | ||
![]() |
9c2552a1c1 | ||
![]() |
ca9bedd538 | ||
![]() |
ab71181545 | ||
![]() |
36533e8c5a | ||
![]() |
775569473d | ||
![]() |
9675affae0 | ||
![]() |
0842daa24e | ||
![]() |
5da2e500d7 | ||
![]() |
27530d484e | ||
![]() |
50b13f75b8 | ||
![]() |
2882778310 | ||
![]() |
65e9fb65e8 | ||
![]() |
68efc64b72 | ||
![]() |
02975a604c | ||
![]() |
3a6ec9ea72 | ||
![]() |
976ddb61d3 | ||
![]() |
83ba1880bf | ||
![]() |
eeeb71ed97 | ||
![]() |
cd3d7cf4ac | ||
![]() |
bc7d4935bb | ||
![]() |
ba8bfaafa7 | ||
![]() |
bf40776aa4 | ||
![]() |
ec73bf53a5 | ||
![]() |
405b94c661 | ||
![]() |
cd47c1942e | ||
![]() |
a340c64a79 | ||
![]() |
b5f7f7737a | ||
![]() |
2c8430e223 | ||
![]() |
deea4ede59 | ||
![]() |
e54231d613 | ||
![]() |
8440cc4817 | ||
![]() |
d9a9a4ffea | ||
![]() |
27d5a57072 | ||
![]() |
c756eb01c8 | ||
![]() |
2fa7092808 | ||
![]() |
02463273c9 | ||
![]() |
fedcf83f33 | ||
![]() |
1b91f41935 | ||
![]() |
c3e290963d | ||
![]() |
78a6946904 | ||
![]() |
c0c789ab50 | ||
![]() |
c216c8d6f2 | ||
![]() |
a14a987c82 | ||
![]() |
507204316a | ||
![]() |
b0bfcc368c | ||
![]() |
f0a22b23fe | ||
![]() |
670101439f | ||
![]() |
b39f7c3364 | ||
![]() |
8c18df7fcd | ||
![]() |
48fca113d1 | ||
![]() |
c09b290cea | ||
![]() |
0af189c00d | ||
![]() |
169c846575 | ||
![]() |
018290a344 | ||
![]() |
ffb3c50da1 | ||
![]() |
327add990f | ||
![]() |
f951881e8c | ||
![]() |
cb60e66085 | ||
![]() |
94655569fe | ||
![]() |
ccd23215ed | ||
![]() |
2f31a16445 | ||
![]() |
04aa9e28d5 | ||
![]() |
ea3c817ac2 | ||
![]() |
97b6a6f037 | ||
![]() |
834f26c3b9 | ||
![]() |
42a1b310e1 | ||
![]() |
6a86492adf | ||
![]() |
099e9bf1ff | ||
![]() |
77311e0dff | ||
![]() |
51289302ab | ||
![]() |
48f5886605 | ||
![]() |
2fa710aa6d | ||
![]() |
45de35fc58 | ||
![]() |
c4e5c54d69 | ||
![]() |
3cf5c213f1 | ||
![]() |
c4c0331f65 | ||
![]() |
88a888f022 | ||
![]() |
393d9d0195 | ||
![]() |
47cf7c25a2 | ||
![]() |
15dac923b9 | ||
![]() |
9c3c1f3725 | ||
![]() |
bcd12de6c3 | ||
![]() |
9e7140b451 | ||
![]() |
1bb63bf669 | ||
![]() |
b60617f5ff | ||
![]() |
453f18040f | ||
![]() |
07c48ccfe0 | ||
![]() |
b71245683b | ||
![]() |
bcd0c49af3 | ||
![]() |
8697d14ec8 | ||
![]() |
66919e370b | ||
![]() |
3ab8a05b37 | ||
![]() |
b58a8ccb02 | ||
![]() |
4684d286de | ||
![]() |
3833905ff2 | ||
![]() |
3fa7e5c62c | ||
![]() |
defe094e9e | ||
![]() |
ddfe906be2 | ||
![]() |
5881601488 | ||
![]() |
8121f85473 | ||
![]() |
47d6f16a04 | ||
![]() |
af9002dd16 | ||
![]() |
cc168054a8 | ||
![]() |
e96ab22462 | ||
![]() |
904b957ae9 | ||
![]() |
aa911e8b41 | ||
![]() |
0998a146d4 | ||
![]() |
3c16bbb73b | ||
![]() |
57e987576f | ||
![]() |
1d12a125e7 | ||
![]() |
a6b6258284 | ||
![]() |
84f106f198 | ||
![]() |
7e7d820d5b | ||
![]() |
0acc270830 | ||
![]() |
7e79831016 | ||
![]() |
672100a84e | ||
![]() |
3d1fa00fce | ||
![]() |
66f36f4735 | ||
![]() |
b1dcaf7f1e | ||
![]() |
7f2daa74a0 | ||
![]() |
6036a0d24f | ||
![]() |
1e224dcb83 | ||
![]() |
0d1e5a21c4 | ||
![]() |
62a332160f | ||
![]() |
4d4231352c | ||
![]() |
f091752a9c | ||
![]() |
4e1ba35458 | ||
![]() |
97d6a4cbd1 | ||
![]() |
bf6fcebfed | ||
![]() |
52b3e1a633 | ||
![]() |
9cb470eba7 | ||
![]() |
1f8e8e5bf1 | ||
![]() |
3e7025022e | ||
![]() |
a63adac604 | ||
![]() |
bf05cd3c99 | ||
![]() |
c7342f35c8 | ||
![]() |
f62dcc9c33 | ||
![]() |
b5bc9ee02d | ||
![]() |
a9b81da575 | ||
![]() |
0620081731 | ||
![]() |
0f014c97e5 | ||
![]() |
e9d07c0c2a | ||
![]() |
d218b0914e | ||
![]() |
06a82af0de | ||
![]() |
ca4e27f5da | ||
![]() |
6ab0870d45 | ||
![]() |
6c2d732bf4 | ||
![]() |
1cb44945fb | ||
![]() |
2104454607 | ||
![]() |
cc43012674 | ||
![]() |
72a43e2378 | ||
![]() |
0bf6b51572 | ||
![]() |
ff37a911ce | ||
![]() |
4682130b60 | ||
![]() |
ac3996a6d1 | ||
![]() |
44600442dc | ||
![]() |
5127e58dab | ||
![]() |
60a10116d1 | ||
![]() |
543ebc900f | ||
![]() |
9216ba58d8 | ||
![]() |
e6c1993f1b | ||
![]() |
fddf66b741 | ||
![]() |
b63e88e506 | ||
![]() |
61d05c1e67 | ||
![]() |
cc04ae1565 | ||
![]() |
e6cf741ae6 | ||
![]() |
158b300952 | ||
![]() |
2865de86ec | ||
![]() |
d12f25f216 | ||
![]() |
725606a678 | ||
![]() |
106c342659 | ||
![]() |
d5edf56bb5 | ||
![]() |
f82280820a | ||
![]() |
716c1d5ff5 | ||
![]() |
81914ce68a | ||
![]() |
ccada0636b | ||
![]() |
cfc79a357a | ||
![]() |
b89ba05ab4 | ||
![]() |
76550dfdc0 | ||
![]() |
945ccfee59 | ||
![]() |
7635ee0f37 | ||
![]() |
1cd926d665 | ||
![]() |
61927ba4ac | ||
![]() |
e07e74fb0f | ||
![]() |
f2c1aea118 | ||
![]() |
71061e9332 | ||
![]() |
615566aa81 | ||
![]() |
86fed469ec | ||
![]() |
327a02d77e | ||
![]() |
3e7aa8fda9 | ||
![]() |
9c2bb7f342 | ||
![]() |
429e652809 | ||
![]() |
4b402746ca | ||
![]() |
f670628ca5 | ||
![]() |
c1a90dc160 | ||
![]() |
bd86de1ac8 | ||
![]() |
2b24aa87d9 | ||
![]() |
25301a84a8 | ||
![]() |
eeb288d568 | ||
![]() |
de9ae32b93 | ||
![]() |
8a1fb40273 | ||
![]() |
5ad4159ebb | ||
![]() |
4526ec7907 | ||
![]() |
5ecde212a8 | ||
![]() |
318ca07657 | ||
![]() |
e7db593a46 | ||
![]() |
45664383f1 | ||
![]() |
7a48bfab47 | ||
![]() |
f024518387 | ||
![]() |
3c4ea94210 | ||
![]() |
016933ad48 | ||
![]() |
ce7b38459a | ||
![]() |
91f87e7513 | ||
![]() |
22dcfa80aa | ||
![]() |
943f9c0356 | ||
![]() |
c3f095c8b3 | ||
![]() |
82b88a7fd0 | ||
![]() |
bc1c18e18c | ||
![]() |
ac04d11abc | ||
![]() |
0fefc6873a | ||
![]() |
b73f99745b | ||
![]() |
71f5314993 | ||
![]() |
b106abe570 | ||
![]() |
259e835b1b | ||
![]() |
1a5482d4d8 | ||
![]() |
cf76ee2cb7 | ||
![]() |
3c2f076ad0 | ||
![]() |
66695533a8 | ||
![]() |
537949a9df | ||
![]() |
91f01a2060 | ||
![]() |
85f3a82355 | ||
![]() |
aa327a1ed4 | ||
![]() |
641fda79bb | ||
![]() |
dbc5090b5e | ||
![]() |
2a21b45fdc | ||
![]() |
a16ca80b09 | ||
![]() |
bb40844e32 | ||
![]() |
0b60d3ffa5 | ||
![]() |
8d5d21aaec | ||
![]() |
d89b4f5ece | ||
![]() |
12ec948490 | ||
![]() |
5b10674b5c | ||
![]() |
726556dde9 | ||
![]() |
ce6318f254 | ||
![]() |
e4985cf619 | ||
![]() |
8f95389742 | ||
![]() |
770c6663d6 | ||
![]() |
dc90501ba3 | ||
![]() |
359a6796da | ||
![]() |
5cc0a364ae | ||
![]() |
bfd62cdaff | ||
![]() |
f60171bb4f | ||
![]() |
f8d744d91a | ||
![]() |
2ba383474d | ||
![]() |
0f751ecee3 | ||
![]() |
1eb8a718bf | ||
![]() |
2dac808dd1 | ||
![]() |
3bda634576 | ||
![]() |
a7949f2dd2 | ||
![]() |
59917dd18e | ||
![]() |
969957f9f2 | ||
![]() |
32f68cc58c | ||
![]() |
9efc42f4f8 | ||
![]() |
750e753134 | ||
![]() |
df7e1fecc1 | ||
![]() |
280ad35553 | ||
![]() |
dcfff3ccc8 | ||
![]() |
d47f257484 | ||
![]() |
106c620a23 | ||
![]() |
4ce20fb3f4 | ||
![]() |
164db8278f | ||
![]() |
9b1a2aa82b | ||
![]() |
d94d0ed12f | ||
![]() |
6d38ad4146 | ||
![]() |
6985a0f516 | ||
![]() |
ad1aad69fb | ||
![]() |
d0495132aa | ||
![]() |
b16c77cdc4 | ||
![]() |
407fad2356 | ||
![]() |
c1553f859f | ||
![]() |
db99840bf6 | ||
![]() |
f380a1658d | ||
![]() |
eacc3b4ccf | ||
![]() |
fe4791b0d5 | ||
![]() |
4d50dc5ab5 | ||
![]() |
37cd112b0f | ||
![]() |
3b2d08a93b | ||
![]() |
519b2e48a8 | ||
![]() |
70a3652693 | ||
![]() |
a762cef917 | ||
![]() |
633dbcb458 | ||
![]() |
3a7ad43fb8 | ||
![]() |
8b0c11c358 | ||
![]() |
8d0c8c5e6b | ||
![]() |
8e8e2d11bf | ||
![]() |
ac1358cd56 | ||
![]() |
91aa1fae2a | ||
![]() |
75d2443bf0 | ||
![]() |
182ea677a0 | ||
![]() |
d82b9f62a9 | ||
![]() |
b987bc36af | ||
![]() |
40ffa2839f | ||
![]() |
270fadc135 | ||
![]() |
f38ed0c560 | ||
![]() |
b71ff28a1a | ||
![]() |
881bef00c7 | ||
![]() |
f4169936ee | ||
![]() |
219cdab676 | ||
![]() |
b0d8a75e48 | ||
![]() |
b608c09781 | ||
![]() |
13234d3c43 | ||
![]() |
0f9760ab6f | ||
![]() |
e0c0e65378 | ||
![]() |
ee5b29ae30 | ||
![]() |
e758f9d457 | ||
![]() |
70c9b3c668 | ||
![]() |
9152d434dc | ||
![]() |
255866419d | ||
![]() |
0c65aed099 | ||
![]() |
add0587fae | ||
![]() |
34be6057da | ||
![]() |
a9ae351667 | ||
![]() |
5f21aba4b0 | ||
![]() |
c42a281439 | ||
![]() |
159cc3b33c | ||
![]() |
f217049dbe | ||
![]() |
47270b6858 | ||
![]() |
b6fe63a505 | ||
![]() |
553e9e291f | ||
![]() |
a981cb2809 | ||
![]() |
888bb6c133 | ||
![]() |
2ff2376fbc | ||
![]() |
d630cda597 | ||
![]() |
39fff1bea0 | ||
![]() |
f65170ea84 | ||
![]() |
297dfd8696 | ||
![]() |
0c0a05046d | ||
![]() |
baa4a290eb | ||
![]() |
3628975a15 | ||
![]() |
70ead526f1 | ||
![]() |
6e07bf3634 | ||
![]() |
9f27d1f843 | ||
![]() |
605ca82e7f | ||
![]() |
d98bd7cc5f | ||
![]() |
f129e09529 | ||
![]() |
68d0f46ec0 | ||
![]() |
6886da7547 | ||
![]() |
7a0bfa6ec6 | ||
![]() |
7e3a82c384 | ||
![]() |
9a780fa7db | ||
![]() |
91fc730d83 | ||
![]() |
299ef2f8eb | ||
![]() |
198b834c97 | ||
![]() |
5b1a8ca5e8 | ||
![]() |
9480da21e8 | ||
![]() |
62cce50d55 | ||
![]() |
35c4a13eb7 | ||
![]() |
bea22782e9 | ||
![]() |
371a64bfe7 | ||
![]() |
cabc29ba24 | ||
![]() |
8a7847c2c9 | ||
![]() |
bf168b24f5 | ||
![]() |
08d0a7fd0f | ||
![]() |
ab20869221 | ||
![]() |
7b18202e74 | ||
![]() |
c23970ec25 | ||
![]() |
9af97fb630 | ||
![]() |
ebe0b57c91 | ||
![]() |
6377f9d966 | ||
![]() |
50dd3eb62c | ||
![]() |
c06991fce6 | ||
![]() |
24d804f79c | ||
![]() |
afd2d797eb | ||
![]() |
c6ccd1e939 | ||
![]() |
6abdd31555 | ||
![]() |
c7e2bd6298 | ||
![]() |
4dca923454 | ||
![]() |
f1909d26f8 | ||
![]() |
316071d79c | ||
![]() |
b632626ec0 | ||
![]() |
b87ebd7af8 | ||
![]() |
bf5cdbdf9d | ||
![]() |
267e73446c | ||
![]() |
337ad83e58 | ||
![]() |
afc8c4836f | ||
![]() |
2d12a52ff0 | ||
![]() |
90f889a56d | ||
![]() |
72746c079d | ||
![]() |
1ca1515dd3 | ||
![]() |
768b1f7281 | ||
![]() |
63a8257fb7 | ||
![]() |
d3db846cc5 | ||
![]() |
99c573f018 | ||
![]() |
b67e1f701f | ||
![]() |
ecdb6a00c2 | ||
![]() |
c96a8dcb5b | ||
![]() |
e6b9609fc0 | ||
![]() |
911bb980b1 | ||
![]() |
9b187954df | ||
![]() |
1d12559b09 | ||
![]() |
7cf13826b7 | ||
![]() |
3c47a0dc6f | ||
![]() |
78a24171a6 | ||
![]() |
380a26112c | ||
![]() |
36e767c147 | ||
![]() |
90ceaba3e4 | ||
![]() |
f0b491a524 | ||
![]() |
6d5a3fe583 | ||
![]() |
e7c453b613 | ||
![]() |
b5770a2007 | ||
![]() |
9ba77ed45b | ||
![]() |
9ba45fa510 | ||
![]() |
3fcd595dfb | ||
![]() |
f27276f44f | ||
![]() |
fce163cd54 | ||
![]() |
8a152a55f7 | ||
![]() |
1d5ca84df6 | ||
![]() |
85aead1790 | ||
![]() |
80474bf65e | ||
![]() |
c1f5194842 | ||
![]() |
0549f5aae9 | ||
![]() |
a68b36c752 | ||
![]() |
6e8dbc76ad | ||
![]() |
61b569b461 | ||
![]() |
7e23f895ca | ||
![]() |
1f3e079a35 | ||
![]() |
9b63cb057a | ||
![]() |
d1eca240fb | ||
![]() |
4260a7f2b3 | ||
![]() |
5993b808f0 | ||
![]() |
4781a67737 | ||
![]() |
318a1ff5ec | ||
![]() |
2b1ec65b5d | ||
![]() |
41b0888a84 | ||
![]() |
5de798f2b2 | ||
![]() |
c8f25fa5c0 | ||
![]() |
27e1bacdb3 | ||
![]() |
3dd20456ab | ||
![]() |
201dcefafe | ||
![]() |
3486abd54a | ||
![]() |
86e340c76e | ||
![]() |
85a541a421 | ||
![]() |
5d4aa325a6 | ||
![]() |
282f3b3d78 | ||
![]() |
817488be47 | ||
![]() |
121e161115 | ||
![]() |
2c24f7178d | ||
![]() |
076d4bd91a | ||
![]() |
7ba9d31e3f | ||
![]() |
cd6f742980 | ||
![]() |
6defef4ab2 | ||
![]() |
880adc3355 | ||
![]() |
394020383d | ||
![]() |
e4c6f8fde7 | ||
![]() |
385599b553 | ||
![]() |
174528de1e | ||
![]() |
5778a7c9cb | ||
![]() |
f16a0a1aa4 | ||
![]() |
834feffe08 | ||
![]() |
17c403d0ab | ||
![]() |
018a2adcb1 | ||
![]() |
2d3d95f7ac | ||
![]() |
228c9940ea | ||
![]() |
8befcd0089 | ||
![]() |
af9d7aa9fb | ||
![]() |
cb339d628f | ||
![]() |
360ac89885 | ||
![]() |
a8eee97b43 | ||
![]() |
a7fa1314da | ||
![]() |
17a8cf5cc3 | ||
![]() |
264f6e70ec | ||
![]() |
c6641782c3 | ||
![]() |
12566c3d0f | ||
![]() |
33ddc645ce | ||
![]() |
68991d7f87 | ||
![]() |
27b5cc31e6 | ||
![]() |
f68cf8ba19 | ||
![]() |
a58e0b2a74 | ||
![]() |
120234fa17 | ||
![]() |
21a1abd8e3 | ||
![]() |
568d4b1d63 | ||
![]() |
d757d7e998 | ||
![]() |
f63eb66ecd | ||
![]() |
95eb505660 | ||
![]() |
2c598d0858 | ||
![]() |
1136db0db0 | ||
![]() |
d793950ec8 | ||
![]() |
af290bfe3b | ||
![]() |
97ec6291ee | ||
![]() |
755fb3d4ec | ||
![]() |
8b2cbaefcf | ||
![]() |
22f7aca097 | ||
![]() |
d7f1d60c51 | ||
![]() |
198a046d3e | ||
![]() |
cb22359d02 | ||
![]() |
05e2b5a59f | ||
![]() |
446d1ee624 | ||
![]() |
b6597745f9 | ||
![]() |
0966757874 | ||
![]() |
7d2690e658 | ||
![]() |
6cc76ec73f | ||
![]() |
4bb01229cd | ||
![]() |
974e81d184 | ||
![]() |
45876b4550 | ||
![]() |
d479c9653e | ||
![]() |
719f39f44e | ||
![]() |
ecc5998bcf | ||
![]() |
0ffbb36ddc | ||
![]() |
f473e892f7 | ||
![]() |
a38e9f412d | ||
![]() |
3d55311062 | ||
![]() |
7317ce8bd4 | ||
![]() |
cbeae53e76 | ||
![]() |
7adeccb33d | ||
![]() |
23f1bfbd85 | ||
![]() |
de5fd00ec5 | ||
![]() |
f6921412d4 | ||
![]() |
485a49d0b8 | ||
![]() |
c56e5dd620 | ||
![]() |
5d48663e04 | ||
![]() |
cb1b1b8fef | ||
![]() |
2ef2243804 | ||
![]() |
f667cc7a4e | ||
![]() |
12fe34516e | ||
![]() |
f09c687ea9 | ||
![]() |
011fdec1e6 | ||
![]() |
4ddae8f524 | ||
![]() |
85c1ee434d | ||
![]() |
360217a233 | ||
![]() |
2218a4c292 | ||
![]() |
0412193bb9 | ||
![]() |
f938ab5e6a | ||
![]() |
eff68a3a4d | ||
![]() |
44f8ee7258 | ||
![]() |
a3128ad33a | ||
![]() |
186dc40e8e | ||
![]() |
b282048fe4 | ||
![]() |
b6f6169348 | ||
![]() |
ba016b710a | ||
![]() |
80f6b243a7 | ||
![]() |
a1c40a2c1a | ||
![]() |
40ab0424d4 | ||
![]() |
4807f1584c | ||
![]() |
cfbb599335 | ||
![]() |
c344dee463 | ||
![]() |
738c8f23c6 | ||
![]() |
18794d8ddc | ||
![]() |
f5141ea45f | ||
![]() |
50b40f114c | ||
![]() |
64a5a8fd6f | ||
![]() |
3fdfbcb73d | ||
![]() |
40bcb96abd | ||
![]() |
1338c71dfb | ||
![]() |
1868582e7d | ||
![]() |
3b74066b10 |
@ -1,12 +1,12 @@
|
|||||||
---
|
---
|
||||||
Language: Cpp
|
Language: Cpp
|
||||||
# BasedOnStyle: Google
|
# BasedOnStyle: Google
|
||||||
# Generated with clang-format 3.8.1
|
# Generated with clang-format 5.0.0
|
||||||
AccessModifierOffset: -1
|
AccessModifierOffset: -1
|
||||||
AlignAfterOpenBracket: Align
|
AlignAfterOpenBracket: Align
|
||||||
AlignConsecutiveAssignments: false
|
AlignConsecutiveAssignments: false
|
||||||
AlignConsecutiveDeclarations: false
|
AlignConsecutiveDeclarations: false
|
||||||
AlignEscapedNewlinesLeft: true
|
AlignEscapedNewlines: Left
|
||||||
AlignOperands: true
|
AlignOperands: true
|
||||||
AlignTrailingComments: true
|
AlignTrailingComments: true
|
||||||
AllowAllParametersOfDeclarationOnNextLine: true
|
AllowAllParametersOfDeclarationOnNextLine: true
|
||||||
@ -33,12 +33,20 @@ BraceWrapping:
|
|||||||
BeforeCatch: false
|
BeforeCatch: false
|
||||||
BeforeElse: false
|
BeforeElse: false
|
||||||
IndentBraces: false
|
IndentBraces: false
|
||||||
|
SplitEmptyFunction: true
|
||||||
|
SplitEmptyRecord: true
|
||||||
|
SplitEmptyNamespace: true
|
||||||
BreakBeforeBinaryOperators: None
|
BreakBeforeBinaryOperators: None
|
||||||
BreakBeforeBraces: Attach
|
BreakBeforeBraces: Attach
|
||||||
|
BreakBeforeInheritanceComma: false
|
||||||
BreakBeforeTernaryOperators: true
|
BreakBeforeTernaryOperators: true
|
||||||
BreakConstructorInitializersBeforeComma: false
|
BreakConstructorInitializersBeforeComma: false
|
||||||
|
BreakConstructorInitializers: BeforeColon
|
||||||
|
BreakAfterJavaFieldAnnotations: false
|
||||||
|
BreakStringLiterals: true
|
||||||
ColumnLimit: 80
|
ColumnLimit: 80
|
||||||
CommentPragmas: '^ IWYU pragma:'
|
CommentPragmas: '^ IWYU pragma:'
|
||||||
|
CompactNamespaces: false
|
||||||
ConstructorInitializerAllOnOneLineOrOnePerLine: false
|
ConstructorInitializerAllOnOneLineOrOnePerLine: false
|
||||||
ConstructorInitializerIndentWidth: 4
|
ConstructorInitializerIndentWidth: 4
|
||||||
ContinuationIndentWidth: 4
|
ContinuationIndentWidth: 4
|
||||||
@ -46,7 +54,11 @@ Cpp11BracedListStyle: false
|
|||||||
DerivePointerAlignment: false
|
DerivePointerAlignment: false
|
||||||
DisableFormat: false
|
DisableFormat: false
|
||||||
ExperimentalAutoDetectBinPacking: false
|
ExperimentalAutoDetectBinPacking: false
|
||||||
ForEachMacros: [ foreach, Q_FOREACH, BOOST_FOREACH ]
|
FixNamespaceComments: true
|
||||||
|
ForEachMacros:
|
||||||
|
- foreach
|
||||||
|
- Q_FOREACH
|
||||||
|
- BOOST_FOREACH
|
||||||
IncludeCategories:
|
IncludeCategories:
|
||||||
- Regex: '^<.*\.h>'
|
- Regex: '^<.*\.h>'
|
||||||
Priority: 1
|
Priority: 1
|
||||||
@ -54,9 +66,12 @@ IncludeCategories:
|
|||||||
Priority: 2
|
Priority: 2
|
||||||
- Regex: '.*'
|
- Regex: '.*'
|
||||||
Priority: 3
|
Priority: 3
|
||||||
|
IncludeIsMainRegex: '([-_](test|unittest))?$'
|
||||||
IndentCaseLabels: true
|
IndentCaseLabels: true
|
||||||
IndentWidth: 2
|
IndentWidth: 2
|
||||||
IndentWrappedFunctionNames: false
|
IndentWrappedFunctionNames: false
|
||||||
|
JavaScriptQuotes: Leave
|
||||||
|
JavaScriptWrapImports: true
|
||||||
KeepEmptyLinesAtTheStartOfBlocks: false
|
KeepEmptyLinesAtTheStartOfBlocks: false
|
||||||
MacroBlockBegin: ''
|
MacroBlockBegin: ''
|
||||||
MacroBlockEnd: ''
|
MacroBlockEnd: ''
|
||||||
@ -65,6 +80,7 @@ NamespaceIndentation: None
|
|||||||
ObjCBlockIndentWidth: 2
|
ObjCBlockIndentWidth: 2
|
||||||
ObjCSpaceAfterProperty: false
|
ObjCSpaceAfterProperty: false
|
||||||
ObjCSpaceBeforeProtocolList: false
|
ObjCSpaceBeforeProtocolList: false
|
||||||
|
PenaltyBreakAssignment: 2
|
||||||
PenaltyBreakBeforeFirstCallParameter: 1
|
PenaltyBreakBeforeFirstCallParameter: 1
|
||||||
PenaltyBreakComment: 300
|
PenaltyBreakComment: 300
|
||||||
PenaltyBreakFirstLessLess: 120
|
PenaltyBreakFirstLessLess: 120
|
||||||
@ -74,7 +90,9 @@ PenaltyReturnTypeOnItsOwnLine: 200
|
|||||||
PointerAlignment: Right
|
PointerAlignment: Right
|
||||||
ReflowComments: true
|
ReflowComments: true
|
||||||
SortIncludes: false
|
SortIncludes: false
|
||||||
|
SortUsingDeclarations: true
|
||||||
SpaceAfterCStyleCast: false
|
SpaceAfterCStyleCast: false
|
||||||
|
SpaceAfterTemplateKeyword: true
|
||||||
SpaceBeforeAssignmentOperators: true
|
SpaceBeforeAssignmentOperators: true
|
||||||
SpaceBeforeParens: ControlStatements
|
SpaceBeforeParens: ControlStatements
|
||||||
SpaceInEmptyParentheses: false
|
SpaceInEmptyParentheses: false
|
||||||
|
5
.mailmap
5
.mailmap
@ -3,6 +3,7 @@ Aℓex Converse <aconverse@google.com>
|
|||||||
Aℓex Converse <aconverse@google.com> <alex.converse@gmail.com>
|
Aℓex Converse <aconverse@google.com> <alex.converse@gmail.com>
|
||||||
Alexis Ballier <aballier@gentoo.org> <alexis.ballier@gmail.com>
|
Alexis Ballier <aballier@gentoo.org> <alexis.ballier@gmail.com>
|
||||||
Alpha Lam <hclam@google.com> <hclam@chromium.org>
|
Alpha Lam <hclam@google.com> <hclam@chromium.org>
|
||||||
|
Chris Cunningham <chcunningham@chromium.org>
|
||||||
Daniele Castagna <dcastagna@chromium.org> <dcastagna@google.com>
|
Daniele Castagna <dcastagna@chromium.org> <dcastagna@google.com>
|
||||||
Deb Mukherjee <debargha@google.com>
|
Deb Mukherjee <debargha@google.com>
|
||||||
Erik Niemeyer <erik.a.niemeyer@intel.com> <erik.a.niemeyer@gmail.com>
|
Erik Niemeyer <erik.a.niemeyer@intel.com> <erik.a.niemeyer@gmail.com>
|
||||||
@ -21,17 +22,21 @@ Marco Paniconi <marpan@google.com>
|
|||||||
Marco Paniconi <marpan@google.com> <marpan@chromium.org>
|
Marco Paniconi <marpan@google.com> <marpan@chromium.org>
|
||||||
Pascal Massimino <pascal.massimino@gmail.com>
|
Pascal Massimino <pascal.massimino@gmail.com>
|
||||||
Paul Wilkins <paulwilkins@google.com>
|
Paul Wilkins <paulwilkins@google.com>
|
||||||
|
Peter Boström <pbos@chromium.org> <pbos@google.com>
|
||||||
Peter de Rivaz <peter.derivaz@gmail.com>
|
Peter de Rivaz <peter.derivaz@gmail.com>
|
||||||
Peter de Rivaz <peter.derivaz@gmail.com> <peter.derivaz@argondesign.com>
|
Peter de Rivaz <peter.derivaz@gmail.com> <peter.derivaz@argondesign.com>
|
||||||
Ralph Giles <giles@xiph.org> <giles@entropywave.com>
|
Ralph Giles <giles@xiph.org> <giles@entropywave.com>
|
||||||
Ralph Giles <giles@xiph.org> <giles@mozilla.com>
|
Ralph Giles <giles@xiph.org> <giles@mozilla.com>
|
||||||
Ronald S. Bultje <rsbultje@gmail.com> <rbultje@google.com>
|
Ronald S. Bultje <rsbultje@gmail.com> <rbultje@google.com>
|
||||||
Sami Pietilä <samipietila@google.com>
|
Sami Pietilä <samipietila@google.com>
|
||||||
|
Shiyou Yin <yinshiyou-hf@loongson.cn>
|
||||||
Tamar Levy <tamar.levy@intel.com>
|
Tamar Levy <tamar.levy@intel.com>
|
||||||
Tamar Levy <tamar.levy@intel.com> <levytamar82@gmail.com>
|
Tamar Levy <tamar.levy@intel.com> <levytamar82@gmail.com>
|
||||||
Tero Rintaluoma <teror@google.com> <tero.rintaluoma@on2.com>
|
Tero Rintaluoma <teror@google.com> <tero.rintaluoma@on2.com>
|
||||||
Timothy B. Terriberry <tterribe@xiph.org> <tterriberry@mozilla.com>
|
Timothy B. Terriberry <tterribe@xiph.org> <tterriberry@mozilla.com>
|
||||||
Tom Finegan <tomfinegan@google.com>
|
Tom Finegan <tomfinegan@google.com>
|
||||||
Tom Finegan <tomfinegan@google.com> <tomfinegan@chromium.org>
|
Tom Finegan <tomfinegan@google.com> <tomfinegan@chromium.org>
|
||||||
|
Urvang Joshi <urvang@google.com> <urvang@chromium.org>
|
||||||
|
Yaowu Xu <yaowu@google.com> <adam@xuyaowu.com>
|
||||||
Yaowu Xu <yaowu@google.com> <yaowu@xuyaowu.com>
|
Yaowu Xu <yaowu@google.com> <yaowu@xuyaowu.com>
|
||||||
Yaowu Xu <yaowu@google.com> <Yaowu Xu>
|
Yaowu Xu <yaowu@google.com> <Yaowu Xu>
|
||||||
|
29
AUTHORS
29
AUTHORS
@ -3,11 +3,13 @@
|
|||||||
|
|
||||||
Aaron Watry <awatry@gmail.com>
|
Aaron Watry <awatry@gmail.com>
|
||||||
Abo Talib Mahfoodh <ab.mahfoodh@gmail.com>
|
Abo Talib Mahfoodh <ab.mahfoodh@gmail.com>
|
||||||
Adam Xu <adam@xuyaowu.com>
|
|
||||||
Adrian Grange <agrange@google.com>
|
Adrian Grange <agrange@google.com>
|
||||||
Aℓex Converse <aconverse@google.com>
|
Aℓex Converse <aconverse@google.com>
|
||||||
Ahmad Sharif <asharif@google.com>
|
Ahmad Sharif <asharif@google.com>
|
||||||
|
Aleksey Vasenev <margtu-fivt@ya.ru>
|
||||||
|
Alexander Potapenko <glider@google.com>
|
||||||
Alexander Voronov <avoronov@graphics.cs.msu.ru>
|
Alexander Voronov <avoronov@graphics.cs.msu.ru>
|
||||||
|
Alexandra Hájková <alexandra.khirnova@gmail.com>
|
||||||
Alexis Ballier <aballier@gentoo.org>
|
Alexis Ballier <aballier@gentoo.org>
|
||||||
Alok Ahuja <waveletcoeff@gmail.com>
|
Alok Ahuja <waveletcoeff@gmail.com>
|
||||||
Alpha Lam <hclam@google.com>
|
Alpha Lam <hclam@google.com>
|
||||||
@ -15,6 +17,7 @@ A.Mahfoodh <ab.mahfoodh@gmail.com>
|
|||||||
Ami Fischman <fischman@chromium.org>
|
Ami Fischman <fischman@chromium.org>
|
||||||
Andoni Morales Alastruey <ylatuya@gmail.com>
|
Andoni Morales Alastruey <ylatuya@gmail.com>
|
||||||
Andres Mejia <mcitadel@gmail.com>
|
Andres Mejia <mcitadel@gmail.com>
|
||||||
|
Andrew Lewis <andrewlewis@google.com>
|
||||||
Andrew Russell <anrussell@google.com>
|
Andrew Russell <anrussell@google.com>
|
||||||
Angie Chiang <angiebird@google.com>
|
Angie Chiang <angiebird@google.com>
|
||||||
Aron Rosenberg <arosenberg@logitech.com>
|
Aron Rosenberg <arosenberg@logitech.com>
|
||||||
@ -22,11 +25,14 @@ Attila Nagy <attilanagy@google.com>
|
|||||||
Brion Vibber <bvibber@wikimedia.org>
|
Brion Vibber <bvibber@wikimedia.org>
|
||||||
changjun.yang <changjun.yang@intel.com>
|
changjun.yang <changjun.yang@intel.com>
|
||||||
Charles 'Buck' Krasic <ckrasic@google.com>
|
Charles 'Buck' Krasic <ckrasic@google.com>
|
||||||
|
Cheng Chen <chengchen@google.com>
|
||||||
chm <chm@rock-chips.com>
|
chm <chm@rock-chips.com>
|
||||||
|
Chris Cunningham <chcunningham@chromium.org>
|
||||||
Christian Duvivier <cduvivier@google.com>
|
Christian Duvivier <cduvivier@google.com>
|
||||||
Daniele Castagna <dcastagna@chromium.org>
|
Daniele Castagna <dcastagna@chromium.org>
|
||||||
Daniel Kang <ddkang@google.com>
|
Daniel Kang <ddkang@google.com>
|
||||||
Deb Mukherjee <debargha@google.com>
|
Deb Mukherjee <debargha@google.com>
|
||||||
|
Deepa K G <deepa.kg@ittiam.com>
|
||||||
Dim Temp <dimtemp0@gmail.com>
|
Dim Temp <dimtemp0@gmail.com>
|
||||||
Dmitry Kovalev <dkovalev@google.com>
|
Dmitry Kovalev <dkovalev@google.com>
|
||||||
Dragan Mrdjan <dmrdjan@mips.com>
|
Dragan Mrdjan <dmrdjan@mips.com>
|
||||||
@ -37,17 +43,21 @@ Fabio Pedretti <fabio.ped@libero.it>
|
|||||||
Frank Galligan <fgalligan@google.com>
|
Frank Galligan <fgalligan@google.com>
|
||||||
Fredrik Söderquist <fs@opera.com>
|
Fredrik Söderquist <fs@opera.com>
|
||||||
Fritz Koenig <frkoenig@google.com>
|
Fritz Koenig <frkoenig@google.com>
|
||||||
|
Gabriel Marin <gmx@chromium.org>
|
||||||
Gaute Strokkenes <gaute.strokkenes@broadcom.com>
|
Gaute Strokkenes <gaute.strokkenes@broadcom.com>
|
||||||
Geza Lore <gezalore@gmail.com>
|
Geza Lore <gezalore@gmail.com>
|
||||||
Ghislain MARY <ghislainmary2@gmail.com>
|
Ghislain MARY <ghislainmary2@gmail.com>
|
||||||
Giuseppe Scrivano <gscrivano@gnu.org>
|
Giuseppe Scrivano <gscrivano@gnu.org>
|
||||||
Gordana Cmiljanovic <gordana.cmiljanovic@imgtec.com>
|
Gordana Cmiljanovic <gordana.cmiljanovic@imgtec.com>
|
||||||
|
Gregor Jasny <gjasny@gmail.com>
|
||||||
Guillaume Martres <gmartres@google.com>
|
Guillaume Martres <gmartres@google.com>
|
||||||
Guillermo Ballester Valor <gbvalor@gmail.com>
|
Guillermo Ballester Valor <gbvalor@gmail.com>
|
||||||
Hangyu Kuang <hkuang@google.com>
|
Hangyu Kuang <hkuang@google.com>
|
||||||
Hanno Böck <hanno@hboeck.de>
|
Hanno Böck <hanno@hboeck.de>
|
||||||
|
Han Shen <shenhan@google.com>
|
||||||
Henrik Lundin <hlundin@google.com>
|
Henrik Lundin <hlundin@google.com>
|
||||||
Hui Su <huisu@google.com>
|
Hui Su <huisu@google.com>
|
||||||
|
Ivan Krasin <krasin@chromium.org>
|
||||||
Ivan Maltz <ivanmaltz@google.com>
|
Ivan Maltz <ivanmaltz@google.com>
|
||||||
Jacek Caban <cjacek@gmail.com>
|
Jacek Caban <cjacek@gmail.com>
|
||||||
Jacky Chen <jackychen@google.com>
|
Jacky Chen <jackychen@google.com>
|
||||||
@ -61,6 +71,7 @@ Jean-Yves Avenard <jyavenard@mozilla.com>
|
|||||||
Jeff Faust <jfaust@google.com>
|
Jeff Faust <jfaust@google.com>
|
||||||
Jeff Muizelaar <jmuizelaar@mozilla.com>
|
Jeff Muizelaar <jmuizelaar@mozilla.com>
|
||||||
Jeff Petkau <jpet@chromium.org>
|
Jeff Petkau <jpet@chromium.org>
|
||||||
|
Jerome Jiang <jianj@google.com>
|
||||||
Jia Jia <jia.jia@linaro.org>
|
Jia Jia <jia.jia@linaro.org>
|
||||||
Jian Zhou <zhoujian@google.com>
|
Jian Zhou <zhoujian@google.com>
|
||||||
Jim Bankoski <jimbankoski@google.com>
|
Jim Bankoski <jimbankoski@google.com>
|
||||||
@ -77,6 +88,7 @@ Justin Clift <justin@salasaga.org>
|
|||||||
Justin Lebar <justin.lebar@gmail.com>
|
Justin Lebar <justin.lebar@gmail.com>
|
||||||
Kaustubh Raste <kaustubh.raste@imgtec.com>
|
Kaustubh Raste <kaustubh.raste@imgtec.com>
|
||||||
KO Myung-Hun <komh@chollian.net>
|
KO Myung-Hun <komh@chollian.net>
|
||||||
|
Kyle Siefring <kylesiefring@gmail.com>
|
||||||
Lawrence Velázquez <larryv@macports.org>
|
Lawrence Velázquez <larryv@macports.org>
|
||||||
Linfeng Zhang <linfengz@google.com>
|
Linfeng Zhang <linfengz@google.com>
|
||||||
Lou Quillio <louquillio@google.com>
|
Lou Quillio <louquillio@google.com>
|
||||||
@ -92,8 +104,12 @@ Michael Kohler <michaelkohler@live.com>
|
|||||||
Mike Frysinger <vapier@chromium.org>
|
Mike Frysinger <vapier@chromium.org>
|
||||||
Mike Hommey <mhommey@mozilla.com>
|
Mike Hommey <mhommey@mozilla.com>
|
||||||
Mikhal Shemer <mikhal@google.com>
|
Mikhal Shemer <mikhal@google.com>
|
||||||
|
Min Chen <chenm003@gmail.com>
|
||||||
Minghai Shang <minghai@google.com>
|
Minghai Shang <minghai@google.com>
|
||||||
|
Min Ye <yeemmi@google.com>
|
||||||
|
Moriyoshi Koizumi <mozo@mozo.jp>
|
||||||
Morton Jonuschat <yabawock@gmail.com>
|
Morton Jonuschat <yabawock@gmail.com>
|
||||||
|
Nathan E. Egge <negge@mozilla.com>
|
||||||
Nico Weber <thakis@chromium.org>
|
Nico Weber <thakis@chromium.org>
|
||||||
Parag Salasakar <img.mips1@gmail.com>
|
Parag Salasakar <img.mips1@gmail.com>
|
||||||
Pascal Massimino <pascal.massimino@gmail.com>
|
Pascal Massimino <pascal.massimino@gmail.com>
|
||||||
@ -102,16 +118,22 @@ Paul Wilkins <paulwilkins@google.com>
|
|||||||
Pavol Rusnak <stick@gk2.sk>
|
Pavol Rusnak <stick@gk2.sk>
|
||||||
Paweł Hajdan <phajdan@google.com>
|
Paweł Hajdan <phajdan@google.com>
|
||||||
Pengchong Jin <pengchong@google.com>
|
Pengchong Jin <pengchong@google.com>
|
||||||
|
Peter Boström <pbos@chromium.org>
|
||||||
|
Peter Collingbourne <pcc@chromium.org>
|
||||||
Peter de Rivaz <peter.derivaz@gmail.com>
|
Peter de Rivaz <peter.derivaz@gmail.com>
|
||||||
Philip Jägenstedt <philipj@opera.com>
|
Philip Jägenstedt <philipj@opera.com>
|
||||||
Priit Laes <plaes@plaes.org>
|
Priit Laes <plaes@plaes.org>
|
||||||
Rafael Ávila de Espíndola <rafael.espindola@gmail.com>
|
Rafael Ávila de Espíndola <rafael.espindola@gmail.com>
|
||||||
Rafaël Carré <funman@videolan.org>
|
Rafaël Carré <funman@videolan.org>
|
||||||
|
Rafael de Lucena Valle <rafaeldelucena@gmail.com>
|
||||||
|
Rahul Chaudhry <rahulchaudhry@google.com>
|
||||||
Ralph Giles <giles@xiph.org>
|
Ralph Giles <giles@xiph.org>
|
||||||
|
Ranjit Kumar Tulabandu <ranjit.tulabandu@ittiam.com>
|
||||||
Rob Bradford <rob@linux.intel.com>
|
Rob Bradford <rob@linux.intel.com>
|
||||||
Ronald S. Bultje <rsbultje@gmail.com>
|
Ronald S. Bultje <rsbultje@gmail.com>
|
||||||
Rui Ueyama <ruiu@google.com>
|
Rui Ueyama <ruiu@google.com>
|
||||||
Sami Pietilä <samipietila@google.com>
|
Sami Pietilä <samipietila@google.com>
|
||||||
|
Sarah Parker <sarahparker@google.com>
|
||||||
Sasi Inguva <isasi@google.com>
|
Sasi Inguva <isasi@google.com>
|
||||||
Scott Graham <scottmg@chromium.org>
|
Scott Graham <scottmg@chromium.org>
|
||||||
Scott LaVarnway <slavarnway@google.com>
|
Scott LaVarnway <slavarnway@google.com>
|
||||||
@ -119,9 +141,11 @@ Sean McGovern <gseanmcg@gmail.com>
|
|||||||
Sergey Kolomenkin <kolomenkin@gmail.com>
|
Sergey Kolomenkin <kolomenkin@gmail.com>
|
||||||
Sergey Ulanov <sergeyu@chromium.org>
|
Sergey Ulanov <sergeyu@chromium.org>
|
||||||
Shimon Doodkin <helpmepro1@gmail.com>
|
Shimon Doodkin <helpmepro1@gmail.com>
|
||||||
|
Shiyou Yin <yinshiyou-hf@loongson.cn>
|
||||||
Shunyao Li <shunyaoli@google.com>
|
Shunyao Li <shunyaoli@google.com>
|
||||||
Stefan Holmer <holmer@google.com>
|
Stefan Holmer <holmer@google.com>
|
||||||
Suman Sunkara <sunkaras@google.com>
|
Suman Sunkara <sunkaras@google.com>
|
||||||
|
Sylvestre Ledru <sylvestre@mozilla.com>
|
||||||
Taekhyun Kim <takim@nvidia.com>
|
Taekhyun Kim <takim@nvidia.com>
|
||||||
Takanori MATSUURA <t.matsuu@gmail.com>
|
Takanori MATSUURA <t.matsuu@gmail.com>
|
||||||
Tamar Levy <tamar.levy@intel.com>
|
Tamar Levy <tamar.levy@intel.com>
|
||||||
@ -131,7 +155,10 @@ Thijs Vermeir <thijsvermeir@gmail.com>
|
|||||||
Tim Kopp <tkopp@google.com>
|
Tim Kopp <tkopp@google.com>
|
||||||
Timothy B. Terriberry <tterribe@xiph.org>
|
Timothy B. Terriberry <tterribe@xiph.org>
|
||||||
Tom Finegan <tomfinegan@google.com>
|
Tom Finegan <tomfinegan@google.com>
|
||||||
|
Tristan Matthews <le.businessman@gmail.com>
|
||||||
|
Urvang Joshi <urvang@google.com>
|
||||||
Vignesh Venkatasubramanian <vigneshv@google.com>
|
Vignesh Venkatasubramanian <vigneshv@google.com>
|
||||||
|
Vlad Tsyrklevich <vtsyrklevich@chromium.org>
|
||||||
Yaowu Xu <yaowu@google.com>
|
Yaowu Xu <yaowu@google.com>
|
||||||
Yi Luo <luoyi@google.com>
|
Yi Luo <luoyi@google.com>
|
||||||
Yongzhe Wang <yongzhe@google.com>
|
Yongzhe Wang <yongzhe@google.com>
|
||||||
|
41
CHANGELOG
41
CHANGELOG
@ -1,3 +1,44 @@
|
|||||||
|
2017-01-04 v1.7.0 "Mandarin Duck"
|
||||||
|
This release focused on high bit depth performance (10/12 bit) and vp9
|
||||||
|
encoding improvements.
|
||||||
|
|
||||||
|
- Upgrading:
|
||||||
|
This release is ABI incompatible due to new vp9 encoder features.
|
||||||
|
|
||||||
|
Frame parallel decoding for vp9 has been removed.
|
||||||
|
|
||||||
|
- Enhancements:
|
||||||
|
vp9 encoding supports additional threads with --row-mt. This can be greater
|
||||||
|
than the number of tiles.
|
||||||
|
|
||||||
|
Two new vp9 encoder options have been added:
|
||||||
|
--corpus-complexity
|
||||||
|
--tune-content=film
|
||||||
|
|
||||||
|
Additional tooling for respecting the vp9 "level" profiles has been added.
|
||||||
|
|
||||||
|
- Bug fixes:
|
||||||
|
A variety of fuzzing issues.
|
||||||
|
vp8 threading fix for ARM.
|
||||||
|
Codec control VP9_SET_SKIP_LOOP_FILTER fixed.
|
||||||
|
Reject invalid multi resolution configurations.
|
||||||
|
|
||||||
|
2017-01-09 v1.6.1 "Long Tailed Duck"
|
||||||
|
This release improves upon the VP9 encoder and speeds up the encoding and
|
||||||
|
decoding processes.
|
||||||
|
|
||||||
|
- Upgrading:
|
||||||
|
This release is ABI compatible with 1.6.0.
|
||||||
|
|
||||||
|
- Enhancements:
|
||||||
|
Faster VP9 encoding and decoding.
|
||||||
|
High bit depth builds now provide similar speed for 8 bit encode and decode
|
||||||
|
for x86 targets. Other platforms and higher bit depth improvements are in
|
||||||
|
progress.
|
||||||
|
|
||||||
|
- Bug Fixes:
|
||||||
|
A variety of fuzzing issues.
|
||||||
|
|
||||||
2016-07-20 v1.6.0 "Khaki Campbell Duck"
|
2016-07-20 v1.6.0 "Khaki Campbell Duck"
|
||||||
This release improves upon the VP9 encoder and speeds up the encoding and
|
This release improves upon the VP9 encoder and speeds up the encoding and
|
||||||
decoding processes.
|
decoding processes.
|
||||||
|
45
README
45
README
@ -1,4 +1,4 @@
|
|||||||
README - 20 July 2016
|
README - 24 January 2018
|
||||||
|
|
||||||
Welcome to the WebM VP8/VP9 Codec SDK!
|
Welcome to the WebM VP8/VP9 Codec SDK!
|
||||||
|
|
||||||
@ -9,22 +9,26 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
|
|
||||||
1. Prerequisites
|
1. Prerequisites
|
||||||
|
|
||||||
* All x86 targets require the Yasm[1] assembler be installed.
|
* All x86 targets require the Yasm[1] assembler be installed[2].
|
||||||
* All Windows builds require that Cygwin[2] be installed.
|
* All Windows builds require that Cygwin[3] be installed.
|
||||||
* Building the documentation requires Doxygen[3]. If you do not
|
* Building the documentation requires Doxygen[4]. If you do not
|
||||||
have this package, the install-docs option will be disabled.
|
have this package, the install-docs option will be disabled.
|
||||||
* Downloading the data for the unit tests requires curl[4] and sha1sum.
|
* Downloading the data for the unit tests requires curl[5] and sha1sum.
|
||||||
sha1sum is provided via the GNU coreutils, installed by default on
|
sha1sum is provided via the GNU coreutils, installed by default on
|
||||||
many *nix platforms, as well as MinGW and Cygwin. If coreutils is not
|
many *nix platforms, as well as MinGW and Cygwin. If coreutils is not
|
||||||
available, a compatible version of sha1sum can be built from
|
available, a compatible version of sha1sum can be built from
|
||||||
source[5]. These requirements are optional if not running the unit
|
source[6]. These requirements are optional if not running the unit
|
||||||
tests.
|
tests.
|
||||||
|
|
||||||
[1]: http://www.tortall.net/projects/yasm
|
[1]: http://www.tortall.net/projects/yasm
|
||||||
[2]: http://www.cygwin.com
|
[2]: For Visual Studio the base yasm binary (not vsyasm) should be in the
|
||||||
[3]: http://www.doxygen.org
|
PATH for Visual Studio. For VS2017 it is sufficient to rename
|
||||||
[4]: http://curl.haxx.se
|
yasm-<version>-<arch>.exe to yasm.exe and place it in:
|
||||||
[5]: http://www.microbrew.org/tools/md5sha1sum/
|
Program Files (x86)/Microsoft Visual Studio/2017/<level>/Common7/Tools/
|
||||||
|
[3]: http://www.cygwin.com
|
||||||
|
[4]: http://www.doxygen.org
|
||||||
|
[5]: http://curl.haxx.se
|
||||||
|
[6]: http://www.microbrew.org/tools/md5sha1sum/
|
||||||
|
|
||||||
2. Out-of-tree builds
|
2. Out-of-tree builds
|
||||||
Out of tree builds are a supported method of building the application. For
|
Out of tree builds are a supported method of building the application. For
|
||||||
@ -41,12 +45,22 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
used to get a list of supported options:
|
used to get a list of supported options:
|
||||||
$ ../libvpx/configure --help
|
$ ../libvpx/configure --help
|
||||||
|
|
||||||
4. Cross development
|
4. Compiler analyzers
|
||||||
|
Compilers have added sanitizers which instrument binaries with information
|
||||||
|
about address calculation, memory usage, threading, undefined behavior, and
|
||||||
|
other common errors. To simplify building libvpx with some of these features
|
||||||
|
use tools/set_analyzer_env.sh before running configure. It will set the
|
||||||
|
compiler and necessary flags for building as well as environment variables
|
||||||
|
read by the analyzer when testing the binaries.
|
||||||
|
$ source ../libvpx/tools/set_analyzer_env.sh address
|
||||||
|
|
||||||
|
5. Cross development
|
||||||
For cross development, the most notable option is the --target option. The
|
For cross development, the most notable option is the --target option. The
|
||||||
most up-to-date list of supported targets can be found at the bottom of the
|
most up-to-date list of supported targets can be found at the bottom of the
|
||||||
--help output of the configure script. As of this writing, the list of
|
--help output of the configure script. As of this writing, the list of
|
||||||
available targets is:
|
available targets is:
|
||||||
|
|
||||||
|
arm64-android-gcc
|
||||||
arm64-darwin-gcc
|
arm64-darwin-gcc
|
||||||
arm64-linux-gcc
|
arm64-linux-gcc
|
||||||
armv7-android-gcc
|
armv7-android-gcc
|
||||||
@ -57,10 +71,13 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
armv7-win32-vs11
|
armv7-win32-vs11
|
||||||
armv7-win32-vs12
|
armv7-win32-vs12
|
||||||
armv7-win32-vs14
|
armv7-win32-vs14
|
||||||
|
armv7-win32-vs15
|
||||||
armv7s-darwin-gcc
|
armv7s-darwin-gcc
|
||||||
armv8-linux-gcc
|
armv8-linux-gcc
|
||||||
mips32-linux-gcc
|
mips32-linux-gcc
|
||||||
mips64-linux-gcc
|
mips64-linux-gcc
|
||||||
|
ppc64-linux-gcc
|
||||||
|
ppc64le-linux-gcc
|
||||||
sparc-solaris-gcc
|
sparc-solaris-gcc
|
||||||
x86-android-gcc
|
x86-android-gcc
|
||||||
x86-darwin8-gcc
|
x86-darwin8-gcc
|
||||||
@ -73,6 +90,7 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
x86-darwin13-gcc
|
x86-darwin13-gcc
|
||||||
x86-darwin14-gcc
|
x86-darwin14-gcc
|
||||||
x86-darwin15-gcc
|
x86-darwin15-gcc
|
||||||
|
x86-darwin16-gcc
|
||||||
x86-iphonesimulator-gcc
|
x86-iphonesimulator-gcc
|
||||||
x86-linux-gcc
|
x86-linux-gcc
|
||||||
x86-linux-icc
|
x86-linux-icc
|
||||||
@ -83,6 +101,7 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
x86-win32-vs11
|
x86-win32-vs11
|
||||||
x86-win32-vs12
|
x86-win32-vs12
|
||||||
x86-win32-vs14
|
x86-win32-vs14
|
||||||
|
x86-win32-vs15
|
||||||
x86_64-android-gcc
|
x86_64-android-gcc
|
||||||
x86_64-darwin9-gcc
|
x86_64-darwin9-gcc
|
||||||
x86_64-darwin10-gcc
|
x86_64-darwin10-gcc
|
||||||
@ -91,6 +110,7 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
x86_64-darwin13-gcc
|
x86_64-darwin13-gcc
|
||||||
x86_64-darwin14-gcc
|
x86_64-darwin14-gcc
|
||||||
x86_64-darwin15-gcc
|
x86_64-darwin15-gcc
|
||||||
|
x86_64-darwin16-gcc
|
||||||
x86_64-iphonesimulator-gcc
|
x86_64-iphonesimulator-gcc
|
||||||
x86_64-linux-gcc
|
x86_64-linux-gcc
|
||||||
x86_64-linux-icc
|
x86_64-linux-icc
|
||||||
@ -100,6 +120,7 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
x86_64-win64-vs11
|
x86_64-win64-vs11
|
||||||
x86_64-win64-vs12
|
x86_64-win64-vs12
|
||||||
x86_64-win64-vs14
|
x86_64-win64-vs14
|
||||||
|
x86_64-win64-vs15
|
||||||
generic-gnu
|
generic-gnu
|
||||||
|
|
||||||
The generic-gnu target, in conjunction with the CROSS environment variable,
|
The generic-gnu target, in conjunction with the CROSS environment variable,
|
||||||
@ -115,7 +136,7 @@ COMPILING THE APPLICATIONS/LIBRARIES:
|
|||||||
environment variables: CC, AR, LD, AS, STRIP, NM. Additional flags can be
|
environment variables: CC, AR, LD, AS, STRIP, NM. Additional flags can be
|
||||||
passed to these executables with CFLAGS, LDFLAGS, and ASFLAGS.
|
passed to these executables with CFLAGS, LDFLAGS, and ASFLAGS.
|
||||||
|
|
||||||
5. Configuration errors
|
6. Configuration errors
|
||||||
If the configuration step fails, the first step is to look in the error log.
|
If the configuration step fails, the first step is to look in the error log.
|
||||||
This defaults to config.log. This should give a good indication of what went
|
This defaults to config.log. This should give a good indication of what went
|
||||||
wrong. If not, contact us for support.
|
wrong. If not, contact us for support.
|
||||||
|
2
build/.gitattributes
vendored
2
build/.gitattributes
vendored
@ -1,2 +0,0 @@
|
|||||||
*-vs8/*.rules -crlf
|
|
||||||
*-msvs/*.rules -crlf
|
|
1
build/.gitignore
vendored
1
build/.gitignore
vendored
@ -1 +0,0 @@
|
|||||||
x86*-win32-vs*
|
|
@ -64,6 +64,9 @@ CONFIG_DIR := $(LOCAL_PATH)/
|
|||||||
LIBVPX_PATH := $(LOCAL_PATH)/libvpx
|
LIBVPX_PATH := $(LOCAL_PATH)/libvpx
|
||||||
ASM_CNV_PATH_LOCAL := $(TARGET_ARCH_ABI)/ads2gas
|
ASM_CNV_PATH_LOCAL := $(TARGET_ARCH_ABI)/ads2gas
|
||||||
ASM_CNV_PATH := $(LOCAL_PATH)/$(ASM_CNV_PATH_LOCAL)
|
ASM_CNV_PATH := $(LOCAL_PATH)/$(ASM_CNV_PATH_LOCAL)
|
||||||
|
ifneq ($(V),1)
|
||||||
|
qexec := @
|
||||||
|
endif
|
||||||
|
|
||||||
# Use the makefiles generated by upstream configure to determine which files to
|
# Use the makefiles generated by upstream configure to determine which files to
|
||||||
# build. Also set any architecture-specific flags.
|
# build. Also set any architecture-specific flags.
|
||||||
@ -103,8 +106,8 @@ LOCAL_ASMFLAGS := -I$(LIBVPX_PATH)
|
|||||||
|
|
||||||
.PRECIOUS: %.asm.S
|
.PRECIOUS: %.asm.S
|
||||||
$(ASM_CNV_PATH)/libvpx/%.asm.S: $(LIBVPX_PATH)/%.asm
|
$(ASM_CNV_PATH)/libvpx/%.asm.S: $(LIBVPX_PATH)/%.asm
|
||||||
@mkdir -p $(dir $@)
|
$(qexec)mkdir -p $(dir $@)
|
||||||
@$(CONFIG_DIR)$(ASM_CONVERSION) <$< > $@
|
$(qexec)$(CONFIG_DIR)$(ASM_CONVERSION) <$< > $@
|
||||||
|
|
||||||
# For building *_rtcd.h, which have rules in libs.mk
|
# For building *_rtcd.h, which have rules in libs.mk
|
||||||
TGT_ISA:=$(word 1, $(subst -, ,$(TOOLCHAIN)))
|
TGT_ISA:=$(word 1, $(subst -, ,$(TOOLCHAIN)))
|
||||||
@ -150,15 +153,27 @@ CODEC_SRCS_ASM_ADS2GAS = $(patsubst %.S, \
|
|||||||
LOCAL_SRC_FILES += $(CODEC_SRCS_ASM_ADS2GAS)
|
LOCAL_SRC_FILES += $(CODEC_SRCS_ASM_ADS2GAS)
|
||||||
|
|
||||||
ifeq ($(TARGET_ARCH_ABI),armeabi-v7a)
|
ifeq ($(TARGET_ARCH_ABI),armeabi-v7a)
|
||||||
|
ASM_INCLUDES := vpx_dsp/arm/idct_neon.asm.S
|
||||||
CODEC_SRCS_ASM_NEON = $(foreach v, \
|
CODEC_SRCS_ASM_NEON = $(foreach v, \
|
||||||
$(CODEC_SRCS_ASM_ARM_ALL),\
|
$(CODEC_SRCS_ASM_ARM_ALL),\
|
||||||
$(if $(findstring neon,$(v)),$(v),))
|
$(if $(findstring neon,$(v)),$(v),))
|
||||||
|
CODEC_SRCS_ASM_NEON := $(filter-out $(addprefix %, $(ASM_INCLUDES)), \
|
||||||
|
$(CODEC_SRCS_ASM_NEON))
|
||||||
CODEC_SRCS_ASM_NEON_ADS2GAS = $(patsubst %.S, \
|
CODEC_SRCS_ASM_NEON_ADS2GAS = $(patsubst %.S, \
|
||||||
$(ASM_CNV_PATH_LOCAL)/libvpx/%.S, \
|
$(ASM_CNV_PATH_LOCAL)/libvpx/%.S, \
|
||||||
$(CODEC_SRCS_ASM_NEON))
|
$(CODEC_SRCS_ASM_NEON))
|
||||||
LOCAL_SRC_FILES += $(patsubst %.S, \
|
LOCAL_SRC_FILES += $(patsubst %.S, \
|
||||||
%.S.neon, \
|
%.S.neon, \
|
||||||
$(CODEC_SRCS_ASM_NEON_ADS2GAS))
|
$(CODEC_SRCS_ASM_NEON_ADS2GAS))
|
||||||
|
|
||||||
|
NEON_ASM_TARGETS = $(patsubst %.S, \
|
||||||
|
$(ASM_CNV_PATH)/libvpx/%.S, \
|
||||||
|
$(CODEC_SRCS_ASM_NEON))
|
||||||
|
# add a dependency to the full path to the ads2gas output to ensure the
|
||||||
|
# includes are converted first.
|
||||||
|
ifneq ($(strip $(NEON_ASM_TARGETS)),)
|
||||||
|
$(NEON_ASM_TARGETS): $(addprefix $(ASM_CNV_PATH)/libvpx/, $(ASM_INCLUDES))
|
||||||
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
LOCAL_CFLAGS += \
|
LOCAL_CFLAGS += \
|
||||||
@ -187,7 +202,7 @@ $$(rtcd_dep_template_SRCS): vpx_scale_rtcd.h
|
|||||||
$$(rtcd_dep_template_SRCS): vpx_dsp_rtcd.h
|
$$(rtcd_dep_template_SRCS): vpx_dsp_rtcd.h
|
||||||
|
|
||||||
rtcd_dep_template_CONFIG_ASM_ABIS := x86 x86_64 armeabi-v7a
|
rtcd_dep_template_CONFIG_ASM_ABIS := x86 x86_64 armeabi-v7a
|
||||||
ifneq ($(findstring $(TARGET_ARCH_ABI),$(rtcd_dep_template_CONFIG_ASM_ABIS)),)
|
ifneq ($$(findstring $(TARGET_ARCH_ABI),$$(rtcd_dep_template_CONFIG_ASM_ABIS)),)
|
||||||
$$(rtcd_dep_template_SRCS): vpx_config.asm
|
$$(rtcd_dep_template_SRCS): vpx_config.asm
|
||||||
endif
|
endif
|
||||||
endef
|
endef
|
||||||
@ -197,16 +212,17 @@ $(eval $(call rtcd_dep_template))
|
|||||||
.PHONY: clean
|
.PHONY: clean
|
||||||
clean:
|
clean:
|
||||||
@echo "Clean: ads2gas files [$(TARGET_ARCH_ABI)]"
|
@echo "Clean: ads2gas files [$(TARGET_ARCH_ABI)]"
|
||||||
@$(RM) $(CODEC_SRCS_ASM_ADS2GAS) $(CODEC_SRCS_ASM_NEON_ADS2GAS)
|
$(qexec)$(RM) $(CODEC_SRCS_ASM_ADS2GAS) $(CODEC_SRCS_ASM_NEON_ADS2GAS)
|
||||||
@$(RM) -r $(ASM_CNV_PATH)
|
$(qexec)$(RM) -r $(ASM_CNV_PATH)
|
||||||
@$(RM) $(CLEAN-OBJS)
|
$(qexec)$(RM) $(CLEAN-OBJS)
|
||||||
|
|
||||||
ifeq ($(ENABLE_SHARED),1)
|
ifeq ($(ENABLE_SHARED),1)
|
||||||
|
LOCAL_CFLAGS += -fPIC
|
||||||
include $(BUILD_SHARED_LIBRARY)
|
include $(BUILD_SHARED_LIBRARY)
|
||||||
else
|
else
|
||||||
include $(BUILD_STATIC_LIBRARY)
|
include $(BUILD_STATIC_LIBRARY)
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(CONFIG_RUNTIME_CPU_DETECT),yes)
|
ifeq ($(CONFIG_RUNTIME_CPU_DETECT),yes)
|
||||||
$(call import-module,cpufeatures)
|
$(call import-module,android/cpufeatures)
|
||||||
endif
|
endif
|
||||||
|
@ -124,6 +124,7 @@ ifeq ($(TOOLCHAIN), x86-os2-gcc)
|
|||||||
CFLAGS += -mstackrealign
|
CFLAGS += -mstackrealign
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# x86[_64]
|
||||||
$(BUILD_PFX)%_mmx.c.d: CFLAGS += -mmmx
|
$(BUILD_PFX)%_mmx.c.d: CFLAGS += -mmmx
|
||||||
$(BUILD_PFX)%_mmx.c.o: CFLAGS += -mmmx
|
$(BUILD_PFX)%_mmx.c.o: CFLAGS += -mmmx
|
||||||
$(BUILD_PFX)%_sse2.c.d: CFLAGS += -msse2
|
$(BUILD_PFX)%_sse2.c.d: CFLAGS += -msse2
|
||||||
@ -138,6 +139,12 @@ $(BUILD_PFX)%_avx.c.d: CFLAGS += -mavx
|
|||||||
$(BUILD_PFX)%_avx.c.o: CFLAGS += -mavx
|
$(BUILD_PFX)%_avx.c.o: CFLAGS += -mavx
|
||||||
$(BUILD_PFX)%_avx2.c.d: CFLAGS += -mavx2
|
$(BUILD_PFX)%_avx2.c.d: CFLAGS += -mavx2
|
||||||
$(BUILD_PFX)%_avx2.c.o: CFLAGS += -mavx2
|
$(BUILD_PFX)%_avx2.c.o: CFLAGS += -mavx2
|
||||||
|
$(BUILD_PFX)%_avx512.c.d: CFLAGS += -mavx512f -mavx512cd -mavx512bw -mavx512dq -mavx512vl
|
||||||
|
$(BUILD_PFX)%_avx512.c.o: CFLAGS += -mavx512f -mavx512cd -mavx512bw -mavx512dq -mavx512vl
|
||||||
|
|
||||||
|
# POWER
|
||||||
|
$(BUILD_PFX)%_vsx.c.d: CFLAGS += -maltivec -mvsx
|
||||||
|
$(BUILD_PFX)%_vsx.c.o: CFLAGS += -maltivec -mvsx
|
||||||
|
|
||||||
$(BUILD_PFX)%.c.d: %.c
|
$(BUILD_PFX)%.c.d: %.c
|
||||||
$(if $(quiet),@echo " [DEP] $@")
|
$(if $(quiet),@echo " [DEP] $@")
|
||||||
|
@ -23,9 +23,11 @@ use lib $FindBin::Bin;
|
|||||||
use thumb;
|
use thumb;
|
||||||
|
|
||||||
my $thumb = 0;
|
my $thumb = 0;
|
||||||
|
my $elf = 1;
|
||||||
|
|
||||||
foreach my $arg (@ARGV) {
|
foreach my $arg (@ARGV) {
|
||||||
$thumb = 1 if ($arg eq "-thumb");
|
$thumb = 1 if ($arg eq "-thumb");
|
||||||
|
$elf = 0 if ($arg eq "-noelf");
|
||||||
}
|
}
|
||||||
|
|
||||||
print "@ This file was created from a .asm file\n";
|
print "@ This file was created from a .asm file\n";
|
||||||
@ -140,7 +142,11 @@ while (<STDIN>)
|
|||||||
|
|
||||||
# Make function visible to linker, and make additional symbol with
|
# Make function visible to linker, and make additional symbol with
|
||||||
# prepended underscore
|
# prepended underscore
|
||||||
|
if ($elf) {
|
||||||
s/EXPORT\s+\|([\$\w]*)\|/.global $1 \n\t.type $1, function/;
|
s/EXPORT\s+\|([\$\w]*)\|/.global $1 \n\t.type $1, function/;
|
||||||
|
} else {
|
||||||
|
s/EXPORT\s+\|([\$\w]*)\|/.global $1/;
|
||||||
|
}
|
||||||
s/IMPORT\s+\|([\$\w]*)\|/.global $1/;
|
s/IMPORT\s+\|([\$\w]*)\|/.global $1/;
|
||||||
|
|
||||||
s/EXPORT\s+([\$\w]*)/.global $1/;
|
s/EXPORT\s+([\$\w]*)/.global $1/;
|
||||||
@ -181,11 +187,16 @@ while (<STDIN>)
|
|||||||
# eabi_attributes numerical equivalents can be found in the
|
# eabi_attributes numerical equivalents can be found in the
|
||||||
# "ARM IHI 0045C" document.
|
# "ARM IHI 0045C" document.
|
||||||
|
|
||||||
|
if ($elf) {
|
||||||
# REQUIRE8 Stack is required to be 8-byte aligned
|
# REQUIRE8 Stack is required to be 8-byte aligned
|
||||||
s/\sREQUIRE8/.eabi_attribute 24, 1 \@Tag_ABI_align_needed/g;
|
s/\sREQUIRE8/.eabi_attribute 24, 1 \@Tag_ABI_align_needed/g;
|
||||||
|
|
||||||
# PRESERVE8 Stack 8-byte align is preserved
|
# PRESERVE8 Stack 8-byte align is preserved
|
||||||
s/\sPRESERVE8/.eabi_attribute 25, 1 \@Tag_ABI_align_preserved/g;
|
s/\sPRESERVE8/.eabi_attribute 25, 1 \@Tag_ABI_align_preserved/g;
|
||||||
|
} else {
|
||||||
|
s/\sREQUIRE8//;
|
||||||
|
s/\sPRESERVE8//;
|
||||||
|
}
|
||||||
|
|
||||||
# Use PROC and ENDP to give the symbols a .size directive.
|
# Use PROC and ENDP to give the symbols a .size directive.
|
||||||
# This makes them show up properly in debugging tools like gdb and valgrind.
|
# This makes them show up properly in debugging tools like gdb and valgrind.
|
||||||
@ -202,7 +213,7 @@ while (<STDIN>)
|
|||||||
my $proc;
|
my $proc;
|
||||||
s/\bENDP\b/@ $&/;
|
s/\bENDP\b/@ $&/;
|
||||||
$proc = pop(@proc_stack);
|
$proc = pop(@proc_stack);
|
||||||
$_ = "\t.size $proc, .-$proc".$_ if ($proc);
|
$_ = "\t.size $proc, .-$proc".$_ if ($proc and $elf);
|
||||||
}
|
}
|
||||||
|
|
||||||
# EQU directive
|
# EQU directive
|
||||||
@ -225,4 +236,4 @@ while (<STDIN>)
|
|||||||
}
|
}
|
||||||
|
|
||||||
# Mark that this object doesn't need an executable stack.
|
# Mark that this object doesn't need an executable stack.
|
||||||
printf ("\t.section\t.note.GNU-stack,\"\",\%\%progbits\n");
|
printf ("\t.section\t.note.GNU-stack,\"\",\%\%progbits\n") if $elf;
|
||||||
|
@ -403,6 +403,23 @@ check_gcc_machine_option() {
|
|||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# tests for -m$2, -m$3, -m$4... toggling the feature given in $1.
|
||||||
|
check_gcc_machine_options() {
|
||||||
|
feature="$1"
|
||||||
|
shift
|
||||||
|
flags="-m$1"
|
||||||
|
shift
|
||||||
|
for opt in $*; do
|
||||||
|
flags="$flags -m$opt"
|
||||||
|
done
|
||||||
|
|
||||||
|
if enabled gcc && ! disabled "$feature" && ! check_cflags $flags; then
|
||||||
|
RTCD_OPTIONS="${RTCD_OPTIONS}--disable-$feature "
|
||||||
|
else
|
||||||
|
soft_enable "$feature"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
write_common_config_banner() {
|
write_common_config_banner() {
|
||||||
print_webm_license config.mk "##" ""
|
print_webm_license config.mk "##" ""
|
||||||
echo '# This file automatically generated by configure. Do not edit!' >> config.mk
|
echo '# This file automatically generated by configure. Do not edit!' >> config.mk
|
||||||
@ -674,7 +691,6 @@ check_xcode_minimum_version() {
|
|||||||
process_common_toolchain() {
|
process_common_toolchain() {
|
||||||
if [ -z "$toolchain" ]; then
|
if [ -z "$toolchain" ]; then
|
||||||
gcctarget="${CHOST:-$(gcc -dumpmachine 2> /dev/null)}"
|
gcctarget="${CHOST:-$(gcc -dumpmachine 2> /dev/null)}"
|
||||||
|
|
||||||
# detect tgt_isa
|
# detect tgt_isa
|
||||||
case "$gcctarget" in
|
case "$gcctarget" in
|
||||||
aarch64*)
|
aarch64*)
|
||||||
@ -697,6 +713,18 @@ process_common_toolchain() {
|
|||||||
*sparc*)
|
*sparc*)
|
||||||
tgt_isa=sparc
|
tgt_isa=sparc
|
||||||
;;
|
;;
|
||||||
|
power*64*-*)
|
||||||
|
tgt_isa=ppc64
|
||||||
|
;;
|
||||||
|
power*)
|
||||||
|
tgt_isa=ppc
|
||||||
|
;;
|
||||||
|
*mips64el*)
|
||||||
|
tgt_isa=mips64
|
||||||
|
;;
|
||||||
|
*mips32el*)
|
||||||
|
tgt_isa=mips32
|
||||||
|
;;
|
||||||
esac
|
esac
|
||||||
|
|
||||||
# detect tgt_os
|
# detect tgt_os
|
||||||
@ -725,9 +753,20 @@ process_common_toolchain() {
|
|||||||
tgt_isa=x86_64
|
tgt_isa=x86_64
|
||||||
tgt_os=darwin15
|
tgt_os=darwin15
|
||||||
;;
|
;;
|
||||||
|
*darwin16*)
|
||||||
|
tgt_isa=x86_64
|
||||||
|
tgt_os=darwin16
|
||||||
|
;;
|
||||||
|
*darwin17*)
|
||||||
|
tgt_isa=x86_64
|
||||||
|
tgt_os=darwin17
|
||||||
|
;;
|
||||||
x86_64*mingw32*)
|
x86_64*mingw32*)
|
||||||
tgt_os=win64
|
tgt_os=win64
|
||||||
;;
|
;;
|
||||||
|
x86_64*cygwin*)
|
||||||
|
tgt_os=win64
|
||||||
|
;;
|
||||||
*mingw32*|*cygwin*)
|
*mingw32*|*cygwin*)
|
||||||
[ -z "$tgt_isa" ] && tgt_isa=x86
|
[ -z "$tgt_isa" ] && tgt_isa=x86
|
||||||
tgt_os=win32
|
tgt_os=win32
|
||||||
@ -775,6 +814,9 @@ process_common_toolchain() {
|
|||||||
mips*)
|
mips*)
|
||||||
enable_feature mips
|
enable_feature mips
|
||||||
;;
|
;;
|
||||||
|
ppc*)
|
||||||
|
enable_feature ppc
|
||||||
|
;;
|
||||||
esac
|
esac
|
||||||
|
|
||||||
# PIC is probably what we want when building shared libs
|
# PIC is probably what we want when building shared libs
|
||||||
@ -843,6 +885,14 @@ process_common_toolchain() {
|
|||||||
add_cflags "-mmacosx-version-min=10.11"
|
add_cflags "-mmacosx-version-min=10.11"
|
||||||
add_ldflags "-mmacosx-version-min=10.11"
|
add_ldflags "-mmacosx-version-min=10.11"
|
||||||
;;
|
;;
|
||||||
|
*-darwin16-*)
|
||||||
|
add_cflags "-mmacosx-version-min=10.12"
|
||||||
|
add_ldflags "-mmacosx-version-min=10.12"
|
||||||
|
;;
|
||||||
|
*-darwin17-*)
|
||||||
|
add_cflags "-mmacosx-version-min=10.13"
|
||||||
|
add_ldflags "-mmacosx-version-min=10.13"
|
||||||
|
;;
|
||||||
*-iphonesimulator-*)
|
*-iphonesimulator-*)
|
||||||
add_cflags "-miphoneos-version-min=${IOS_VERSION_MIN}"
|
add_cflags "-miphoneos-version-min=${IOS_VERSION_MIN}"
|
||||||
add_ldflags "-miphoneos-version-min=${IOS_VERSION_MIN}"
|
add_ldflags "-miphoneos-version-min=${IOS_VERSION_MIN}"
|
||||||
@ -891,7 +941,6 @@ process_common_toolchain() {
|
|||||||
setup_gnu_toolchain
|
setup_gnu_toolchain
|
||||||
arch_int=${tgt_isa##armv}
|
arch_int=${tgt_isa##armv}
|
||||||
arch_int=${arch_int%%te}
|
arch_int=${arch_int%%te}
|
||||||
check_add_asflags --defsym ARCHITECTURE=${arch_int}
|
|
||||||
tune_cflags="-mtune="
|
tune_cflags="-mtune="
|
||||||
if [ ${tgt_isa} = "armv7" ] || [ ${tgt_isa} = "armv7s" ]; then
|
if [ ${tgt_isa} = "armv7" ] || [ ${tgt_isa} = "armv7s" ]; then
|
||||||
if [ -z "${float_abi}" ]; then
|
if [ -z "${float_abi}" ]; then
|
||||||
@ -918,6 +967,19 @@ EOF
|
|||||||
|
|
||||||
enabled debug && add_asflags -g
|
enabled debug && add_asflags -g
|
||||||
asm_conversion_cmd="${source_path}/build/make/ads2gas.pl"
|
asm_conversion_cmd="${source_path}/build/make/ads2gas.pl"
|
||||||
|
|
||||||
|
case ${tgt_os} in
|
||||||
|
win*)
|
||||||
|
asm_conversion_cmd="$asm_conversion_cmd -noelf"
|
||||||
|
AS="$CC -c"
|
||||||
|
EXE_SFX=.exe
|
||||||
|
enable_feature thumb
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
check_add_asflags --defsym ARCHITECTURE=${arch_int}
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
if enabled thumb; then
|
if enabled thumb; then
|
||||||
asm_conversion_cmd="$asm_conversion_cmd -thumb"
|
asm_conversion_cmd="$asm_conversion_cmd -thumb"
|
||||||
check_add_cflags -mthumb
|
check_add_cflags -mthumb
|
||||||
@ -1144,12 +1206,25 @@ EOF
|
|||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
if enabled mmi; then
|
||||||
|
tgt_isa=loongson3a
|
||||||
|
check_add_ldflags -march=loongson3a
|
||||||
|
fi
|
||||||
|
|
||||||
check_add_cflags -march=${tgt_isa}
|
check_add_cflags -march=${tgt_isa}
|
||||||
check_add_asflags -march=${tgt_isa}
|
check_add_asflags -march=${tgt_isa}
|
||||||
check_add_asflags -KPIC
|
check_add_asflags -KPIC
|
||||||
;;
|
;;
|
||||||
|
ppc*)
|
||||||
|
link_with_cc=gcc
|
||||||
|
setup_gnu_toolchain
|
||||||
|
check_gcc_machine_option "vsx"
|
||||||
|
;;
|
||||||
x86*)
|
x86*)
|
||||||
case ${tgt_os} in
|
case ${tgt_os} in
|
||||||
|
android)
|
||||||
|
soft_enable realtime_only
|
||||||
|
;;
|
||||||
win*)
|
win*)
|
||||||
enabled gcc && add_cflags -fno-common
|
enabled gcc && add_cflags -fno-common
|
||||||
;;
|
;;
|
||||||
@ -1202,6 +1277,13 @@ EOF
|
|||||||
AS=msvs
|
AS=msvs
|
||||||
msvs_arch_dir=x86-msvs
|
msvs_arch_dir=x86-msvs
|
||||||
vc_version=${tgt_cc##vs}
|
vc_version=${tgt_cc##vs}
|
||||||
|
case $vc_version in
|
||||||
|
7|8|9|10|11|12|13|14)
|
||||||
|
echo "${tgt_cc} does not support avx512, disabling....."
|
||||||
|
RTCD_OPTIONS="${RTCD_OPTIONS}--disable-avx512 "
|
||||||
|
soft_disable avx512
|
||||||
|
;;
|
||||||
|
esac
|
||||||
case $vc_version in
|
case $vc_version in
|
||||||
7|8|9|10)
|
7|8|9|10)
|
||||||
echo "${tgt_cc} does not support avx/avx2, disabling....."
|
echo "${tgt_cc} does not support avx/avx2, disabling....."
|
||||||
@ -1245,10 +1327,14 @@ EOF
|
|||||||
fi
|
fi
|
||||||
elif disabled $ext; then
|
elif disabled $ext; then
|
||||||
disable_exts="yes"
|
disable_exts="yes"
|
||||||
|
else
|
||||||
|
if [ "$ext" = "avx512" ]; then
|
||||||
|
check_gcc_machine_options $ext avx512f avx512cd avx512bw avx512dq avx512vl
|
||||||
else
|
else
|
||||||
# use the shortened version for the flag: sse4_1 -> sse4
|
# use the shortened version for the flag: sse4_1 -> sse4
|
||||||
check_gcc_machine_option ${ext%_*} $ext
|
check_gcc_machine_option ${ext%_*} $ext
|
||||||
fi
|
fi
|
||||||
|
fi
|
||||||
done
|
done
|
||||||
|
|
||||||
if enabled external_build; then
|
if enabled external_build; then
|
||||||
@ -1273,7 +1359,6 @@ EOF
|
|||||||
esac
|
esac
|
||||||
log_echo " using $AS"
|
log_echo " using $AS"
|
||||||
fi
|
fi
|
||||||
[ "${AS##*/}" = nasm ] && add_asflags -Ox
|
|
||||||
AS_SFX=.asm
|
AS_SFX=.asm
|
||||||
case ${tgt_os} in
|
case ${tgt_os} in
|
||||||
win32)
|
win32)
|
||||||
@ -1282,7 +1367,7 @@ EOF
|
|||||||
EXE_SFX=.exe
|
EXE_SFX=.exe
|
||||||
;;
|
;;
|
||||||
win64)
|
win64)
|
||||||
add_asflags -f x64
|
add_asflags -f win64
|
||||||
enabled debug && add_asflags -g cv8
|
enabled debug && add_asflags -g cv8
|
||||||
EXE_SFX=.exe
|
EXE_SFX=.exe
|
||||||
;;
|
;;
|
||||||
@ -1309,7 +1394,8 @@ EOF
|
|||||||
add_cflags ${sim_arch}
|
add_cflags ${sim_arch}
|
||||||
add_ldflags ${sim_arch}
|
add_ldflags ${sim_arch}
|
||||||
|
|
||||||
if [ "$(show_darwin_sdk_major_version iphonesimulator)" -gt 8 ]; then
|
if [ "$(disabled external_build)" ] &&
|
||||||
|
[ "$(show_darwin_sdk_major_version iphonesimulator)" -gt 8 ]; then
|
||||||
# yasm v1.3.0 doesn't know what -fembed-bitcode means, so turning it
|
# yasm v1.3.0 doesn't know what -fembed-bitcode means, so turning it
|
||||||
# on is pointless (unless building a C-only lib). Warn the user, but
|
# on is pointless (unless building a C-only lib). Warn the user, but
|
||||||
# do nothing here.
|
# do nothing here.
|
||||||
@ -1416,6 +1502,10 @@ EOF
|
|||||||
echo "msa optimizations are available only for little endian platforms"
|
echo "msa optimizations are available only for little endian platforms"
|
||||||
disable_feature msa
|
disable_feature msa
|
||||||
fi
|
fi
|
||||||
|
if enabled mmi; then
|
||||||
|
echo "mmi optimizations are available only for little endian platforms"
|
||||||
|
disable_feature mmi
|
||||||
|
fi
|
||||||
fi
|
fi
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
|
@ -25,7 +25,7 @@ files.
|
|||||||
Options:
|
Options:
|
||||||
--help Print this message
|
--help Print this message
|
||||||
--out=outfile Redirect output to a file
|
--out=outfile Redirect output to a file
|
||||||
--ver=version Version (7,8,9,10,11,12,14) of visual studio to generate for
|
--ver=version Version (7,8,9,10,11,12,14,15) of visual studio to generate for
|
||||||
--target=isa-os-cc Target specifier
|
--target=isa-os-cc Target specifier
|
||||||
EOF
|
EOF
|
||||||
exit 1
|
exit 1
|
||||||
@ -215,7 +215,7 @@ for opt in "$@"; do
|
|||||||
;;
|
;;
|
||||||
--ver=*) vs_ver="$optval"
|
--ver=*) vs_ver="$optval"
|
||||||
case $optval in
|
case $optval in
|
||||||
10|11|12|14)
|
10|11|12|14|15)
|
||||||
;;
|
;;
|
||||||
*) die Unrecognized Visual Studio Version in $opt
|
*) die Unrecognized Visual Studio Version in $opt
|
||||||
;;
|
;;
|
||||||
@ -240,9 +240,12 @@ case "${vs_ver:-10}" in
|
|||||||
12) sln_vers="12.00"
|
12) sln_vers="12.00"
|
||||||
sln_vers_str="Visual Studio 2013"
|
sln_vers_str="Visual Studio 2013"
|
||||||
;;
|
;;
|
||||||
14) sln_vers="14.00"
|
14) sln_vers="12.00"
|
||||||
sln_vers_str="Visual Studio 2015"
|
sln_vers_str="Visual Studio 2015"
|
||||||
;;
|
;;
|
||||||
|
15) sln_vers="12.00"
|
||||||
|
sln_vers_str="Visual Studio 2017"
|
||||||
|
;;
|
||||||
esac
|
esac
|
||||||
sfx=vcxproj
|
sfx=vcxproj
|
||||||
|
|
||||||
|
@ -34,7 +34,7 @@ Options:
|
|||||||
--name=project_name Name of the project (required)
|
--name=project_name Name of the project (required)
|
||||||
--proj-guid=GUID GUID to use for the project
|
--proj-guid=GUID GUID to use for the project
|
||||||
--module-def=filename File containing export definitions (for DLLs)
|
--module-def=filename File containing export definitions (for DLLs)
|
||||||
--ver=version Version (10,11,12,14) of visual studio to generate for
|
--ver=version Version (10,11,12,14,15) of visual studio to generate for
|
||||||
--src-path-bare=dir Path to root of source tree
|
--src-path-bare=dir Path to root of source tree
|
||||||
-Ipath/to/include Additional include directories
|
-Ipath/to/include Additional include directories
|
||||||
-DFLAG[=value] Preprocessor macros to define
|
-DFLAG[=value] Preprocessor macros to define
|
||||||
@ -168,7 +168,7 @@ for opt in "$@"; do
|
|||||||
--ver=*)
|
--ver=*)
|
||||||
vs_ver="$optval"
|
vs_ver="$optval"
|
||||||
case "$optval" in
|
case "$optval" in
|
||||||
10|11|12|14)
|
10|11|12|14|15)
|
||||||
;;
|
;;
|
||||||
*) die Unrecognized Visual Studio Version in $opt
|
*) die Unrecognized Visual Studio Version in $opt
|
||||||
;;
|
;;
|
||||||
@ -218,7 +218,7 @@ guid=${guid:-`generate_uuid`}
|
|||||||
asm_use_custom_step=false
|
asm_use_custom_step=false
|
||||||
uses_asm=${uses_asm:-false}
|
uses_asm=${uses_asm:-false}
|
||||||
case "${vs_ver:-11}" in
|
case "${vs_ver:-11}" in
|
||||||
10|11|12|14)
|
10|11|12|14|15)
|
||||||
asm_use_custom_step=$uses_asm
|
asm_use_custom_step=$uses_asm
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
@ -347,6 +347,9 @@ generate_vcxproj() {
|
|||||||
if [ "$vs_ver" = "14" ]; then
|
if [ "$vs_ver" = "14" ]; then
|
||||||
tag_content PlatformToolset v140
|
tag_content PlatformToolset v140
|
||||||
fi
|
fi
|
||||||
|
if [ "$vs_ver" = "15" ]; then
|
||||||
|
tag_content PlatformToolset v141
|
||||||
|
fi
|
||||||
tag_content CharacterSet Unicode
|
tag_content CharacterSet Unicode
|
||||||
if [ "$config" = "Release" ]; then
|
if [ "$config" = "Release" ]; then
|
||||||
tag_content WholeProgramOptimization true
|
tag_content WholeProgramOptimization true
|
||||||
|
@ -35,8 +35,8 @@ ARM_TARGETS="arm64-darwin-gcc
|
|||||||
armv7s-darwin-gcc"
|
armv7s-darwin-gcc"
|
||||||
SIM_TARGETS="x86-iphonesimulator-gcc
|
SIM_TARGETS="x86-iphonesimulator-gcc
|
||||||
x86_64-iphonesimulator-gcc"
|
x86_64-iphonesimulator-gcc"
|
||||||
OSX_TARGETS="x86-darwin15-gcc
|
OSX_TARGETS="x86-darwin16-gcc
|
||||||
x86_64-darwin15-gcc"
|
x86_64-darwin16-gcc"
|
||||||
TARGETS="${ARM_TARGETS} ${SIM_TARGETS}"
|
TARGETS="${ARM_TARGETS} ${SIM_TARGETS}"
|
||||||
|
|
||||||
# Configures for the target specified by $1, and invokes make with the dist
|
# Configures for the target specified by $1, and invokes make with the dist
|
||||||
@ -271,7 +271,7 @@ cat << EOF
|
|||||||
--help: Display this message and exit.
|
--help: Display this message and exit.
|
||||||
--enable-shared: Build a dynamic framework for use on iOS 8 or later.
|
--enable-shared: Build a dynamic framework for use on iOS 8 or later.
|
||||||
--extra-configure-args <args>: Extra args to pass when configuring libvpx.
|
--extra-configure-args <args>: Extra args to pass when configuring libvpx.
|
||||||
--macosx: Uses darwin15 targets instead of iphonesimulator targets for x86
|
--macosx: Uses darwin16 targets instead of iphonesimulator targets for x86
|
||||||
and x86_64. Allows linking to framework when builds target MacOSX
|
and x86_64. Allows linking to framework when builds target MacOSX
|
||||||
instead of iOS.
|
instead of iOS.
|
||||||
--preserve-build-output: Do not delete the build directory.
|
--preserve-build-output: Do not delete the build directory.
|
||||||
|
@ -41,6 +41,15 @@ fix_path() {
|
|||||||
# Corrects the paths in file_list in one pass for efficiency.
|
# Corrects the paths in file_list in one pass for efficiency.
|
||||||
# $1 is the name of the array to be modified.
|
# $1 is the name of the array to be modified.
|
||||||
fix_file_list() {
|
fix_file_list() {
|
||||||
|
if [ "${FIXPATH}" = "echo_path" ] ; then
|
||||||
|
# When used with echo_path, fix_file_list is a no-op. Avoid warning about
|
||||||
|
# unsupported 'declare -n' when it is not important.
|
||||||
|
return 0
|
||||||
|
elif [ "${BASH_VERSINFO}" -lt 4 ] ; then
|
||||||
|
echo "Cygwin path conversion has failed. Please use a version of bash"
|
||||||
|
echo "which supports nameref (-n), introduced in bash 4.3"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
declare -n array_ref=$1
|
declare -n array_ref=$1
|
||||||
files=$(fix_path "${array_ref[@]}")
|
files=$(fix_path "${array_ref[@]}")
|
||||||
local IFS=$'\n'
|
local IFS=$'\n'
|
||||||
|
@ -1,4 +1,13 @@
|
|||||||
#!/usr/bin/env perl
|
#!/usr/bin/env perl
|
||||||
|
##
|
||||||
|
## Copyright (c) 2017 The WebM project authors. All Rights Reserved.
|
||||||
|
##
|
||||||
|
## Use of this source code is governed by a BSD-style license
|
||||||
|
## that can be found in the LICENSE file in the root of the source
|
||||||
|
## tree. An additional intellectual property rights grant can be found
|
||||||
|
## in the file PATENTS. All contributing project authors may
|
||||||
|
## be found in the AUTHORS file in the root of the source tree.
|
||||||
|
##
|
||||||
|
|
||||||
no strict 'refs';
|
no strict 'refs';
|
||||||
use warnings;
|
use warnings;
|
||||||
@ -200,6 +209,7 @@ sub filter {
|
|||||||
sub common_top() {
|
sub common_top() {
|
||||||
my $include_guard = uc($opts{sym})."_H_";
|
my $include_guard = uc($opts{sym})."_H_";
|
||||||
print <<EOF;
|
print <<EOF;
|
||||||
|
// This file is generated. Do not edit.
|
||||||
#ifndef ${include_guard}
|
#ifndef ${include_guard}
|
||||||
#define ${include_guard}
|
#define ${include_guard}
|
||||||
|
|
||||||
@ -335,6 +345,36 @@ EOF
|
|||||||
common_bottom;
|
common_bottom;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sub ppc() {
|
||||||
|
determine_indirection("c", @ALL_ARCHS);
|
||||||
|
|
||||||
|
# Assign the helper variable for each enabled extension
|
||||||
|
foreach my $opt (@ALL_ARCHS) {
|
||||||
|
my $opt_uc = uc $opt;
|
||||||
|
eval "\$have_${opt}=\"flags & HAS_${opt_uc}\"";
|
||||||
|
}
|
||||||
|
|
||||||
|
common_top;
|
||||||
|
print <<EOF;
|
||||||
|
#include "vpx_config.h"
|
||||||
|
|
||||||
|
#ifdef RTCD_C
|
||||||
|
#include "vpx_ports/ppc.h"
|
||||||
|
static void setup_rtcd_internal(void)
|
||||||
|
{
|
||||||
|
int flags = ppc_simd_caps();
|
||||||
|
(void)flags;
|
||||||
|
EOF
|
||||||
|
|
||||||
|
set_function_pointers("c", @ALL_ARCHS);
|
||||||
|
|
||||||
|
print <<EOF;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
EOF
|
||||||
|
common_bottom;
|
||||||
|
}
|
||||||
|
|
||||||
sub unoptimized() {
|
sub unoptimized() {
|
||||||
determine_indirection "c";
|
determine_indirection "c";
|
||||||
common_top;
|
common_top;
|
||||||
@ -361,10 +401,10 @@ EOF
|
|||||||
|
|
||||||
&require("c");
|
&require("c");
|
||||||
if ($opts{arch} eq 'x86') {
|
if ($opts{arch} eq 'x86') {
|
||||||
@ALL_ARCHS = filter(qw/mmx sse sse2 sse3 ssse3 sse4_1 avx avx2/);
|
@ALL_ARCHS = filter(qw/mmx sse sse2 sse3 ssse3 sse4_1 avx avx2 avx512/);
|
||||||
x86;
|
x86;
|
||||||
} elsif ($opts{arch} eq 'x86_64') {
|
} elsif ($opts{arch} eq 'x86_64') {
|
||||||
@ALL_ARCHS = filter(qw/mmx sse sse2 sse3 ssse3 sse4_1 avx avx2/);
|
@ALL_ARCHS = filter(qw/mmx sse sse2 sse3 ssse3 sse4_1 avx avx2 avx512/);
|
||||||
@REQUIRES = filter(keys %required ? keys %required : qw/mmx sse sse2/);
|
@REQUIRES = filter(keys %required ? keys %required : qw/mmx sse sse2/);
|
||||||
&require(@REQUIRES);
|
&require(@REQUIRES);
|
||||||
x86;
|
x86;
|
||||||
@ -381,6 +421,10 @@ if ($opts{arch} eq 'x86') {
|
|||||||
@ALL_ARCHS = filter("$opts{arch}", qw/msa/);
|
@ALL_ARCHS = filter("$opts{arch}", qw/msa/);
|
||||||
last;
|
last;
|
||||||
}
|
}
|
||||||
|
if (/HAVE_MMI=yes/) {
|
||||||
|
@ALL_ARCHS = filter("$opts{arch}", qw/mmi/);
|
||||||
|
last;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
close CONFIG_FILE;
|
close CONFIG_FILE;
|
||||||
mips;
|
mips;
|
||||||
@ -390,6 +434,9 @@ if ($opts{arch} eq 'x86') {
|
|||||||
} elsif ($opts{arch} eq 'armv8' || $opts{arch} eq 'arm64' ) {
|
} elsif ($opts{arch} eq 'armv8' || $opts{arch} eq 'arm64' ) {
|
||||||
@ALL_ARCHS = filter(qw/neon/);
|
@ALL_ARCHS = filter(qw/neon/);
|
||||||
arm;
|
arm;
|
||||||
|
} elsif ($opts{arch} =~ /^ppc/ ) {
|
||||||
|
@ALL_ARCHS = filter(qw/vsx/);
|
||||||
|
ppc;
|
||||||
} else {
|
} else {
|
||||||
unoptimized;
|
unoptimized;
|
||||||
}
|
}
|
||||||
|
@ -54,13 +54,6 @@ sub FixThumbInstructions($$)
|
|||||||
# "addne r0, r0, r2".
|
# "addne r0, r0, r2".
|
||||||
s/^(\s*)((ldr|str)(ne)?[bhd]?)(\s+)(\w+),(\s*\w+,)?\s*\[(\w+)\],\s*(\w+)/$1$2$5$6,$7 [$8]\n$1add$4$5$8, $8, $9/g;
|
s/^(\s*)((ldr|str)(ne)?[bhd]?)(\s+)(\w+),(\s*\w+,)?\s*\[(\w+)\],\s*(\w+)/$1$2$5$6,$7 [$8]\n$1add$4$5$8, $8, $9/g;
|
||||||
|
|
||||||
# Convert a conditional addition to the pc register into a series of
|
|
||||||
# instructions. This converts "addlt pc, pc, r3, lsl #2" into
|
|
||||||
# "itttt lt", "movlt.n r12, pc", "addlt.w r12, #12",
|
|
||||||
# "addlt.w r12, r12, r3, lsl #2", "movlt.n pc, r12".
|
|
||||||
# This assumes that r12 is free at this point.
|
|
||||||
s/^(\s*)addlt(\s+)pc,\s*pc,\s*(\w+),\s*lsl\s*#(\d+)/$1itttt$2lt\n$1movlt.n$2r12, pc\n$1addlt.w$2r12, #12\n$1addlt.w$2r12, r12, $3, lsl #($4-$branch_shift_offset)\n$1movlt.n$2pc, r12/g;
|
|
||||||
|
|
||||||
# Convert "mov pc, lr" into "bx lr", since the former only works
|
# Convert "mov pc, lr" into "bx lr", since the former only works
|
||||||
# for switching from arm to thumb (and only in armv7), but not
|
# for switching from arm to thumb (and only in armv7), but not
|
||||||
# from thumb to arm.
|
# from thumb to arm.
|
||||||
|
@ -60,6 +60,7 @@ if [ ${bare} ]; then
|
|||||||
echo "${changelog_version}${git_version_id}" > $$.tmp
|
echo "${changelog_version}${git_version_id}" > $$.tmp
|
||||||
else
|
else
|
||||||
cat<<EOF>$$.tmp
|
cat<<EOF>$$.tmp
|
||||||
|
// This file is generated. Do not edit.
|
||||||
#define VERSION_MAJOR $major_version
|
#define VERSION_MAJOR $major_version
|
||||||
#define VERSION_MINOR $minor_version
|
#define VERSION_MINOR $minor_version
|
||||||
#define VERSION_PATCH $patch_version
|
#define VERSION_PATCH $patch_version
|
||||||
|
@ -1,5 +1,4 @@
|
|||||||
# This file is used by gcl to get repository specific information.
|
# This file is used by git cl to get repository specific information.
|
||||||
GERRIT_HOST: chromium-review.googlesource.com
|
GERRIT_HOST: True
|
||||||
GERRIT_PORT: 29418
|
|
||||||
CODE_REVIEW_SERVER: chromium-review.googlesource.com
|
CODE_REVIEW_SERVER: chromium-review.googlesource.com
|
||||||
GERRIT_SQUASH_UPLOADS: False
|
GERRIT_SQUASH_UPLOADS: False
|
||||||
|
40
configure
vendored
40
configure
vendored
@ -101,18 +101,23 @@ EOF
|
|||||||
all_platforms="${all_platforms} arm64-android-gcc"
|
all_platforms="${all_platforms} arm64-android-gcc"
|
||||||
all_platforms="${all_platforms} arm64-darwin-gcc"
|
all_platforms="${all_platforms} arm64-darwin-gcc"
|
||||||
all_platforms="${all_platforms} arm64-linux-gcc"
|
all_platforms="${all_platforms} arm64-linux-gcc"
|
||||||
|
all_platforms="${all_platforms} arm64-win64-gcc"
|
||||||
all_platforms="${all_platforms} armv7-android-gcc" #neon Cortex-A8
|
all_platforms="${all_platforms} armv7-android-gcc" #neon Cortex-A8
|
||||||
all_platforms="${all_platforms} armv7-darwin-gcc" #neon Cortex-A8
|
all_platforms="${all_platforms} armv7-darwin-gcc" #neon Cortex-A8
|
||||||
all_platforms="${all_platforms} armv7-linux-rvct" #neon Cortex-A8
|
all_platforms="${all_platforms} armv7-linux-rvct" #neon Cortex-A8
|
||||||
all_platforms="${all_platforms} armv7-linux-gcc" #neon Cortex-A8
|
all_platforms="${all_platforms} armv7-linux-gcc" #neon Cortex-A8
|
||||||
all_platforms="${all_platforms} armv7-none-rvct" #neon Cortex-A8
|
all_platforms="${all_platforms} armv7-none-rvct" #neon Cortex-A8
|
||||||
|
all_platforms="${all_platforms} armv7-win32-gcc"
|
||||||
all_platforms="${all_platforms} armv7-win32-vs11"
|
all_platforms="${all_platforms} armv7-win32-vs11"
|
||||||
all_platforms="${all_platforms} armv7-win32-vs12"
|
all_platforms="${all_platforms} armv7-win32-vs12"
|
||||||
all_platforms="${all_platforms} armv7-win32-vs14"
|
all_platforms="${all_platforms} armv7-win32-vs14"
|
||||||
|
all_platforms="${all_platforms} armv7-win32-vs15"
|
||||||
all_platforms="${all_platforms} armv7s-darwin-gcc"
|
all_platforms="${all_platforms} armv7s-darwin-gcc"
|
||||||
all_platforms="${all_platforms} armv8-linux-gcc"
|
all_platforms="${all_platforms} armv8-linux-gcc"
|
||||||
all_platforms="${all_platforms} mips32-linux-gcc"
|
all_platforms="${all_platforms} mips32-linux-gcc"
|
||||||
all_platforms="${all_platforms} mips64-linux-gcc"
|
all_platforms="${all_platforms} mips64-linux-gcc"
|
||||||
|
all_platforms="${all_platforms} ppc64-linux-gcc"
|
||||||
|
all_platforms="${all_platforms} ppc64le-linux-gcc"
|
||||||
all_platforms="${all_platforms} sparc-solaris-gcc"
|
all_platforms="${all_platforms} sparc-solaris-gcc"
|
||||||
all_platforms="${all_platforms} x86-android-gcc"
|
all_platforms="${all_platforms} x86-android-gcc"
|
||||||
all_platforms="${all_platforms} x86-darwin8-gcc"
|
all_platforms="${all_platforms} x86-darwin8-gcc"
|
||||||
@ -125,6 +130,8 @@ all_platforms="${all_platforms} x86-darwin12-gcc"
|
|||||||
all_platforms="${all_platforms} x86-darwin13-gcc"
|
all_platforms="${all_platforms} x86-darwin13-gcc"
|
||||||
all_platforms="${all_platforms} x86-darwin14-gcc"
|
all_platforms="${all_platforms} x86-darwin14-gcc"
|
||||||
all_platforms="${all_platforms} x86-darwin15-gcc"
|
all_platforms="${all_platforms} x86-darwin15-gcc"
|
||||||
|
all_platforms="${all_platforms} x86-darwin16-gcc"
|
||||||
|
all_platforms="${all_platforms} x86-darwin17-gcc"
|
||||||
all_platforms="${all_platforms} x86-iphonesimulator-gcc"
|
all_platforms="${all_platforms} x86-iphonesimulator-gcc"
|
||||||
all_platforms="${all_platforms} x86-linux-gcc"
|
all_platforms="${all_platforms} x86-linux-gcc"
|
||||||
all_platforms="${all_platforms} x86-linux-icc"
|
all_platforms="${all_platforms} x86-linux-icc"
|
||||||
@ -135,6 +142,7 @@ all_platforms="${all_platforms} x86-win32-vs10"
|
|||||||
all_platforms="${all_platforms} x86-win32-vs11"
|
all_platforms="${all_platforms} x86-win32-vs11"
|
||||||
all_platforms="${all_platforms} x86-win32-vs12"
|
all_platforms="${all_platforms} x86-win32-vs12"
|
||||||
all_platforms="${all_platforms} x86-win32-vs14"
|
all_platforms="${all_platforms} x86-win32-vs14"
|
||||||
|
all_platforms="${all_platforms} x86-win32-vs15"
|
||||||
all_platforms="${all_platforms} x86_64-android-gcc"
|
all_platforms="${all_platforms} x86_64-android-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-darwin9-gcc"
|
all_platforms="${all_platforms} x86_64-darwin9-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-darwin10-gcc"
|
all_platforms="${all_platforms} x86_64-darwin10-gcc"
|
||||||
@ -143,6 +151,8 @@ all_platforms="${all_platforms} x86_64-darwin12-gcc"
|
|||||||
all_platforms="${all_platforms} x86_64-darwin13-gcc"
|
all_platforms="${all_platforms} x86_64-darwin13-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-darwin14-gcc"
|
all_platforms="${all_platforms} x86_64-darwin14-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-darwin15-gcc"
|
all_platforms="${all_platforms} x86_64-darwin15-gcc"
|
||||||
|
all_platforms="${all_platforms} x86_64-darwin16-gcc"
|
||||||
|
all_platforms="${all_platforms} x86_64-darwin17-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-iphonesimulator-gcc"
|
all_platforms="${all_platforms} x86_64-iphonesimulator-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-linux-gcc"
|
all_platforms="${all_platforms} x86_64-linux-gcc"
|
||||||
all_platforms="${all_platforms} x86_64-linux-icc"
|
all_platforms="${all_platforms} x86_64-linux-icc"
|
||||||
@ -152,6 +162,7 @@ all_platforms="${all_platforms} x86_64-win64-vs10"
|
|||||||
all_platforms="${all_platforms} x86_64-win64-vs11"
|
all_platforms="${all_platforms} x86_64-win64-vs11"
|
||||||
all_platforms="${all_platforms} x86_64-win64-vs12"
|
all_platforms="${all_platforms} x86_64-win64-vs12"
|
||||||
all_platforms="${all_platforms} x86_64-win64-vs14"
|
all_platforms="${all_platforms} x86_64-win64-vs14"
|
||||||
|
all_platforms="${all_platforms} x86_64-win64-vs15"
|
||||||
all_platforms="${all_platforms} generic-gnu"
|
all_platforms="${all_platforms} generic-gnu"
|
||||||
|
|
||||||
# all_targets is a list of all targets that can be configured
|
# all_targets is a list of all targets that can be configured
|
||||||
@ -163,11 +174,14 @@ for t in ${all_targets}; do
|
|||||||
[ -f "${source_path}/${t}.mk" ] && enable_feature ${t}
|
[ -f "${source_path}/${t}.mk" ] && enable_feature ${t}
|
||||||
done
|
done
|
||||||
|
|
||||||
|
if ! diff --version >/dev/null; then
|
||||||
|
die "diff missing: Try installing diffutils via your package manager."
|
||||||
|
fi
|
||||||
|
|
||||||
if ! perl --version >/dev/null; then
|
if ! perl --version >/dev/null; then
|
||||||
die "Perl is required to build"
|
die "Perl is required to build"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
|
||||||
if [ "`cd \"${source_path}\" && pwd`" != "`pwd`" ]; then
|
if [ "`cd \"${source_path}\" && pwd`" != "`pwd`" ]; then
|
||||||
# test to see if source_path already configured
|
# test to see if source_path already configured
|
||||||
if [ -f "${source_path}/vpx_config.h" ]; then
|
if [ -f "${source_path}/vpx_config.h" ]; then
|
||||||
@ -223,6 +237,7 @@ ARCH_LIST="
|
|||||||
mips
|
mips
|
||||||
x86
|
x86
|
||||||
x86_64
|
x86_64
|
||||||
|
ppc
|
||||||
"
|
"
|
||||||
ARCH_EXT_LIST_X86="
|
ARCH_EXT_LIST_X86="
|
||||||
mmx
|
mmx
|
||||||
@ -233,7 +248,13 @@ ARCH_EXT_LIST_X86="
|
|||||||
sse4_1
|
sse4_1
|
||||||
avx
|
avx
|
||||||
avx2
|
avx2
|
||||||
|
avx512
|
||||||
"
|
"
|
||||||
|
|
||||||
|
ARCH_EXT_LIST_LOONGSON="
|
||||||
|
mmi
|
||||||
|
"
|
||||||
|
|
||||||
ARCH_EXT_LIST="
|
ARCH_EXT_LIST="
|
||||||
neon
|
neon
|
||||||
neon_asm
|
neon_asm
|
||||||
@ -244,6 +265,10 @@ ARCH_EXT_LIST="
|
|||||||
mips64
|
mips64
|
||||||
|
|
||||||
${ARCH_EXT_LIST_X86}
|
${ARCH_EXT_LIST_X86}
|
||||||
|
|
||||||
|
vsx
|
||||||
|
|
||||||
|
${ARCH_EXT_LIST_LOONGSON}
|
||||||
"
|
"
|
||||||
HAVE_LIST="
|
HAVE_LIST="
|
||||||
${ARCH_EXT_LIST}
|
${ARCH_EXT_LIST}
|
||||||
@ -252,10 +277,8 @@ HAVE_LIST="
|
|||||||
unistd_h
|
unistd_h
|
||||||
"
|
"
|
||||||
EXPERIMENT_LIST="
|
EXPERIMENT_LIST="
|
||||||
spatial_svc
|
|
||||||
fp_mb_stats
|
fp_mb_stats
|
||||||
emulate_hardware
|
emulate_hardware
|
||||||
misc_fixes
|
|
||||||
"
|
"
|
||||||
CONFIG_LIST="
|
CONFIG_LIST="
|
||||||
dependency_tracking
|
dependency_tracking
|
||||||
@ -310,6 +333,7 @@ CONFIG_LIST="
|
|||||||
better_hw_compatibility
|
better_hw_compatibility
|
||||||
experimental
|
experimental
|
||||||
size_limit
|
size_limit
|
||||||
|
always_adjust_bpm
|
||||||
${EXPERIMENT_LIST}
|
${EXPERIMENT_LIST}
|
||||||
"
|
"
|
||||||
CMDLINE_SELECT="
|
CMDLINE_SELECT="
|
||||||
@ -369,6 +393,7 @@ CMDLINE_SELECT="
|
|||||||
better_hw_compatibility
|
better_hw_compatibility
|
||||||
vp9_highbitdepth
|
vp9_highbitdepth
|
||||||
experimental
|
experimental
|
||||||
|
always_adjust_bpm
|
||||||
"
|
"
|
||||||
|
|
||||||
process_cmdline() {
|
process_cmdline() {
|
||||||
@ -570,6 +595,7 @@ process_toolchain() {
|
|||||||
check_add_cflags -Wdeclaration-after-statement
|
check_add_cflags -Wdeclaration-after-statement
|
||||||
check_add_cflags -Wdisabled-optimization
|
check_add_cflags -Wdisabled-optimization
|
||||||
check_add_cflags -Wfloat-conversion
|
check_add_cflags -Wfloat-conversion
|
||||||
|
check_add_cflags -Wparentheses-equality
|
||||||
check_add_cflags -Wpointer-arith
|
check_add_cflags -Wpointer-arith
|
||||||
check_add_cflags -Wtype-limits
|
check_add_cflags -Wtype-limits
|
||||||
check_add_cflags -Wcast-qual
|
check_add_cflags -Wcast-qual
|
||||||
@ -583,17 +609,17 @@ process_toolchain() {
|
|||||||
# https://bugs.chromium.org/p/webm/issues/detail?id=1069
|
# https://bugs.chromium.org/p/webm/issues/detail?id=1069
|
||||||
check_add_cflags -Wextra
|
check_add_cflags -Wextra
|
||||||
# check_add_cflags also adds to cxxflags. gtest does not do well with
|
# check_add_cflags also adds to cxxflags. gtest does not do well with
|
||||||
# -Wundef so add it explicitly to CFLAGS only.
|
# these flags so add them explicitly to CFLAGS only.
|
||||||
check_cflags -Wundef && add_cflags_only -Wundef
|
check_cflags -Wundef && add_cflags_only -Wundef
|
||||||
|
check_cflags -Wframe-larger-than=52000 && \
|
||||||
|
add_cflags_only -Wframe-larger-than=52000
|
||||||
if enabled mips || [ -z "${INLINE}" ]; then
|
if enabled mips || [ -z "${INLINE}" ]; then
|
||||||
enabled extra_warnings || check_add_cflags -Wno-unused-function
|
enabled extra_warnings || check_add_cflags -Wno-unused-function
|
||||||
fi
|
fi
|
||||||
if ! enabled vp9_highbitdepth; then
|
|
||||||
# Avoid this warning for third_party C++ sources. Some reorganization
|
# Avoid this warning for third_party C++ sources. Some reorganization
|
||||||
# would be needed to apply this only to test/*.cc.
|
# would be needed to apply this only to test/*.cc.
|
||||||
check_cflags -Wshorten-64-to-32 && add_cflags_only -Wshorten-64-to-32
|
check_cflags -Wshorten-64-to-32 && add_cflags_only -Wshorten-64-to-32
|
||||||
fi
|
fi
|
||||||
fi
|
|
||||||
|
|
||||||
if enabled icc; then
|
if enabled icc; then
|
||||||
enabled werror && check_add_cflags -Werror
|
enabled werror && check_add_cflags -Werror
|
||||||
@ -644,7 +670,7 @@ process_toolchain() {
|
|||||||
gen_vcproj_cmd=${source_path}/build/make/gen_msvs_vcxproj.sh
|
gen_vcproj_cmd=${source_path}/build/make/gen_msvs_vcxproj.sh
|
||||||
enabled werror && gen_vcproj_cmd="${gen_vcproj_cmd} --enable-werror"
|
enabled werror && gen_vcproj_cmd="${gen_vcproj_cmd} --enable-werror"
|
||||||
all_targets="${all_targets} solution"
|
all_targets="${all_targets} solution"
|
||||||
INLINE="__forceinline"
|
INLINE="__inline"
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
|
|
||||||
|
@ -109,7 +109,7 @@ ifeq ($(CONFIG_WEBM_IO),yes)
|
|||||||
endif
|
endif
|
||||||
vpxenc.GUID = 548DEC74-7A15-4B2B-AFC3-AA102E7C25C1
|
vpxenc.GUID = 548DEC74-7A15-4B2B-AFC3-AA102E7C25C1
|
||||||
vpxenc.DESCRIPTION = Full featured encoder
|
vpxenc.DESCRIPTION = Full featured encoder
|
||||||
ifeq ($(CONFIG_SPATIAL_SVC),yes)
|
|
||||||
EXAMPLES-$(CONFIG_VP9_ENCODER) += vp9_spatial_svc_encoder.c
|
EXAMPLES-$(CONFIG_VP9_ENCODER) += vp9_spatial_svc_encoder.c
|
||||||
vp9_spatial_svc_encoder.SRCS += args.c args.h
|
vp9_spatial_svc_encoder.SRCS += args.c args.h
|
||||||
vp9_spatial_svc_encoder.SRCS += ivfenc.c ivfenc.h
|
vp9_spatial_svc_encoder.SRCS += ivfenc.c ivfenc.h
|
||||||
@ -120,7 +120,6 @@ ifeq ($(CONFIG_SPATIAL_SVC),yes)
|
|||||||
vp9_spatial_svc_encoder.SRCS += vpxstats.c vpxstats.h
|
vp9_spatial_svc_encoder.SRCS += vpxstats.c vpxstats.h
|
||||||
vp9_spatial_svc_encoder.GUID = 4A38598D-627D-4505-9C7B-D4020C84100D
|
vp9_spatial_svc_encoder.GUID = 4A38598D-627D-4505-9C7B-D4020C84100D
|
||||||
vp9_spatial_svc_encoder.DESCRIPTION = VP9 Spatial SVC Encoder
|
vp9_spatial_svc_encoder.DESCRIPTION = VP9 Spatial SVC Encoder
|
||||||
endif
|
|
||||||
|
|
||||||
ifneq ($(CONFIG_SHARED),yes)
|
ifneq ($(CONFIG_SHARED),yes)
|
||||||
EXAMPLES-$(CONFIG_VP9_ENCODER) += resize_util.c
|
EXAMPLES-$(CONFIG_VP9_ENCODER) += resize_util.c
|
||||||
|
@ -151,7 +151,7 @@ static void write_ivf_frame_header(FILE *outfile,
|
|||||||
if (pkt->kind != VPX_CODEC_CX_FRAME_PKT) return;
|
if (pkt->kind != VPX_CODEC_CX_FRAME_PKT) return;
|
||||||
|
|
||||||
pts = pkt->data.frame.pts;
|
pts = pkt->data.frame.pts;
|
||||||
mem_put_le32(header, pkt->data.frame.sz);
|
mem_put_le32(header, (int)pkt->data.frame.sz);
|
||||||
mem_put_le32(header + 4, pts & 0xFFFFFFFF);
|
mem_put_le32(header + 4, pts & 0xFFFFFFFF);
|
||||||
mem_put_le32(header + 8, pts >> 32);
|
mem_put_le32(header + 8, pts >> 32);
|
||||||
|
|
||||||
@ -190,7 +190,7 @@ static void set_temporal_layer_pattern(int num_temporal_layers,
|
|||||||
cfg->ts_layer_id[0] = 0;
|
cfg->ts_layer_id[0] = 0;
|
||||||
cfg->ts_layer_id[1] = 1;
|
cfg->ts_layer_id[1] = 1;
|
||||||
// Use 60/40 bit allocation as example.
|
// Use 60/40 bit allocation as example.
|
||||||
cfg->ts_target_bitrate[0] = 0.6f * bitrate;
|
cfg->ts_target_bitrate[0] = (int)(0.6f * bitrate);
|
||||||
cfg->ts_target_bitrate[1] = bitrate;
|
cfg->ts_target_bitrate[1] = bitrate;
|
||||||
|
|
||||||
/* 0=L, 1=GF */
|
/* 0=L, 1=GF */
|
||||||
@ -240,9 +240,9 @@ static void set_temporal_layer_pattern(int num_temporal_layers,
|
|||||||
cfg->ts_layer_id[1] = 2;
|
cfg->ts_layer_id[1] = 2;
|
||||||
cfg->ts_layer_id[2] = 1;
|
cfg->ts_layer_id[2] = 1;
|
||||||
cfg->ts_layer_id[3] = 2;
|
cfg->ts_layer_id[3] = 2;
|
||||||
// Use 40/20/40 bit allocation as example.
|
// Use 45/20/35 bit allocation as example.
|
||||||
cfg->ts_target_bitrate[0] = 0.4f * bitrate;
|
cfg->ts_target_bitrate[0] = (int)(0.45f * bitrate);
|
||||||
cfg->ts_target_bitrate[1] = 0.6f * bitrate;
|
cfg->ts_target_bitrate[1] = (int)(0.65f * bitrate);
|
||||||
cfg->ts_target_bitrate[2] = bitrate;
|
cfg->ts_target_bitrate[2] = bitrate;
|
||||||
|
|
||||||
/* 0=L, 1=GF, 2=ARF */
|
/* 0=L, 1=GF, 2=ARF */
|
||||||
@ -294,8 +294,8 @@ int main(int argc, char **argv) {
|
|||||||
vpx_codec_err_t res[NUM_ENCODERS];
|
vpx_codec_err_t res[NUM_ENCODERS];
|
||||||
|
|
||||||
int i;
|
int i;
|
||||||
long width;
|
int width;
|
||||||
long height;
|
int height;
|
||||||
int length_frame;
|
int length_frame;
|
||||||
int frame_avail;
|
int frame_avail;
|
||||||
int got_data;
|
int got_data;
|
||||||
@ -347,9 +347,9 @@ int main(int argc, char **argv) {
|
|||||||
|
|
||||||
printf("Using %s\n", vpx_codec_iface_name(interface));
|
printf("Using %s\n", vpx_codec_iface_name(interface));
|
||||||
|
|
||||||
width = strtol(argv[1], NULL, 0);
|
width = (int)strtol(argv[1], NULL, 0);
|
||||||
height = strtol(argv[2], NULL, 0);
|
height = (int)strtol(argv[2], NULL, 0);
|
||||||
framerate = strtol(argv[3], NULL, 0);
|
framerate = (int)strtol(argv[3], NULL, 0);
|
||||||
|
|
||||||
if (width < 16 || width % 2 || height < 16 || height % 2)
|
if (width < 16 || width % 2 || height < 16 || height % 2)
|
||||||
die("Invalid resolution: %ldx%ld", width, height);
|
die("Invalid resolution: %ldx%ld", width, height);
|
||||||
@ -371,12 +371,13 @@ int main(int argc, char **argv) {
|
|||||||
|
|
||||||
// Bitrates per spatial layer: overwrite default rates above.
|
// Bitrates per spatial layer: overwrite default rates above.
|
||||||
for (i = 0; i < NUM_ENCODERS; i++) {
|
for (i = 0; i < NUM_ENCODERS; i++) {
|
||||||
target_bitrate[i] = strtol(argv[NUM_ENCODERS + 5 + i], NULL, 0);
|
target_bitrate[i] = (int)strtol(argv[NUM_ENCODERS + 5 + i], NULL, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Temporal layers per spatial layers: overwrite default settings above.
|
// Temporal layers per spatial layers: overwrite default settings above.
|
||||||
for (i = 0; i < NUM_ENCODERS; i++) {
|
for (i = 0; i < NUM_ENCODERS; i++) {
|
||||||
num_temporal_layers[i] = strtol(argv[2 * NUM_ENCODERS + 5 + i], NULL, 0);
|
num_temporal_layers[i] =
|
||||||
|
(int)strtol(argv[2 * NUM_ENCODERS + 5 + i], NULL, 0);
|
||||||
if (num_temporal_layers[i] < 1 || num_temporal_layers[i] > 3)
|
if (num_temporal_layers[i] < 1 || num_temporal_layers[i] > 3)
|
||||||
die("Invalid temporal layers: %d, Must be 1, 2, or 3. \n",
|
die("Invalid temporal layers: %d, Must be 1, 2, or 3. \n",
|
||||||
num_temporal_layers);
|
num_temporal_layers);
|
||||||
@ -391,9 +392,9 @@ int main(int argc, char **argv) {
|
|||||||
downsampled_input[i] = fopen(filename, "wb");
|
downsampled_input[i] = fopen(filename, "wb");
|
||||||
}
|
}
|
||||||
|
|
||||||
key_frame_insert = strtol(argv[3 * NUM_ENCODERS + 5], NULL, 0);
|
key_frame_insert = (int)strtol(argv[3 * NUM_ENCODERS + 5], NULL, 0);
|
||||||
|
|
||||||
show_psnr = strtol(argv[3 * NUM_ENCODERS + 6], NULL, 0);
|
show_psnr = (int)strtol(argv[3 * NUM_ENCODERS + 6], NULL, 0);
|
||||||
|
|
||||||
/* Populate default encoder configuration */
|
/* Populate default encoder configuration */
|
||||||
for (i = 0; i < NUM_ENCODERS; i++) {
|
for (i = 0; i < NUM_ENCODERS; i++) {
|
||||||
@ -460,7 +461,7 @@ int main(int argc, char **argv) {
|
|||||||
|
|
||||||
// Set the number of threads per encode/spatial layer.
|
// Set the number of threads per encode/spatial layer.
|
||||||
// (1, 1, 1) means no encoder threading.
|
// (1, 1, 1) means no encoder threading.
|
||||||
cfg[0].g_threads = 2;
|
cfg[0].g_threads = 1;
|
||||||
cfg[1].g_threads = 1;
|
cfg[1].g_threads = 1;
|
||||||
cfg[2].g_threads = 1;
|
cfg[2].g_threads = 1;
|
||||||
|
|
||||||
@ -469,7 +470,7 @@ int main(int argc, char **argv) {
|
|||||||
if (!vpx_img_alloc(&raw[i], VPX_IMG_FMT_I420, cfg[i].g_w, cfg[i].g_h, 32))
|
if (!vpx_img_alloc(&raw[i], VPX_IMG_FMT_I420, cfg[i].g_w, cfg[i].g_h, 32))
|
||||||
die("Failed to allocate image", cfg[i].g_w, cfg[i].g_h);
|
die("Failed to allocate image", cfg[i].g_w, cfg[i].g_h);
|
||||||
|
|
||||||
if (raw[0].stride[VPX_PLANE_Y] == raw[0].d_w)
|
if (raw[0].stride[VPX_PLANE_Y] == (int)raw[0].d_w)
|
||||||
read_frame_p = read_frame;
|
read_frame_p = read_frame;
|
||||||
else
|
else
|
||||||
read_frame_p = read_frame_by_row;
|
read_frame_p = read_frame_by_row;
|
||||||
@ -507,9 +508,11 @@ int main(int argc, char **argv) {
|
|||||||
|
|
||||||
/* Set NOISE_SENSITIVITY to do TEMPORAL_DENOISING */
|
/* Set NOISE_SENSITIVITY to do TEMPORAL_DENOISING */
|
||||||
/* Enable denoising for the highest-resolution encoder. */
|
/* Enable denoising for the highest-resolution encoder. */
|
||||||
if (vpx_codec_control(&codec[0], VP8E_SET_NOISE_SENSITIVITY, 4))
|
if (vpx_codec_control(&codec[0], VP8E_SET_NOISE_SENSITIVITY, 1))
|
||||||
die_codec(&codec[0], "Failed to set noise_sensitivity");
|
die_codec(&codec[0], "Failed to set noise_sensitivity");
|
||||||
for (i = 1; i < NUM_ENCODERS; i++) {
|
if (vpx_codec_control(&codec[1], VP8E_SET_NOISE_SENSITIVITY, 1))
|
||||||
|
die_codec(&codec[1], "Failed to set noise_sensitivity");
|
||||||
|
for (i = 2; i < NUM_ENCODERS; i++) {
|
||||||
if (vpx_codec_control(&codec[i], VP8E_SET_NOISE_SENSITIVITY, 0))
|
if (vpx_codec_control(&codec[i], VP8E_SET_NOISE_SENSITIVITY, 0))
|
||||||
die_codec(&codec[i], "Failed to set noise_sensitivity");
|
die_codec(&codec[i], "Failed to set noise_sensitivity");
|
||||||
}
|
}
|
||||||
@ -556,7 +559,8 @@ int main(int argc, char **argv) {
|
|||||||
/* Write out down-sampled input. */
|
/* Write out down-sampled input. */
|
||||||
length_frame = cfg[i].g_w * cfg[i].g_h * 3 / 2;
|
length_frame = cfg[i].g_w * cfg[i].g_h * 3 / 2;
|
||||||
if (fwrite(raw[i].planes[0], 1, length_frame,
|
if (fwrite(raw[i].planes[0], 1, length_frame,
|
||||||
downsampled_input[NUM_ENCODERS - i - 1]) != length_frame) {
|
downsampled_input[NUM_ENCODERS - i - 1]) !=
|
||||||
|
(unsigned int)length_frame) {
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -617,10 +621,6 @@ int main(int argc, char **argv) {
|
|||||||
break;
|
break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
printf(pkt[i]->kind == VPX_CODEC_CX_FRAME_PKT &&
|
|
||||||
(pkt[i]->data.frame.flags & VPX_FRAME_IS_KEY)
|
|
||||||
? "K"
|
|
||||||
: "");
|
|
||||||
fflush(stdout);
|
fflush(stdout);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -661,7 +661,6 @@ int main(int argc, char **argv) {
|
|||||||
write_ivf_file_header(outfile[i], &cfg[i], frame_cnt - 1);
|
write_ivf_file_header(outfile[i], &cfg[i], frame_cnt - 1);
|
||||||
fclose(outfile[i]);
|
fclose(outfile[i]);
|
||||||
}
|
}
|
||||||
printf("\n");
|
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
@ -168,7 +168,7 @@ void usage_exit(void) {
|
|||||||
static void parse_command_line(int argc, const char **argv_,
|
static void parse_command_line(int argc, const char **argv_,
|
||||||
AppInput *app_input, SvcContext *svc_ctx,
|
AppInput *app_input, SvcContext *svc_ctx,
|
||||||
vpx_codec_enc_cfg_t *enc_cfg) {
|
vpx_codec_enc_cfg_t *enc_cfg) {
|
||||||
struct arg arg = { 0 };
|
struct arg arg;
|
||||||
char **argv = NULL;
|
char **argv = NULL;
|
||||||
char **argi = NULL;
|
char **argi = NULL;
|
||||||
char **argj = NULL;
|
char **argj = NULL;
|
||||||
@ -429,7 +429,8 @@ static void set_rate_control_stats(struct RateControlStats *rc,
|
|||||||
rc->layer_framerate[layer] = framerate / cfg->ts_rate_decimator[tl];
|
rc->layer_framerate[layer] = framerate / cfg->ts_rate_decimator[tl];
|
||||||
if (tl > 0) {
|
if (tl > 0) {
|
||||||
rc->layer_pfb[layer] =
|
rc->layer_pfb[layer] =
|
||||||
1000.0 * (cfg->layer_target_bitrate[layer] -
|
1000.0 *
|
||||||
|
(cfg->layer_target_bitrate[layer] -
|
||||||
cfg->layer_target_bitrate[layer - 1]) /
|
cfg->layer_target_bitrate[layer - 1]) /
|
||||||
(rc->layer_framerate[layer] - rc->layer_framerate[layer - 1]);
|
(rc->layer_framerate[layer] - rc->layer_framerate[layer - 1]);
|
||||||
} else {
|
} else {
|
||||||
@ -502,14 +503,12 @@ static void printout_rate_control_summary(struct RateControlStats *rc,
|
|||||||
printf("Average, rms-variance, and percent-fluct: %f %f %f \n",
|
printf("Average, rms-variance, and percent-fluct: %f %f %f \n",
|
||||||
rc->avg_st_encoding_bitrate, sqrt(rc->variance_st_encoding_bitrate),
|
rc->avg_st_encoding_bitrate, sqrt(rc->variance_st_encoding_bitrate),
|
||||||
perc_fluctuation);
|
perc_fluctuation);
|
||||||
if (frame_cnt != tot_num_frames)
|
printf("Num of input, num of encoded (super) frames: %d %d \n", frame_cnt,
|
||||||
die("Error: Number of input frames not equal to output encoded frames != "
|
tot_num_frames);
|
||||||
"%d tot_num_frames = %d\n",
|
|
||||||
frame_cnt, tot_num_frames);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
vpx_codec_err_t parse_superframe_index(const uint8_t *data, size_t data_sz,
|
vpx_codec_err_t parse_superframe_index(const uint8_t *data, size_t data_sz,
|
||||||
uint32_t sizes[8], int *count) {
|
uint64_t sizes[8], int *count) {
|
||||||
// A chunk ending with a byte matching 0xc0 is an invalid chunk unless
|
// A chunk ending with a byte matching 0xc0 is an invalid chunk unless
|
||||||
// it is a super frame index. If the last byte of real video compression
|
// it is a super frame index. If the last byte of real video compression
|
||||||
// data is 0xc0 the encoder must add a 0 byte. If we have the marker but
|
// data is 0xc0 the encoder must add a 0 byte. If we have the marker but
|
||||||
@ -561,9 +560,10 @@ vpx_codec_err_t parse_superframe_index(const uint8_t *data, size_t data_sz,
|
|||||||
// bypass/flexible mode. The pattern corresponds to the pattern
|
// bypass/flexible mode. The pattern corresponds to the pattern
|
||||||
// VP9E_TEMPORAL_LAYERING_MODE_0101 (temporal_layering_mode == 2) used in
|
// VP9E_TEMPORAL_LAYERING_MODE_0101 (temporal_layering_mode == 2) used in
|
||||||
// non-flexible mode.
|
// non-flexible mode.
|
||||||
void set_frame_flags_bypass_mode(int sl, int tl, int num_spatial_layers,
|
void set_frame_flags_bypass_mode(int tl, int num_spatial_layers,
|
||||||
int is_key_frame,
|
int is_key_frame,
|
||||||
vpx_svc_ref_frame_config_t *ref_frame_config) {
|
vpx_svc_ref_frame_config_t *ref_frame_config) {
|
||||||
|
int sl;
|
||||||
for (sl = 0; sl < num_spatial_layers; ++sl) {
|
for (sl = 0; sl < num_spatial_layers; ++sl) {
|
||||||
if (!tl) {
|
if (!tl) {
|
||||||
if (!sl) {
|
if (!sl) {
|
||||||
@ -573,8 +573,8 @@ void set_frame_flags_bypass_mode(int sl, int tl, int num_spatial_layers,
|
|||||||
} else {
|
} else {
|
||||||
if (is_key_frame) {
|
if (is_key_frame) {
|
||||||
ref_frame_config->frame_flags[sl] =
|
ref_frame_config->frame_flags[sl] =
|
||||||
VP8_EFLAG_NO_REF_LAST | VP8_EFLAG_NO_REF_ARF |
|
VP8_EFLAG_NO_REF_GF | VP8_EFLAG_NO_REF_ARF |
|
||||||
VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_ARF;
|
VP8_EFLAG_NO_UPD_LAST | VP8_EFLAG_NO_UPD_ARF;
|
||||||
} else {
|
} else {
|
||||||
ref_frame_config->frame_flags[sl] =
|
ref_frame_config->frame_flags[sl] =
|
||||||
VP8_EFLAG_NO_REF_ARF | VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_ARF;
|
VP8_EFLAG_NO_REF_ARF | VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_ARF;
|
||||||
@ -588,14 +588,24 @@ void set_frame_flags_bypass_mode(int sl, int tl, int num_spatial_layers,
|
|||||||
} else {
|
} else {
|
||||||
ref_frame_config->frame_flags[sl] =
|
ref_frame_config->frame_flags[sl] =
|
||||||
VP8_EFLAG_NO_REF_ARF | VP8_EFLAG_NO_UPD_LAST | VP8_EFLAG_NO_UPD_GF;
|
VP8_EFLAG_NO_REF_ARF | VP8_EFLAG_NO_UPD_LAST | VP8_EFLAG_NO_UPD_GF;
|
||||||
|
if (sl == num_spatial_layers - 1)
|
||||||
|
ref_frame_config->frame_flags[sl] =
|
||||||
|
VP8_EFLAG_NO_UPD_ARF | VP8_EFLAG_NO_REF_ARF |
|
||||||
|
VP8_EFLAG_NO_UPD_LAST | VP8_EFLAG_NO_UPD_GF;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (tl == 0) {
|
if (tl == 0) {
|
||||||
ref_frame_config->lst_fb_idx[sl] = sl;
|
ref_frame_config->lst_fb_idx[sl] = sl;
|
||||||
if (sl)
|
if (sl) {
|
||||||
|
if (is_key_frame) {
|
||||||
|
ref_frame_config->lst_fb_idx[sl] = sl - 1;
|
||||||
|
ref_frame_config->gld_fb_idx[sl] = sl;
|
||||||
|
} else {
|
||||||
ref_frame_config->gld_fb_idx[sl] = sl - 1;
|
ref_frame_config->gld_fb_idx[sl] = sl - 1;
|
||||||
else
|
}
|
||||||
|
} else {
|
||||||
ref_frame_config->gld_fb_idx[sl] = 0;
|
ref_frame_config->gld_fb_idx[sl] = 0;
|
||||||
|
}
|
||||||
ref_frame_config->alt_fb_idx[sl] = 0;
|
ref_frame_config->alt_fb_idx[sl] = 0;
|
||||||
} else if (tl == 1) {
|
} else if (tl == 1) {
|
||||||
ref_frame_config->lst_fb_idx[sl] = sl;
|
ref_frame_config->lst_fb_idx[sl] = sl;
|
||||||
@ -606,9 +616,9 @@ void set_frame_flags_bypass_mode(int sl, int tl, int num_spatial_layers,
|
|||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, const char **argv) {
|
int main(int argc, const char **argv) {
|
||||||
AppInput app_input = { 0 };
|
AppInput app_input;
|
||||||
VpxVideoWriter *writer = NULL;
|
VpxVideoWriter *writer = NULL;
|
||||||
VpxVideoInfo info = { 0 };
|
VpxVideoInfo info;
|
||||||
vpx_codec_ctx_t codec;
|
vpx_codec_ctx_t codec;
|
||||||
vpx_codec_enc_cfg_t enc_cfg;
|
vpx_codec_enc_cfg_t enc_cfg;
|
||||||
SvcContext svc_ctx;
|
SvcContext svc_ctx;
|
||||||
@ -622,7 +632,7 @@ int main(int argc, const char **argv) {
|
|||||||
int end_of_stream = 0;
|
int end_of_stream = 0;
|
||||||
int frames_received = 0;
|
int frames_received = 0;
|
||||||
#if OUTPUT_RC_STATS
|
#if OUTPUT_RC_STATS
|
||||||
VpxVideoWriter *outfile[VPX_TS_MAX_LAYERS] = { NULL };
|
VpxVideoWriter *outfile[VPX_SS_MAX_LAYERS] = { NULL };
|
||||||
struct RateControlStats rc;
|
struct RateControlStats rc;
|
||||||
vpx_svc_layer_id_t layer_id;
|
vpx_svc_layer_id_t layer_id;
|
||||||
vpx_svc_ref_frame_config_t ref_frame_config;
|
vpx_svc_ref_frame_config_t ref_frame_config;
|
||||||
@ -634,13 +644,15 @@ int main(int argc, const char **argv) {
|
|||||||
struct vpx_usec_timer timer;
|
struct vpx_usec_timer timer;
|
||||||
int64_t cx_time = 0;
|
int64_t cx_time = 0;
|
||||||
memset(&svc_ctx, 0, sizeof(svc_ctx));
|
memset(&svc_ctx, 0, sizeof(svc_ctx));
|
||||||
svc_ctx.log_print = 1;
|
memset(&app_input, 0, sizeof(AppInput));
|
||||||
|
memset(&info, 0, sizeof(VpxVideoInfo));
|
||||||
exec_name = argv[0];
|
exec_name = argv[0];
|
||||||
parse_command_line(argc, argv, &app_input, &svc_ctx, &enc_cfg);
|
parse_command_line(argc, argv, &app_input, &svc_ctx, &enc_cfg);
|
||||||
|
|
||||||
// Allocate image buffer
|
// Allocate image buffer
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
if (!vpx_img_alloc(&raw, enc_cfg.g_input_bit_depth == 8 ? VPX_IMG_FMT_I420
|
if (!vpx_img_alloc(&raw,
|
||||||
|
enc_cfg.g_input_bit_depth == 8 ? VPX_IMG_FMT_I420
|
||||||
: VPX_IMG_FMT_I42016,
|
: VPX_IMG_FMT_I42016,
|
||||||
enc_cfg.g_w, enc_cfg.g_h, 32)) {
|
enc_cfg.g_w, enc_cfg.g_h, 32)) {
|
||||||
die("Failed to allocate image %dx%d\n", enc_cfg.g_w, enc_cfg.g_h);
|
die("Failed to allocate image %dx%d\n", enc_cfg.g_w, enc_cfg.g_h);
|
||||||
@ -660,6 +672,10 @@ int main(int argc, const char **argv) {
|
|||||||
die("Failed to initialize encoder\n");
|
die("Failed to initialize encoder\n");
|
||||||
|
|
||||||
#if OUTPUT_RC_STATS
|
#if OUTPUT_RC_STATS
|
||||||
|
rc.window_count = 1;
|
||||||
|
rc.window_size = 15; // Silence a static analysis warning.
|
||||||
|
rc.avg_st_encoding_bitrate = 0.0;
|
||||||
|
rc.variance_st_encoding_bitrate = 0.0;
|
||||||
if (svc_ctx.output_rc_stat) {
|
if (svc_ctx.output_rc_stat) {
|
||||||
set_rate_control_stats(&rc, &enc_cfg);
|
set_rate_control_stats(&rc, &enc_cfg);
|
||||||
framerate = enc_cfg.g_timebase.den / enc_cfg.g_timebase.num;
|
framerate = enc_cfg.g_timebase.den / enc_cfg.g_timebase.num;
|
||||||
@ -678,16 +694,16 @@ int main(int argc, const char **argv) {
|
|||||||
die("Failed to open %s for writing\n", app_input.output_filename);
|
die("Failed to open %s for writing\n", app_input.output_filename);
|
||||||
}
|
}
|
||||||
#if OUTPUT_RC_STATS
|
#if OUTPUT_RC_STATS
|
||||||
// For now, just write temporal layer streams.
|
// Write out spatial layer stream.
|
||||||
// TODO(wonkap): do spatial by re-writing superframe.
|
// TODO(marpan/jianj): allow for writing each spatial and temporal stream.
|
||||||
if (svc_ctx.output_rc_stat) {
|
if (svc_ctx.output_rc_stat) {
|
||||||
for (tl = 0; tl < enc_cfg.ts_number_layers; ++tl) {
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
char file_name[PATH_MAX];
|
char file_name[PATH_MAX];
|
||||||
|
|
||||||
snprintf(file_name, sizeof(file_name), "%s_t%d.ivf",
|
snprintf(file_name, sizeof(file_name), "%s_s%d.ivf",
|
||||||
app_input.output_filename, tl);
|
app_input.output_filename, sl);
|
||||||
outfile[tl] = vpx_video_writer_open(file_name, kContainerIVF, &info);
|
outfile[sl] = vpx_video_writer_open(file_name, kContainerIVF, &info);
|
||||||
if (!outfile[tl]) die("Failed to open %s for writing", file_name);
|
if (!outfile[sl]) die("Failed to open %s for writing", file_name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@ -697,12 +713,22 @@ int main(int argc, const char **argv) {
|
|||||||
|
|
||||||
if (svc_ctx.speed != -1)
|
if (svc_ctx.speed != -1)
|
||||||
vpx_codec_control(&codec, VP8E_SET_CPUUSED, svc_ctx.speed);
|
vpx_codec_control(&codec, VP8E_SET_CPUUSED, svc_ctx.speed);
|
||||||
if (svc_ctx.threads)
|
if (svc_ctx.threads) {
|
||||||
vpx_codec_control(&codec, VP9E_SET_TILE_COLUMNS, (svc_ctx.threads >> 1));
|
vpx_codec_control(&codec, VP9E_SET_TILE_COLUMNS, get_msb(svc_ctx.threads));
|
||||||
|
if (svc_ctx.threads > 1)
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_ROW_MT, 1);
|
||||||
|
else
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_ROW_MT, 0);
|
||||||
|
}
|
||||||
if (svc_ctx.speed >= 5 && svc_ctx.aqmode == 1)
|
if (svc_ctx.speed >= 5 && svc_ctx.aqmode == 1)
|
||||||
vpx_codec_control(&codec, VP9E_SET_AQ_MODE, 3);
|
vpx_codec_control(&codec, VP9E_SET_AQ_MODE, 3);
|
||||||
if (svc_ctx.speed >= 5)
|
if (svc_ctx.speed >= 5)
|
||||||
vpx_codec_control(&codec, VP8E_SET_STATIC_THRESHOLD, 1);
|
vpx_codec_control(&codec, VP8E_SET_STATIC_THRESHOLD, 1);
|
||||||
|
vpx_codec_control(&codec, VP8E_SET_MAX_INTRA_BITRATE_PCT, 900);
|
||||||
|
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_SVC_INTER_LAYER_PRED, 0);
|
||||||
|
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_NOISE_SENSITIVITY, 0);
|
||||||
|
|
||||||
// Encode frames
|
// Encode frames
|
||||||
while (!end_of_stream) {
|
while (!end_of_stream) {
|
||||||
@ -731,7 +757,9 @@ int main(int argc, const char **argv) {
|
|||||||
// the encode for the whole superframe. The encoder will internally loop
|
// the encode for the whole superframe. The encoder will internally loop
|
||||||
// over all the spatial layers for the current superframe.
|
// over all the spatial layers for the current superframe.
|
||||||
vpx_codec_control(&codec, VP9E_SET_SVC_LAYER_ID, &layer_id);
|
vpx_codec_control(&codec, VP9E_SET_SVC_LAYER_ID, &layer_id);
|
||||||
set_frame_flags_bypass_mode(sl, layer_id.temporal_layer_id,
|
// TODO(jianj): Fix the parameter passing for "is_key_frame" in
|
||||||
|
// set_frame_flags_bypass_model() for case of periodic key frames.
|
||||||
|
set_frame_flags_bypass_mode(layer_id.temporal_layer_id,
|
||||||
svc_ctx.spatial_layers, frame_cnt == 0,
|
svc_ctx.spatial_layers, frame_cnt == 0,
|
||||||
&ref_frame_config);
|
&ref_frame_config);
|
||||||
vpx_codec_control(&codec, VP9E_SET_SVC_REF_FRAME_CONFIG,
|
vpx_codec_control(&codec, VP9E_SET_SVC_REF_FRAME_CONFIG,
|
||||||
@ -742,6 +770,17 @@ int main(int argc, const char **argv) {
|
|||||||
++rc.layer_input_frames[sl * enc_cfg.ts_number_layers +
|
++rc.layer_input_frames[sl * enc_cfg.ts_number_layers +
|
||||||
layer_id.temporal_layer_id];
|
layer_id.temporal_layer_id];
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
// For the fixed pattern SVC, temporal layer is given by superframe count.
|
||||||
|
unsigned int tl = 0;
|
||||||
|
if (enc_cfg.ts_number_layers == 2)
|
||||||
|
tl = (frame_cnt % 2 != 0);
|
||||||
|
else if (enc_cfg.ts_number_layers == 3) {
|
||||||
|
if (frame_cnt % 2 != 0) tl = 2;
|
||||||
|
if ((frame_cnt > 1) && ((frame_cnt - 2) % 4 == 0)) tl = 1;
|
||||||
|
}
|
||||||
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl)
|
||||||
|
++rc.layer_input_frames[sl * enc_cfg.ts_number_layers + tl];
|
||||||
}
|
}
|
||||||
|
|
||||||
vpx_usec_timer_start(&timer);
|
vpx_usec_timer_start(&timer);
|
||||||
@ -751,7 +790,6 @@ int main(int argc, const char **argv) {
|
|||||||
vpx_usec_timer_mark(&timer);
|
vpx_usec_timer_mark(&timer);
|
||||||
cx_time += vpx_usec_timer_elapsed(&timer);
|
cx_time += vpx_usec_timer_elapsed(&timer);
|
||||||
|
|
||||||
printf("%s", vpx_svc_get_message(&svc_ctx));
|
|
||||||
fflush(stdout);
|
fflush(stdout);
|
||||||
if (res != VPX_CODEC_OK) {
|
if (res != VPX_CODEC_OK) {
|
||||||
die_codec(&codec, "Failed to encode frame");
|
die_codec(&codec, "Failed to encode frame");
|
||||||
@ -763,37 +801,49 @@ int main(int argc, const char **argv) {
|
|||||||
SvcInternal_t *const si = (SvcInternal_t *)svc_ctx.internal;
|
SvcInternal_t *const si = (SvcInternal_t *)svc_ctx.internal;
|
||||||
if (cx_pkt->data.frame.sz > 0) {
|
if (cx_pkt->data.frame.sz > 0) {
|
||||||
#if OUTPUT_RC_STATS
|
#if OUTPUT_RC_STATS
|
||||||
uint32_t sizes[8];
|
uint64_t sizes[8];
|
||||||
|
uint64_t sizes_parsed[8];
|
||||||
int count = 0;
|
int count = 0;
|
||||||
|
vp9_zero(sizes);
|
||||||
|
vp9_zero(sizes_parsed);
|
||||||
#endif
|
#endif
|
||||||
vpx_video_writer_write_frame(writer, cx_pkt->data.frame.buf,
|
vpx_video_writer_write_frame(writer, cx_pkt->data.frame.buf,
|
||||||
cx_pkt->data.frame.sz,
|
cx_pkt->data.frame.sz,
|
||||||
cx_pkt->data.frame.pts);
|
cx_pkt->data.frame.pts);
|
||||||
#if OUTPUT_RC_STATS
|
#if OUTPUT_RC_STATS
|
||||||
// TODO(marpan/wonkap): Put this (to line728) in separate function.
|
// TODO(marpan): Put this (to line728) in separate function.
|
||||||
if (svc_ctx.output_rc_stat) {
|
if (svc_ctx.output_rc_stat) {
|
||||||
vpx_codec_control(&codec, VP9E_GET_SVC_LAYER_ID, &layer_id);
|
vpx_codec_control(&codec, VP9E_GET_SVC_LAYER_ID, &layer_id);
|
||||||
parse_superframe_index(cx_pkt->data.frame.buf,
|
parse_superframe_index(cx_pkt->data.frame.buf,
|
||||||
cx_pkt->data.frame.sz, sizes, &count);
|
cx_pkt->data.frame.sz, sizes_parsed,
|
||||||
// Note computing input_layer_frames here won't account for frame
|
&count);
|
||||||
// drops in rate control stats.
|
if (enc_cfg.ss_number_layers == 1)
|
||||||
// TODO(marpan): Fix this for non-bypass mode so we can get stats
|
sizes[0] = cx_pkt->data.frame.sz;
|
||||||
// for dropped frames.
|
|
||||||
if (svc_ctx.temporal_layering_mode !=
|
if (svc_ctx.temporal_layering_mode !=
|
||||||
VP9E_TEMPORAL_LAYERING_MODE_BYPASS) {
|
VP9E_TEMPORAL_LAYERING_MODE_BYPASS) {
|
||||||
|
int num_layers_encoded = 0;
|
||||||
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
++rc.layer_input_frames[sl * enc_cfg.ts_number_layers +
|
sizes[sl] = 0;
|
||||||
layer_id.temporal_layer_id];
|
if (cx_pkt->data.frame.spatial_layer_encoded[sl]) {
|
||||||
|
sizes[sl] = sizes_parsed[num_layers_encoded];
|
||||||
|
num_layers_encoded++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (tl = layer_id.temporal_layer_id;
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
tl < enc_cfg.ts_number_layers; ++tl) {
|
unsigned int sl2;
|
||||||
|
uint64_t tot_size = 0;
|
||||||
|
for (sl2 = 0; sl2 <= sl; ++sl2) {
|
||||||
|
if (cx_pkt->data.frame.spatial_layer_encoded[sl2])
|
||||||
|
tot_size += sizes[sl2];
|
||||||
|
}
|
||||||
|
if (tot_size > 0)
|
||||||
vpx_video_writer_write_frame(
|
vpx_video_writer_write_frame(
|
||||||
outfile[tl], cx_pkt->data.frame.buf, cx_pkt->data.frame.sz,
|
outfile[sl], cx_pkt->data.frame.buf, (size_t)(tot_size),
|
||||||
cx_pkt->data.frame.pts);
|
cx_pkt->data.frame.pts);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
|
if (cx_pkt->data.frame.spatial_layer_encoded[sl]) {
|
||||||
for (tl = layer_id.temporal_layer_id;
|
for (tl = layer_id.temporal_layer_id;
|
||||||
tl < enc_cfg.ts_number_layers; ++tl) {
|
tl < enc_cfg.ts_number_layers; ++tl) {
|
||||||
const int layer = sl * enc_cfg.ts_number_layers + tl;
|
const int layer = sl * enc_cfg.ts_number_layers + tl;
|
||||||
@ -811,13 +861,14 @@ int main(int argc, const char **argv) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Update for short-time encoding bitrate states, for moving
|
// Update for short-time encoding bitrate states, for moving
|
||||||
// window of size rc->window, shifted by rc->window / 2.
|
// window of size rc->window, shifted by rc->window / 2.
|
||||||
// Ignore first window segment, due to key frame.
|
// Ignore first window segment, due to key frame.
|
||||||
if (frame_cnt > (unsigned int)rc.window_size) {
|
if (frame_cnt > (unsigned int)rc.window_size) {
|
||||||
tl = layer_id.temporal_layer_id;
|
|
||||||
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
|
if (cx_pkt->data.frame.spatial_layer_encoded[sl])
|
||||||
sum_bitrate += 0.001 * 8.0 * sizes[sl] * framerate;
|
sum_bitrate += 0.001 * 8.0 * sizes[sl] * framerate;
|
||||||
}
|
}
|
||||||
if (frame_cnt % rc.window_size == 0) {
|
if (frame_cnt % rc.window_size == 0) {
|
||||||
@ -833,7 +884,6 @@ int main(int argc, const char **argv) {
|
|||||||
// Second shifted window.
|
// Second shifted window.
|
||||||
if (frame_cnt >
|
if (frame_cnt >
|
||||||
(unsigned int)(rc.window_size + rc.window_size / 2)) {
|
(unsigned int)(rc.window_size + rc.window_size / 2)) {
|
||||||
tl = layer_id.temporal_layer_id;
|
|
||||||
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
sum_bitrate2 += 0.001 * 8.0 * sizes[sl] * framerate;
|
sum_bitrate2 += 0.001 * 8.0 * sizes[sl] * framerate;
|
||||||
}
|
}
|
||||||
@ -900,8 +950,8 @@ int main(int argc, const char **argv) {
|
|||||||
}
|
}
|
||||||
#if OUTPUT_RC_STATS
|
#if OUTPUT_RC_STATS
|
||||||
if (svc_ctx.output_rc_stat) {
|
if (svc_ctx.output_rc_stat) {
|
||||||
for (tl = 0; tl < enc_cfg.ts_number_layers; ++tl) {
|
for (sl = 0; sl < enc_cfg.ss_number_layers; ++sl) {
|
||||||
vpx_video_writer_close(outfile[tl]);
|
vpx_video_writer_close(outfile[sl]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@ -910,7 +960,7 @@ int main(int argc, const char **argv) {
|
|||||||
1000000 * (double)frame_cnt / (double)cx_time);
|
1000000 * (double)frame_cnt / (double)cx_time);
|
||||||
vpx_img_free(&raw);
|
vpx_img_free(&raw);
|
||||||
// display average size, psnr
|
// display average size, psnr
|
||||||
printf("%s", vpx_svc_dump_statistics(&svc_ctx));
|
vpx_svc_dump_statistics(&svc_ctx);
|
||||||
vpx_svc_release(&svc_ctx);
|
vpx_svc_release(&svc_ctx);
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
@ -22,21 +22,34 @@
|
|||||||
#include "../vpx_ports/vpx_timer.h"
|
#include "../vpx_ports/vpx_timer.h"
|
||||||
#include "vpx/vp8cx.h"
|
#include "vpx/vp8cx.h"
|
||||||
#include "vpx/vpx_encoder.h"
|
#include "vpx/vpx_encoder.h"
|
||||||
|
#include "vpx_ports/bitops.h"
|
||||||
|
|
||||||
#include "../tools_common.h"
|
#include "../tools_common.h"
|
||||||
#include "../video_writer.h"
|
#include "../video_writer.h"
|
||||||
|
|
||||||
|
#define ROI_MAP 0
|
||||||
|
|
||||||
|
#define zero(Dest) memset(&Dest, 0, sizeof(Dest));
|
||||||
|
|
||||||
static const char *exec_name;
|
static const char *exec_name;
|
||||||
|
|
||||||
void usage_exit(void) { exit(EXIT_FAILURE); }
|
void usage_exit(void) { exit(EXIT_FAILURE); }
|
||||||
|
|
||||||
// Denoiser states, for temporal denoising.
|
// Denoiser states for vp8, for temporal denoising.
|
||||||
enum denoiserState {
|
enum denoiserStateVp8 {
|
||||||
kDenoiserOff,
|
kVp8DenoiserOff,
|
||||||
kDenoiserOnYOnly,
|
kVp8DenoiserOnYOnly,
|
||||||
kDenoiserOnYUV,
|
kVp8DenoiserOnYUV,
|
||||||
kDenoiserOnYUVAggressive,
|
kVp8DenoiserOnYUVAggressive,
|
||||||
kDenoiserOnAdaptive
|
kVp8DenoiserOnAdaptive
|
||||||
|
};
|
||||||
|
|
||||||
|
// Denoiser states for vp9, for temporal denoising.
|
||||||
|
enum denoiserStateVp9 {
|
||||||
|
kVp9DenoiserOff,
|
||||||
|
kVp9DenoiserOnYOnly,
|
||||||
|
// For SVC: denoise the top two spatial layers.
|
||||||
|
kVp9DenoiserOnYTwoSpatialLayers
|
||||||
};
|
};
|
||||||
|
|
||||||
static int mode_to_num_layers[13] = { 1, 2, 2, 3, 3, 3, 3, 5, 2, 3, 3, 3, 3 };
|
static int mode_to_num_layers[13] = { 1, 2, 2, 3, 3, 3, 3, 5, 2, 3, 3, 3, 3 };
|
||||||
@ -89,8 +102,9 @@ static void set_rate_control_metrics(struct RateControlMetrics *rc,
|
|||||||
for (i = 0; i < cfg->ts_number_layers; ++i) {
|
for (i = 0; i < cfg->ts_number_layers; ++i) {
|
||||||
if (i > 0) {
|
if (i > 0) {
|
||||||
rc->layer_framerate[i] = framerate / cfg->ts_rate_decimator[i];
|
rc->layer_framerate[i] = framerate / cfg->ts_rate_decimator[i];
|
||||||
rc->layer_pfb[i] = 1000.0 * (rc->layer_target_bitrate[i] -
|
rc->layer_pfb[i] =
|
||||||
rc->layer_target_bitrate[i - 1]) /
|
1000.0 *
|
||||||
|
(rc->layer_target_bitrate[i] - rc->layer_target_bitrate[i - 1]) /
|
||||||
(rc->layer_framerate[i] - rc->layer_framerate[i - 1]);
|
(rc->layer_framerate[i] - rc->layer_framerate[i - 1]);
|
||||||
}
|
}
|
||||||
rc->layer_input_frames[i] = 0;
|
rc->layer_input_frames[i] = 0;
|
||||||
@ -154,6 +168,75 @@ static void printout_rate_control_summary(struct RateControlMetrics *rc,
|
|||||||
die("Error: Number of input frames not equal to output! \n");
|
die("Error: Number of input frames not equal to output! \n");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if ROI_MAP
|
||||||
|
static void set_roi_map(const char *enc_name, vpx_codec_enc_cfg_t *cfg,
|
||||||
|
vpx_roi_map_t *roi) {
|
||||||
|
unsigned int i, j;
|
||||||
|
int block_size = 0;
|
||||||
|
uint8_t is_vp8 = strncmp(enc_name, "vp8", 3) == 0 ? 1 : 0;
|
||||||
|
uint8_t is_vp9 = strncmp(enc_name, "vp9", 3) == 0 ? 1 : 0;
|
||||||
|
if (!is_vp8 && !is_vp9) {
|
||||||
|
die("unsupported codec.");
|
||||||
|
}
|
||||||
|
zero(*roi);
|
||||||
|
|
||||||
|
block_size = is_vp9 && !is_vp8 ? 8 : 16;
|
||||||
|
|
||||||
|
// ROI is based on the segments (4 for vp8, 8 for vp9), smallest unit for
|
||||||
|
// segment is 16x16 for vp8, 8x8 for vp9.
|
||||||
|
roi->rows = (cfg->g_h + block_size - 1) / block_size;
|
||||||
|
roi->cols = (cfg->g_w + block_size - 1) / block_size;
|
||||||
|
|
||||||
|
// Applies delta QP on the segment blocks, varies from -63 to 63.
|
||||||
|
// Setting to negative means lower QP (better quality).
|
||||||
|
// Below we set delta_q to the extreme (-63) to show strong effect.
|
||||||
|
// VP8 uses the first 4 segments. VP9 uses all 8 segments.
|
||||||
|
zero(roi->delta_q);
|
||||||
|
roi->delta_q[1] = -63;
|
||||||
|
|
||||||
|
// Applies delta loopfilter strength on the segment blocks, varies from -63 to
|
||||||
|
// 63. Setting to positive means stronger loopfilter. VP8 uses the first 4
|
||||||
|
// segments. VP9 uses all 8 segments.
|
||||||
|
zero(roi->delta_lf);
|
||||||
|
|
||||||
|
if (is_vp8) {
|
||||||
|
// Applies skip encoding threshold on the segment blocks, varies from 0 to
|
||||||
|
// UINT_MAX. Larger value means more skipping of encoding is possible.
|
||||||
|
// This skip threshold only applies on delta frames.
|
||||||
|
zero(roi->static_threshold);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (is_vp9) {
|
||||||
|
// Apply skip segment. Setting to 1 means this block will be copied from
|
||||||
|
// previous frame.
|
||||||
|
zero(roi->skip);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (is_vp9) {
|
||||||
|
// Apply ref frame segment.
|
||||||
|
// -1 : Do not apply this segment.
|
||||||
|
// 0 : Froce using intra.
|
||||||
|
// 1 : Force using last.
|
||||||
|
// 2 : Force using golden.
|
||||||
|
// 3 : Force using alfref but not used in non-rd pickmode for 0 lag.
|
||||||
|
memset(roi->ref_frame, -1, sizeof(roi->ref_frame));
|
||||||
|
roi->ref_frame[1] = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Use 2 states: 1 is center square, 0 is the rest.
|
||||||
|
roi->roi_map =
|
||||||
|
(uint8_t *)calloc(roi->rows * roi->cols, sizeof(*roi->roi_map));
|
||||||
|
for (i = 0; i < roi->rows; ++i) {
|
||||||
|
for (j = 0; j < roi->cols; ++j) {
|
||||||
|
if (i > (roi->rows >> 2) && i < ((roi->rows * 3) >> 2) &&
|
||||||
|
j > (roi->cols >> 2) && j < ((roi->cols * 3) >> 2)) {
|
||||||
|
roi->roi_map[i * roi->cols + j] = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
// Temporal scaling parameters:
|
// Temporal scaling parameters:
|
||||||
// NOTE: The 3 prediction frames cannot be used interchangeably due to
|
// NOTE: The 3 prediction frames cannot be used interchangeably due to
|
||||||
// differences in the way they are handled throughout the code. The
|
// differences in the way they are handled throughout the code. The
|
||||||
@ -495,6 +578,7 @@ int main(int argc, char **argv) {
|
|||||||
vpx_codec_err_t res;
|
vpx_codec_err_t res;
|
||||||
unsigned int width;
|
unsigned int width;
|
||||||
unsigned int height;
|
unsigned int height;
|
||||||
|
uint32_t error_resilient = 0;
|
||||||
int speed;
|
int speed;
|
||||||
int frame_avail;
|
int frame_avail;
|
||||||
int got_data;
|
int got_data;
|
||||||
@ -505,16 +589,15 @@ int main(int argc, char **argv) {
|
|||||||
int layering_mode = 0;
|
int layering_mode = 0;
|
||||||
int layer_flags[VPX_TS_MAX_PERIODICITY] = { 0 };
|
int layer_flags[VPX_TS_MAX_PERIODICITY] = { 0 };
|
||||||
int flag_periodicity = 1;
|
int flag_periodicity = 1;
|
||||||
#if VPX_ENCODER_ABI_VERSION > (4 + VPX_CODEC_ABI_VERSION)
|
#if ROI_MAP
|
||||||
vpx_svc_layer_id_t layer_id = { 0, 0 };
|
vpx_roi_map_t roi;
|
||||||
#else
|
|
||||||
vpx_svc_layer_id_t layer_id = { 0 };
|
|
||||||
#endif
|
#endif
|
||||||
|
vpx_svc_layer_id_t layer_id = { 0, 0 };
|
||||||
const VpxInterface *encoder = NULL;
|
const VpxInterface *encoder = NULL;
|
||||||
FILE *infile = NULL;
|
FILE *infile = NULL;
|
||||||
struct RateControlMetrics rc;
|
struct RateControlMetrics rc;
|
||||||
int64_t cx_time = 0;
|
int64_t cx_time = 0;
|
||||||
const int min_args_base = 12;
|
const int min_args_base = 13;
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
vpx_bit_depth_t bit_depth = VPX_BITS_8;
|
vpx_bit_depth_t bit_depth = VPX_BITS_8;
|
||||||
int input_bit_depth = 8;
|
int input_bit_depth = 8;
|
||||||
@ -526,17 +609,21 @@ int main(int argc, char **argv) {
|
|||||||
double sum_bitrate2 = 0.0;
|
double sum_bitrate2 = 0.0;
|
||||||
double framerate = 30.0;
|
double framerate = 30.0;
|
||||||
|
|
||||||
|
zero(rc.layer_target_bitrate);
|
||||||
|
|
||||||
exec_name = argv[0];
|
exec_name = argv[0];
|
||||||
// Check usage and arguments.
|
// Check usage and arguments.
|
||||||
if (argc < min_args) {
|
if (argc < min_args) {
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
die("Usage: %s <infile> <outfile> <codec_type(vp8/vp9)> <width> <height> "
|
die("Usage: %s <infile> <outfile> <codec_type(vp8/vp9)> <width> <height> "
|
||||||
"<rate_num> <rate_den> <speed> <frame_drop_threshold> <threads> <mode> "
|
"<rate_num> <rate_den> <speed> <frame_drop_threshold> "
|
||||||
|
"<error_resilient> <threads> <mode> "
|
||||||
"<Rate_0> ... <Rate_nlayers-1> <bit-depth> \n",
|
"<Rate_0> ... <Rate_nlayers-1> <bit-depth> \n",
|
||||||
argv[0]);
|
argv[0]);
|
||||||
#else
|
#else
|
||||||
die("Usage: %s <infile> <outfile> <codec_type(vp8/vp9)> <width> <height> "
|
die("Usage: %s <infile> <outfile> <codec_type(vp8/vp9)> <width> <height> "
|
||||||
"<rate_num> <rate_den> <speed> <frame_drop_threshold> <threads> <mode> "
|
"<rate_num> <rate_den> <speed> <frame_drop_threshold> "
|
||||||
|
"<error_resilient> <threads> <mode> "
|
||||||
"<Rate_0> ... <Rate_nlayers-1> \n",
|
"<Rate_0> ... <Rate_nlayers-1> \n",
|
||||||
argv[0]);
|
argv[0]);
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
@ -553,9 +640,9 @@ int main(int argc, char **argv) {
|
|||||||
die("Invalid resolution: %d x %d", width, height);
|
die("Invalid resolution: %d x %d", width, height);
|
||||||
}
|
}
|
||||||
|
|
||||||
layering_mode = (int)strtol(argv[11], NULL, 0);
|
layering_mode = (int)strtol(argv[12], NULL, 0);
|
||||||
if (layering_mode < 0 || layering_mode > 13) {
|
if (layering_mode < 0 || layering_mode > 13) {
|
||||||
die("Invalid layering mode (0..12) %s", argv[11]);
|
die("Invalid layering mode (0..12) %s", argv[12]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (argc != min_args + mode_to_num_layers[layering_mode]) {
|
if (argc != min_args + mode_to_num_layers[layering_mode]) {
|
||||||
@ -619,11 +706,11 @@ int main(int argc, char **argv) {
|
|||||||
|
|
||||||
for (i = min_args_base;
|
for (i = min_args_base;
|
||||||
(int)i < min_args_base + mode_to_num_layers[layering_mode]; ++i) {
|
(int)i < min_args_base + mode_to_num_layers[layering_mode]; ++i) {
|
||||||
rc.layer_target_bitrate[i - 12] = (int)strtol(argv[i], NULL, 0);
|
rc.layer_target_bitrate[i - 13] = (int)strtol(argv[i], NULL, 0);
|
||||||
if (strncmp(encoder->name, "vp8", 3) == 0)
|
if (strncmp(encoder->name, "vp8", 3) == 0)
|
||||||
cfg.ts_target_bitrate[i - 12] = rc.layer_target_bitrate[i - 12];
|
cfg.ts_target_bitrate[i - 13] = rc.layer_target_bitrate[i - 13];
|
||||||
else if (strncmp(encoder->name, "vp9", 3) == 0)
|
else if (strncmp(encoder->name, "vp9", 3) == 0)
|
||||||
cfg.layer_target_bitrate[i - 12] = rc.layer_target_bitrate[i - 12];
|
cfg.layer_target_bitrate[i - 13] = rc.layer_target_bitrate[i - 13];
|
||||||
}
|
}
|
||||||
|
|
||||||
// Real time parameters.
|
// Real time parameters.
|
||||||
@ -634,7 +721,7 @@ int main(int argc, char **argv) {
|
|||||||
if (strncmp(encoder->name, "vp9", 3) == 0) cfg.rc_max_quantizer = 52;
|
if (strncmp(encoder->name, "vp9", 3) == 0) cfg.rc_max_quantizer = 52;
|
||||||
cfg.rc_undershoot_pct = 50;
|
cfg.rc_undershoot_pct = 50;
|
||||||
cfg.rc_overshoot_pct = 50;
|
cfg.rc_overshoot_pct = 50;
|
||||||
cfg.rc_buf_initial_sz = 500;
|
cfg.rc_buf_initial_sz = 600;
|
||||||
cfg.rc_buf_optimal_sz = 600;
|
cfg.rc_buf_optimal_sz = 600;
|
||||||
cfg.rc_buf_sz = 1000;
|
cfg.rc_buf_sz = 1000;
|
||||||
|
|
||||||
@ -642,10 +729,14 @@ int main(int argc, char **argv) {
|
|||||||
cfg.rc_resize_allowed = 0;
|
cfg.rc_resize_allowed = 0;
|
||||||
|
|
||||||
// Use 1 thread as default.
|
// Use 1 thread as default.
|
||||||
cfg.g_threads = (unsigned int)strtoul(argv[10], NULL, 0);
|
cfg.g_threads = (unsigned int)strtoul(argv[11], NULL, 0);
|
||||||
|
|
||||||
|
error_resilient = (uint32_t)strtoul(argv[10], NULL, 0);
|
||||||
|
if (error_resilient != 0 && error_resilient != 1) {
|
||||||
|
die("Invalid value for error resilient (0, 1): %d.", error_resilient);
|
||||||
|
}
|
||||||
// Enable error resilient mode.
|
// Enable error resilient mode.
|
||||||
cfg.g_error_resilient = 1;
|
cfg.g_error_resilient = error_resilient;
|
||||||
cfg.g_lag_in_frames = 0;
|
cfg.g_lag_in_frames = 0;
|
||||||
cfg.kf_mode = VPX_KF_AUTO;
|
cfg.kf_mode = VPX_KF_AUTO;
|
||||||
|
|
||||||
@ -700,18 +791,39 @@ int main(int argc, char **argv) {
|
|||||||
|
|
||||||
if (strncmp(encoder->name, "vp8", 3) == 0) {
|
if (strncmp(encoder->name, "vp8", 3) == 0) {
|
||||||
vpx_codec_control(&codec, VP8E_SET_CPUUSED, -speed);
|
vpx_codec_control(&codec, VP8E_SET_CPUUSED, -speed);
|
||||||
vpx_codec_control(&codec, VP8E_SET_NOISE_SENSITIVITY, kDenoiserOff);
|
vpx_codec_control(&codec, VP8E_SET_NOISE_SENSITIVITY, kVp8DenoiserOff);
|
||||||
vpx_codec_control(&codec, VP8E_SET_STATIC_THRESHOLD, 1);
|
vpx_codec_control(&codec, VP8E_SET_STATIC_THRESHOLD, 1);
|
||||||
|
vpx_codec_control(&codec, VP8E_SET_GF_CBR_BOOST_PCT, 0);
|
||||||
|
#if ROI_MAP
|
||||||
|
set_roi_map(encoder->name, &cfg, &roi);
|
||||||
|
if (vpx_codec_control(&codec, VP8E_SET_ROI_MAP, &roi))
|
||||||
|
die_codec(&codec, "Failed to set ROI map");
|
||||||
|
#endif
|
||||||
|
|
||||||
} else if (strncmp(encoder->name, "vp9", 3) == 0) {
|
} else if (strncmp(encoder->name, "vp9", 3) == 0) {
|
||||||
vpx_svc_extra_cfg_t svc_params;
|
vpx_svc_extra_cfg_t svc_params;
|
||||||
memset(&svc_params, 0, sizeof(svc_params));
|
memset(&svc_params, 0, sizeof(svc_params));
|
||||||
vpx_codec_control(&codec, VP8E_SET_CPUUSED, speed);
|
vpx_codec_control(&codec, VP8E_SET_CPUUSED, speed);
|
||||||
vpx_codec_control(&codec, VP9E_SET_AQ_MODE, 3);
|
vpx_codec_control(&codec, VP9E_SET_AQ_MODE, 3);
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_GF_CBR_BOOST_PCT, 0);
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_FRAME_PARALLEL_DECODING, 0);
|
||||||
vpx_codec_control(&codec, VP9E_SET_FRAME_PERIODIC_BOOST, 0);
|
vpx_codec_control(&codec, VP9E_SET_FRAME_PERIODIC_BOOST, 0);
|
||||||
vpx_codec_control(&codec, VP9E_SET_NOISE_SENSITIVITY, kDenoiserOff);
|
vpx_codec_control(&codec, VP9E_SET_NOISE_SENSITIVITY, kVp9DenoiserOff);
|
||||||
vpx_codec_control(&codec, VP8E_SET_STATIC_THRESHOLD, 1);
|
vpx_codec_control(&codec, VP8E_SET_STATIC_THRESHOLD, 1);
|
||||||
vpx_codec_control(&codec, VP9E_SET_TUNE_CONTENT, 0);
|
vpx_codec_control(&codec, VP9E_SET_TUNE_CONTENT, 0);
|
||||||
vpx_codec_control(&codec, VP9E_SET_TILE_COLUMNS, (cfg.g_threads >> 1));
|
vpx_codec_control(&codec, VP9E_SET_TILE_COLUMNS, get_msb(cfg.g_threads));
|
||||||
|
#if ROI_MAP
|
||||||
|
set_roi_map(encoder->name, &cfg, &roi);
|
||||||
|
if (vpx_codec_control(&codec, VP9E_SET_ROI_MAP, &roi))
|
||||||
|
die_codec(&codec, "Failed to set ROI map");
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_AQ_MODE, 0);
|
||||||
|
#endif
|
||||||
|
// TODO(marpan/jianj): There is an issue with row-mt for low resolutons at
|
||||||
|
// high speed settings, disable its use for those cases for now.
|
||||||
|
if (cfg.g_threads > 1 && ((cfg.g_w > 320 && cfg.g_h > 240) || speed < 7))
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_ROW_MT, 1);
|
||||||
|
else
|
||||||
|
vpx_codec_control(&codec, VP9E_SET_ROW_MT, 0);
|
||||||
if (vpx_codec_control(&codec, VP9E_SET_SVC, layering_mode > 0 ? 1 : 0))
|
if (vpx_codec_control(&codec, VP9E_SET_SVC, layering_mode > 0 ? 1 : 0))
|
||||||
die_codec(&codec, "Failed to set SVC");
|
die_codec(&codec, "Failed to set SVC");
|
||||||
for (i = 0; i < cfg.ts_number_layers; ++i) {
|
for (i = 0; i < cfg.ts_number_layers; ++i) {
|
||||||
@ -730,7 +842,7 @@ int main(int argc, char **argv) {
|
|||||||
// For generating smaller key frames, use a smaller max_intra_size_pct
|
// For generating smaller key frames, use a smaller max_intra_size_pct
|
||||||
// value, like 100 or 200.
|
// value, like 100 or 200.
|
||||||
{
|
{
|
||||||
const int max_intra_size_pct = 900;
|
const int max_intra_size_pct = 1000;
|
||||||
vpx_codec_control(&codec, VP8E_SET_MAX_INTRA_BITRATE_PCT,
|
vpx_codec_control(&codec, VP8E_SET_MAX_INTRA_BITRATE_PCT,
|
||||||
max_intra_size_pct);
|
max_intra_size_pct);
|
||||||
}
|
}
|
||||||
@ -740,10 +852,8 @@ int main(int argc, char **argv) {
|
|||||||
struct vpx_usec_timer timer;
|
struct vpx_usec_timer timer;
|
||||||
vpx_codec_iter_t iter = NULL;
|
vpx_codec_iter_t iter = NULL;
|
||||||
const vpx_codec_cx_pkt_t *pkt;
|
const vpx_codec_cx_pkt_t *pkt;
|
||||||
#if VPX_ENCODER_ABI_VERSION > (4 + VPX_CODEC_ABI_VERSION)
|
|
||||||
// Update the temporal layer_id. No spatial layers in this test.
|
// Update the temporal layer_id. No spatial layers in this test.
|
||||||
layer_id.spatial_layer_id = 0;
|
layer_id.spatial_layer_id = 0;
|
||||||
#endif
|
|
||||||
layer_id.temporal_layer_id =
|
layer_id.temporal_layer_id =
|
||||||
cfg.ts_layer_id[frame_cnt % cfg.ts_periodicity];
|
cfg.ts_layer_id[frame_cnt % cfg.ts_periodicity];
|
||||||
if (strncmp(encoder->name, "vp9", 3) == 0) {
|
if (strncmp(encoder->name, "vp9", 3) == 0) {
|
||||||
@ -835,5 +945,8 @@ int main(int argc, char **argv) {
|
|||||||
for (i = 0; i < cfg.ts_number_layers; ++i) vpx_video_writer_close(outfile[i]);
|
for (i = 0; i < cfg.ts_number_layers; ++i) vpx_video_writer_close(outfile[i]);
|
||||||
|
|
||||||
vpx_img_free(&raw);
|
vpx_img_free(&raw);
|
||||||
|
#if ROI_MAP
|
||||||
|
free(roi.roi_map);
|
||||||
|
#endif
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
@ -943,18 +943,6 @@ GENERATE_XML = NO
|
|||||||
|
|
||||||
XML_OUTPUT = xml
|
XML_OUTPUT = xml
|
||||||
|
|
||||||
# The XML_SCHEMA tag can be used to specify an XML schema,
|
|
||||||
# which can be used by a validating XML parser to check the
|
|
||||||
# syntax of the XML files.
|
|
||||||
|
|
||||||
XML_SCHEMA =
|
|
||||||
|
|
||||||
# The XML_DTD tag can be used to specify an XML DTD,
|
|
||||||
# which can be used by a validating XML parser to check the
|
|
||||||
# syntax of the XML files.
|
|
||||||
|
|
||||||
XML_DTD =
|
|
||||||
|
|
||||||
# If the XML_PROGRAMLISTING tag is set to YES Doxygen will
|
# If the XML_PROGRAMLISTING tag is set to YES Doxygen will
|
||||||
# dump the program listings (including syntax highlighting
|
# dump the program listings (including syntax highlighting
|
||||||
# and cross-referencing information) to the XML output. Note that
|
# and cross-referencing information) to the XML output. Note that
|
||||||
|
49
libs.mk
49
libs.mk
@ -88,7 +88,7 @@ ifeq ($(CONFIG_VP9_ENCODER),yes)
|
|||||||
CODEC_EXPORTS-yes += $(addprefix $(VP9_PREFIX),$(VP9_CX_EXPORTS))
|
CODEC_EXPORTS-yes += $(addprefix $(VP9_PREFIX),$(VP9_CX_EXPORTS))
|
||||||
CODEC_SRCS-yes += $(VP9_PREFIX)vp9cx.mk vpx/vp8.h vpx/vp8cx.h
|
CODEC_SRCS-yes += $(VP9_PREFIX)vp9cx.mk vpx/vp8.h vpx/vp8cx.h
|
||||||
INSTALL-LIBS-yes += include/vpx/vp8.h include/vpx/vp8cx.h
|
INSTALL-LIBS-yes += include/vpx/vp8.h include/vpx/vp8cx.h
|
||||||
INSTALL-LIBS-$(CONFIG_SPATIAL_SVC) += include/vpx/svc_context.h
|
INSTALL-LIBS-yes += include/vpx/svc_context.h
|
||||||
INSTALL_MAPS += include/vpx/% $(SRC_PATH_BARE)/$(VP9_PREFIX)/%
|
INSTALL_MAPS += include/vpx/% $(SRC_PATH_BARE)/$(VP9_PREFIX)/%
|
||||||
CODEC_DOC_SRCS += vpx/vp8.h vpx/vp8cx.h
|
CODEC_DOC_SRCS += vpx/vp8.h vpx/vp8cx.h
|
||||||
CODEC_DOC_SECTIONS += vp9 vp9_encoder
|
CODEC_DOC_SECTIONS += vp9 vp9_encoder
|
||||||
@ -149,12 +149,11 @@ CODEC_SRCS-yes += $(BUILD_PFX)vpx_config.c
|
|||||||
INSTALL-SRCS-no += $(BUILD_PFX)vpx_config.c
|
INSTALL-SRCS-no += $(BUILD_PFX)vpx_config.c
|
||||||
ifeq ($(ARCH_X86)$(ARCH_X86_64),yes)
|
ifeq ($(ARCH_X86)$(ARCH_X86_64),yes)
|
||||||
INSTALL-SRCS-$(CONFIG_CODEC_SRCS) += third_party/x86inc/x86inc.asm
|
INSTALL-SRCS-$(CONFIG_CODEC_SRCS) += third_party/x86inc/x86inc.asm
|
||||||
|
INSTALL-SRCS-$(CONFIG_CODEC_SRCS) += vpx_dsp/x86/bitdepth_conversion_sse2.asm
|
||||||
endif
|
endif
|
||||||
CODEC_EXPORTS-yes += vpx/exports_com
|
CODEC_EXPORTS-yes += vpx/exports_com
|
||||||
CODEC_EXPORTS-$(CONFIG_ENCODERS) += vpx/exports_enc
|
CODEC_EXPORTS-$(CONFIG_ENCODERS) += vpx/exports_enc
|
||||||
ifeq ($(CONFIG_SPATIAL_SVC),yes)
|
CODEC_EXPORTS-$(CONFIG_VP9_ENCODER) += vpx/exports_spatial_svc
|
||||||
CODEC_EXPORTS-$(CONFIG_ENCODERS) += vpx/exports_spatial_svc
|
|
||||||
endif
|
|
||||||
CODEC_EXPORTS-$(CONFIG_DECODERS) += vpx/exports_dec
|
CODEC_EXPORTS-$(CONFIG_DECODERS) += vpx/exports_dec
|
||||||
|
|
||||||
INSTALL-LIBS-yes += include/vpx/vpx_codec.h
|
INSTALL-LIBS-yes += include/vpx/vpx_codec.h
|
||||||
@ -187,6 +186,13 @@ libvpx_srcs.txt:
|
|||||||
@echo $(CODEC_SRCS) | xargs -n1 echo | LC_ALL=C sort -u > $@
|
@echo $(CODEC_SRCS) | xargs -n1 echo | LC_ALL=C sort -u > $@
|
||||||
CLEAN-OBJS += libvpx_srcs.txt
|
CLEAN-OBJS += libvpx_srcs.txt
|
||||||
|
|
||||||
|
# Assembly files that are included, but don't define symbols themselves.
|
||||||
|
# Filtered out to avoid Windows build warnings.
|
||||||
|
ASM_INCLUDES := \
|
||||||
|
third_party/x86inc/x86inc.asm \
|
||||||
|
vpx_config.asm \
|
||||||
|
vpx_ports/x86_abi_support.asm \
|
||||||
|
vpx_dsp/x86/bitdepth_conversion_sse2.asm \
|
||||||
|
|
||||||
ifeq ($(CONFIG_EXTERNAL_BUILD),yes)
|
ifeq ($(CONFIG_EXTERNAL_BUILD),yes)
|
||||||
ifeq ($(CONFIG_MSVS),yes)
|
ifeq ($(CONFIG_MSVS),yes)
|
||||||
@ -198,12 +204,7 @@ vpx.def: $(call enabled,CODEC_EXPORTS)
|
|||||||
--out=$@ $^
|
--out=$@ $^
|
||||||
CLEAN-OBJS += vpx.def
|
CLEAN-OBJS += vpx.def
|
||||||
|
|
||||||
# Assembly files that are included, but don't define symbols themselves.
|
vpx.$(VCPROJ_SFX): VCPROJ_SRCS=$(filter-out $(addprefix %, $(ASM_INCLUDES)), $^)
|
||||||
# Filtered out to avoid Visual Studio build warnings.
|
|
||||||
ASM_INCLUDES := \
|
|
||||||
third_party/x86inc/x86inc.asm \
|
|
||||||
vpx_config.asm \
|
|
||||||
vpx_ports/x86_abi_support.asm \
|
|
||||||
|
|
||||||
vpx.$(VCPROJ_SFX): $(CODEC_SRCS) vpx.def
|
vpx.$(VCPROJ_SFX): $(CODEC_SRCS) vpx.def
|
||||||
@echo " [CREATE] $@"
|
@echo " [CREATE] $@"
|
||||||
@ -217,7 +218,15 @@ vpx.$(VCPROJ_SFX): $(CODEC_SRCS) vpx.def
|
|||||||
--ver=$(CONFIG_VS_VERSION) \
|
--ver=$(CONFIG_VS_VERSION) \
|
||||||
--src-path-bare="$(SRC_PATH_BARE)" \
|
--src-path-bare="$(SRC_PATH_BARE)" \
|
||||||
--out=$@ $(CFLAGS) \
|
--out=$@ $(CFLAGS) \
|
||||||
$(filter-out $(addprefix %, $(ASM_INCLUDES)), $^) \
|
$(filter $(SRC_PATH_BARE)/vp8/%.c, $(VCPROJ_SRCS)) \
|
||||||
|
$(filter $(SRC_PATH_BARE)/vp8/%.h, $(VCPROJ_SRCS)) \
|
||||||
|
$(filter $(SRC_PATH_BARE)/vp9/%.c, $(VCPROJ_SRCS)) \
|
||||||
|
$(filter $(SRC_PATH_BARE)/vp9/%.h, $(VCPROJ_SRCS)) \
|
||||||
|
$(filter $(SRC_PATH_BARE)/vpx/%, $(VCPROJ_SRCS)) \
|
||||||
|
$(filter $(SRC_PATH_BARE)/vpx_dsp/%, $(VCPROJ_SRCS)) \
|
||||||
|
$(filter-out $(addprefix $(SRC_PATH_BARE)/, \
|
||||||
|
vp8/%.c vp8/%.h vp9/%.c vp9/%.h vpx/% vpx_dsp/%), \
|
||||||
|
$(VCPROJ_SRCS)) \
|
||||||
--src-path-bare="$(SRC_PATH_BARE)" \
|
--src-path-bare="$(SRC_PATH_BARE)" \
|
||||||
|
|
||||||
PROJECTS-yes += vpx.$(VCPROJ_SFX)
|
PROJECTS-yes += vpx.$(VCPROJ_SFX)
|
||||||
@ -227,12 +236,12 @@ vpx.$(VCPROJ_SFX): $(RTCD)
|
|||||||
|
|
||||||
endif
|
endif
|
||||||
else
|
else
|
||||||
LIBVPX_OBJS=$(call objs,$(CODEC_SRCS))
|
LIBVPX_OBJS=$(call objs, $(filter-out $(ASM_INCLUDES), $(CODEC_SRCS)))
|
||||||
OBJS-yes += $(LIBVPX_OBJS)
|
OBJS-yes += $(LIBVPX_OBJS)
|
||||||
LIBS-$(if yes,$(CONFIG_STATIC)) += $(BUILD_PFX)libvpx.a $(BUILD_PFX)libvpx_g.a
|
LIBS-$(if yes,$(CONFIG_STATIC)) += $(BUILD_PFX)libvpx.a $(BUILD_PFX)libvpx_g.a
|
||||||
$(BUILD_PFX)libvpx_g.a: $(LIBVPX_OBJS)
|
$(BUILD_PFX)libvpx_g.a: $(LIBVPX_OBJS)
|
||||||
|
|
||||||
SO_VERSION_MAJOR := 4
|
SO_VERSION_MAJOR := 5
|
||||||
SO_VERSION_MINOR := 0
|
SO_VERSION_MINOR := 0
|
||||||
SO_VERSION_PATCH := 0
|
SO_VERSION_PATCH := 0
|
||||||
ifeq ($(filter darwin%,$(TGT_OS)),$(TGT_OS))
|
ifeq ($(filter darwin%,$(TGT_OS)),$(TGT_OS))
|
||||||
@ -391,7 +400,7 @@ LIBVPX_TEST_SRCS=$(addprefix test/,$(call enabled,LIBVPX_TEST_SRCS))
|
|||||||
LIBVPX_TEST_BIN=./test_libvpx$(EXE_SFX)
|
LIBVPX_TEST_BIN=./test_libvpx$(EXE_SFX)
|
||||||
LIBVPX_TEST_DATA=$(addprefix $(LIBVPX_TEST_DATA_PATH)/,\
|
LIBVPX_TEST_DATA=$(addprefix $(LIBVPX_TEST_DATA_PATH)/,\
|
||||||
$(call enabled,LIBVPX_TEST_DATA))
|
$(call enabled,LIBVPX_TEST_DATA))
|
||||||
libvpx_test_data_url=http://downloads.webmproject.org/test_data/libvpx/$(1)
|
libvpx_test_data_url=https://storage.googleapis.com/downloads.webmproject.org/test_data/libvpx/$(1)
|
||||||
|
|
||||||
TEST_INTRA_PRED_SPEED_BIN=./test_intra_pred_speed$(EXE_SFX)
|
TEST_INTRA_PRED_SPEED_BIN=./test_intra_pred_speed$(EXE_SFX)
|
||||||
TEST_INTRA_PRED_SPEED_SRCS=$(addprefix test/,$(call enabled,TEST_INTRA_PRED_SPEED_SRCS))
|
TEST_INTRA_PRED_SPEED_SRCS=$(addprefix test/,$(call enabled,TEST_INTRA_PRED_SPEED_SRCS))
|
||||||
@ -404,8 +413,16 @@ CLEAN-OBJS += libvpx_test_srcs.txt
|
|||||||
|
|
||||||
$(LIBVPX_TEST_DATA): $(SRC_PATH_BARE)/test/test-data.sha1
|
$(LIBVPX_TEST_DATA): $(SRC_PATH_BARE)/test/test-data.sha1
|
||||||
@echo " [DOWNLOAD] $@"
|
@echo " [DOWNLOAD] $@"
|
||||||
$(qexec)trap 'rm -f $@' INT TERM &&\
|
# Attempt to download the file using curl, retrying once if it fails for a
|
||||||
curl -L -o $@ $(call libvpx_test_data_url,$(@F))
|
# partial file (18).
|
||||||
|
$(qexec)( \
|
||||||
|
trap 'rm -f $@' INT TERM; \
|
||||||
|
curl="curl --retry 1 -L -o $@ $(call libvpx_test_data_url,$(@F))"; \
|
||||||
|
$$curl; \
|
||||||
|
case "$$?" in \
|
||||||
|
18) $$curl -C -;; \
|
||||||
|
esac \
|
||||||
|
)
|
||||||
|
|
||||||
testdata:: $(LIBVPX_TEST_DATA)
|
testdata:: $(LIBVPX_TEST_DATA)
|
||||||
$(qexec)[ -x "$$(which sha1sum)" ] && sha1sum=sha1sum;\
|
$(qexec)[ -x "$$(which sha1sum)" ] && sha1sum=sha1sum;\
|
||||||
|
25
rate_hist.c
25
rate_hist.c
@ -37,7 +37,13 @@ struct rate_hist {
|
|||||||
struct rate_hist *init_rate_histogram(const vpx_codec_enc_cfg_t *cfg,
|
struct rate_hist *init_rate_histogram(const vpx_codec_enc_cfg_t *cfg,
|
||||||
const vpx_rational_t *fps) {
|
const vpx_rational_t *fps) {
|
||||||
int i;
|
int i;
|
||||||
struct rate_hist *hist = malloc(sizeof(*hist));
|
struct rate_hist *hist = calloc(1, sizeof(*hist));
|
||||||
|
|
||||||
|
if (hist == NULL || cfg == NULL || fps == NULL || fps->num == 0 ||
|
||||||
|
fps->den == 0) {
|
||||||
|
destroy_rate_histogram(hist);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
// Determine the number of samples in the buffer. Use the file's framerate
|
// Determine the number of samples in the buffer. Use the file's framerate
|
||||||
// to determine the number of frames in rc_buf_sz milliseconds, with an
|
// to determine the number of frames in rc_buf_sz milliseconds, with an
|
||||||
@ -80,7 +86,11 @@ void update_rate_histogram(struct rate_hist *hist,
|
|||||||
(uint64_t)cfg->g_timebase.num /
|
(uint64_t)cfg->g_timebase.num /
|
||||||
(uint64_t)cfg->g_timebase.den;
|
(uint64_t)cfg->g_timebase.den;
|
||||||
|
|
||||||
int idx = hist->frames++ % hist->samples;
|
int idx;
|
||||||
|
|
||||||
|
if (hist == NULL || cfg == NULL || pkt == NULL) return;
|
||||||
|
|
||||||
|
idx = hist->frames++ % hist->samples;
|
||||||
hist->pts[idx] = now;
|
hist->pts[idx] = now;
|
||||||
hist->sz[idx] = (int)pkt->data.frame.sz;
|
hist->sz[idx] = (int)pkt->data.frame.sz;
|
||||||
|
|
||||||
@ -116,9 +126,14 @@ void update_rate_histogram(struct rate_hist *hist,
|
|||||||
static int merge_hist_buckets(struct hist_bucket *bucket, int max_buckets,
|
static int merge_hist_buckets(struct hist_bucket *bucket, int max_buckets,
|
||||||
int *num_buckets) {
|
int *num_buckets) {
|
||||||
int small_bucket = 0, merge_bucket = INT_MAX, big_bucket = 0;
|
int small_bucket = 0, merge_bucket = INT_MAX, big_bucket = 0;
|
||||||
int buckets = *num_buckets;
|
int buckets;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
assert(bucket != NULL);
|
||||||
|
assert(num_buckets != NULL);
|
||||||
|
|
||||||
|
buckets = *num_buckets;
|
||||||
|
|
||||||
/* Find the extrema for this list of buckets */
|
/* Find the extrema for this list of buckets */
|
||||||
big_bucket = small_bucket = 0;
|
big_bucket = small_bucket = 0;
|
||||||
for (i = 0; i < buckets; i++) {
|
for (i = 0; i < buckets; i++) {
|
||||||
@ -181,6 +196,8 @@ static void show_histogram(const struct hist_bucket *bucket, int buckets,
|
|||||||
const char *pat1, *pat2;
|
const char *pat1, *pat2;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
assert(bucket != NULL);
|
||||||
|
|
||||||
switch ((int)(log(bucket[buckets - 1].high) / log(10)) + 1) {
|
switch ((int)(log(bucket[buckets - 1].high) / log(10)) + 1) {
|
||||||
case 1:
|
case 1:
|
||||||
case 2:
|
case 2:
|
||||||
@ -259,6 +276,8 @@ void show_rate_histogram(struct rate_hist *hist, const vpx_codec_enc_cfg_t *cfg,
|
|||||||
int i, scale;
|
int i, scale;
|
||||||
int buckets = 0;
|
int buckets = 0;
|
||||||
|
|
||||||
|
if (hist == NULL || cfg == NULL) return;
|
||||||
|
|
||||||
for (i = 0; i < RATE_BINS; i++) {
|
for (i = 0; i < RATE_BINS; i++) {
|
||||||
if (hist->bucket[i].low == INT_MAX) continue;
|
if (hist->bucket[i].low == INT_MAX) continue;
|
||||||
hist->bucket[buckets++] = hist->bucket[i];
|
hist->bucket[buckets++] = hist->bucket[i];
|
||||||
|
@ -11,6 +11,10 @@
|
|||||||
#ifndef TEST_ACM_RANDOM_H_
|
#ifndef TEST_ACM_RANDOM_H_
|
||||||
#define TEST_ACM_RANDOM_H_
|
#define TEST_ACM_RANDOM_H_
|
||||||
|
|
||||||
|
#include <assert.h>
|
||||||
|
|
||||||
|
#include <limits>
|
||||||
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
#include "vpx/vpx_integer.h"
|
#include "vpx/vpx_integer.h"
|
||||||
@ -50,6 +54,13 @@ class ACMRandom {
|
|||||||
return r < 128 ? r << 4 : r >> 4;
|
return r < 128 ? r << 4 : r >> 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint32_t RandRange(const uint32_t range) {
|
||||||
|
// testing::internal::Random::Generate provides values in the range
|
||||||
|
// testing::internal::Random::kMaxRange.
|
||||||
|
assert(range <= testing::internal::Random::kMaxRange);
|
||||||
|
return random_.Generate(range);
|
||||||
|
}
|
||||||
|
|
||||||
int PseudoUniform(int range) { return random_.Generate(range); }
|
int PseudoUniform(int range) { return random_.Generate(range); }
|
||||||
|
|
||||||
int operator()(int n) { return PseudoUniform(n); }
|
int operator()(int n) { return PseudoUniform(n); }
|
||||||
|
@ -32,6 +32,7 @@ LOCAL_CPP_EXTENSION := .cc
|
|||||||
LOCAL_MODULE := gtest
|
LOCAL_MODULE := gtest
|
||||||
LOCAL_C_INCLUDES := $(LOCAL_PATH)/third_party/googletest/src/
|
LOCAL_C_INCLUDES := $(LOCAL_PATH)/third_party/googletest/src/
|
||||||
LOCAL_C_INCLUDES += $(LOCAL_PATH)/third_party/googletest/src/include/
|
LOCAL_C_INCLUDES += $(LOCAL_PATH)/third_party/googletest/src/include/
|
||||||
|
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/third_party/googletest/src/include/
|
||||||
LOCAL_SRC_FILES := ./third_party/googletest/src/src/gtest-all.cc
|
LOCAL_SRC_FILES := ./third_party/googletest/src/src/gtest-all.cc
|
||||||
include $(BUILD_STATIC_LIBRARY)
|
include $(BUILD_STATIC_LIBRARY)
|
||||||
|
|
||||||
|
208
test/avg_test.cc
208
test/avg_test.cc
@ -14,6 +14,7 @@
|
|||||||
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vp9_rtcd.h"
|
||||||
#include "./vpx_config.h"
|
#include "./vpx_config.h"
|
||||||
#include "./vpx_dsp_rtcd.h"
|
#include "./vpx_dsp_rtcd.h"
|
||||||
|
|
||||||
@ -22,6 +23,7 @@
|
|||||||
#include "test/register_state_check.h"
|
#include "test/register_state_check.h"
|
||||||
#include "test/util.h"
|
#include "test/util.h"
|
||||||
#include "vpx_mem/vpx_mem.h"
|
#include "vpx_mem/vpx_mem.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
|
|
||||||
@ -89,7 +91,7 @@ class AverageTestBase : public ::testing::Test {
|
|||||||
};
|
};
|
||||||
typedef unsigned int (*AverageFunction)(const uint8_t *s, int pitch);
|
typedef unsigned int (*AverageFunction)(const uint8_t *s, int pitch);
|
||||||
|
|
||||||
typedef std::tr1::tuple<int, int, int, int, AverageFunction> AvgFunc;
|
typedef ::testing::tuple<int, int, int, int, AverageFunction> AvgFunc;
|
||||||
|
|
||||||
class AverageTest : public AverageTestBase,
|
class AverageTest : public AverageTestBase,
|
||||||
public ::testing::WithParamInterface<AvgFunc> {
|
public ::testing::WithParamInterface<AvgFunc> {
|
||||||
@ -120,7 +122,7 @@ class AverageTest : public AverageTestBase,
|
|||||||
typedef void (*IntProRowFunc)(int16_t hbuf[16], uint8_t const *ref,
|
typedef void (*IntProRowFunc)(int16_t hbuf[16], uint8_t const *ref,
|
||||||
const int ref_stride, const int height);
|
const int ref_stride, const int height);
|
||||||
|
|
||||||
typedef std::tr1::tuple<int, IntProRowFunc, IntProRowFunc> IntProRowParam;
|
typedef ::testing::tuple<int, IntProRowFunc, IntProRowFunc> IntProRowParam;
|
||||||
|
|
||||||
class IntProRowTest : public AverageTestBase,
|
class IntProRowTest : public AverageTestBase,
|
||||||
public ::testing::WithParamInterface<IntProRowParam> {
|
public ::testing::WithParamInterface<IntProRowParam> {
|
||||||
@ -162,7 +164,7 @@ class IntProRowTest : public AverageTestBase,
|
|||||||
|
|
||||||
typedef int16_t (*IntProColFunc)(uint8_t const *ref, const int width);
|
typedef int16_t (*IntProColFunc)(uint8_t const *ref, const int width);
|
||||||
|
|
||||||
typedef std::tr1::tuple<int, IntProColFunc, IntProColFunc> IntProColParam;
|
typedef ::testing::tuple<int, IntProColFunc, IntProColFunc> IntProColParam;
|
||||||
|
|
||||||
class IntProColTest : public AverageTestBase,
|
class IntProColTest : public AverageTestBase,
|
||||||
public ::testing::WithParamInterface<IntProColParam> {
|
public ::testing::WithParamInterface<IntProColParam> {
|
||||||
@ -186,8 +188,8 @@ class IntProColTest : public AverageTestBase,
|
|||||||
int16_t sum_c_;
|
int16_t sum_c_;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef int (*SatdFunc)(const int16_t *coeffs, int length);
|
typedef int (*SatdFunc)(const tran_low_t *coeffs, int length);
|
||||||
typedef std::tr1::tuple<int, SatdFunc> SatdTestParam;
|
typedef ::testing::tuple<int, SatdFunc> SatdTestParam;
|
||||||
|
|
||||||
class SatdTest : public ::testing::Test,
|
class SatdTest : public ::testing::Test,
|
||||||
public ::testing::WithParamInterface<SatdTestParam> {
|
public ::testing::WithParamInterface<SatdTestParam> {
|
||||||
@ -196,7 +198,7 @@ class SatdTest : public ::testing::Test,
|
|||||||
satd_size_ = GET_PARAM(0);
|
satd_size_ = GET_PARAM(0);
|
||||||
satd_func_ = GET_PARAM(1);
|
satd_func_ = GET_PARAM(1);
|
||||||
rnd_.Reset(ACMRandom::DeterministicSeed());
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
src_ = reinterpret_cast<int16_t *>(
|
src_ = reinterpret_cast<tran_low_t *>(
|
||||||
vpx_memalign(16, sizeof(*src_) * satd_size_));
|
vpx_memalign(16, sizeof(*src_) * satd_size_));
|
||||||
ASSERT_TRUE(src_ != NULL);
|
ASSERT_TRUE(src_ != NULL);
|
||||||
}
|
}
|
||||||
@ -206,12 +208,15 @@ class SatdTest : public ::testing::Test,
|
|||||||
vpx_free(src_);
|
vpx_free(src_);
|
||||||
}
|
}
|
||||||
|
|
||||||
void FillConstant(const int16_t val) {
|
void FillConstant(const tran_low_t val) {
|
||||||
for (int i = 0; i < satd_size_; ++i) src_[i] = val;
|
for (int i = 0; i < satd_size_; ++i) src_[i] = val;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FillRandom() {
|
void FillRandom() {
|
||||||
for (int i = 0; i < satd_size_; ++i) src_[i] = rnd_.Rand16();
|
for (int i = 0; i < satd_size_; ++i) {
|
||||||
|
const int16_t tmp = rnd_.Rand16();
|
||||||
|
src_[i] = (tran_low_t)tmp;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Check(const int expected) {
|
void Check(const int expected) {
|
||||||
@ -223,11 +228,66 @@ class SatdTest : public ::testing::Test,
|
|||||||
int satd_size_;
|
int satd_size_;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
int16_t *src_;
|
tran_low_t *src_;
|
||||||
SatdFunc satd_func_;
|
SatdFunc satd_func_;
|
||||||
ACMRandom rnd_;
|
ACMRandom rnd_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef int64_t (*BlockErrorFunc)(const tran_low_t *coeff,
|
||||||
|
const tran_low_t *dqcoeff, int block_size);
|
||||||
|
typedef ::testing::tuple<int, BlockErrorFunc> BlockErrorTestFPParam;
|
||||||
|
|
||||||
|
class BlockErrorTestFP
|
||||||
|
: public ::testing::Test,
|
||||||
|
public ::testing::WithParamInterface<BlockErrorTestFPParam> {
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() {
|
||||||
|
txfm_size_ = GET_PARAM(0);
|
||||||
|
block_error_func_ = GET_PARAM(1);
|
||||||
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
coeff_ = reinterpret_cast<tran_low_t *>(
|
||||||
|
vpx_memalign(16, sizeof(*coeff_) * txfm_size_));
|
||||||
|
dqcoeff_ = reinterpret_cast<tran_low_t *>(
|
||||||
|
vpx_memalign(16, sizeof(*dqcoeff_) * txfm_size_));
|
||||||
|
ASSERT_TRUE(coeff_ != NULL);
|
||||||
|
ASSERT_TRUE(dqcoeff_ != NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void TearDown() {
|
||||||
|
libvpx_test::ClearSystemState();
|
||||||
|
vpx_free(coeff_);
|
||||||
|
vpx_free(dqcoeff_);
|
||||||
|
}
|
||||||
|
|
||||||
|
void FillConstant(const tran_low_t coeff_val, const tran_low_t dqcoeff_val) {
|
||||||
|
for (int i = 0; i < txfm_size_; ++i) coeff_[i] = coeff_val;
|
||||||
|
for (int i = 0; i < txfm_size_; ++i) dqcoeff_[i] = dqcoeff_val;
|
||||||
|
}
|
||||||
|
|
||||||
|
void FillRandom() {
|
||||||
|
// Just two fixed seeds
|
||||||
|
rnd_.Reset(0xb0b9);
|
||||||
|
for (int i = 0; i < txfm_size_; ++i) coeff_[i] = rnd_.Rand16() >> 1;
|
||||||
|
rnd_.Reset(0xb0c8);
|
||||||
|
for (int i = 0; i < txfm_size_; ++i) dqcoeff_[i] = rnd_.Rand16() >> 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Check(const int64_t expected) {
|
||||||
|
int64_t total;
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
total = block_error_func_(coeff_, dqcoeff_, txfm_size_));
|
||||||
|
EXPECT_EQ(expected, total);
|
||||||
|
}
|
||||||
|
|
||||||
|
int txfm_size_;
|
||||||
|
|
||||||
|
private:
|
||||||
|
tran_low_t *coeff_;
|
||||||
|
tran_low_t *dqcoeff_;
|
||||||
|
BlockErrorFunc block_error_func_;
|
||||||
|
ACMRandom rnd_;
|
||||||
|
};
|
||||||
|
|
||||||
uint8_t *AverageTestBase::source_data_ = NULL;
|
uint8_t *AverageTestBase::source_data_ = NULL;
|
||||||
|
|
||||||
TEST_P(AverageTest, MinValue) {
|
TEST_P(AverageTest, MinValue) {
|
||||||
@ -308,7 +368,67 @@ TEST_P(SatdTest, Random) {
|
|||||||
Check(expected);
|
Check(expected);
|
||||||
}
|
}
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
TEST_P(SatdTest, DISABLED_Speed) {
|
||||||
|
const int kCountSpeedTestBlock = 20000;
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
DECLARE_ALIGNED(16, tran_low_t, coeff[1024]);
|
||||||
|
const int blocksize = GET_PARAM(0);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int i = 0; i < kCountSpeedTestBlock; ++i) {
|
||||||
|
GET_PARAM(1)(coeff, blocksize);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("blocksize: %4d time: %4d us\n", blocksize, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(BlockErrorTestFP, MinValue) {
|
||||||
|
const int64_t kMin = -32640;
|
||||||
|
const int64_t expected = kMin * kMin * txfm_size_;
|
||||||
|
FillConstant(kMin, 0);
|
||||||
|
Check(expected);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(BlockErrorTestFP, MaxValue) {
|
||||||
|
const int64_t kMax = 32640;
|
||||||
|
const int64_t expected = kMax * kMax * txfm_size_;
|
||||||
|
FillConstant(kMax, 0);
|
||||||
|
Check(expected);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(BlockErrorTestFP, Random) {
|
||||||
|
int64_t expected;
|
||||||
|
switch (txfm_size_) {
|
||||||
|
case 16: expected = 2051681432; break;
|
||||||
|
case 64: expected = 11075114379; break;
|
||||||
|
case 256: expected = 44386271116; break;
|
||||||
|
case 1024: expected = 184774996089; break;
|
||||||
|
default:
|
||||||
|
FAIL() << "Invalid satd size (" << txfm_size_
|
||||||
|
<< ") valid: 16/64/256/1024";
|
||||||
|
}
|
||||||
|
FillRandom();
|
||||||
|
Check(expected);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(BlockErrorTestFP, DISABLED_Speed) {
|
||||||
|
const int kCountSpeedTestBlock = 20000;
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
DECLARE_ALIGNED(16, tran_low_t, coeff[1024]);
|
||||||
|
DECLARE_ALIGNED(16, tran_low_t, dqcoeff[1024]);
|
||||||
|
const int blocksize = GET_PARAM(0);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int i = 0; i < kCountSpeedTestBlock; ++i) {
|
||||||
|
GET_PARAM(1)(coeff, dqcoeff, blocksize);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("blocksize: %4d time: %4d us\n", blocksize, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
C, AverageTest,
|
C, AverageTest,
|
||||||
@ -321,6 +441,13 @@ INSTANTIATE_TEST_CASE_P(C, SatdTest,
|
|||||||
make_tuple(256, &vpx_satd_c),
|
make_tuple(256, &vpx_satd_c),
|
||||||
make_tuple(1024, &vpx_satd_c)));
|
make_tuple(1024, &vpx_satd_c)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
C, BlockErrorTestFP,
|
||||||
|
::testing::Values(make_tuple(16, &vp9_block_error_fp_c),
|
||||||
|
make_tuple(64, &vp9_block_error_fp_c),
|
||||||
|
make_tuple(256, &vp9_block_error_fp_c),
|
||||||
|
make_tuple(1024, &vp9_block_error_fp_c)));
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2, AverageTest,
|
SSE2, AverageTest,
|
||||||
@ -350,6 +477,28 @@ INSTANTIATE_TEST_CASE_P(SSE2, SatdTest,
|
|||||||
make_tuple(64, &vpx_satd_sse2),
|
make_tuple(64, &vpx_satd_sse2),
|
||||||
make_tuple(256, &vpx_satd_sse2),
|
make_tuple(256, &vpx_satd_sse2),
|
||||||
make_tuple(1024, &vpx_satd_sse2)));
|
make_tuple(1024, &vpx_satd_sse2)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSE2, BlockErrorTestFP,
|
||||||
|
::testing::Values(make_tuple(16, &vp9_block_error_fp_sse2),
|
||||||
|
make_tuple(64, &vp9_block_error_fp_sse2),
|
||||||
|
make_tuple(256, &vp9_block_error_fp_sse2),
|
||||||
|
make_tuple(1024, &vp9_block_error_fp_sse2)));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_AVX2
|
||||||
|
INSTANTIATE_TEST_CASE_P(AVX2, SatdTest,
|
||||||
|
::testing::Values(make_tuple(16, &vpx_satd_avx2),
|
||||||
|
make_tuple(64, &vpx_satd_avx2),
|
||||||
|
make_tuple(256, &vpx_satd_avx2),
|
||||||
|
make_tuple(1024, &vpx_satd_avx2)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
AVX2, BlockErrorTestFP,
|
||||||
|
::testing::Values(make_tuple(16, &vp9_block_error_fp_avx2),
|
||||||
|
make_tuple(64, &vp9_block_error_fp_avx2),
|
||||||
|
make_tuple(256, &vp9_block_error_fp_avx2),
|
||||||
|
make_tuple(1024, &vp9_block_error_fp_avx2)));
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if HAVE_NEON
|
#if HAVE_NEON
|
||||||
@ -381,7 +530,18 @@ INSTANTIATE_TEST_CASE_P(NEON, SatdTest,
|
|||||||
make_tuple(64, &vpx_satd_neon),
|
make_tuple(64, &vpx_satd_neon),
|
||||||
make_tuple(256, &vpx_satd_neon),
|
make_tuple(256, &vpx_satd_neon),
|
||||||
make_tuple(1024, &vpx_satd_neon)));
|
make_tuple(1024, &vpx_satd_neon)));
|
||||||
#endif
|
|
||||||
|
// TODO(jianj): Remove the highbitdepth flag once the SIMD functions are
|
||||||
|
// in place.
|
||||||
|
#if !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, BlockErrorTestFP,
|
||||||
|
::testing::Values(make_tuple(16, &vp9_block_error_fp_neon),
|
||||||
|
make_tuple(64, &vp9_block_error_fp_neon),
|
||||||
|
make_tuple(256, &vp9_block_error_fp_neon),
|
||||||
|
make_tuple(1024, &vp9_block_error_fp_neon)));
|
||||||
|
#endif // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
#if HAVE_MSA
|
#if HAVE_MSA
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -392,6 +552,30 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(16, 16, 0, 4, &vpx_avg_4x4_msa),
|
make_tuple(16, 16, 0, 4, &vpx_avg_4x4_msa),
|
||||||
make_tuple(16, 16, 5, 4, &vpx_avg_4x4_msa),
|
make_tuple(16, 16, 5, 4, &vpx_avg_4x4_msa),
|
||||||
make_tuple(32, 32, 15, 4, &vpx_avg_4x4_msa)));
|
make_tuple(32, 32, 15, 4, &vpx_avg_4x4_msa)));
|
||||||
#endif
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MSA, IntProRowTest,
|
||||||
|
::testing::Values(make_tuple(16, &vpx_int_pro_row_msa, &vpx_int_pro_row_c),
|
||||||
|
make_tuple(32, &vpx_int_pro_row_msa, &vpx_int_pro_row_c),
|
||||||
|
make_tuple(64, &vpx_int_pro_row_msa,
|
||||||
|
&vpx_int_pro_row_c)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MSA, IntProColTest,
|
||||||
|
::testing::Values(make_tuple(16, &vpx_int_pro_col_msa, &vpx_int_pro_col_c),
|
||||||
|
make_tuple(32, &vpx_int_pro_col_msa, &vpx_int_pro_col_c),
|
||||||
|
make_tuple(64, &vpx_int_pro_col_msa,
|
||||||
|
&vpx_int_pro_col_c)));
|
||||||
|
|
||||||
|
// TODO(jingning): Remove the highbitdepth flag once the SIMD functions are
|
||||||
|
// in place.
|
||||||
|
#if !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, SatdTest,
|
||||||
|
::testing::Values(make_tuple(16, &vpx_satd_msa),
|
||||||
|
make_tuple(64, &vpx_satd_msa),
|
||||||
|
make_tuple(256, &vpx_satd_msa),
|
||||||
|
make_tuple(1024, &vpx_satd_msa)));
|
||||||
|
#endif // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -141,7 +141,7 @@ class BlockinessTestBase : public ::testing::Test {
|
|||||||
};
|
};
|
||||||
|
|
||||||
#if CONFIG_VP9_ENCODER
|
#if CONFIG_VP9_ENCODER
|
||||||
typedef std::tr1::tuple<int, int> BlockinessParam;
|
typedef ::testing::tuple<int, int> BlockinessParam;
|
||||||
class BlockinessVP9Test
|
class BlockinessVP9Test
|
||||||
: public BlockinessTestBase,
|
: public BlockinessTestBase,
|
||||||
public ::testing::WithParamInterface<BlockinessParam> {
|
public ::testing::WithParamInterface<BlockinessParam> {
|
||||||
@ -208,14 +208,14 @@ TEST_P(BlockinessVP9Test, WorstCaseBlockiness) {
|
|||||||
}
|
}
|
||||||
#endif // CONFIG_VP9_ENCODER
|
#endif // CONFIG_VP9_ENCODER
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
// C functions
|
// C functions
|
||||||
|
|
||||||
#if CONFIG_VP9_ENCODER
|
#if CONFIG_VP9_ENCODER
|
||||||
const BlockinessParam c_vp9_tests[] = {
|
const BlockinessParam c_vp9_tests[] = {
|
||||||
make_tuple(320, 240), make_tuple(318, 242), make_tuple(318, 238),
|
make_tuple(320, 240), make_tuple(318, 242), make_tuple(318, 238)
|
||||||
};
|
};
|
||||||
INSTANTIATE_TEST_CASE_P(C, BlockinessVP9Test, ::testing::ValuesIn(c_vp9_tests));
|
INSTANTIATE_TEST_CASE_P(C, BlockinessVP9Test, ::testing::ValuesIn(c_vp9_tests));
|
||||||
#endif
|
#endif
|
||||||
|
382
test/buffer.h
Normal file
382
test/buffer.h
Normal file
@ -0,0 +1,382 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef TEST_BUFFER_H_
|
||||||
|
#define TEST_BUFFER_H_
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
#include <limits>
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "test/acm_random.h"
|
||||||
|
#include "vpx/vpx_integer.h"
|
||||||
|
#include "vpx_mem/vpx_mem.h"
|
||||||
|
|
||||||
|
namespace libvpx_test {
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
class Buffer {
|
||||||
|
public:
|
||||||
|
Buffer(int width, int height, int top_padding, int left_padding,
|
||||||
|
int right_padding, int bottom_padding)
|
||||||
|
: width_(width), height_(height), top_padding_(top_padding),
|
||||||
|
left_padding_(left_padding), right_padding_(right_padding),
|
||||||
|
bottom_padding_(bottom_padding), alignment_(0), padding_value_(0),
|
||||||
|
stride_(0), raw_size_(0), num_elements_(0), raw_buffer_(NULL) {}
|
||||||
|
|
||||||
|
Buffer(int width, int height, int top_padding, int left_padding,
|
||||||
|
int right_padding, int bottom_padding, unsigned int alignment)
|
||||||
|
: width_(width), height_(height), top_padding_(top_padding),
|
||||||
|
left_padding_(left_padding), right_padding_(right_padding),
|
||||||
|
bottom_padding_(bottom_padding), alignment_(alignment),
|
||||||
|
padding_value_(0), stride_(0), raw_size_(0), num_elements_(0),
|
||||||
|
raw_buffer_(NULL) {}
|
||||||
|
|
||||||
|
Buffer(int width, int height, int padding)
|
||||||
|
: width_(width), height_(height), top_padding_(padding),
|
||||||
|
left_padding_(padding), right_padding_(padding),
|
||||||
|
bottom_padding_(padding), alignment_(0), padding_value_(0), stride_(0),
|
||||||
|
raw_size_(0), num_elements_(0), raw_buffer_(NULL) {}
|
||||||
|
|
||||||
|
Buffer(int width, int height, int padding, unsigned int alignment)
|
||||||
|
: width_(width), height_(height), top_padding_(padding),
|
||||||
|
left_padding_(padding), right_padding_(padding),
|
||||||
|
bottom_padding_(padding), alignment_(alignment), padding_value_(0),
|
||||||
|
stride_(0), raw_size_(0), num_elements_(0), raw_buffer_(NULL) {}
|
||||||
|
|
||||||
|
~Buffer() {
|
||||||
|
if (alignment_) {
|
||||||
|
vpx_free(raw_buffer_);
|
||||||
|
} else {
|
||||||
|
delete[] raw_buffer_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
T *TopLeftPixel() const;
|
||||||
|
|
||||||
|
int stride() const { return stride_; }
|
||||||
|
|
||||||
|
// Set the buffer (excluding padding) to 'value'.
|
||||||
|
void Set(const T value);
|
||||||
|
|
||||||
|
// Set the buffer (excluding padding) to the output of ACMRandom function
|
||||||
|
// 'rand_func'.
|
||||||
|
void Set(ACMRandom *rand_class, T (ACMRandom::*rand_func)());
|
||||||
|
|
||||||
|
// Set the buffer (excluding padding) to the output of ACMRandom function
|
||||||
|
// 'RandRange' with range 'low' to 'high' which typically must be within
|
||||||
|
// testing::internal::Random::kMaxRange (1u << 31). However, because we want
|
||||||
|
// to allow negative low (and high) values, it is restricted to INT32_MAX
|
||||||
|
// here.
|
||||||
|
void Set(ACMRandom *rand_class, const T low, const T high);
|
||||||
|
|
||||||
|
// Copy the contents of Buffer 'a' (excluding padding).
|
||||||
|
void CopyFrom(const Buffer<T> &a);
|
||||||
|
|
||||||
|
void DumpBuffer() const;
|
||||||
|
|
||||||
|
// Highlight the differences between two buffers if they are the same size.
|
||||||
|
void PrintDifference(const Buffer<T> &a) const;
|
||||||
|
|
||||||
|
bool HasPadding() const;
|
||||||
|
|
||||||
|
// Sets all the values in the buffer to 'padding_value'.
|
||||||
|
void SetPadding(const T padding_value);
|
||||||
|
|
||||||
|
// Checks if all the values (excluding padding) are equal to 'value' if the
|
||||||
|
// Buffers are the same size.
|
||||||
|
bool CheckValues(const T value) const;
|
||||||
|
|
||||||
|
// Check that padding matches the expected value or there is no padding.
|
||||||
|
bool CheckPadding() const;
|
||||||
|
|
||||||
|
// Compare the non-padding portion of two buffers if they are the same size.
|
||||||
|
bool CheckValues(const Buffer<T> &a) const;
|
||||||
|
|
||||||
|
bool Init() {
|
||||||
|
if (raw_buffer_ != NULL) return false;
|
||||||
|
EXPECT_GT(width_, 0);
|
||||||
|
EXPECT_GT(height_, 0);
|
||||||
|
EXPECT_GE(top_padding_, 0);
|
||||||
|
EXPECT_GE(left_padding_, 0);
|
||||||
|
EXPECT_GE(right_padding_, 0);
|
||||||
|
EXPECT_GE(bottom_padding_, 0);
|
||||||
|
stride_ = left_padding_ + width_ + right_padding_;
|
||||||
|
num_elements_ = stride_ * (top_padding_ + height_ + bottom_padding_);
|
||||||
|
raw_size_ = num_elements_ * sizeof(T);
|
||||||
|
if (alignment_) {
|
||||||
|
EXPECT_GE(alignment_, sizeof(T));
|
||||||
|
// Ensure alignment of the first value will be preserved.
|
||||||
|
EXPECT_EQ((left_padding_ * sizeof(T)) % alignment_, 0u);
|
||||||
|
// Ensure alignment of the subsequent rows will be preserved when there is
|
||||||
|
// a stride.
|
||||||
|
if (stride_ != width_) {
|
||||||
|
EXPECT_EQ((stride_ * sizeof(T)) % alignment_, 0u);
|
||||||
|
}
|
||||||
|
raw_buffer_ = reinterpret_cast<T *>(vpx_memalign(alignment_, raw_size_));
|
||||||
|
} else {
|
||||||
|
raw_buffer_ = new (std::nothrow) T[num_elements_];
|
||||||
|
}
|
||||||
|
EXPECT_TRUE(raw_buffer_ != NULL);
|
||||||
|
SetPadding(std::numeric_limits<T>::max());
|
||||||
|
return !::testing::Test::HasFailure();
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
bool BufferSizesMatch(const Buffer<T> &a) const;
|
||||||
|
|
||||||
|
const int width_;
|
||||||
|
const int height_;
|
||||||
|
const int top_padding_;
|
||||||
|
const int left_padding_;
|
||||||
|
const int right_padding_;
|
||||||
|
const int bottom_padding_;
|
||||||
|
const unsigned int alignment_;
|
||||||
|
T padding_value_;
|
||||||
|
int stride_;
|
||||||
|
int raw_size_;
|
||||||
|
int num_elements_;
|
||||||
|
T *raw_buffer_;
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
T *Buffer<T>::TopLeftPixel() const {
|
||||||
|
if (!raw_buffer_) return NULL;
|
||||||
|
return raw_buffer_ + (top_padding_ * stride_) + left_padding_;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::Set(const T value) {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
T *src = TopLeftPixel();
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
src[width] = value;
|
||||||
|
}
|
||||||
|
src += stride_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::Set(ACMRandom *rand_class, T (ACMRandom::*rand_func)()) {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
T *src = TopLeftPixel();
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
src[width] = (*rand_class.*rand_func)();
|
||||||
|
}
|
||||||
|
src += stride_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::Set(ACMRandom *rand_class, const T low, const T high) {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
|
||||||
|
EXPECT_LE(low, high);
|
||||||
|
EXPECT_LE(static_cast<int64_t>(high) - low,
|
||||||
|
std::numeric_limits<int32_t>::max());
|
||||||
|
|
||||||
|
T *src = TopLeftPixel();
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
// 'low' will be promoted to unsigned given the return type of RandRange.
|
||||||
|
// Store the value as an int to avoid unsigned overflow warnings when
|
||||||
|
// 'low' is negative.
|
||||||
|
const int32_t value =
|
||||||
|
static_cast<int32_t>((*rand_class).RandRange(high - low));
|
||||||
|
src[width] = static_cast<T>(value + low);
|
||||||
|
}
|
||||||
|
src += stride_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::CopyFrom(const Buffer<T> &a) {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
if (!BufferSizesMatch(a)) return;
|
||||||
|
|
||||||
|
T *a_src = a.TopLeftPixel();
|
||||||
|
T *b_src = this->TopLeftPixel();
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
b_src[width] = a_src[width];
|
||||||
|
}
|
||||||
|
a_src += a.stride();
|
||||||
|
b_src += this->stride();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::DumpBuffer() const {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
for (int height = 0; height < height_ + top_padding_ + bottom_padding_;
|
||||||
|
++height) {
|
||||||
|
for (int width = 0; width < stride_; ++width) {
|
||||||
|
printf("%4d", raw_buffer_[height + width * stride_]);
|
||||||
|
}
|
||||||
|
printf("\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
bool Buffer<T>::HasPadding() const {
|
||||||
|
if (!raw_buffer_) return false;
|
||||||
|
return top_padding_ || left_padding_ || right_padding_ || bottom_padding_;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::PrintDifference(const Buffer<T> &a) const {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
if (!BufferSizesMatch(a)) return;
|
||||||
|
|
||||||
|
T *a_src = a.TopLeftPixel();
|
||||||
|
T *b_src = TopLeftPixel();
|
||||||
|
|
||||||
|
printf("This buffer:\n");
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
if (a_src[width] != b_src[width]) {
|
||||||
|
printf("*%3d", b_src[width]);
|
||||||
|
} else {
|
||||||
|
printf("%4d", b_src[width]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
printf("\n");
|
||||||
|
a_src += a.stride();
|
||||||
|
b_src += this->stride();
|
||||||
|
}
|
||||||
|
|
||||||
|
a_src = a.TopLeftPixel();
|
||||||
|
b_src = TopLeftPixel();
|
||||||
|
|
||||||
|
printf("Reference buffer:\n");
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
if (a_src[width] != b_src[width]) {
|
||||||
|
printf("*%3d", a_src[width]);
|
||||||
|
} else {
|
||||||
|
printf("%4d", a_src[width]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
printf("\n");
|
||||||
|
a_src += a.stride();
|
||||||
|
b_src += this->stride();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
void Buffer<T>::SetPadding(const T padding_value) {
|
||||||
|
if (!raw_buffer_) return;
|
||||||
|
padding_value_ = padding_value;
|
||||||
|
|
||||||
|
T *src = raw_buffer_;
|
||||||
|
for (int i = 0; i < num_elements_; ++i) {
|
||||||
|
src[i] = padding_value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
bool Buffer<T>::CheckValues(const T value) const {
|
||||||
|
if (!raw_buffer_) return false;
|
||||||
|
T *src = TopLeftPixel();
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
if (value != src[width]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
src += stride_;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
bool Buffer<T>::CheckPadding() const {
|
||||||
|
if (!raw_buffer_) return false;
|
||||||
|
if (!HasPadding()) return true;
|
||||||
|
|
||||||
|
// Top padding.
|
||||||
|
T const *top = raw_buffer_;
|
||||||
|
for (int i = 0; i < stride_ * top_padding_; ++i) {
|
||||||
|
if (padding_value_ != top[i]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Left padding.
|
||||||
|
T const *left = TopLeftPixel() - left_padding_;
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < left_padding_; ++width) {
|
||||||
|
if (padding_value_ != left[width]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
left += stride_;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Right padding.
|
||||||
|
T const *right = TopLeftPixel() + width_;
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < right_padding_; ++width) {
|
||||||
|
if (padding_value_ != right[width]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
right += stride_;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Bottom padding
|
||||||
|
T const *bottom = raw_buffer_ + (top_padding_ + height_) * stride_;
|
||||||
|
for (int i = 0; i < stride_ * bottom_padding_; ++i) {
|
||||||
|
if (padding_value_ != bottom[i]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
bool Buffer<T>::CheckValues(const Buffer<T> &a) const {
|
||||||
|
if (!raw_buffer_) return false;
|
||||||
|
if (!BufferSizesMatch(a)) return false;
|
||||||
|
|
||||||
|
T *a_src = a.TopLeftPixel();
|
||||||
|
T *b_src = this->TopLeftPixel();
|
||||||
|
for (int height = 0; height < height_; ++height) {
|
||||||
|
for (int width = 0; width < width_; ++width) {
|
||||||
|
if (a_src[width] != b_src[width]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
a_src += a.stride();
|
||||||
|
b_src += this->stride();
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
bool Buffer<T>::BufferSizesMatch(const Buffer<T> &a) const {
|
||||||
|
if (!raw_buffer_) return false;
|
||||||
|
if (a.width_ != this->width_ || a.height_ != this->height_) {
|
||||||
|
printf(
|
||||||
|
"Reference buffer of size %dx%d does not match this buffer which is "
|
||||||
|
"size %dx%d\n",
|
||||||
|
a.width_, a.height_, this->width_, this->height_);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
} // namespace libvpx_test
|
||||||
|
#endif // TEST_BUFFER_H_
|
@ -128,8 +128,8 @@ class ByteAlignmentTest
|
|||||||
// TODO(fgalligan): Move the MD5 testing code into another class.
|
// TODO(fgalligan): Move the MD5 testing code into another class.
|
||||||
void OpenMd5File(const std::string &md5_file_name_) {
|
void OpenMd5File(const std::string &md5_file_name_) {
|
||||||
md5_file_ = libvpx_test::OpenTestDataFile(md5_file_name_);
|
md5_file_ = libvpx_test::OpenTestDataFile(md5_file_name_);
|
||||||
ASSERT_TRUE(md5_file_ != NULL) << "MD5 file open failed. Filename: "
|
ASSERT_TRUE(md5_file_ != NULL)
|
||||||
<< md5_file_name_;
|
<< "MD5 file open failed. Filename: " << md5_file_name_;
|
||||||
}
|
}
|
||||||
|
|
||||||
void CheckMd5(const vpx_image_t &img) {
|
void CheckMd5(const vpx_image_t &img) {
|
||||||
@ -171,9 +171,10 @@ TEST_F(ByteAlignmentTest, SwitchByteAlignment) {
|
|||||||
TEST_P(ByteAlignmentTest, TestAlignment) {
|
TEST_P(ByteAlignmentTest, TestAlignment) {
|
||||||
const ByteAlignmentTestParam t = GetParam();
|
const ByteAlignmentTestParam t = GetParam();
|
||||||
SetByteAlignment(t.byte_alignment, t.expected_value);
|
SetByteAlignment(t.byte_alignment, t.expected_value);
|
||||||
if (t.decode_remaining)
|
if (t.decode_remaining) {
|
||||||
ASSERT_EQ(VPX_CODEC_OK, DecodeRemainingFrames(t.byte_alignment));
|
ASSERT_EQ(VPX_CODEC_OK, DecodeRemainingFrames(t.byte_alignment));
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(Alignments, ByteAlignmentTest,
|
INSTANTIATE_TEST_CASE_P(Alignments, ByteAlignmentTest,
|
||||||
::testing::ValuesIn(kBaTestParams));
|
::testing::ValuesIn(kBaTestParams));
|
||||||
|
@ -11,19 +11,13 @@
|
|||||||
#define TEST_CLEAR_SYSTEM_STATE_H_
|
#define TEST_CLEAR_SYSTEM_STATE_H_
|
||||||
|
|
||||||
#include "./vpx_config.h"
|
#include "./vpx_config.h"
|
||||||
#if ARCH_X86 || ARCH_X86_64
|
#include "vpx_ports/system_state.h"
|
||||||
#include "vpx_ports/x86.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace libvpx_test {
|
namespace libvpx_test {
|
||||||
|
|
||||||
// Reset system to a known state. This function should be used for all non-API
|
// Reset system to a known state. This function should be used for all non-API
|
||||||
// test cases.
|
// test cases.
|
||||||
inline void ClearSystemState() {
|
inline void ClearSystemState() { vpx_clear_system_state(); }
|
||||||
#if ARCH_X86 || ARCH_X86_64
|
|
||||||
vpx_reset_mmx_state();
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace libvpx_test
|
} // namespace libvpx_test
|
||||||
#endif // TEST_CLEAR_SYSTEM_STATE_H_
|
#endif // TEST_CLEAR_SYSTEM_STATE_H_
|
||||||
|
@ -53,23 +53,22 @@ class CodecFactory {
|
|||||||
template <class T1>
|
template <class T1>
|
||||||
class CodecTestWithParam
|
class CodecTestWithParam
|
||||||
: public ::testing::TestWithParam<
|
: public ::testing::TestWithParam<
|
||||||
std::tr1::tuple<const libvpx_test::CodecFactory *, T1> > {};
|
::testing::tuple<const libvpx_test::CodecFactory *, T1> > {};
|
||||||
|
|
||||||
template <class T1, class T2>
|
template <class T1, class T2>
|
||||||
class CodecTestWith2Params
|
class CodecTestWith2Params
|
||||||
: public ::testing::TestWithParam<
|
: public ::testing::TestWithParam<
|
||||||
std::tr1::tuple<const libvpx_test::CodecFactory *, T1, T2> > {};
|
::testing::tuple<const libvpx_test::CodecFactory *, T1, T2> > {};
|
||||||
|
|
||||||
template <class T1, class T2, class T3>
|
template <class T1, class T2, class T3>
|
||||||
class CodecTestWith3Params
|
class CodecTestWith3Params
|
||||||
: public ::testing::TestWithParam<
|
: public ::testing::TestWithParam<
|
||||||
std::tr1::tuple<const libvpx_test::CodecFactory *, T1, T2, T3> > {};
|
::testing::tuple<const libvpx_test::CodecFactory *, T1, T2, T3> > {};
|
||||||
|
|
||||||
template <class T1, class T2, class T3, class T4>
|
template <class T1, class T2, class T3, class T4>
|
||||||
class CodecTestWith4Params
|
class CodecTestWith4Params
|
||||||
: public ::testing::TestWithParam<
|
: public ::testing::TestWithParam< ::testing::tuple<
|
||||||
std::tr1::tuple<const libvpx_test::CodecFactory *, T1, T2, T3, T4> > {
|
const libvpx_test::CodecFactory *, T1, T2, T3, T4> > {};
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* VP8 Codec Definitions
|
* VP8 Codec Definitions
|
||||||
|
182
test/comp_avg_pred_test.cc
Normal file
182
test/comp_avg_pred_test.cc
Normal file
@ -0,0 +1,182 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2017 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vpx_dsp_rtcd.h"
|
||||||
|
|
||||||
|
#include "test/acm_random.h"
|
||||||
|
#include "test/buffer.h"
|
||||||
|
#include "test/register_state_check.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
using ::libvpx_test::ACMRandom;
|
||||||
|
using ::libvpx_test::Buffer;
|
||||||
|
|
||||||
|
typedef void (*AvgPredFunc)(uint8_t *a, const uint8_t *b, int w, int h,
|
||||||
|
const uint8_t *c, int c_stride);
|
||||||
|
|
||||||
|
uint8_t avg_with_rounding(uint8_t a, uint8_t b) { return (a + b + 1) >> 1; }
|
||||||
|
|
||||||
|
void reference_pred(const Buffer<uint8_t> &pred, const Buffer<uint8_t> &ref,
|
||||||
|
int width, int height, Buffer<uint8_t> *avg) {
|
||||||
|
for (int y = 0; y < height; ++y) {
|
||||||
|
for (int x = 0; x < width; ++x) {
|
||||||
|
avg->TopLeftPixel()[y * avg->stride() + x] =
|
||||||
|
avg_with_rounding(pred.TopLeftPixel()[y * pred.stride() + x],
|
||||||
|
ref.TopLeftPixel()[y * ref.stride() + x]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class AvgPredTest : public ::testing::TestWithParam<AvgPredFunc> {
|
||||||
|
public:
|
||||||
|
virtual void SetUp() {
|
||||||
|
avg_pred_func_ = GetParam();
|
||||||
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
AvgPredFunc avg_pred_func_;
|
||||||
|
ACMRandom rnd_;
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(AvgPredTest, SizeCombinations) {
|
||||||
|
// This is called as part of the sub pixel variance. As such it must be one of
|
||||||
|
// the variance block sizes.
|
||||||
|
|
||||||
|
for (int width_pow = 2; width_pow <= 6; ++width_pow) {
|
||||||
|
for (int height_pow = width_pow - 1; height_pow <= width_pow + 1;
|
||||||
|
++height_pow) {
|
||||||
|
// Don't test 4x2 or 64x128
|
||||||
|
if (height_pow == 1 || height_pow == 7) continue;
|
||||||
|
|
||||||
|
// The sse2 special-cases when ref width == stride, so make sure to test
|
||||||
|
// it.
|
||||||
|
for (int ref_padding = 0; ref_padding < 2; ref_padding++) {
|
||||||
|
const int width = 1 << width_pow;
|
||||||
|
const int height = 1 << height_pow;
|
||||||
|
// Only the reference buffer may have a stride not equal to width.
|
||||||
|
Buffer<uint8_t> ref =
|
||||||
|
Buffer<uint8_t>(width, height, ref_padding ? 8 : 0);
|
||||||
|
ASSERT_TRUE(ref.Init());
|
||||||
|
Buffer<uint8_t> pred = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(pred.Init());
|
||||||
|
Buffer<uint8_t> avg_ref = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(avg_ref.Init());
|
||||||
|
Buffer<uint8_t> avg_chk = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(avg_chk.Init());
|
||||||
|
|
||||||
|
ref.Set(&rnd_, &ACMRandom::Rand8);
|
||||||
|
pred.Set(&rnd_, &ACMRandom::Rand8);
|
||||||
|
|
||||||
|
reference_pred(pred, ref, width, height, &avg_ref);
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
avg_pred_func_(avg_chk.TopLeftPixel(), pred.TopLeftPixel(), width,
|
||||||
|
height, ref.TopLeftPixel(), ref.stride()));
|
||||||
|
|
||||||
|
EXPECT_TRUE(avg_chk.CheckValues(avg_ref));
|
||||||
|
if (HasFailure()) {
|
||||||
|
printf("Width: %d Height: %d\n", width, height);
|
||||||
|
avg_chk.PrintDifference(avg_ref);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(AvgPredTest, CompareReferenceRandom) {
|
||||||
|
const int width = 64;
|
||||||
|
const int height = 32;
|
||||||
|
Buffer<uint8_t> ref = Buffer<uint8_t>(width, height, 8);
|
||||||
|
ASSERT_TRUE(ref.Init());
|
||||||
|
Buffer<uint8_t> pred = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(pred.Init());
|
||||||
|
Buffer<uint8_t> avg_ref = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(avg_ref.Init());
|
||||||
|
Buffer<uint8_t> avg_chk = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(avg_chk.Init());
|
||||||
|
|
||||||
|
for (int i = 0; i < 500; ++i) {
|
||||||
|
ref.Set(&rnd_, &ACMRandom::Rand8);
|
||||||
|
pred.Set(&rnd_, &ACMRandom::Rand8);
|
||||||
|
|
||||||
|
reference_pred(pred, ref, width, height, &avg_ref);
|
||||||
|
ASM_REGISTER_STATE_CHECK(avg_pred_func_(avg_chk.TopLeftPixel(),
|
||||||
|
pred.TopLeftPixel(), width, height,
|
||||||
|
ref.TopLeftPixel(), ref.stride()));
|
||||||
|
EXPECT_TRUE(avg_chk.CheckValues(avg_ref));
|
||||||
|
if (HasFailure()) {
|
||||||
|
printf("Width: %d Height: %d\n", width, height);
|
||||||
|
avg_chk.PrintDifference(avg_ref);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(AvgPredTest, DISABLED_Speed) {
|
||||||
|
for (int width_pow = 2; width_pow <= 6; ++width_pow) {
|
||||||
|
for (int height_pow = width_pow - 1; height_pow <= width_pow + 1;
|
||||||
|
++height_pow) {
|
||||||
|
// Don't test 4x2 or 64x128
|
||||||
|
if (height_pow == 1 || height_pow == 7) continue;
|
||||||
|
|
||||||
|
for (int ref_padding = 0; ref_padding < 2; ref_padding++) {
|
||||||
|
const int width = 1 << width_pow;
|
||||||
|
const int height = 1 << height_pow;
|
||||||
|
Buffer<uint8_t> ref =
|
||||||
|
Buffer<uint8_t>(width, height, ref_padding ? 8 : 0);
|
||||||
|
ASSERT_TRUE(ref.Init());
|
||||||
|
Buffer<uint8_t> pred = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(pred.Init());
|
||||||
|
Buffer<uint8_t> avg = Buffer<uint8_t>(width, height, 0, 16);
|
||||||
|
ASSERT_TRUE(avg.Init());
|
||||||
|
|
||||||
|
ref.Set(&rnd_, &ACMRandom::Rand8);
|
||||||
|
pred.Set(&rnd_, &ACMRandom::Rand8);
|
||||||
|
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int i = 0; i < 10000000 / (width * height); ++i) {
|
||||||
|
avg_pred_func_(avg.TopLeftPixel(), pred.TopLeftPixel(), width, height,
|
||||||
|
ref.TopLeftPixel(), ref.stride());
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time =
|
||||||
|
static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("Average Test (ref_padding: %d) %dx%d time: %5d us\n",
|
||||||
|
ref_padding, width, height, elapsed_time);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(C, AvgPredTest,
|
||||||
|
::testing::Values(&vpx_comp_avg_pred_c));
|
||||||
|
|
||||||
|
#if HAVE_SSE2
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, AvgPredTest,
|
||||||
|
::testing::Values(&vpx_comp_avg_pred_sse2));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
INSTANTIATE_TEST_CASE_P(NEON, AvgPredTest,
|
||||||
|
::testing::Values(&vpx_comp_avg_pred_neon));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if HAVE_VSX
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, AvgPredTest,
|
||||||
|
::testing::Values(&vpx_comp_avg_pred_vsx));
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
} // namespace
|
@ -127,7 +127,7 @@ class ConsistencyTestBase : public ::testing::Test {
|
|||||||
};
|
};
|
||||||
|
|
||||||
#if CONFIG_VP9_ENCODER
|
#if CONFIG_VP9_ENCODER
|
||||||
typedef std::tr1::tuple<int, int> ConsistencyParam;
|
typedef ::testing::tuple<int, int> ConsistencyParam;
|
||||||
class ConsistencyVP9Test
|
class ConsistencyVP9Test
|
||||||
: public ConsistencyTestBase,
|
: public ConsistencyTestBase,
|
||||||
public ::testing::WithParamInterface<ConsistencyParam> {
|
public ::testing::WithParamInterface<ConsistencyParam> {
|
||||||
@ -198,14 +198,14 @@ TEST_P(ConsistencyVP9Test, ConsistencyIsZero) {
|
|||||||
}
|
}
|
||||||
#endif // CONFIG_VP9_ENCODER
|
#endif // CONFIG_VP9_ENCODER
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
// C functions
|
// C functions
|
||||||
|
|
||||||
#if CONFIG_VP9_ENCODER
|
#if CONFIG_VP9_ENCODER
|
||||||
const ConsistencyParam c_vp9_tests[] = {
|
const ConsistencyParam c_vp9_tests[] = {
|
||||||
make_tuple(320, 240), make_tuple(318, 242), make_tuple(318, 238),
|
make_tuple(320, 240), make_tuple(318, 242), make_tuple(318, 238)
|
||||||
};
|
};
|
||||||
INSTANTIATE_TEST_CASE_P(C, ConsistencyVP9Test,
|
INSTANTIATE_TEST_CASE_P(C, ConsistencyVP9Test,
|
||||||
::testing::ValuesIn(c_vp9_tests));
|
::testing::ValuesIn(c_vp9_tests));
|
||||||
|
@ -25,6 +25,7 @@
|
|||||||
#include "vpx_dsp/vpx_filter.h"
|
#include "vpx_dsp/vpx_filter.h"
|
||||||
#include "vpx_mem/vpx_mem.h"
|
#include "vpx_mem/vpx_mem.h"
|
||||||
#include "vpx_ports/mem.h"
|
#include "vpx_ports/mem.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
@ -32,9 +33,9 @@ static const unsigned int kMaxDimension = 64;
|
|||||||
|
|
||||||
typedef void (*ConvolveFunc)(const uint8_t *src, ptrdiff_t src_stride,
|
typedef void (*ConvolveFunc)(const uint8_t *src, ptrdiff_t src_stride,
|
||||||
uint8_t *dst, ptrdiff_t dst_stride,
|
uint8_t *dst, ptrdiff_t dst_stride,
|
||||||
const int16_t *filter_x, int filter_x_stride,
|
const InterpKernel *filter, int x0_q4,
|
||||||
const int16_t *filter_y, int filter_y_stride,
|
int x_step_q4, int y0_q4, int y_step_q4, int w,
|
||||||
int w, int h);
|
int h);
|
||||||
|
|
||||||
typedef void (*WrapperFilterBlock2d8Func)(
|
typedef void (*WrapperFilterBlock2d8Func)(
|
||||||
const uint8_t *src_ptr, const unsigned int src_stride,
|
const uint8_t *src_ptr, const unsigned int src_stride,
|
||||||
@ -76,7 +77,7 @@ struct ConvolveFunctions {
|
|||||||
int use_highbd_; // 0 if high bitdepth not used, else the actual bit depth.
|
int use_highbd_; // 0 if high bitdepth not used, else the actual bit depth.
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef std::tr1::tuple<int, int, const ConvolveFunctions *> ConvolveParam;
|
typedef ::testing::tuple<int, int, const ConvolveFunctions *> ConvolveParam;
|
||||||
|
|
||||||
#define ALL_SIZES(convolve_fn) \
|
#define ALL_SIZES(convolve_fn) \
|
||||||
make_tuple(4, 4, &convolve_fn), make_tuple(8, 4, &convolve_fn), \
|
make_tuple(4, 4, &convolve_fn), make_tuple(8, 4, &convolve_fn), \
|
||||||
@ -300,9 +301,9 @@ void wrapper_filter_average_block2d_8_c(
|
|||||||
filter_average_block2d_8_c(src_ptr, src_stride, hfilter, vfilter, dst_ptr,
|
filter_average_block2d_8_c(src_ptr, src_stride, hfilter, vfilter, dst_ptr,
|
||||||
dst_stride, output_width, output_height);
|
dst_stride, output_width, output_height);
|
||||||
} else {
|
} else {
|
||||||
highbd_filter_average_block2d_8_c(CONVERT_TO_SHORTPTR(src_ptr), src_stride,
|
highbd_filter_average_block2d_8_c(CAST_TO_SHORTPTR(src_ptr), src_stride,
|
||||||
hfilter, vfilter,
|
hfilter, vfilter,
|
||||||
CONVERT_TO_SHORTPTR(dst_ptr), dst_stride,
|
CAST_TO_SHORTPTR(dst_ptr), dst_stride,
|
||||||
output_width, output_height, use_highbd);
|
output_width, output_height, use_highbd);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
@ -323,8 +324,8 @@ void wrapper_filter_block2d_8_c(const uint8_t *src_ptr,
|
|||||||
filter_block2d_8_c(src_ptr, src_stride, hfilter, vfilter, dst_ptr,
|
filter_block2d_8_c(src_ptr, src_stride, hfilter, vfilter, dst_ptr,
|
||||||
dst_stride, output_width, output_height);
|
dst_stride, output_width, output_height);
|
||||||
} else {
|
} else {
|
||||||
highbd_filter_block2d_8_c(CONVERT_TO_SHORTPTR(src_ptr), src_stride, hfilter,
|
highbd_filter_block2d_8_c(CAST_TO_SHORTPTR(src_ptr), src_stride, hfilter,
|
||||||
vfilter, CONVERT_TO_SHORTPTR(dst_ptr), dst_stride,
|
vfilter, CAST_TO_SHORTPTR(dst_ptr), dst_stride,
|
||||||
output_width, output_height, use_highbd);
|
output_width, output_height, use_highbd);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
@ -449,7 +450,9 @@ class ConvolveTest : public ::testing::TestWithParam<ConvolveParam> {
|
|||||||
|
|
||||||
void CheckGuardBlocks() {
|
void CheckGuardBlocks() {
|
||||||
for (int i = 0; i < kOutputBufferSize; ++i) {
|
for (int i = 0; i < kOutputBufferSize; ++i) {
|
||||||
if (IsIndexInBorder(i)) EXPECT_EQ(255, output_[i]);
|
if (IsIndexInBorder(i)) {
|
||||||
|
EXPECT_EQ(255, output_[i]);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -459,7 +462,7 @@ class ConvolveTest : public ::testing::TestWithParam<ConvolveParam> {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
return input_ + offset;
|
return input_ + offset;
|
||||||
} else {
|
} else {
|
||||||
return CONVERT_TO_BYTEPTR(input16_) + offset;
|
return CAST_TO_BYTEPTR(input16_ + offset);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
return input_ + offset;
|
return input_ + offset;
|
||||||
@ -472,7 +475,7 @@ class ConvolveTest : public ::testing::TestWithParam<ConvolveParam> {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
return output_ + offset;
|
return output_ + offset;
|
||||||
} else {
|
} else {
|
||||||
return CONVERT_TO_BYTEPTR(output16_) + offset;
|
return CAST_TO_BYTEPTR(output16_ + offset);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
return output_ + offset;
|
return output_ + offset;
|
||||||
@ -485,7 +488,7 @@ class ConvolveTest : public ::testing::TestWithParam<ConvolveParam> {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
return output_ref_ + offset;
|
return output_ref_ + offset;
|
||||||
} else {
|
} else {
|
||||||
return CONVERT_TO_BYTEPTR(output16_ref_) + offset;
|
return CAST_TO_BYTEPTR(output16_ref_ + offset);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
return output_ref_ + offset;
|
return output_ref_ + offset;
|
||||||
@ -497,7 +500,7 @@ class ConvolveTest : public ::testing::TestWithParam<ConvolveParam> {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
return list[index];
|
return list[index];
|
||||||
} else {
|
} else {
|
||||||
return CONVERT_TO_SHORTPTR(list)[index];
|
return CAST_TO_SHORTPTR(list)[index];
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
return list[index];
|
return list[index];
|
||||||
@ -509,7 +512,7 @@ class ConvolveTest : public ::testing::TestWithParam<ConvolveParam> {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
list[index] = (uint8_t)val;
|
list[index] = (uint8_t)val;
|
||||||
} else {
|
} else {
|
||||||
CONVERT_TO_SHORTPTR(list)[index] = val;
|
CAST_TO_SHORTPTR(list)[index] = val;
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
list[index] = (uint8_t)val;
|
list[index] = (uint8_t)val;
|
||||||
@ -539,12 +542,167 @@ uint16_t *ConvolveTest::output16_ref_ = NULL;
|
|||||||
|
|
||||||
TEST_P(ConvolveTest, GuardBlocks) { CheckGuardBlocks(); }
|
TEST_P(ConvolveTest, GuardBlocks) { CheckGuardBlocks(); }
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_Copy_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->copy_[0](in, kInputStride, out, kOutputStride, NULL, 0, 0, 0, 0,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve_copy_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_Avg_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->copy_[1](in, kInputStride, out, kOutputStride, NULL, 0, 0, 0, 0,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve_avg_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_Scale_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const InterpKernel *const eighttap = vp9_filter_kernels[EIGHTTAP];
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
SetConstantInput(127);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->shv8_[0](in, kInputStride, out, kOutputStride, eighttap, 8, 16, 8, 16,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve_scale_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_8Tap_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const InterpKernel *const eighttap = vp9_filter_kernels[EIGHTTAP_SHARP];
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
SetConstantInput(127);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->hv8_[0](in, kInputStride, out, kOutputStride, eighttap, 8, 16, 8, 16,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve8_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_8Tap_Horiz_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const InterpKernel *const eighttap = vp9_filter_kernels[EIGHTTAP_SHARP];
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
SetConstantInput(127);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->h8_[0](in, kInputStride, out, kOutputStride, eighttap, 8, 16, 8, 16,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve8_horiz_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_8Tap_Vert_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const InterpKernel *const eighttap = vp9_filter_kernels[EIGHTTAP_SHARP];
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
SetConstantInput(127);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->v8_[0](in, kInputStride, out, kOutputStride, eighttap, 8, 16, 8, 16,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve8_vert_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(ConvolveTest, DISABLED_8Tap_Avg_Speed) {
|
||||||
|
const uint8_t *const in = input();
|
||||||
|
uint8_t *const out = output();
|
||||||
|
const InterpKernel *const eighttap = vp9_filter_kernels[EIGHTTAP_SHARP];
|
||||||
|
const int kNumTests = 5000000;
|
||||||
|
const int width = Width();
|
||||||
|
const int height = Height();
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
SetConstantInput(127);
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int n = 0; n < kNumTests; ++n) {
|
||||||
|
UUT_->hv8_[1](in, kInputStride, out, kOutputStride, eighttap, 8, 16, 8, 16,
|
||||||
|
width, height);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("convolve8_avg_%dx%d_%d: %d us\n", width, height,
|
||||||
|
UUT_->use_highbd_ ? UUT_->use_highbd_ : 8, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
TEST_P(ConvolveTest, Copy) {
|
TEST_P(ConvolveTest, Copy) {
|
||||||
uint8_t *const in = input();
|
uint8_t *const in = input();
|
||||||
uint8_t *const out = output();
|
uint8_t *const out = output();
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->copy_[0](in, kInputStride, out, kOutputStride,
|
ASM_REGISTER_STATE_CHECK(UUT_->copy_[0](in, kInputStride, out, kOutputStride,
|
||||||
NULL, 0, NULL, 0, Width(), Height()));
|
NULL, 0, 0, 0, 0, Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
@ -563,7 +721,7 @@ TEST_P(ConvolveTest, Avg) {
|
|||||||
CopyOutputToRef();
|
CopyOutputToRef();
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->copy_[1](in, kInputStride, out, kOutputStride,
|
ASM_REGISTER_STATE_CHECK(UUT_->copy_[1](in, kInputStride, out, kOutputStride,
|
||||||
NULL, 0, NULL, 0, Width(), Height()));
|
NULL, 0, 0, 0, 0, Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
@ -580,12 +738,10 @@ TEST_P(ConvolveTest, Avg) {
|
|||||||
TEST_P(ConvolveTest, CopyHoriz) {
|
TEST_P(ConvolveTest, CopyHoriz) {
|
||||||
uint8_t *const in = input();
|
uint8_t *const in = input();
|
||||||
uint8_t *const out = output();
|
uint8_t *const out = output();
|
||||||
DECLARE_ALIGNED(256, const int16_t,
|
|
||||||
filter8[8]) = { 0, 0, 0, 128, 0, 0, 0, 0 };
|
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->sh8_[0](in, kInputStride, out, kOutputStride,
|
ASM_REGISTER_STATE_CHECK(UUT_->sh8_[0](in, kInputStride, out, kOutputStride,
|
||||||
filter8, 16, filter8, 16, Width(),
|
vp9_filter_kernels[0], 0, 16, 0, 16,
|
||||||
Height()));
|
Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
@ -600,12 +756,10 @@ TEST_P(ConvolveTest, CopyHoriz) {
|
|||||||
TEST_P(ConvolveTest, CopyVert) {
|
TEST_P(ConvolveTest, CopyVert) {
|
||||||
uint8_t *const in = input();
|
uint8_t *const in = input();
|
||||||
uint8_t *const out = output();
|
uint8_t *const out = output();
|
||||||
DECLARE_ALIGNED(256, const int16_t,
|
|
||||||
filter8[8]) = { 0, 0, 0, 128, 0, 0, 0, 0 };
|
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->sv8_[0](in, kInputStride, out, kOutputStride,
|
ASM_REGISTER_STATE_CHECK(UUT_->sv8_[0](in, kInputStride, out, kOutputStride,
|
||||||
filter8, 16, filter8, 16, Width(),
|
vp9_filter_kernels[0], 0, 16, 0, 16,
|
||||||
Height()));
|
Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
@ -620,12 +774,10 @@ TEST_P(ConvolveTest, CopyVert) {
|
|||||||
TEST_P(ConvolveTest, Copy2D) {
|
TEST_P(ConvolveTest, Copy2D) {
|
||||||
uint8_t *const in = input();
|
uint8_t *const in = input();
|
||||||
uint8_t *const out = output();
|
uint8_t *const out = output();
|
||||||
DECLARE_ALIGNED(256, const int16_t,
|
|
||||||
filter8[8]) = { 0, 0, 0, 128, 0, 0, 0, 0 };
|
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->shv8_[0](in, kInputStride, out, kOutputStride,
|
ASM_REGISTER_STATE_CHECK(UUT_->shv8_[0](in, kInputStride, out, kOutputStride,
|
||||||
filter8, 16, filter8, 16, Width(),
|
vp9_filter_kernels[0], 0, 16, 0, 16,
|
||||||
Height()));
|
Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
@ -661,7 +813,6 @@ TEST(ConvolveTest, FiltersWontSaturateWhenAddedPairwise) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const int16_t kInvalidFilter[8] = { 0 };
|
|
||||||
const WrapperFilterBlock2d8Func wrapper_filter_block2d_8[2] = {
|
const WrapperFilterBlock2d8Func wrapper_filter_block2d_8[2] = {
|
||||||
wrapper_filter_block2d_8_c, wrapper_filter_average_block2d_8_c
|
wrapper_filter_block2d_8_c, wrapper_filter_average_block2d_8_c
|
||||||
};
|
};
|
||||||
@ -677,7 +828,7 @@ TEST_P(ConvolveTest, MatchesReferenceSubpixelFilter) {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
ref = ref8;
|
ref = ref8;
|
||||||
} else {
|
} else {
|
||||||
ref = CONVERT_TO_BYTEPTR(ref16);
|
ref = CAST_TO_BYTEPTR(ref16);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
uint8_t ref[kOutputStride * kMaxDimension];
|
uint8_t ref[kOutputStride * kMaxDimension];
|
||||||
@ -714,21 +865,21 @@ TEST_P(ConvolveTest, MatchesReferenceSubpixelFilter) {
|
|||||||
Width(), Height(), UUT_->use_highbd_);
|
Width(), Height(), UUT_->use_highbd_);
|
||||||
|
|
||||||
if (filter_x && filter_y)
|
if (filter_x && filter_y)
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->hv8_[i](
|
ASM_REGISTER_STATE_CHECK(
|
||||||
in, kInputStride, out, kOutputStride, filters[filter_x], 16,
|
UUT_->hv8_[i](in, kInputStride, out, kOutputStride, filters,
|
||||||
filters[filter_y], 16, Width(), Height()));
|
filter_x, 16, filter_y, 16, Width(), Height()));
|
||||||
else if (filter_y)
|
else if (filter_y)
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->v8_[i](
|
ASM_REGISTER_STATE_CHECK(
|
||||||
in, kInputStride, out, kOutputStride, kInvalidFilter, 16,
|
UUT_->v8_[i](in, kInputStride, out, kOutputStride, filters, 0,
|
||||||
filters[filter_y], 16, Width(), Height()));
|
16, filter_y, 16, Width(), Height()));
|
||||||
else if (filter_x)
|
else if (filter_x)
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->h8_[i](
|
ASM_REGISTER_STATE_CHECK(
|
||||||
in, kInputStride, out, kOutputStride, filters[filter_x], 16,
|
UUT_->h8_[i](in, kInputStride, out, kOutputStride, filters,
|
||||||
kInvalidFilter, 16, Width(), Height()));
|
filter_x, 16, 0, 16, Width(), Height()));
|
||||||
else
|
else
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->copy_[i](
|
ASM_REGISTER_STATE_CHECK(UUT_->copy_[i](in, kInputStride, out,
|
||||||
in, kInputStride, out, kOutputStride, kInvalidFilter, 0,
|
kOutputStride, NULL, 0, 0,
|
||||||
kInvalidFilter, 0, Width(), Height()));
|
0, 0, Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
@ -756,7 +907,7 @@ TEST_P(ConvolveTest, FilterExtremes) {
|
|||||||
if (UUT_->use_highbd_ == 0) {
|
if (UUT_->use_highbd_ == 0) {
|
||||||
ref = ref8;
|
ref = ref8;
|
||||||
} else {
|
} else {
|
||||||
ref = CONVERT_TO_BYTEPTR(ref16);
|
ref = CAST_TO_BYTEPTR(ref16);
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
uint8_t ref[kOutputStride * kMaxDimension];
|
uint8_t ref[kOutputStride * kMaxDimension];
|
||||||
@ -812,21 +963,21 @@ TEST_P(ConvolveTest, FilterExtremes) {
|
|||||||
filters[filter_y], ref, kOutputStride,
|
filters[filter_y], ref, kOutputStride,
|
||||||
Width(), Height(), UUT_->use_highbd_);
|
Width(), Height(), UUT_->use_highbd_);
|
||||||
if (filter_x && filter_y)
|
if (filter_x && filter_y)
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->hv8_[0](
|
ASM_REGISTER_STATE_CHECK(
|
||||||
in, kInputStride, out, kOutputStride, filters[filter_x], 16,
|
UUT_->hv8_[0](in, kInputStride, out, kOutputStride, filters,
|
||||||
filters[filter_y], 16, Width(), Height()));
|
filter_x, 16, filter_y, 16, Width(), Height()));
|
||||||
else if (filter_y)
|
else if (filter_y)
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->v8_[0](
|
ASM_REGISTER_STATE_CHECK(
|
||||||
in, kInputStride, out, kOutputStride, kInvalidFilter, 16,
|
UUT_->v8_[0](in, kInputStride, out, kOutputStride, filters, 0,
|
||||||
filters[filter_y], 16, Width(), Height()));
|
16, filter_y, 16, Width(), Height()));
|
||||||
else if (filter_x)
|
else if (filter_x)
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->h8_[0](
|
ASM_REGISTER_STATE_CHECK(
|
||||||
in, kInputStride, out, kOutputStride, filters[filter_x], 16,
|
UUT_->h8_[0](in, kInputStride, out, kOutputStride, filters,
|
||||||
kInvalidFilter, 16, Width(), Height()));
|
filter_x, 16, 0, 16, Width(), Height()));
|
||||||
else
|
else
|
||||||
ASM_REGISTER_STATE_CHECK(UUT_->copy_[0](
|
ASM_REGISTER_STATE_CHECK(UUT_->copy_[0](in, kInputStride, out,
|
||||||
in, kInputStride, out, kOutputStride, kInvalidFilter, 0,
|
kOutputStride, NULL, 0, 0,
|
||||||
kInvalidFilter, 0, Width(), Height()));
|
0, 0, Width(), Height()));
|
||||||
|
|
||||||
for (int y = 0; y < Height(); ++y) {
|
for (int y = 0; y < Height(); ++y) {
|
||||||
for (int x = 0; x < Width(); ++x)
|
for (int x = 0; x < Width(); ++x)
|
||||||
@ -845,25 +996,40 @@ TEST_P(ConvolveTest, FilterExtremes) {
|
|||||||
|
|
||||||
/* This test exercises that enough rows and columns are filtered with every
|
/* This test exercises that enough rows and columns are filtered with every
|
||||||
possible initial fractional positions and scaling steps. */
|
possible initial fractional positions and scaling steps. */
|
||||||
|
#if !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
static const ConvolveFunc scaled_2d_c_funcs[2] = { vpx_scaled_2d_c,
|
||||||
|
vpx_scaled_avg_2d_c };
|
||||||
|
|
||||||
TEST_P(ConvolveTest, CheckScalingFiltering) {
|
TEST_P(ConvolveTest, CheckScalingFiltering) {
|
||||||
uint8_t *const in = input();
|
uint8_t *const in = input();
|
||||||
uint8_t *const out = output();
|
uint8_t *const out = output();
|
||||||
const InterpKernel *const eighttap = vp9_filter_kernels[EIGHTTAP];
|
uint8_t ref[kOutputStride * kMaxDimension];
|
||||||
|
|
||||||
SetConstantInput(127);
|
::libvpx_test::ACMRandom prng;
|
||||||
|
for (int y = 0; y < Height(); ++y) {
|
||||||
|
for (int x = 0; x < Width(); ++x) {
|
||||||
|
const uint16_t r = prng.Rand8Extremes();
|
||||||
|
assign_val(in, y * kInputStride + x, r);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < 2; ++i) {
|
||||||
|
for (INTERP_FILTER filter_type = 0; filter_type < 4; ++filter_type) {
|
||||||
|
const InterpKernel *const eighttap = vp9_filter_kernels[filter_type];
|
||||||
for (int frac = 0; frac < 16; ++frac) {
|
for (int frac = 0; frac < 16; ++frac) {
|
||||||
for (int step = 1; step <= 32; ++step) {
|
for (int step = 1; step <= 32; ++step) {
|
||||||
/* Test the horizontal and vertical filters in combination. */
|
/* Test the horizontal and vertical filters in combination. */
|
||||||
|
scaled_2d_c_funcs[i](in, kInputStride, ref, kOutputStride, eighttap,
|
||||||
|
frac, step, frac, step, Width(), Height());
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
UUT_->shv8_[0](in, kInputStride, out, kOutputStride, eighttap[frac],
|
UUT_->shv8_[i](in, kInputStride, out, kOutputStride, eighttap,
|
||||||
step, eighttap[frac], step, Width(), Height()));
|
frac, step, frac, step, Width(), Height()));
|
||||||
|
|
||||||
CheckGuardBlocks();
|
CheckGuardBlocks();
|
||||||
|
|
||||||
for (int y = 0; y < Height(); ++y) {
|
for (int y = 0; y < Height(); ++y) {
|
||||||
for (int x = 0; x < Width(); ++x) {
|
for (int x = 0; x < Width(); ++x) {
|
||||||
ASSERT_EQ(lookup(in, y * kInputStride + x),
|
ASSERT_EQ(lookup(ref, y * kOutputStride + x),
|
||||||
lookup(out, y * kOutputStride + x))
|
lookup(out, y * kOutputStride + x))
|
||||||
<< "x == " << x << ", y == " << y << ", frac == " << frac
|
<< "x == " << x << ", y == " << y << ", frac == " << frac
|
||||||
<< ", step == " << step;
|
<< ", step == " << step;
|
||||||
@ -872,17 +1038,21 @@ TEST_P(ConvolveTest, CheckScalingFiltering) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
#define WRAP(func, bd) \
|
#define WRAP(func, bd) \
|
||||||
void wrap_##func##_##bd( \
|
void wrap_##func##_##bd( \
|
||||||
const uint8_t *src, ptrdiff_t src_stride, uint8_t *dst, \
|
const uint8_t *src, ptrdiff_t src_stride, uint8_t *dst, \
|
||||||
ptrdiff_t dst_stride, const int16_t *filter_x, int filter_x_stride, \
|
ptrdiff_t dst_stride, const InterpKernel *filter, int x0_q4, \
|
||||||
const int16_t *filter_y, int filter_y_stride, int w, int h) { \
|
int x_step_q4, int y0_q4, int y_step_q4, int w, int h) { \
|
||||||
vpx_highbd_##func(src, src_stride, dst, dst_stride, filter_x, \
|
vpx_highbd_##func(reinterpret_cast<const uint16_t *>(src), src_stride, \
|
||||||
filter_x_stride, filter_y, filter_y_stride, w, h, bd); \
|
reinterpret_cast<uint16_t *>(dst), dst_stride, filter, \
|
||||||
|
x0_q4, x_step_q4, y0_q4, y_step_q4, w, h, bd); \
|
||||||
}
|
}
|
||||||
|
|
||||||
#if HAVE_SSE2 && ARCH_X86_64
|
#if HAVE_SSE2 && ARCH_X86_64
|
||||||
@ -912,6 +1082,35 @@ WRAP(convolve8_sse2, 12)
|
|||||||
WRAP(convolve8_avg_sse2, 12)
|
WRAP(convolve8_avg_sse2, 12)
|
||||||
#endif // HAVE_SSE2 && ARCH_X86_64
|
#endif // HAVE_SSE2 && ARCH_X86_64
|
||||||
|
|
||||||
|
#if HAVE_AVX2
|
||||||
|
WRAP(convolve_copy_avx2, 8)
|
||||||
|
WRAP(convolve_avg_avx2, 8)
|
||||||
|
WRAP(convolve8_horiz_avx2, 8)
|
||||||
|
WRAP(convolve8_avg_horiz_avx2, 8)
|
||||||
|
WRAP(convolve8_vert_avx2, 8)
|
||||||
|
WRAP(convolve8_avg_vert_avx2, 8)
|
||||||
|
WRAP(convolve8_avx2, 8)
|
||||||
|
WRAP(convolve8_avg_avx2, 8)
|
||||||
|
|
||||||
|
WRAP(convolve_copy_avx2, 10)
|
||||||
|
WRAP(convolve_avg_avx2, 10)
|
||||||
|
WRAP(convolve8_avx2, 10)
|
||||||
|
WRAP(convolve8_horiz_avx2, 10)
|
||||||
|
WRAP(convolve8_vert_avx2, 10)
|
||||||
|
WRAP(convolve8_avg_avx2, 10)
|
||||||
|
WRAP(convolve8_avg_horiz_avx2, 10)
|
||||||
|
WRAP(convolve8_avg_vert_avx2, 10)
|
||||||
|
|
||||||
|
WRAP(convolve_copy_avx2, 12)
|
||||||
|
WRAP(convolve_avg_avx2, 12)
|
||||||
|
WRAP(convolve8_avx2, 12)
|
||||||
|
WRAP(convolve8_horiz_avx2, 12)
|
||||||
|
WRAP(convolve8_vert_avx2, 12)
|
||||||
|
WRAP(convolve8_avg_avx2, 12)
|
||||||
|
WRAP(convolve8_avg_horiz_avx2, 12)
|
||||||
|
WRAP(convolve8_avg_vert_avx2, 12)
|
||||||
|
#endif // HAVE_AVX2
|
||||||
|
|
||||||
#if HAVE_NEON
|
#if HAVE_NEON
|
||||||
WRAP(convolve_copy_neon, 8)
|
WRAP(convolve_copy_neon, 8)
|
||||||
WRAP(convolve_avg_neon, 8)
|
WRAP(convolve_avg_neon, 8)
|
||||||
@ -1057,18 +1256,48 @@ INSTANTIATE_TEST_CASE_P(SSSE3, ConvolveTest,
|
|||||||
::testing::ValuesIn(kArrayConvolve8_ssse3));
|
::testing::ValuesIn(kArrayConvolve8_ssse3));
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if HAVE_AVX2 && HAVE_SSSE3
|
#if HAVE_AVX2
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
const ConvolveFunctions convolve8_avx2(
|
||||||
|
wrap_convolve_copy_avx2_8, wrap_convolve_avg_avx2_8,
|
||||||
|
wrap_convolve8_horiz_avx2_8, wrap_convolve8_avg_horiz_avx2_8,
|
||||||
|
wrap_convolve8_vert_avx2_8, wrap_convolve8_avg_vert_avx2_8,
|
||||||
|
wrap_convolve8_avx2_8, wrap_convolve8_avg_avx2_8, wrap_convolve8_horiz_c_8,
|
||||||
|
wrap_convolve8_avg_horiz_c_8, wrap_convolve8_vert_c_8,
|
||||||
|
wrap_convolve8_avg_vert_c_8, wrap_convolve8_c_8, wrap_convolve8_avg_c_8, 8);
|
||||||
|
const ConvolveFunctions convolve10_avx2(
|
||||||
|
wrap_convolve_copy_avx2_10, wrap_convolve_avg_avx2_10,
|
||||||
|
wrap_convolve8_horiz_avx2_10, wrap_convolve8_avg_horiz_avx2_10,
|
||||||
|
wrap_convolve8_vert_avx2_10, wrap_convolve8_avg_vert_avx2_10,
|
||||||
|
wrap_convolve8_avx2_10, wrap_convolve8_avg_avx2_10,
|
||||||
|
wrap_convolve8_horiz_c_10, wrap_convolve8_avg_horiz_c_10,
|
||||||
|
wrap_convolve8_vert_c_10, wrap_convolve8_avg_vert_c_10, wrap_convolve8_c_10,
|
||||||
|
wrap_convolve8_avg_c_10, 10);
|
||||||
|
const ConvolveFunctions convolve12_avx2(
|
||||||
|
wrap_convolve_copy_avx2_12, wrap_convolve_avg_avx2_12,
|
||||||
|
wrap_convolve8_horiz_avx2_12, wrap_convolve8_avg_horiz_avx2_12,
|
||||||
|
wrap_convolve8_vert_avx2_12, wrap_convolve8_avg_vert_avx2_12,
|
||||||
|
wrap_convolve8_avx2_12, wrap_convolve8_avg_avx2_12,
|
||||||
|
wrap_convolve8_horiz_c_12, wrap_convolve8_avg_horiz_c_12,
|
||||||
|
wrap_convolve8_vert_c_12, wrap_convolve8_avg_vert_c_12, wrap_convolve8_c_12,
|
||||||
|
wrap_convolve8_avg_c_12, 12);
|
||||||
|
const ConvolveParam kArrayConvolve8_avx2[] = { ALL_SIZES(convolve8_avx2),
|
||||||
|
ALL_SIZES(convolve10_avx2),
|
||||||
|
ALL_SIZES(convolve12_avx2) };
|
||||||
|
INSTANTIATE_TEST_CASE_P(AVX2, ConvolveTest,
|
||||||
|
::testing::ValuesIn(kArrayConvolve8_avx2));
|
||||||
|
#else // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
const ConvolveFunctions convolve8_avx2(
|
const ConvolveFunctions convolve8_avx2(
|
||||||
vpx_convolve_copy_c, vpx_convolve_avg_c, vpx_convolve8_horiz_avx2,
|
vpx_convolve_copy_c, vpx_convolve_avg_c, vpx_convolve8_horiz_avx2,
|
||||||
vpx_convolve8_avg_horiz_ssse3, vpx_convolve8_vert_avx2,
|
vpx_convolve8_avg_horiz_avx2, vpx_convolve8_vert_avx2,
|
||||||
vpx_convolve8_avg_vert_ssse3, vpx_convolve8_avx2, vpx_convolve8_avg_ssse3,
|
vpx_convolve8_avg_vert_avx2, vpx_convolve8_avx2, vpx_convolve8_avg_avx2,
|
||||||
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
||||||
vpx_scaled_avg_vert_c, vpx_scaled_2d_c, vpx_scaled_avg_2d_c, 0);
|
vpx_scaled_avg_vert_c, vpx_scaled_2d_c, vpx_scaled_avg_2d_c, 0);
|
||||||
|
|
||||||
const ConvolveParam kArrayConvolve8_avx2[] = { ALL_SIZES(convolve8_avx2) };
|
const ConvolveParam kArrayConvolve8_avx2[] = { ALL_SIZES(convolve8_avx2) };
|
||||||
INSTANTIATE_TEST_CASE_P(AVX2, ConvolveTest,
|
INSTANTIATE_TEST_CASE_P(AVX2, ConvolveTest,
|
||||||
::testing::ValuesIn(kArrayConvolve8_avx2));
|
::testing::ValuesIn(kArrayConvolve8_avx2));
|
||||||
#endif // HAVE_AVX2 && HAVE_SSSE3
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_AVX2
|
||||||
|
|
||||||
#if HAVE_NEON
|
#if HAVE_NEON
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
@ -1105,7 +1334,7 @@ const ConvolveFunctions convolve8_neon(
|
|||||||
vpx_convolve8_avg_horiz_neon, vpx_convolve8_vert_neon,
|
vpx_convolve8_avg_horiz_neon, vpx_convolve8_vert_neon,
|
||||||
vpx_convolve8_avg_vert_neon, vpx_convolve8_neon, vpx_convolve8_avg_neon,
|
vpx_convolve8_avg_vert_neon, vpx_convolve8_neon, vpx_convolve8_avg_neon,
|
||||||
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
||||||
vpx_scaled_avg_vert_c, vpx_scaled_2d_c, vpx_scaled_avg_2d_c, 0);
|
vpx_scaled_avg_vert_c, vpx_scaled_2d_neon, vpx_scaled_avg_2d_c, 0);
|
||||||
|
|
||||||
const ConvolveParam kArrayConvolve_neon[] = { ALL_SIZES(convolve8_neon) };
|
const ConvolveParam kArrayConvolve_neon[] = { ALL_SIZES(convolve8_neon) };
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
@ -1132,10 +1361,34 @@ const ConvolveFunctions convolve8_msa(
|
|||||||
vpx_convolve8_avg_horiz_msa, vpx_convolve8_vert_msa,
|
vpx_convolve8_avg_horiz_msa, vpx_convolve8_vert_msa,
|
||||||
vpx_convolve8_avg_vert_msa, vpx_convolve8_msa, vpx_convolve8_avg_msa,
|
vpx_convolve8_avg_vert_msa, vpx_convolve8_msa, vpx_convolve8_avg_msa,
|
||||||
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
||||||
vpx_scaled_avg_vert_c, vpx_scaled_2d_c, vpx_scaled_avg_2d_c, 0);
|
vpx_scaled_avg_vert_c, vpx_scaled_2d_msa, vpx_scaled_avg_2d_c, 0);
|
||||||
|
|
||||||
const ConvolveParam kArrayConvolve8_msa[] = { ALL_SIZES(convolve8_msa) };
|
const ConvolveParam kArrayConvolve8_msa[] = { ALL_SIZES(convolve8_msa) };
|
||||||
INSTANTIATE_TEST_CASE_P(MSA, ConvolveTest,
|
INSTANTIATE_TEST_CASE_P(MSA, ConvolveTest,
|
||||||
::testing::ValuesIn(kArrayConvolve8_msa));
|
::testing::ValuesIn(kArrayConvolve8_msa));
|
||||||
#endif // HAVE_MSA
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
|
#if HAVE_VSX
|
||||||
|
const ConvolveFunctions convolve8_vsx(
|
||||||
|
vpx_convolve_copy_vsx, vpx_convolve_avg_vsx, vpx_convolve8_horiz_vsx,
|
||||||
|
vpx_convolve8_avg_horiz_vsx, vpx_convolve8_vert_vsx,
|
||||||
|
vpx_convolve8_avg_vert_vsx, vpx_convolve8_vsx, vpx_convolve8_avg_vsx,
|
||||||
|
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
||||||
|
vpx_scaled_avg_vert_c, vpx_scaled_2d_c, vpx_scaled_avg_2d_c, 0);
|
||||||
|
const ConvolveParam kArrayConvolve_vsx[] = { ALL_SIZES(convolve8_vsx) };
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, ConvolveTest,
|
||||||
|
::testing::ValuesIn(kArrayConvolve_vsx));
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
|
||||||
|
#if HAVE_MMI
|
||||||
|
const ConvolveFunctions convolve8_mmi(
|
||||||
|
vpx_convolve_copy_c, vpx_convolve_avg_c, vpx_convolve8_horiz_mmi,
|
||||||
|
vpx_convolve8_avg_horiz_c, vpx_convolve8_vert_mmi,
|
||||||
|
vpx_convolve8_avg_vert_mmi, vpx_convolve8_mmi, vpx_convolve8_avg_mmi,
|
||||||
|
vpx_scaled_horiz_c, vpx_scaled_avg_horiz_c, vpx_scaled_vert_c,
|
||||||
|
vpx_scaled_avg_vert_c, vpx_scaled_2d_c, vpx_scaled_avg_2d_c, 0);
|
||||||
|
const ConvolveParam kArrayConvolve_mmi[] = { ALL_SIZES(convolve8_mmi) };
|
||||||
|
INSTANTIATE_TEST_CASE_P(MMI, ConvolveTest,
|
||||||
|
::testing::ValuesIn(kArrayConvolve_mmi));
|
||||||
|
#endif // HAVE_MMI
|
||||||
} // namespace
|
} // namespace
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -229,9 +229,10 @@ typedef void (*FhtFunc)(const int16_t *in, tran_low_t *out, int stride,
|
|||||||
typedef void (*IhtFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
typedef void (*IhtFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
int tx_type);
|
int tx_type);
|
||||||
|
|
||||||
typedef std::tr1::tuple<FdctFunc, IdctFunc, int, vpx_bit_depth_t> Dct16x16Param;
|
typedef ::testing::tuple<FdctFunc, IdctFunc, int, vpx_bit_depth_t>
|
||||||
typedef std::tr1::tuple<FhtFunc, IhtFunc, int, vpx_bit_depth_t> Ht16x16Param;
|
Dct16x16Param;
|
||||||
typedef std::tr1::tuple<IdctFunc, IdctFunc, int, vpx_bit_depth_t>
|
typedef ::testing::tuple<FhtFunc, IhtFunc, int, vpx_bit_depth_t> Ht16x16Param;
|
||||||
|
typedef ::testing::tuple<IdctFunc, IdctFunc, int, vpx_bit_depth_t>
|
||||||
Idct16x16Param;
|
Idct16x16Param;
|
||||||
|
|
||||||
void fdct16x16_ref(const int16_t *in, tran_low_t *out, int stride,
|
void fdct16x16_ref(const int16_t *in, tran_low_t *out, int stride,
|
||||||
@ -255,11 +256,11 @@ void iht16x16_ref(const tran_low_t *in, uint8_t *dest, int stride,
|
|||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
void idct16x16_10(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_10(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_256_add_c(in, out, stride, 10);
|
vpx_highbd_idct16x16_256_add_c(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_12(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_12(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_256_add_c(in, out, stride, 12);
|
vpx_highbd_idct16x16_256_add_c(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_10_ref(const tran_low_t *in, uint8_t *out, int stride,
|
void idct16x16_10_ref(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
@ -273,36 +274,36 @@ void idct16x16_12_ref(const tran_low_t *in, uint8_t *out, int stride,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void iht16x16_10(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
void iht16x16_10(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
||||||
vp9_highbd_iht16x16_256_add_c(in, out, stride, tx_type, 10);
|
vp9_highbd_iht16x16_256_add_c(in, CAST_TO_SHORTPTR(out), stride, tx_type, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void iht16x16_12(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
void iht16x16_12(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
||||||
vp9_highbd_iht16x16_256_add_c(in, out, stride, tx_type, 12);
|
vp9_highbd_iht16x16_256_add_c(in, CAST_TO_SHORTPTR(out), stride, tx_type, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
void idct16x16_10_add_10_c(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_10_add_10_c(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_10_add_c(in, out, stride, 10);
|
vpx_highbd_idct16x16_10_add_c(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_10_add_12_c(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_10_add_12_c(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_10_add_c(in, out, stride, 12);
|
vpx_highbd_idct16x16_10_add_c(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_256_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_256_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_256_add_sse2(in, out, stride, 10);
|
vpx_highbd_idct16x16_256_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_256_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_256_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_256_add_sse2(in, out, stride, 12);
|
vpx_highbd_idct16x16_256_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_10_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_10_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_10_add_sse2(in, out, stride, 10);
|
vpx_highbd_idct16x16_10_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct16x16_10_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct16x16_10_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct16x16_10_add_sse2(in, out, stride, 12);
|
vpx_highbd_idct16x16_10_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
@ -353,7 +354,7 @@ class Trans16x16TestBase {
|
|||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(test_temp_block, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(test_temp_block, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -475,10 +476,10 @@ class Trans16x16TestBase {
|
|||||||
ASM_REGISTER_STATE_CHECK(RunInvTxfm(output_ref_block, dst, pitch_));
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(output_ref_block, dst, pitch_));
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
inv_txfm_ref(output_ref_block, CONVERT_TO_BYTEPTR(ref16), pitch_,
|
inv_txfm_ref(output_ref_block, CAST_TO_BYTEPTR(ref16), pitch_,
|
||||||
tx_type_);
|
tx_type_);
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(output_ref_block, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(output_ref_block, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
if (bit_depth_ == VPX_BITS_8) {
|
if (bit_depth_ == VPX_BITS_8) {
|
||||||
@ -530,8 +531,7 @@ class Trans16x16TestBase {
|
|||||||
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, 16));
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, 16));
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, CAST_TO_BYTEPTR(dst16), 16));
|
||||||
RunInvTxfm(coeff, CONVERT_TO_BYTEPTR(dst16), 16));
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -543,8 +543,8 @@ class Trans16x16TestBase {
|
|||||||
const uint32_t diff = dst[j] - src[j];
|
const uint32_t diff = dst[j] - src[j];
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
const uint32_t error = diff * diff;
|
const uint32_t error = diff * diff;
|
||||||
EXPECT_GE(1u, error) << "Error: 16x16 IDCT has error " << error
|
EXPECT_GE(1u, error)
|
||||||
<< " at index " << j;
|
<< "Error: 16x16 IDCT has error " << error << " at index " << j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -585,9 +585,9 @@ class Trans16x16TestBase {
|
|||||||
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, pitch_));
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, pitch_));
|
||||||
} else {
|
} else {
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
ref_txfm(coeff, CONVERT_TO_BYTEPTR(ref16), pitch_);
|
ref_txfm(coeff, CAST_TO_BYTEPTR(ref16), pitch_);
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(coeff, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(coeff, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -745,67 +745,7 @@ TEST_P(InvTrans16x16DCT, CompareReference) {
|
|||||||
CompareInvReference(ref_txfm_, thresh_);
|
CompareInvReference(ref_txfm_, thresh_);
|
||||||
}
|
}
|
||||||
|
|
||||||
class PartialTrans16x16Test : public ::testing::TestWithParam<
|
using ::testing::make_tuple;
|
||||||
std::tr1::tuple<FdctFunc, vpx_bit_depth_t> > {
|
|
||||||
public:
|
|
||||||
virtual ~PartialTrans16x16Test() {}
|
|
||||||
virtual void SetUp() {
|
|
||||||
fwd_txfm_ = GET_PARAM(0);
|
|
||||||
bit_depth_ = GET_PARAM(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
|
||||||
|
|
||||||
protected:
|
|
||||||
vpx_bit_depth_t bit_depth_;
|
|
||||||
FdctFunc fwd_txfm_;
|
|
||||||
};
|
|
||||||
|
|
||||||
TEST_P(PartialTrans16x16Test, Extremes) {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int16_t maxval =
|
|
||||||
static_cast<int16_t>(clip_pixel_highbd(1 << 30, bit_depth_));
|
|
||||||
#else
|
|
||||||
const int16_t maxval = 255;
|
|
||||||
#endif
|
|
||||||
const int minval = -maxval;
|
|
||||||
DECLARE_ALIGNED(16, int16_t, input[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output[kNumCoeffs]);
|
|
||||||
|
|
||||||
for (int i = 0; i < kNumCoeffs; ++i) input[i] = maxval;
|
|
||||||
output[0] = 0;
|
|
||||||
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input, output, 16));
|
|
||||||
EXPECT_EQ((maxval * kNumCoeffs) >> 1, output[0]);
|
|
||||||
|
|
||||||
for (int i = 0; i < kNumCoeffs; ++i) input[i] = minval;
|
|
||||||
output[0] = 0;
|
|
||||||
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input, output, 16));
|
|
||||||
EXPECT_EQ((minval * kNumCoeffs) >> 1, output[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_P(PartialTrans16x16Test, Random) {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int16_t maxval =
|
|
||||||
static_cast<int16_t>(clip_pixel_highbd(1 << 30, bit_depth_));
|
|
||||||
#else
|
|
||||||
const int16_t maxval = 255;
|
|
||||||
#endif
|
|
||||||
DECLARE_ALIGNED(16, int16_t, input[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output[kNumCoeffs]);
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
|
|
||||||
int sum = 0;
|
|
||||||
for (int i = 0; i < kNumCoeffs; ++i) {
|
|
||||||
const int val = (i & 1) ? -rnd(maxval + 1) : rnd(maxval + 1);
|
|
||||||
input[i] = val;
|
|
||||||
sum += val;
|
|
||||||
}
|
|
||||||
output[0] = 0;
|
|
||||||
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input, output, 16));
|
|
||||||
EXPECT_EQ(sum >> 1, output[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -837,11 +777,6 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 1, VPX_BITS_8),
|
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 1, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 2, VPX_BITS_8),
|
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 2, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 3, VPX_BITS_8)));
|
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 3, VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
C, PartialTrans16x16Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_highbd_fdct16x16_1_c, VPX_BITS_8),
|
|
||||||
make_tuple(&vpx_highbd_fdct16x16_1_c, VPX_BITS_10),
|
|
||||||
make_tuple(&vpx_highbd_fdct16x16_1_c, VPX_BITS_12)));
|
|
||||||
#else
|
#else
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
C, Trans16x16HT,
|
C, Trans16x16HT,
|
||||||
@ -850,17 +785,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 1, VPX_BITS_8),
|
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 1, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 2, VPX_BITS_8),
|
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 2, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 3, VPX_BITS_8)));
|
make_tuple(&vp9_fht16x16_c, &vp9_iht16x16_256_add_c, 3, VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(C, PartialTrans16x16Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct16x16_1_c,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
#if HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_NEON && !CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
NEON, Trans16x16DCT,
|
NEON, Trans16x16DCT,
|
||||||
::testing::Values(make_tuple(&vpx_fdct16x16_c, &vpx_idct16x16_256_add_neon,
|
::testing::Values(make_tuple(&vpx_fdct16x16_neon,
|
||||||
0, VPX_BITS_8)));
|
&vpx_idct16x16_256_add_neon, 0, VPX_BITS_8)));
|
||||||
#endif
|
#endif // HAVE_NEON && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -877,9 +809,6 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
2, VPX_BITS_8),
|
2, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht16x16_sse2, &vp9_iht16x16_256_add_sse2,
|
make_tuple(&vp9_fht16x16_sse2, &vp9_iht16x16_256_add_sse2,
|
||||||
3, VPX_BITS_8)));
|
3, VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, PartialTrans16x16Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct16x16_1_sse2,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
@ -914,9 +843,6 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&idct16x16_10_add_12_sse2, 3167, VPX_BITS_12),
|
&idct16x16_10_add_12_sse2, 3167, VPX_BITS_12),
|
||||||
make_tuple(&idct16x16_12, &idct16x16_256_add_12_sse2,
|
make_tuple(&idct16x16_12, &idct16x16_256_add_12_sse2,
|
||||||
3167, VPX_BITS_12)));
|
3167, VPX_BITS_12)));
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, PartialTrans16x16Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct16x16_1_sse2,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
@ -932,8 +858,12 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp9_fht16x16_msa, &vp9_iht16x16_256_add_msa, 2, VPX_BITS_8),
|
make_tuple(&vp9_fht16x16_msa, &vp9_iht16x16_256_add_msa, 2, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht16x16_msa, &vp9_iht16x16_256_add_msa, 3,
|
make_tuple(&vp9_fht16x16_msa, &vp9_iht16x16_256_add_msa, 3,
|
||||||
VPX_BITS_8)));
|
VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(MSA, PartialTrans16x16Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct16x16_1_msa,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
#if HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, Trans16x16DCT,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct16x16_c,
|
||||||
|
&vpx_idct16x16_256_add_vsx,
|
||||||
|
0, VPX_BITS_8)));
|
||||||
|
#endif // HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -66,16 +66,16 @@ void reference_32x32_dct_2d(const int16_t input[kNumCoeffs],
|
|||||||
typedef void (*FwdTxfmFunc)(const int16_t *in, tran_low_t *out, int stride);
|
typedef void (*FwdTxfmFunc)(const int16_t *in, tran_low_t *out, int stride);
|
||||||
typedef void (*InvTxfmFunc)(const tran_low_t *in, uint8_t *out, int stride);
|
typedef void (*InvTxfmFunc)(const tran_low_t *in, uint8_t *out, int stride);
|
||||||
|
|
||||||
typedef std::tr1::tuple<FwdTxfmFunc, InvTxfmFunc, int, vpx_bit_depth_t>
|
typedef ::testing::tuple<FwdTxfmFunc, InvTxfmFunc, int, vpx_bit_depth_t>
|
||||||
Trans32x32Param;
|
Trans32x32Param;
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
void idct32x32_10(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct32x32_10(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct32x32_1024_add_c(in, out, stride, 10);
|
vpx_highbd_idct32x32_1024_add_c(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct32x32_12(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct32x32_12(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct32x32_1024_add_c(in, out, stride, 12);
|
vpx_highbd_idct32x32_1024_add_c(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
@ -137,7 +137,7 @@ TEST_P(Trans32x32Test, AccuracyCheck) {
|
|||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
inv_txfm_(test_temp_block, CONVERT_TO_BYTEPTR(dst16), 32));
|
inv_txfm_(test_temp_block, CAST_TO_BYTEPTR(dst16), 32));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -275,7 +275,7 @@ TEST_P(Trans32x32Test, InverseAccuracy) {
|
|||||||
ASM_REGISTER_STATE_CHECK(inv_txfm_(coeff, dst, 32));
|
ASM_REGISTER_STATE_CHECK(inv_txfm_(coeff, dst, 32));
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(inv_txfm_(coeff, CONVERT_TO_BYTEPTR(dst16), 32));
|
ASM_REGISTER_STATE_CHECK(inv_txfm_(coeff, CAST_TO_BYTEPTR(dst16), 32));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
for (int j = 0; j < kNumCoeffs; ++j) {
|
||||||
@ -292,68 +292,7 @@ TEST_P(Trans32x32Test, InverseAccuracy) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class PartialTrans32x32Test
|
using ::testing::make_tuple;
|
||||||
: public ::testing::TestWithParam<
|
|
||||||
std::tr1::tuple<FwdTxfmFunc, vpx_bit_depth_t> > {
|
|
||||||
public:
|
|
||||||
virtual ~PartialTrans32x32Test() {}
|
|
||||||
virtual void SetUp() {
|
|
||||||
fwd_txfm_ = GET_PARAM(0);
|
|
||||||
bit_depth_ = GET_PARAM(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
|
||||||
|
|
||||||
protected:
|
|
||||||
vpx_bit_depth_t bit_depth_;
|
|
||||||
FwdTxfmFunc fwd_txfm_;
|
|
||||||
};
|
|
||||||
|
|
||||||
TEST_P(PartialTrans32x32Test, Extremes) {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int16_t maxval =
|
|
||||||
static_cast<int16_t>(clip_pixel_highbd(1 << 30, bit_depth_));
|
|
||||||
#else
|
|
||||||
const int16_t maxval = 255;
|
|
||||||
#endif
|
|
||||||
const int minval = -maxval;
|
|
||||||
DECLARE_ALIGNED(16, int16_t, input[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output[kNumCoeffs]);
|
|
||||||
|
|
||||||
for (int i = 0; i < kNumCoeffs; ++i) input[i] = maxval;
|
|
||||||
output[0] = 0;
|
|
||||||
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input, output, 32));
|
|
||||||
EXPECT_EQ((maxval * kNumCoeffs) >> 3, output[0]);
|
|
||||||
|
|
||||||
for (int i = 0; i < kNumCoeffs; ++i) input[i] = minval;
|
|
||||||
output[0] = 0;
|
|
||||||
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input, output, 32));
|
|
||||||
EXPECT_EQ((minval * kNumCoeffs) >> 3, output[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_P(PartialTrans32x32Test, Random) {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int16_t maxval =
|
|
||||||
static_cast<int16_t>(clip_pixel_highbd(1 << 30, bit_depth_));
|
|
||||||
#else
|
|
||||||
const int16_t maxval = 255;
|
|
||||||
#endif
|
|
||||||
DECLARE_ALIGNED(16, int16_t, input[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output[kNumCoeffs]);
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
|
|
||||||
int sum = 0;
|
|
||||||
for (int i = 0; i < kNumCoeffs; ++i) {
|
|
||||||
const int val = (i & 1) ? -rnd(maxval + 1) : rnd(maxval + 1);
|
|
||||||
input[i] = val;
|
|
||||||
sum += val;
|
|
||||||
}
|
|
||||||
output[0] = 0;
|
|
||||||
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input, output, 32));
|
|
||||||
EXPECT_EQ(sum >> 3, output[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -366,11 +305,6 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vpx_fdct32x32_c, &vpx_idct32x32_1024_add_c, 0, VPX_BITS_8),
|
make_tuple(&vpx_fdct32x32_c, &vpx_idct32x32_1024_add_c, 0, VPX_BITS_8),
|
||||||
make_tuple(&vpx_fdct32x32_rd_c, &vpx_idct32x32_1024_add_c, 1,
|
make_tuple(&vpx_fdct32x32_rd_c, &vpx_idct32x32_1024_add_c, 1,
|
||||||
VPX_BITS_8)));
|
VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
C, PartialTrans32x32Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_highbd_fdct32x32_1_c, VPX_BITS_8),
|
|
||||||
make_tuple(&vpx_highbd_fdct32x32_1_c, VPX_BITS_10),
|
|
||||||
make_tuple(&vpx_highbd_fdct32x32_1_c, VPX_BITS_12)));
|
|
||||||
#else
|
#else
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
C, Trans32x32Test,
|
C, Trans32x32Test,
|
||||||
@ -378,19 +312,16 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
VPX_BITS_8),
|
VPX_BITS_8),
|
||||||
make_tuple(&vpx_fdct32x32_rd_c, &vpx_idct32x32_1024_add_c,
|
make_tuple(&vpx_fdct32x32_rd_c, &vpx_idct32x32_1024_add_c,
|
||||||
1, VPX_BITS_8)));
|
1, VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(C, PartialTrans32x32Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct32x32_1_c,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
#if HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_NEON && !CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
NEON, Trans32x32Test,
|
NEON, Trans32x32Test,
|
||||||
::testing::Values(make_tuple(&vpx_fdct32x32_c, &vpx_idct32x32_1024_add_neon,
|
::testing::Values(make_tuple(&vpx_fdct32x32_neon,
|
||||||
0, VPX_BITS_8),
|
&vpx_idct32x32_1024_add_neon, 0, VPX_BITS_8),
|
||||||
make_tuple(&vpx_fdct32x32_rd_c,
|
make_tuple(&vpx_fdct32x32_rd_neon,
|
||||||
&vpx_idct32x32_1024_add_neon, 1, VPX_BITS_8)));
|
&vpx_idct32x32_1024_add_neon, 1, VPX_BITS_8)));
|
||||||
#endif // HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_NEON && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -399,9 +330,6 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_idct32x32_1024_add_sse2, 0, VPX_BITS_8),
|
&vpx_idct32x32_1024_add_sse2, 0, VPX_BITS_8),
|
||||||
make_tuple(&vpx_fdct32x32_rd_sse2,
|
make_tuple(&vpx_fdct32x32_rd_sse2,
|
||||||
&vpx_idct32x32_1024_add_sse2, 1, VPX_BITS_8)));
|
&vpx_idct32x32_1024_add_sse2, 1, VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, PartialTrans32x32Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct32x32_1_sse2,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
@ -418,9 +346,6 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
VPX_BITS_8),
|
VPX_BITS_8),
|
||||||
make_tuple(&vpx_fdct32x32_rd_sse2, &vpx_idct32x32_1024_add_c, 1,
|
make_tuple(&vpx_fdct32x32_rd_sse2, &vpx_idct32x32_1024_add_c, 1,
|
||||||
VPX_BITS_8)));
|
VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, PartialTrans32x32Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct32x32_1_sse2,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_AVX2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_AVX2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
@ -439,8 +364,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_idct32x32_1024_add_msa, 0, VPX_BITS_8),
|
&vpx_idct32x32_1024_add_msa, 0, VPX_BITS_8),
|
||||||
make_tuple(&vpx_fdct32x32_rd_msa,
|
make_tuple(&vpx_fdct32x32_rd_msa,
|
||||||
&vpx_idct32x32_1024_add_msa, 1, VPX_BITS_8)));
|
&vpx_idct32x32_1024_add_msa, 1, VPX_BITS_8)));
|
||||||
INSTANTIATE_TEST_CASE_P(MSA, PartialTrans32x32Test,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct32x32_1_msa,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
#if HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
VSX, Trans32x32Test,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct32x32_c, &vpx_idct32x32_1024_add_vsx,
|
||||||
|
0, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct32x32_rd_c,
|
||||||
|
&vpx_idct32x32_1024_add_vsx, 1, VPX_BITS_8)));
|
||||||
|
#endif // HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
} // namespace
|
} // namespace
|
||||||
|
169
test/dct_partial_test.cc
Normal file
169
test/dct_partial_test.cc
Normal file
@ -0,0 +1,169 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2017 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <math.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <limits>
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vpx_dsp_rtcd.h"
|
||||||
|
#include "test/acm_random.h"
|
||||||
|
#include "test/buffer.h"
|
||||||
|
#include "test/clear_system_state.h"
|
||||||
|
#include "test/register_state_check.h"
|
||||||
|
#include "test/util.h"
|
||||||
|
#include "vpx/vpx_codec.h"
|
||||||
|
#include "vpx/vpx_integer.h"
|
||||||
|
#include "vpx_dsp/vpx_dsp_common.h"
|
||||||
|
|
||||||
|
using ::testing::make_tuple;
|
||||||
|
using ::testing::tuple;
|
||||||
|
using libvpx_test::ACMRandom;
|
||||||
|
using libvpx_test::Buffer;
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
typedef void (*PartialFdctFunc)(const int16_t *in, tran_low_t *out, int stride);
|
||||||
|
|
||||||
|
typedef tuple<PartialFdctFunc, int /* size */, vpx_bit_depth_t>
|
||||||
|
PartialFdctParam;
|
||||||
|
|
||||||
|
tran_low_t partial_fdct_ref(const Buffer<int16_t> &in, int size) {
|
||||||
|
int64_t sum = 0;
|
||||||
|
for (int y = 0; y < size; ++y) {
|
||||||
|
for (int x = 0; x < size; ++x) {
|
||||||
|
sum += in.TopLeftPixel()[y * in.stride() + x];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (size) {
|
||||||
|
case 4: sum *= 2; break;
|
||||||
|
case 8: /*sum = sum;*/ break;
|
||||||
|
case 16: sum >>= 1; break;
|
||||||
|
case 32: sum >>= 3; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return static_cast<tran_low_t>(sum);
|
||||||
|
}
|
||||||
|
|
||||||
|
class PartialFdctTest : public ::testing::TestWithParam<PartialFdctParam> {
|
||||||
|
public:
|
||||||
|
PartialFdctTest() {
|
||||||
|
fwd_txfm_ = GET_PARAM(0);
|
||||||
|
size_ = GET_PARAM(1);
|
||||||
|
bit_depth_ = GET_PARAM(2);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void RunTest() {
|
||||||
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
|
const int16_t maxvalue =
|
||||||
|
clip_pixel_highbd(std::numeric_limits<int16_t>::max(), bit_depth_);
|
||||||
|
const int16_t minvalue = -maxvalue;
|
||||||
|
Buffer<int16_t> input_block =
|
||||||
|
Buffer<int16_t>(size_, size_, 8, size_ == 4 ? 0 : 16);
|
||||||
|
ASSERT_TRUE(input_block.Init());
|
||||||
|
Buffer<tran_low_t> output_block = Buffer<tran_low_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(output_block.Init());
|
||||||
|
|
||||||
|
for (int i = 0; i < 100; ++i) {
|
||||||
|
if (i == 0) {
|
||||||
|
input_block.Set(maxvalue);
|
||||||
|
} else if (i == 1) {
|
||||||
|
input_block.Set(minvalue);
|
||||||
|
} else {
|
||||||
|
input_block.Set(&rnd, minvalue, maxvalue);
|
||||||
|
}
|
||||||
|
|
||||||
|
ASM_REGISTER_STATE_CHECK(fwd_txfm_(input_block.TopLeftPixel(),
|
||||||
|
output_block.TopLeftPixel(),
|
||||||
|
input_block.stride()));
|
||||||
|
|
||||||
|
EXPECT_EQ(partial_fdct_ref(input_block, size_),
|
||||||
|
output_block.TopLeftPixel()[0]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
PartialFdctFunc fwd_txfm_;
|
||||||
|
vpx_bit_depth_t bit_depth_;
|
||||||
|
int size_;
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(PartialFdctTest, PartialFdctTest) { RunTest(); }
|
||||||
|
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
C, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_highbd_fdct32x32_1_c, 32, VPX_BITS_12),
|
||||||
|
make_tuple(&vpx_highbd_fdct32x32_1_c, 32, VPX_BITS_10),
|
||||||
|
make_tuple(&vpx_fdct32x32_1_c, 32, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_highbd_fdct16x16_1_c, 16, VPX_BITS_12),
|
||||||
|
make_tuple(&vpx_highbd_fdct16x16_1_c, 16, VPX_BITS_10),
|
||||||
|
make_tuple(&vpx_fdct16x16_1_c, 16, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_highbd_fdct8x8_1_c, 8, VPX_BITS_12),
|
||||||
|
make_tuple(&vpx_highbd_fdct8x8_1_c, 8, VPX_BITS_10),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_c, 8, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct4x4_1_c, 4, VPX_BITS_8)));
|
||||||
|
#else
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
C, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct32x32_1_c, 32, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct16x16_1_c, 16, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_c, 8, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct4x4_1_c, 4, VPX_BITS_8)));
|
||||||
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
#if HAVE_SSE2
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSE2, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct32x32_1_sse2, 32, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct16x16_1_sse2, 16, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_sse2, 8, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct4x4_1_sse2, 4, VPX_BITS_8)));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct32x32_1_neon, 32, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct16x16_1_neon, 16, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_neon, 8, VPX_BITS_12),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_neon, 8, VPX_BITS_10),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_neon, 8, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct4x4_1_neon, 4, VPX_BITS_8)));
|
||||||
|
#else
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct32x32_1_neon, 32, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct16x16_1_neon, 16, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_neon, 8, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct4x4_1_neon, 4, VPX_BITS_8)));
|
||||||
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if HAVE_MSA
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct8x8_1_msa, 8,
|
||||||
|
VPX_BITS_8)));
|
||||||
|
#else // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MSA, PartialFdctTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct32x32_1_msa, 32, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct16x16_1_msa, 16, VPX_BITS_8),
|
||||||
|
make_tuple(&vpx_fdct8x8_1_msa, 8, VPX_BITS_8)));
|
||||||
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
} // namespace
|
728
test/dct_test.cc
Normal file
728
test/dct_test.cc
Normal file
@ -0,0 +1,728 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2017 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <math.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vp9_rtcd.h"
|
||||||
|
#include "./vpx_dsp_rtcd.h"
|
||||||
|
#include "test/acm_random.h"
|
||||||
|
#include "test/buffer.h"
|
||||||
|
#include "test/clear_system_state.h"
|
||||||
|
#include "test/register_state_check.h"
|
||||||
|
#include "test/util.h"
|
||||||
|
#include "vp9/common/vp9_entropy.h"
|
||||||
|
#include "vpx/vpx_codec.h"
|
||||||
|
#include "vpx/vpx_integer.h"
|
||||||
|
#include "vpx_ports/mem.h"
|
||||||
|
|
||||||
|
using ::testing::make_tuple;
|
||||||
|
using ::testing::tuple;
|
||||||
|
using libvpx_test::ACMRandom;
|
||||||
|
using libvpx_test::Buffer;
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
typedef void (*FdctFunc)(const int16_t *in, tran_low_t *out, int stride);
|
||||||
|
typedef void (*IdctFunc)(const tran_low_t *in, uint8_t *out, int stride);
|
||||||
|
typedef void (*FhtFunc)(const int16_t *in, tran_low_t *out, int stride,
|
||||||
|
int tx_type);
|
||||||
|
typedef void (*FhtFuncRef)(const Buffer<int16_t> &in, Buffer<tran_low_t> *out,
|
||||||
|
int size, int tx_type);
|
||||||
|
typedef void (*IhtFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
|
int tx_type);
|
||||||
|
typedef void (*IhtWithBdFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
|
int tx_type, int bd);
|
||||||
|
|
||||||
|
template <FdctFunc fn>
|
||||||
|
void fdct_wrapper(const int16_t *in, tran_low_t *out, int stride, int tx_type) {
|
||||||
|
(void)tx_type;
|
||||||
|
fn(in, out, stride);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <IdctFunc fn>
|
||||||
|
void idct_wrapper(const tran_low_t *in, uint8_t *out, int stride, int tx_type,
|
||||||
|
int bd) {
|
||||||
|
(void)tx_type;
|
||||||
|
(void)bd;
|
||||||
|
fn(in, out, stride);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <IhtFunc fn>
|
||||||
|
void iht_wrapper(const tran_low_t *in, uint8_t *out, int stride, int tx_type,
|
||||||
|
int bd) {
|
||||||
|
(void)bd;
|
||||||
|
fn(in, out, stride, tx_type);
|
||||||
|
}
|
||||||
|
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
typedef void (*HighbdIdctFunc)(const tran_low_t *in, uint16_t *out, int stride,
|
||||||
|
int bd);
|
||||||
|
|
||||||
|
typedef void (*HighbdIhtFunc)(const tran_low_t *in, uint16_t *out, int stride,
|
||||||
|
int tx_type, int bd);
|
||||||
|
|
||||||
|
template <HighbdIdctFunc fn>
|
||||||
|
void highbd_idct_wrapper(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
|
int tx_type, int bd) {
|
||||||
|
(void)tx_type;
|
||||||
|
fn(in, CAST_TO_SHORTPTR(out), stride, bd);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <HighbdIhtFunc fn>
|
||||||
|
void highbd_iht_wrapper(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
|
int tx_type, int bd) {
|
||||||
|
fn(in, CAST_TO_SHORTPTR(out), stride, tx_type, bd);
|
||||||
|
}
|
||||||
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
struct FuncInfo {
|
||||||
|
FhtFunc ft_func;
|
||||||
|
IhtWithBdFunc it_func;
|
||||||
|
int size;
|
||||||
|
int pixel_size;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* forward transform, inverse transform, size, transform type, bit depth */
|
||||||
|
typedef tuple<int, const FuncInfo *, int, vpx_bit_depth_t> DctParam;
|
||||||
|
|
||||||
|
void fdct_ref(const Buffer<int16_t> &in, Buffer<tran_low_t> *out, int size,
|
||||||
|
int /*tx_type*/) {
|
||||||
|
const int16_t *i = in.TopLeftPixel();
|
||||||
|
const int i_stride = in.stride();
|
||||||
|
tran_low_t *o = out->TopLeftPixel();
|
||||||
|
if (size == 4) {
|
||||||
|
vpx_fdct4x4_c(i, o, i_stride);
|
||||||
|
} else if (size == 8) {
|
||||||
|
vpx_fdct8x8_c(i, o, i_stride);
|
||||||
|
} else if (size == 16) {
|
||||||
|
vpx_fdct16x16_c(i, o, i_stride);
|
||||||
|
} else if (size == 32) {
|
||||||
|
vpx_fdct32x32_c(i, o, i_stride);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void fht_ref(const Buffer<int16_t> &in, Buffer<tran_low_t> *out, int size,
|
||||||
|
int tx_type) {
|
||||||
|
const int16_t *i = in.TopLeftPixel();
|
||||||
|
const int i_stride = in.stride();
|
||||||
|
tran_low_t *o = out->TopLeftPixel();
|
||||||
|
if (size == 4) {
|
||||||
|
vp9_fht4x4_c(i, o, i_stride, tx_type);
|
||||||
|
} else if (size == 8) {
|
||||||
|
vp9_fht8x8_c(i, o, i_stride, tx_type);
|
||||||
|
} else if (size == 16) {
|
||||||
|
vp9_fht16x16_c(i, o, i_stride, tx_type);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void fwht_ref(const Buffer<int16_t> &in, Buffer<tran_low_t> *out, int size,
|
||||||
|
int /*tx_type*/) {
|
||||||
|
ASSERT_EQ(size, 4);
|
||||||
|
vp9_fwht4x4_c(in.TopLeftPixel(), out->TopLeftPixel(), in.stride());
|
||||||
|
}
|
||||||
|
|
||||||
|
class TransTestBase : public ::testing::TestWithParam<DctParam> {
|
||||||
|
public:
|
||||||
|
virtual void SetUp() {
|
||||||
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
const int idx = GET_PARAM(0);
|
||||||
|
const FuncInfo *func_info = &(GET_PARAM(1)[idx]);
|
||||||
|
tx_type_ = GET_PARAM(2);
|
||||||
|
bit_depth_ = GET_PARAM(3);
|
||||||
|
fwd_txfm_ = func_info->ft_func;
|
||||||
|
inv_txfm_ = func_info->it_func;
|
||||||
|
size_ = func_info->size;
|
||||||
|
pixel_size_ = func_info->pixel_size;
|
||||||
|
max_pixel_value_ = (1 << bit_depth_) - 1;
|
||||||
|
|
||||||
|
// Randomize stride_ to a value less than or equal to 1024
|
||||||
|
stride_ = rnd_(1024) + 1;
|
||||||
|
if (stride_ < size_) {
|
||||||
|
stride_ = size_;
|
||||||
|
}
|
||||||
|
// Align stride_ to 16 if it's bigger than 16.
|
||||||
|
if (stride_ > 16) {
|
||||||
|
stride_ &= ~15;
|
||||||
|
}
|
||||||
|
|
||||||
|
block_size_ = size_ * stride_;
|
||||||
|
|
||||||
|
src_ = reinterpret_cast<uint8_t *>(
|
||||||
|
vpx_memalign(16, pixel_size_ * block_size_));
|
||||||
|
ASSERT_TRUE(src_ != NULL);
|
||||||
|
dst_ = reinterpret_cast<uint8_t *>(
|
||||||
|
vpx_memalign(16, pixel_size_ * block_size_));
|
||||||
|
ASSERT_TRUE(dst_ != NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void TearDown() {
|
||||||
|
vpx_free(src_);
|
||||||
|
src_ = NULL;
|
||||||
|
vpx_free(dst_);
|
||||||
|
dst_ = NULL;
|
||||||
|
libvpx_test::ClearSystemState();
|
||||||
|
}
|
||||||
|
|
||||||
|
void InitMem() {
|
||||||
|
if (pixel_size_ == 1 && bit_depth_ > VPX_BITS_8) return;
|
||||||
|
if (pixel_size_ == 1) {
|
||||||
|
for (int j = 0; j < block_size_; ++j) {
|
||||||
|
src_[j] = rnd_.Rand16() & max_pixel_value_;
|
||||||
|
}
|
||||||
|
for (int j = 0; j < block_size_; ++j) {
|
||||||
|
dst_[j] = rnd_.Rand16() & max_pixel_value_;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
ASSERT_EQ(pixel_size_, 2);
|
||||||
|
uint16_t *const src = reinterpret_cast<uint16_t *>(src_);
|
||||||
|
uint16_t *const dst = reinterpret_cast<uint16_t *>(dst_);
|
||||||
|
for (int j = 0; j < block_size_; ++j) {
|
||||||
|
src[j] = rnd_.Rand16() & max_pixel_value_;
|
||||||
|
}
|
||||||
|
for (int j = 0; j < block_size_; ++j) {
|
||||||
|
dst[j] = rnd_.Rand16() & max_pixel_value_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunFwdTxfm(const Buffer<int16_t> &in, Buffer<tran_low_t> *out) {
|
||||||
|
fwd_txfm_(in.TopLeftPixel(), out->TopLeftPixel(), in.stride(), tx_type_);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunInvTxfm(const Buffer<tran_low_t> &in, uint8_t *out) {
|
||||||
|
inv_txfm_(in.TopLeftPixel(), out, stride_, tx_type_, bit_depth_);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void RunAccuracyCheck(int limit) {
|
||||||
|
if (pixel_size_ == 1 && bit_depth_ > VPX_BITS_8) return;
|
||||||
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
|
Buffer<int16_t> test_input_block =
|
||||||
|
Buffer<int16_t>(size_, size_, 8, size_ == 4 ? 0 : 16);
|
||||||
|
ASSERT_TRUE(test_input_block.Init());
|
||||||
|
Buffer<tran_low_t> test_temp_block =
|
||||||
|
Buffer<tran_low_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(test_temp_block.Init());
|
||||||
|
uint32_t max_error = 0;
|
||||||
|
int64_t total_error = 0;
|
||||||
|
const int count_test_block = 10000;
|
||||||
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
|
InitMem();
|
||||||
|
for (int h = 0; h < size_; ++h) {
|
||||||
|
for (int w = 0; w < size_; ++w) {
|
||||||
|
if (pixel_size_ == 1) {
|
||||||
|
test_input_block.TopLeftPixel()[h * test_input_block.stride() + w] =
|
||||||
|
src_[h * stride_ + w] - dst_[h * stride_ + w];
|
||||||
|
} else {
|
||||||
|
ASSERT_EQ(pixel_size_, 2);
|
||||||
|
const uint16_t *const src = reinterpret_cast<uint16_t *>(src_);
|
||||||
|
const uint16_t *const dst = reinterpret_cast<uint16_t *>(dst_);
|
||||||
|
test_input_block.TopLeftPixel()[h * test_input_block.stride() + w] =
|
||||||
|
src[h * stride_ + w] - dst[h * stride_ + w];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ASM_REGISTER_STATE_CHECK(RunFwdTxfm(test_input_block, &test_temp_block));
|
||||||
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(test_temp_block, dst_));
|
||||||
|
|
||||||
|
for (int h = 0; h < size_; ++h) {
|
||||||
|
for (int w = 0; w < size_; ++w) {
|
||||||
|
int diff;
|
||||||
|
if (pixel_size_ == 1) {
|
||||||
|
diff = dst_[h * stride_ + w] - src_[h * stride_ + w];
|
||||||
|
} else {
|
||||||
|
ASSERT_EQ(pixel_size_, 2);
|
||||||
|
const uint16_t *const src = reinterpret_cast<uint16_t *>(src_);
|
||||||
|
const uint16_t *const dst = reinterpret_cast<uint16_t *>(dst_);
|
||||||
|
diff = dst[h * stride_ + w] - src[h * stride_ + w];
|
||||||
|
}
|
||||||
|
const uint32_t error = diff * diff;
|
||||||
|
if (max_error < error) max_error = error;
|
||||||
|
total_error += error;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
EXPECT_GE(static_cast<uint32_t>(limit), max_error)
|
||||||
|
<< "Error: " << size_ << "x" << size_
|
||||||
|
<< " transform/inverse transform has an individual round trip error > "
|
||||||
|
<< limit;
|
||||||
|
|
||||||
|
EXPECT_GE(count_test_block * limit, total_error)
|
||||||
|
<< "Error: " << size_ << "x" << size_
|
||||||
|
<< " transform/inverse transform has average round trip error > "
|
||||||
|
<< limit << " per block";
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunCoeffCheck() {
|
||||||
|
if (pixel_size_ == 1 && bit_depth_ > VPX_BITS_8) return;
|
||||||
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
|
const int count_test_block = 5000;
|
||||||
|
Buffer<int16_t> input_block =
|
||||||
|
Buffer<int16_t>(size_, size_, 8, size_ == 4 ? 0 : 16);
|
||||||
|
ASSERT_TRUE(input_block.Init());
|
||||||
|
Buffer<tran_low_t> output_ref_block = Buffer<tran_low_t>(size_, size_, 0);
|
||||||
|
ASSERT_TRUE(output_ref_block.Init());
|
||||||
|
Buffer<tran_low_t> output_block = Buffer<tran_low_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(output_block.Init());
|
||||||
|
|
||||||
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
|
// Initialize a test block with input range [-max_pixel_value_,
|
||||||
|
// max_pixel_value_].
|
||||||
|
input_block.Set(&rnd, -max_pixel_value_, max_pixel_value_);
|
||||||
|
|
||||||
|
fwd_txfm_ref(input_block, &output_ref_block, size_, tx_type_);
|
||||||
|
ASM_REGISTER_STATE_CHECK(RunFwdTxfm(input_block, &output_block));
|
||||||
|
|
||||||
|
// The minimum quant value is 4.
|
||||||
|
EXPECT_TRUE(output_block.CheckValues(output_ref_block));
|
||||||
|
if (::testing::Test::HasFailure()) {
|
||||||
|
printf("Size: %d Transform type: %d\n", size_, tx_type_);
|
||||||
|
output_block.PrintDifference(output_ref_block);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunMemCheck() {
|
||||||
|
if (pixel_size_ == 1 && bit_depth_ > VPX_BITS_8) return;
|
||||||
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
|
const int count_test_block = 5000;
|
||||||
|
Buffer<int16_t> input_extreme_block =
|
||||||
|
Buffer<int16_t>(size_, size_, 8, size_ == 4 ? 0 : 16);
|
||||||
|
ASSERT_TRUE(input_extreme_block.Init());
|
||||||
|
Buffer<tran_low_t> output_ref_block = Buffer<tran_low_t>(size_, size_, 0);
|
||||||
|
ASSERT_TRUE(output_ref_block.Init());
|
||||||
|
Buffer<tran_low_t> output_block = Buffer<tran_low_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(output_block.Init());
|
||||||
|
|
||||||
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
|
// Initialize a test block with -max_pixel_value_ or max_pixel_value_.
|
||||||
|
if (i == 0) {
|
||||||
|
input_extreme_block.Set(max_pixel_value_);
|
||||||
|
} else if (i == 1) {
|
||||||
|
input_extreme_block.Set(-max_pixel_value_);
|
||||||
|
} else {
|
||||||
|
for (int h = 0; h < size_; ++h) {
|
||||||
|
for (int w = 0; w < size_; ++w) {
|
||||||
|
input_extreme_block
|
||||||
|
.TopLeftPixel()[h * input_extreme_block.stride() + w] =
|
||||||
|
rnd.Rand8() % 2 ? max_pixel_value_ : -max_pixel_value_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fwd_txfm_ref(input_extreme_block, &output_ref_block, size_, tx_type_);
|
||||||
|
ASM_REGISTER_STATE_CHECK(RunFwdTxfm(input_extreme_block, &output_block));
|
||||||
|
|
||||||
|
// The minimum quant value is 4.
|
||||||
|
EXPECT_TRUE(output_block.CheckValues(output_ref_block));
|
||||||
|
for (int h = 0; h < size_; ++h) {
|
||||||
|
for (int w = 0; w < size_; ++w) {
|
||||||
|
EXPECT_GE(
|
||||||
|
4 * DCT_MAX_VALUE << (bit_depth_ - 8),
|
||||||
|
abs(output_block.TopLeftPixel()[h * output_block.stride() + w]))
|
||||||
|
<< "Error: " << size_ << "x" << size_
|
||||||
|
<< " transform has coefficient larger than 4*DCT_MAX_VALUE"
|
||||||
|
<< " at " << w << "," << h;
|
||||||
|
if (::testing::Test::HasFailure()) {
|
||||||
|
printf("Size: %d Transform type: %d\n", size_, tx_type_);
|
||||||
|
output_block.DumpBuffer();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunInvAccuracyCheck(int limit) {
|
||||||
|
if (pixel_size_ == 1 && bit_depth_ > VPX_BITS_8) return;
|
||||||
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
|
const int count_test_block = 1000;
|
||||||
|
Buffer<int16_t> in = Buffer<int16_t>(size_, size_, 4);
|
||||||
|
ASSERT_TRUE(in.Init());
|
||||||
|
Buffer<tran_low_t> coeff = Buffer<tran_low_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(coeff.Init());
|
||||||
|
Buffer<uint8_t> dst = Buffer<uint8_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(dst.Init());
|
||||||
|
Buffer<uint8_t> src = Buffer<uint8_t>(size_, size_, 0);
|
||||||
|
ASSERT_TRUE(src.Init());
|
||||||
|
Buffer<uint16_t> dst16 = Buffer<uint16_t>(size_, size_, 0, 16);
|
||||||
|
ASSERT_TRUE(dst16.Init());
|
||||||
|
Buffer<uint16_t> src16 = Buffer<uint16_t>(size_, size_, 0);
|
||||||
|
ASSERT_TRUE(src16.Init());
|
||||||
|
|
||||||
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
|
InitMem();
|
||||||
|
// Initialize a test block with input range [-max_pixel_value_,
|
||||||
|
// max_pixel_value_].
|
||||||
|
for (int h = 0; h < size_; ++h) {
|
||||||
|
for (int w = 0; w < size_; ++w) {
|
||||||
|
if (pixel_size_ == 1) {
|
||||||
|
in.TopLeftPixel()[h * in.stride() + w] =
|
||||||
|
src_[h * stride_ + w] - dst_[h * stride_ + w];
|
||||||
|
} else {
|
||||||
|
ASSERT_EQ(pixel_size_, 2);
|
||||||
|
const uint16_t *const src = reinterpret_cast<uint16_t *>(src_);
|
||||||
|
const uint16_t *const dst = reinterpret_cast<uint16_t *>(dst_);
|
||||||
|
in.TopLeftPixel()[h * in.stride() + w] =
|
||||||
|
src[h * stride_ + w] - dst[h * stride_ + w];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fwd_txfm_ref(in, &coeff, size_, tx_type_);
|
||||||
|
|
||||||
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst_));
|
||||||
|
|
||||||
|
for (int h = 0; h < size_; ++h) {
|
||||||
|
for (int w = 0; w < size_; ++w) {
|
||||||
|
int diff;
|
||||||
|
if (pixel_size_ == 1) {
|
||||||
|
diff = dst_[h * stride_ + w] - src_[h * stride_ + w];
|
||||||
|
} else {
|
||||||
|
ASSERT_EQ(pixel_size_, 2);
|
||||||
|
const uint16_t *const src = reinterpret_cast<uint16_t *>(src_);
|
||||||
|
const uint16_t *const dst = reinterpret_cast<uint16_t *>(dst_);
|
||||||
|
diff = dst[h * stride_ + w] - src[h * stride_ + w];
|
||||||
|
}
|
||||||
|
const uint32_t error = diff * diff;
|
||||||
|
EXPECT_GE(static_cast<uint32_t>(limit), error)
|
||||||
|
<< "Error: " << size_ << "x" << size_
|
||||||
|
<< " inverse transform has error " << error << " at " << w << ","
|
||||||
|
<< h;
|
||||||
|
if (::testing::Test::HasFailure()) {
|
||||||
|
printf("Size: %d Transform type: %d\n", size_, tx_type_);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
FhtFunc fwd_txfm_;
|
||||||
|
FhtFuncRef fwd_txfm_ref;
|
||||||
|
IhtWithBdFunc inv_txfm_;
|
||||||
|
ACMRandom rnd_;
|
||||||
|
uint8_t *src_;
|
||||||
|
uint8_t *dst_;
|
||||||
|
vpx_bit_depth_t bit_depth_;
|
||||||
|
int tx_type_;
|
||||||
|
int max_pixel_value_;
|
||||||
|
int size_;
|
||||||
|
int stride_;
|
||||||
|
int pixel_size_;
|
||||||
|
int block_size_;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* -------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
class TransDCT : public TransTestBase {
|
||||||
|
public:
|
||||||
|
TransDCT() { fwd_txfm_ref = fdct_ref; }
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(TransDCT, AccuracyCheck) {
|
||||||
|
int t = 1;
|
||||||
|
if (size_ == 16 && bit_depth_ > 10 && pixel_size_ == 2) {
|
||||||
|
t = 2;
|
||||||
|
} else if (size_ == 32 && bit_depth_ > 10 && pixel_size_ == 2) {
|
||||||
|
t = 7;
|
||||||
|
}
|
||||||
|
RunAccuracyCheck(t);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(TransDCT, CoeffCheck) { RunCoeffCheck(); }
|
||||||
|
|
||||||
|
TEST_P(TransDCT, MemCheck) { RunMemCheck(); }
|
||||||
|
|
||||||
|
TEST_P(TransDCT, InvAccuracyCheck) { RunInvAccuracyCheck(1); }
|
||||||
|
|
||||||
|
static const FuncInfo dct_c_func_info[] = {
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct4x4_c>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct4x4_16_add_c>, 4, 2 },
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct8x8_c>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct8x8_64_add_c>, 8, 2 },
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct16x16_c>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct16x16_256_add_c>, 16, 2 },
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct32x32_c>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct32x32_1024_add_c>, 32, 2 },
|
||||||
|
#endif
|
||||||
|
{ &fdct_wrapper<vpx_fdct4x4_c>, &idct_wrapper<vpx_idct4x4_16_add_c>, 4, 1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct8x8_c>, &idct_wrapper<vpx_idct8x8_64_add_c>, 8, 1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct16x16_c>, &idct_wrapper<vpx_idct16x16_256_add_c>, 16,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct32x32_c>, &idct_wrapper<vpx_idct32x32_1024_add_c>, 32,
|
||||||
|
1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
C, TransDCT,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Range(0, static_cast<int>(sizeof(dct_c_func_info) /
|
||||||
|
sizeof(dct_c_func_info[0]))),
|
||||||
|
::testing::Values(dct_c_func_info), ::testing::Values(0),
|
||||||
|
::testing::Values(VPX_BITS_8, VPX_BITS_10, VPX_BITS_12)));
|
||||||
|
|
||||||
|
#if !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
#if HAVE_SSE2
|
||||||
|
static const FuncInfo dct_sse2_func_info[] = {
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct4x4_sse2>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct4x4_16_add_sse2>, 4, 2 },
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct8x8_sse2>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct8x8_64_add_sse2>, 8, 2 },
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct16x16_sse2>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct16x16_256_add_sse2>, 16, 2 },
|
||||||
|
{ &fdct_wrapper<vpx_highbd_fdct32x32_sse2>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_idct32x32_1024_add_sse2>, 32, 2 },
|
||||||
|
#endif
|
||||||
|
{ &fdct_wrapper<vpx_fdct4x4_sse2>, &idct_wrapper<vpx_idct4x4_16_add_sse2>, 4,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct8x8_sse2>, &idct_wrapper<vpx_idct8x8_64_add_sse2>, 8,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct16x16_sse2>,
|
||||||
|
&idct_wrapper<vpx_idct16x16_256_add_sse2>, 16, 1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct32x32_sse2>,
|
||||||
|
&idct_wrapper<vpx_idct32x32_1024_add_sse2>, 32, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSE2, TransDCT,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Range(0, static_cast<int>(sizeof(dct_sse2_func_info) /
|
||||||
|
sizeof(dct_sse2_func_info[0]))),
|
||||||
|
::testing::Values(dct_sse2_func_info), ::testing::Values(0),
|
||||||
|
::testing::Values(VPX_BITS_8, VPX_BITS_10, VPX_BITS_12)));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_SSSE3 && !CONFIG_VP9_HIGHBITDEPTH && ARCH_X86_64
|
||||||
|
// vpx_fdct8x8_ssse3 is only available in 64 bit builds.
|
||||||
|
static const FuncInfo dct_ssse3_func_info = {
|
||||||
|
&fdct_wrapper<vpx_fdct8x8_ssse3>, &idct_wrapper<vpx_idct8x8_64_add_sse2>, 8, 1
|
||||||
|
};
|
||||||
|
|
||||||
|
// TODO(johannkoenig): high bit depth fdct8x8.
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSSE3, TransDCT,
|
||||||
|
::testing::Values(make_tuple(0, &dct_ssse3_func_info, 0,
|
||||||
|
VPX_BITS_8)));
|
||||||
|
#endif // HAVE_SSSE3 && !CONFIG_VP9_HIGHBITDEPTH && ARCH_X86_64
|
||||||
|
|
||||||
|
#if HAVE_AVX2 && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
static const FuncInfo dct_avx2_func_info = {
|
||||||
|
&fdct_wrapper<vpx_fdct32x32_avx2>, &idct_wrapper<vpx_idct32x32_1024_add_sse2>,
|
||||||
|
32, 1
|
||||||
|
};
|
||||||
|
|
||||||
|
// TODO(johannkoenig): high bit depth fdct32x32.
|
||||||
|
INSTANTIATE_TEST_CASE_P(AVX2, TransDCT,
|
||||||
|
::testing::Values(make_tuple(0, &dct_avx2_func_info, 0,
|
||||||
|
VPX_BITS_8)));
|
||||||
|
#endif // HAVE_AVX2 && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
static const FuncInfo dct_neon_func_info[4] = {
|
||||||
|
{ &fdct_wrapper<vpx_fdct4x4_neon>, &idct_wrapper<vpx_idct4x4_16_add_neon>, 4,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct8x8_neon>, &idct_wrapper<vpx_idct8x8_64_add_neon>, 8,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct16x16_neon>,
|
||||||
|
&idct_wrapper<vpx_idct16x16_256_add_neon>, 16, 1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct32x32_neon>,
|
||||||
|
&idct_wrapper<vpx_idct32x32_1024_add_neon>, 32, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, TransDCT,
|
||||||
|
::testing::Combine(::testing::Range(0, 4),
|
||||||
|
::testing::Values(dct_neon_func_info),
|
||||||
|
::testing::Values(0), ::testing::Values(VPX_BITS_8)));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
static const FuncInfo dct_msa_func_info[4] = {
|
||||||
|
{ &fdct_wrapper<vpx_fdct4x4_msa>, &idct_wrapper<vpx_idct4x4_16_add_msa>, 4,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct8x8_msa>, &idct_wrapper<vpx_idct8x8_64_add_msa>, 8,
|
||||||
|
1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct16x16_msa>, &idct_wrapper<vpx_idct16x16_256_add_msa>,
|
||||||
|
16, 1 },
|
||||||
|
{ &fdct_wrapper<vpx_fdct32x32_msa>, &idct_wrapper<vpx_idct32x32_1024_add_msa>,
|
||||||
|
32, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, TransDCT,
|
||||||
|
::testing::Combine(::testing::Range(0, 4),
|
||||||
|
::testing::Values(dct_msa_func_info),
|
||||||
|
::testing::Values(0),
|
||||||
|
::testing::Values(VPX_BITS_8)));
|
||||||
|
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
#if HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
static const FuncInfo dct_vsx_func_info = {
|
||||||
|
&fdct_wrapper<vpx_fdct4x4_c>, &idct_wrapper<vpx_idct4x4_16_add_vsx>, 4, 1
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, TransDCT,
|
||||||
|
::testing::Values(make_tuple(0, &dct_vsx_func_info, 0,
|
||||||
|
VPX_BITS_8)));
|
||||||
|
#endif // HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH &&
|
||||||
|
|
||||||
|
#endif // !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
/* -------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
class TransHT : public TransTestBase {
|
||||||
|
public:
|
||||||
|
TransHT() { fwd_txfm_ref = fht_ref; }
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(TransHT, AccuracyCheck) {
|
||||||
|
RunAccuracyCheck(size_ == 16 && bit_depth_ > 10 && pixel_size_ == 2 ? 2 : 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(TransHT, CoeffCheck) { RunCoeffCheck(); }
|
||||||
|
|
||||||
|
TEST_P(TransHT, MemCheck) { RunMemCheck(); }
|
||||||
|
|
||||||
|
TEST_P(TransHT, InvAccuracyCheck) { RunInvAccuracyCheck(1); }
|
||||||
|
|
||||||
|
static const FuncInfo ht_c_func_info[] = {
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
{ &vp9_highbd_fht4x4_c, &highbd_iht_wrapper<vp9_highbd_iht4x4_16_add_c>, 4,
|
||||||
|
2 },
|
||||||
|
{ &vp9_highbd_fht8x8_c, &highbd_iht_wrapper<vp9_highbd_iht8x8_64_add_c>, 8,
|
||||||
|
2 },
|
||||||
|
{ &vp9_highbd_fht16x16_c, &highbd_iht_wrapper<vp9_highbd_iht16x16_256_add_c>,
|
||||||
|
16, 2 },
|
||||||
|
#endif
|
||||||
|
{ &vp9_fht4x4_c, &iht_wrapper<vp9_iht4x4_16_add_c>, 4, 1 },
|
||||||
|
{ &vp9_fht8x8_c, &iht_wrapper<vp9_iht8x8_64_add_c>, 8, 1 },
|
||||||
|
{ &vp9_fht16x16_c, &iht_wrapper<vp9_iht16x16_256_add_c>, 16, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
C, TransHT,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Range(0, static_cast<int>(sizeof(ht_c_func_info) /
|
||||||
|
sizeof(ht_c_func_info[0]))),
|
||||||
|
::testing::Values(ht_c_func_info), ::testing::Range(0, 4),
|
||||||
|
::testing::Values(VPX_BITS_8, VPX_BITS_10, VPX_BITS_12)));
|
||||||
|
|
||||||
|
#if !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
|
||||||
|
static const FuncInfo ht_neon_func_info[] = {
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
{ &vp9_highbd_fht4x4_c, &highbd_iht_wrapper<vp9_highbd_iht4x4_16_add_neon>, 4,
|
||||||
|
2 },
|
||||||
|
{ &vp9_highbd_fht8x8_c, &highbd_iht_wrapper<vp9_highbd_iht8x8_64_add_neon>, 8,
|
||||||
|
2 },
|
||||||
|
{ &vp9_highbd_fht16x16_c,
|
||||||
|
&highbd_iht_wrapper<vp9_highbd_iht16x16_256_add_neon>, 16, 2 },
|
||||||
|
#endif
|
||||||
|
{ &vp9_fht4x4_c, &iht_wrapper<vp9_iht4x4_16_add_neon>, 4, 1 },
|
||||||
|
{ &vp9_fht8x8_c, &iht_wrapper<vp9_iht8x8_64_add_neon>, 8, 1 },
|
||||||
|
{ &vp9_fht16x16_c, &iht_wrapper<vp9_iht16x16_256_add_neon>, 16, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, TransHT,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Range(0, static_cast<int>(sizeof(ht_neon_func_info) /
|
||||||
|
sizeof(ht_neon_func_info[0]))),
|
||||||
|
::testing::Values(ht_neon_func_info), ::testing::Range(0, 4),
|
||||||
|
::testing::Values(VPX_BITS_8, VPX_BITS_10, VPX_BITS_12)));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if HAVE_SSE2
|
||||||
|
|
||||||
|
static const FuncInfo ht_sse2_func_info[3] = {
|
||||||
|
{ &vp9_fht4x4_sse2, &iht_wrapper<vp9_iht4x4_16_add_sse2>, 4, 1 },
|
||||||
|
{ &vp9_fht8x8_sse2, &iht_wrapper<vp9_iht8x8_64_add_sse2>, 8, 1 },
|
||||||
|
{ &vp9_fht16x16_sse2, &iht_wrapper<vp9_iht16x16_256_add_sse2>, 16, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, TransHT,
|
||||||
|
::testing::Combine(::testing::Range(0, 3),
|
||||||
|
::testing::Values(ht_sse2_func_info),
|
||||||
|
::testing::Range(0, 4),
|
||||||
|
::testing::Values(VPX_BITS_8)));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_SSE4_1 && CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
static const FuncInfo ht_sse4_1_func_info[3] = {
|
||||||
|
{ &vp9_highbd_fht4x4_c, &highbd_iht_wrapper<vp9_highbd_iht4x4_16_add_sse4_1>,
|
||||||
|
4, 2 },
|
||||||
|
{ vp9_highbd_fht8x8_c, &highbd_iht_wrapper<vp9_highbd_iht8x8_64_add_sse4_1>,
|
||||||
|
8, 2 },
|
||||||
|
{ &vp9_highbd_fht16x16_c,
|
||||||
|
&highbd_iht_wrapper<vp9_highbd_iht16x16_256_add_sse4_1>, 16, 2 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSE4_1, TransHT,
|
||||||
|
::testing::Combine(::testing::Range(0, 3),
|
||||||
|
::testing::Values(ht_sse4_1_func_info),
|
||||||
|
::testing::Range(0, 4),
|
||||||
|
::testing::Values(VPX_BITS_8, VPX_BITS_10,
|
||||||
|
VPX_BITS_12)));
|
||||||
|
#endif // HAVE_SSE4_1 && CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
#endif // !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
/* -------------------------------------------------------------------------- */
|
||||||
|
|
||||||
|
class TransWHT : public TransTestBase {
|
||||||
|
public:
|
||||||
|
TransWHT() { fwd_txfm_ref = fwht_ref; }
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(TransWHT, AccuracyCheck) { RunAccuracyCheck(0); }
|
||||||
|
|
||||||
|
TEST_P(TransWHT, CoeffCheck) { RunCoeffCheck(); }
|
||||||
|
|
||||||
|
TEST_P(TransWHT, MemCheck) { RunMemCheck(); }
|
||||||
|
|
||||||
|
TEST_P(TransWHT, InvAccuracyCheck) { RunInvAccuracyCheck(0); }
|
||||||
|
|
||||||
|
static const FuncInfo wht_c_func_info[] = {
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
{ &fdct_wrapper<vp9_highbd_fwht4x4_c>,
|
||||||
|
&highbd_idct_wrapper<vpx_highbd_iwht4x4_16_add_c>, 4, 2 },
|
||||||
|
#endif
|
||||||
|
{ &fdct_wrapper<vp9_fwht4x4_c>, &idct_wrapper<vpx_iwht4x4_16_add_c>, 4, 1 }
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
C, TransWHT,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Range(0, static_cast<int>(sizeof(wht_c_func_info) /
|
||||||
|
sizeof(wht_c_func_info[0]))),
|
||||||
|
::testing::Values(wht_c_func_info), ::testing::Values(0),
|
||||||
|
::testing::Values(VPX_BITS_8, VPX_BITS_10, VPX_BITS_12)));
|
||||||
|
|
||||||
|
#if HAVE_SSE2 && !CONFIG_EMULATE_HARDWARE
|
||||||
|
static const FuncInfo wht_sse2_func_info = {
|
||||||
|
&fdct_wrapper<vp9_fwht4x4_sse2>, &idct_wrapper<vpx_iwht4x4_16_add_sse2>, 4, 1
|
||||||
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, TransWHT,
|
||||||
|
::testing::Values(make_tuple(0, &wht_sse2_func_info, 0,
|
||||||
|
VPX_BITS_8)));
|
||||||
|
#endif // HAVE_SSE2 && !CONFIG_EMULATE_HARDWARE
|
||||||
|
} // namespace
|
@ -172,4 +172,21 @@ TEST(DecodeAPI, Vp9PeekSI) {
|
|||||||
}
|
}
|
||||||
#endif // CONFIG_VP9_DECODER
|
#endif // CONFIG_VP9_DECODER
|
||||||
|
|
||||||
|
TEST(DecodeAPI, HighBitDepthCapability) {
|
||||||
|
// VP8 should not claim VP9 HBD as a capability.
|
||||||
|
#if CONFIG_VP8_DECODER
|
||||||
|
const vpx_codec_caps_t vp8_caps = vpx_codec_get_caps(&vpx_codec_vp8_dx_algo);
|
||||||
|
EXPECT_EQ(vp8_caps & VPX_CODEC_CAP_HIGHBITDEPTH, 0);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if CONFIG_VP9_DECODER
|
||||||
|
const vpx_codec_caps_t vp9_caps = vpx_codec_get_caps(&vpx_codec_vp9_dx_algo);
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
EXPECT_EQ(vp9_caps & VPX_CODEC_CAP_HIGHBITDEPTH, VPX_CODEC_CAP_HIGHBITDEPTH);
|
||||||
|
#else
|
||||||
|
EXPECT_EQ(vp9_caps & VPX_CODEC_CAP_HIGHBITDEPTH, 0);
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -21,7 +21,7 @@
|
|||||||
#include "./ivfenc.h"
|
#include "./ivfenc.h"
|
||||||
#include "./vpx_version.h"
|
#include "./vpx_version.h"
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
@ -34,7 +34,7 @@ const char kNewEncodeOutputFile[] = "new_encode.ivf";
|
|||||||
/*
|
/*
|
||||||
DecodePerfTest takes a tuple of filename + number of threads to decode with
|
DecodePerfTest takes a tuple of filename + number of threads to decode with
|
||||||
*/
|
*/
|
||||||
typedef std::tr1::tuple<const char *, unsigned> DecodePerfParam;
|
typedef ::testing::tuple<const char *, unsigned> DecodePerfParam;
|
||||||
|
|
||||||
const DecodePerfParam kVP9DecodePerfVectors[] = {
|
const DecodePerfParam kVP9DecodePerfVectors[] = {
|
||||||
make_tuple("vp90-2-bbb_426x240_tile_1x1_180kbps.webm", 1),
|
make_tuple("vp90-2-bbb_426x240_tile_1x1_180kbps.webm", 1),
|
||||||
|
@ -52,14 +52,15 @@ void DecoderTest::HandlePeekResult(Decoder *const decoder,
|
|||||||
/* Vp8's implementation of PeekStream returns an error if the frame you
|
/* Vp8's implementation of PeekStream returns an error if the frame you
|
||||||
* pass it is not a keyframe, so we only expect VPX_CODEC_OK on the first
|
* pass it is not a keyframe, so we only expect VPX_CODEC_OK on the first
|
||||||
* frame, which must be a keyframe. */
|
* frame, which must be a keyframe. */
|
||||||
if (video->frame_number() == 0)
|
if (video->frame_number() == 0) {
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res_peek) << "Peek return failed: "
|
ASSERT_EQ(VPX_CODEC_OK, res_peek)
|
||||||
<< vpx_codec_err_to_string(res_peek);
|
<< "Peek return failed: " << vpx_codec_err_to_string(res_peek);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
/* The Vp9 implementation of PeekStream returns an error only if the
|
/* The Vp9 implementation of PeekStream returns an error only if the
|
||||||
* data passed to it isn't a valid Vp9 chunk. */
|
* data passed to it isn't a valid Vp9 chunk. */
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res_peek) << "Peek return failed: "
|
ASSERT_EQ(VPX_CODEC_OK, res_peek)
|
||||||
<< vpx_codec_err_to_string(res_peek);
|
<< "Peek return failed: " << vpx_codec_err_to_string(res_peek);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -62,4 +62,134 @@ TEST(EncodeAPI, InvalidParams) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST(EncodeAPI, HighBitDepthCapability) {
|
||||||
|
// VP8 should not claim VP9 HBD as a capability.
|
||||||
|
#if CONFIG_VP8_ENCODER
|
||||||
|
const vpx_codec_caps_t vp8_caps = vpx_codec_get_caps(&vpx_codec_vp8_cx_algo);
|
||||||
|
EXPECT_EQ(vp8_caps & VPX_CODEC_CAP_HIGHBITDEPTH, 0);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if CONFIG_VP9_ENCODER
|
||||||
|
const vpx_codec_caps_t vp9_caps = vpx_codec_get_caps(&vpx_codec_vp9_cx_algo);
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
EXPECT_EQ(vp9_caps & VPX_CODEC_CAP_HIGHBITDEPTH, VPX_CODEC_CAP_HIGHBITDEPTH);
|
||||||
|
#else
|
||||||
|
EXPECT_EQ(vp9_caps & VPX_CODEC_CAP_HIGHBITDEPTH, 0);
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
#if CONFIG_VP8_ENCODER
|
||||||
|
TEST(EncodeAPI, ImageSizeSetting) {
|
||||||
|
const int width = 711;
|
||||||
|
const int height = 360;
|
||||||
|
const int bps = 12;
|
||||||
|
vpx_image_t img;
|
||||||
|
vpx_codec_ctx_t enc;
|
||||||
|
vpx_codec_enc_cfg_t cfg;
|
||||||
|
uint8_t *img_buf = reinterpret_cast<uint8_t *>(
|
||||||
|
calloc(width * height * bps / 8, sizeof(*img_buf)));
|
||||||
|
vpx_codec_enc_config_default(vpx_codec_vp8_cx(), &cfg, 0);
|
||||||
|
|
||||||
|
cfg.g_w = width;
|
||||||
|
cfg.g_h = height;
|
||||||
|
|
||||||
|
vpx_img_wrap(&img, VPX_IMG_FMT_I420, width, height, 1, img_buf);
|
||||||
|
|
||||||
|
vpx_codec_enc_init(&enc, vpx_codec_vp8_cx(), &cfg, 0);
|
||||||
|
|
||||||
|
EXPECT_EQ(VPX_CODEC_OK, vpx_codec_encode(&enc, &img, 0, 1, 0, 0));
|
||||||
|
|
||||||
|
free(img_buf);
|
||||||
|
|
||||||
|
vpx_codec_destroy(&enc);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Set up 2 spatial streams with 2 temporal layers per stream, and generate
|
||||||
|
// invalid configuration by setting the temporal layer rate allocation
|
||||||
|
// (ts_target_bitrate[]) to 0 for both layers. This should fail independent of
|
||||||
|
// CONFIG_MULTI_RES_ENCODING.
|
||||||
|
TEST(EncodeAPI, MultiResEncode) {
|
||||||
|
static const vpx_codec_iface_t *kCodecs[] = {
|
||||||
|
#if CONFIG_VP8_ENCODER
|
||||||
|
&vpx_codec_vp8_cx_algo,
|
||||||
|
#endif
|
||||||
|
#if CONFIG_VP9_ENCODER
|
||||||
|
&vpx_codec_vp9_cx_algo,
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
const int width = 1280;
|
||||||
|
const int height = 720;
|
||||||
|
const int width_down = width / 2;
|
||||||
|
const int height_down = height / 2;
|
||||||
|
const int target_bitrate = 1000;
|
||||||
|
const int framerate = 30;
|
||||||
|
|
||||||
|
for (int c = 0; c < NELEMENTS(kCodecs); ++c) {
|
||||||
|
const vpx_codec_iface_t *const iface = kCodecs[c];
|
||||||
|
vpx_codec_ctx_t enc[2];
|
||||||
|
vpx_codec_enc_cfg_t cfg[2];
|
||||||
|
vpx_rational_t dsf[2] = { { 2, 1 }, { 2, 1 } };
|
||||||
|
|
||||||
|
memset(enc, 0, sizeof(enc));
|
||||||
|
|
||||||
|
for (int i = 0; i < 2; i++) {
|
||||||
|
vpx_codec_enc_config_default(iface, &cfg[i], 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Highest-resolution encoder settings */
|
||||||
|
cfg[0].g_w = width;
|
||||||
|
cfg[0].g_h = height;
|
||||||
|
cfg[0].rc_dropframe_thresh = 0;
|
||||||
|
cfg[0].rc_end_usage = VPX_CBR;
|
||||||
|
cfg[0].rc_resize_allowed = 0;
|
||||||
|
cfg[0].rc_min_quantizer = 2;
|
||||||
|
cfg[0].rc_max_quantizer = 56;
|
||||||
|
cfg[0].rc_undershoot_pct = 100;
|
||||||
|
cfg[0].rc_overshoot_pct = 15;
|
||||||
|
cfg[0].rc_buf_initial_sz = 500;
|
||||||
|
cfg[0].rc_buf_optimal_sz = 600;
|
||||||
|
cfg[0].rc_buf_sz = 1000;
|
||||||
|
cfg[0].g_error_resilient = 1; /* Enable error resilient mode */
|
||||||
|
cfg[0].g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
cfg[0].kf_mode = VPX_KF_AUTO;
|
||||||
|
cfg[0].kf_min_dist = 3000;
|
||||||
|
cfg[0].kf_max_dist = 3000;
|
||||||
|
|
||||||
|
cfg[0].rc_target_bitrate = target_bitrate; /* Set target bitrate */
|
||||||
|
cfg[0].g_timebase.num = 1; /* Set fps */
|
||||||
|
cfg[0].g_timebase.den = framerate;
|
||||||
|
|
||||||
|
memcpy(&cfg[1], &cfg[0], sizeof(cfg[0]));
|
||||||
|
cfg[1].rc_target_bitrate = 500;
|
||||||
|
cfg[1].g_w = width_down;
|
||||||
|
cfg[1].g_h = height_down;
|
||||||
|
|
||||||
|
for (int i = 0; i < 2; i++) {
|
||||||
|
cfg[i].ts_number_layers = 2;
|
||||||
|
cfg[i].ts_periodicity = 2;
|
||||||
|
cfg[i].ts_rate_decimator[0] = 2;
|
||||||
|
cfg[i].ts_rate_decimator[1] = 1;
|
||||||
|
cfg[i].ts_layer_id[0] = 0;
|
||||||
|
cfg[i].ts_layer_id[1] = 1;
|
||||||
|
// Invalid parameters.
|
||||||
|
cfg[i].ts_target_bitrate[0] = 0;
|
||||||
|
cfg[i].ts_target_bitrate[1] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// VP9 should report incapable, VP8 invalid for all configurations.
|
||||||
|
const char kVP9Name[] = "WebM Project VP9";
|
||||||
|
const bool is_vp9 = strncmp(kVP9Name, vpx_codec_iface_name(iface),
|
||||||
|
sizeof(kVP9Name) - 1) == 0;
|
||||||
|
EXPECT_EQ(is_vp9 ? VPX_CODEC_INCAPABLE : VPX_CODEC_INVALID_PARAM,
|
||||||
|
vpx_codec_enc_init_multi(&enc[0], iface, &cfg[0], 2, 0, &dsf[0]));
|
||||||
|
|
||||||
|
for (int i = 0; i < 2; i++) {
|
||||||
|
vpx_codec_destroy(&enc[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -201,6 +201,8 @@ void EncoderTest::RunLoop(VideoSource *video) {
|
|||||||
PreEncodeFrameHook(video, encoder.get());
|
PreEncodeFrameHook(video, encoder.get());
|
||||||
encoder->EncodeFrame(video, frame_flags_);
|
encoder->EncodeFrame(video, frame_flags_);
|
||||||
|
|
||||||
|
PostEncodeFrameHook();
|
||||||
|
|
||||||
CxDataIterator iter = encoder->GetCxData();
|
CxDataIterator iter = encoder->GetCxData();
|
||||||
|
|
||||||
bool has_cxdata = false;
|
bool has_cxdata = false;
|
||||||
@ -226,6 +228,8 @@ void EncoderTest::RunLoop(VideoSource *video) {
|
|||||||
|
|
||||||
case VPX_CODEC_PSNR_PKT: PSNRPktHook(pkt); break;
|
case VPX_CODEC_PSNR_PKT: PSNRPktHook(pkt); break;
|
||||||
|
|
||||||
|
case VPX_CODEC_STATS_PKT: StatsPktHook(pkt); break;
|
||||||
|
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -128,17 +128,31 @@ class Encoder {
|
|||||||
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Control(int ctrl_id, struct vpx_svc_ref_frame_config *arg) {
|
||||||
|
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
||||||
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
|
}
|
||||||
|
|
||||||
void Control(int ctrl_id, struct vpx_svc_parameters *arg) {
|
void Control(int ctrl_id, struct vpx_svc_parameters *arg) {
|
||||||
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Control(int ctrl_id, struct vpx_svc_frame_drop *arg) {
|
||||||
|
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
||||||
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
|
}
|
||||||
#if CONFIG_VP8_ENCODER || CONFIG_VP9_ENCODER
|
#if CONFIG_VP8_ENCODER || CONFIG_VP9_ENCODER
|
||||||
void Control(int ctrl_id, vpx_active_map_t *arg) {
|
void Control(int ctrl_id, vpx_active_map_t *arg) {
|
||||||
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
|
void Control(int ctrl_id, vpx_roi_map_t *arg) {
|
||||||
|
const vpx_codec_err_t res = vpx_codec_control_(&encoder_, ctrl_id, arg);
|
||||||
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
void Config(const vpx_codec_enc_cfg_t *cfg) {
|
void Config(const vpx_codec_enc_cfg_t *cfg) {
|
||||||
const vpx_codec_err_t res = vpx_codec_enc_config_set(&encoder_, cfg);
|
const vpx_codec_err_t res = vpx_codec_enc_config_set(&encoder_, cfg);
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
ASSERT_EQ(VPX_CODEC_OK, res) << EncoderError();
|
||||||
@ -212,12 +226,17 @@ class EncoderTest {
|
|||||||
virtual void PreEncodeFrameHook(VideoSource * /*video*/,
|
virtual void PreEncodeFrameHook(VideoSource * /*video*/,
|
||||||
Encoder * /*encoder*/) {}
|
Encoder * /*encoder*/) {}
|
||||||
|
|
||||||
|
virtual void PostEncodeFrameHook() {}
|
||||||
|
|
||||||
// Hook to be called on every compressed data packet.
|
// Hook to be called on every compressed data packet.
|
||||||
virtual void FramePktHook(const vpx_codec_cx_pkt_t * /*pkt*/) {}
|
virtual void FramePktHook(const vpx_codec_cx_pkt_t * /*pkt*/) {}
|
||||||
|
|
||||||
// Hook to be called on every PSNR packet.
|
// Hook to be called on every PSNR packet.
|
||||||
virtual void PSNRPktHook(const vpx_codec_cx_pkt_t * /*pkt*/) {}
|
virtual void PSNRPktHook(const vpx_codec_cx_pkt_t * /*pkt*/) {}
|
||||||
|
|
||||||
|
// Hook to be called on every first pass stats packet.
|
||||||
|
virtual void StatsPktHook(const vpx_codec_cx_pkt_t * /*pkt*/) {}
|
||||||
|
|
||||||
// Hook to determine whether the encode loop should continue.
|
// Hook to determine whether the encode loop should continue.
|
||||||
virtual bool Continue() const {
|
virtual bool Continue() const {
|
||||||
return !(::testing::Test::HasFatalFailure() || abort_);
|
return !(::testing::Test::HasFatalFailure() || abort_);
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
example_tests=$(ls $(dirname $0)/*.sh)
|
example_tests=$(ls $(dirname $0)/*.sh)
|
||||||
|
|
||||||
# List of script names to exclude.
|
# List of script names to exclude.
|
||||||
exclude_list="examples tools_common"
|
exclude_list="examples stress tools_common"
|
||||||
|
|
||||||
# Filter out the scripts in $exclude_list.
|
# Filter out the scripts in $exclude_list.
|
||||||
for word in ${exclude_list}; do
|
for word in ${exclude_list}; do
|
||||||
|
@ -34,7 +34,8 @@ struct ExternalFrameBuffer {
|
|||||||
// Class to manipulate a list of external frame buffers.
|
// Class to manipulate a list of external frame buffers.
|
||||||
class ExternalFrameBufferList {
|
class ExternalFrameBufferList {
|
||||||
public:
|
public:
|
||||||
ExternalFrameBufferList() : num_buffers_(0), ext_fb_list_(NULL) {}
|
ExternalFrameBufferList()
|
||||||
|
: num_buffers_(0), num_used_buffers_(0), ext_fb_list_(NULL) {}
|
||||||
|
|
||||||
virtual ~ExternalFrameBufferList() {
|
virtual ~ExternalFrameBufferList() {
|
||||||
for (int i = 0; i < num_buffers_; ++i) {
|
for (int i = 0; i < num_buffers_; ++i) {
|
||||||
@ -71,6 +72,8 @@ class ExternalFrameBufferList {
|
|||||||
}
|
}
|
||||||
|
|
||||||
SetFrameBuffer(idx, fb);
|
SetFrameBuffer(idx, fb);
|
||||||
|
|
||||||
|
num_used_buffers_++;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -106,6 +109,7 @@ class ExternalFrameBufferList {
|
|||||||
}
|
}
|
||||||
EXPECT_EQ(1, ext_fb->in_use);
|
EXPECT_EQ(1, ext_fb->in_use);
|
||||||
ext_fb->in_use = 0;
|
ext_fb->in_use = 0;
|
||||||
|
num_used_buffers_--;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -121,6 +125,8 @@ class ExternalFrameBufferList {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int num_used_buffers() const { return num_used_buffers_; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// Returns the index of the first free frame buffer. Returns |num_buffers_|
|
// Returns the index of the first free frame buffer. Returns |num_buffers_|
|
||||||
// if there are no free frame buffers.
|
// if there are no free frame buffers.
|
||||||
@ -145,6 +151,7 @@ class ExternalFrameBufferList {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int num_buffers_;
|
int num_buffers_;
|
||||||
|
int num_used_buffers_;
|
||||||
ExternalFrameBuffer *ext_fb_list_;
|
ExternalFrameBuffer *ext_fb_list_;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -220,8 +227,8 @@ class ExternalFrameBufferMD5Test
|
|||||||
|
|
||||||
void OpenMD5File(const std::string &md5_file_name_) {
|
void OpenMD5File(const std::string &md5_file_name_) {
|
||||||
md5_file_ = libvpx_test::OpenTestDataFile(md5_file_name_);
|
md5_file_ = libvpx_test::OpenTestDataFile(md5_file_name_);
|
||||||
ASSERT_TRUE(md5_file_ != NULL) << "Md5 file open failed. Filename: "
|
ASSERT_TRUE(md5_file_ != NULL)
|
||||||
<< md5_file_name_;
|
<< "Md5 file open failed. Filename: " << md5_file_name_;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
||||||
@ -273,6 +280,7 @@ class ExternalFrameBufferMD5Test
|
|||||||
|
|
||||||
#if CONFIG_WEBM_IO
|
#if CONFIG_WEBM_IO
|
||||||
const char kVP9TestFile[] = "vp90-2-02-size-lf-1920x1080.webm";
|
const char kVP9TestFile[] = "vp90-2-02-size-lf-1920x1080.webm";
|
||||||
|
const char kVP9NonRefTestFile[] = "vp90-2-22-svc_1280x720_1.webm";
|
||||||
|
|
||||||
// Class for testing passing in external frame buffers to libvpx.
|
// Class for testing passing in external frame buffers to libvpx.
|
||||||
class ExternalFrameBufferTest : public ::testing::Test {
|
class ExternalFrameBufferTest : public ::testing::Test {
|
||||||
@ -292,7 +300,9 @@ class ExternalFrameBufferTest : public ::testing::Test {
|
|||||||
|
|
||||||
virtual void TearDown() {
|
virtual void TearDown() {
|
||||||
delete decoder_;
|
delete decoder_;
|
||||||
|
decoder_ = NULL;
|
||||||
delete video_;
|
delete video_;
|
||||||
|
video_ = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Passes the external frame buffer information to libvpx.
|
// Passes the external frame buffer information to libvpx.
|
||||||
@ -325,7 +335,7 @@ class ExternalFrameBufferTest : public ::testing::Test {
|
|||||||
return VPX_CODEC_OK;
|
return VPX_CODEC_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
protected:
|
||||||
void CheckDecodedFrames() {
|
void CheckDecodedFrames() {
|
||||||
libvpx_test::DxDataIterator dec_iter = decoder_->GetDxData();
|
libvpx_test::DxDataIterator dec_iter = decoder_->GetDxData();
|
||||||
const vpx_image_t *img = NULL;
|
const vpx_image_t *img = NULL;
|
||||||
@ -341,6 +351,25 @@ class ExternalFrameBufferTest : public ::testing::Test {
|
|||||||
int num_buffers_;
|
int num_buffers_;
|
||||||
ExternalFrameBufferList fb_list_;
|
ExternalFrameBufferList fb_list_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class ExternalFrameBufferNonRefTest : public ExternalFrameBufferTest {
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() {
|
||||||
|
video_ = new libvpx_test::WebMVideoSource(kVP9NonRefTestFile);
|
||||||
|
ASSERT_TRUE(video_ != NULL);
|
||||||
|
video_->Init();
|
||||||
|
video_->Begin();
|
||||||
|
|
||||||
|
vpx_codec_dec_cfg_t cfg = vpx_codec_dec_cfg_t();
|
||||||
|
decoder_ = new libvpx_test::VP9Decoder(cfg, 0);
|
||||||
|
ASSERT_TRUE(decoder_ != NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void CheckFrameBufferRelease() {
|
||||||
|
TearDown();
|
||||||
|
ASSERT_EQ(0, fb_list_.num_used_buffers());
|
||||||
|
}
|
||||||
|
};
|
||||||
#endif // CONFIG_WEBM_IO
|
#endif // CONFIG_WEBM_IO
|
||||||
|
|
||||||
// This test runs through the set of test vectors, and decodes them.
|
// This test runs through the set of test vectors, and decodes them.
|
||||||
@ -419,6 +448,8 @@ TEST_F(ExternalFrameBufferTest, NotEnoughBuffers) {
|
|||||||
SetFrameBufferFunctions(num_buffers, get_vp9_frame_buffer,
|
SetFrameBufferFunctions(num_buffers, get_vp9_frame_buffer,
|
||||||
release_vp9_frame_buffer));
|
release_vp9_frame_buffer));
|
||||||
ASSERT_EQ(VPX_CODEC_OK, DecodeOneFrame());
|
ASSERT_EQ(VPX_CODEC_OK, DecodeOneFrame());
|
||||||
|
// Only run this on long clips. Decoding a very short clip will return
|
||||||
|
// VPX_CODEC_OK even with only 2 buffers.
|
||||||
ASSERT_EQ(VPX_CODEC_MEM_ERROR, DecodeRemainingFrames());
|
ASSERT_EQ(VPX_CODEC_MEM_ERROR, DecodeRemainingFrames());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -467,6 +498,15 @@ TEST_F(ExternalFrameBufferTest, SetAfterDecode) {
|
|||||||
SetFrameBufferFunctions(num_buffers, get_vp9_frame_buffer,
|
SetFrameBufferFunctions(num_buffers, get_vp9_frame_buffer,
|
||||||
release_vp9_frame_buffer));
|
release_vp9_frame_buffer));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_F(ExternalFrameBufferNonRefTest, ReleaseNonRefFrameBuffer) {
|
||||||
|
const int num_buffers = VP9_MAXIMUM_REF_BUFFERS + VPX_MAXIMUM_WORK_BUFFERS;
|
||||||
|
ASSERT_EQ(VPX_CODEC_OK,
|
||||||
|
SetFrameBufferFunctions(num_buffers, get_vp9_frame_buffer,
|
||||||
|
release_vp9_frame_buffer));
|
||||||
|
ASSERT_EQ(VPX_CODEC_OK, DecodeRemainingFrames());
|
||||||
|
CheckFrameBufferRelease();
|
||||||
|
}
|
||||||
#endif // CONFIG_WEBM_IO
|
#endif // CONFIG_WEBM_IO
|
||||||
|
|
||||||
VP9_INSTANTIATE_TEST_CASE(
|
VP9_INSTANTIATE_TEST_CASE(
|
||||||
|
@ -1,512 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (c) 2012 The WebM project authors. All Rights Reserved.
|
|
||||||
*
|
|
||||||
* Use of this source code is governed by a BSD-style license
|
|
||||||
* that can be found in the LICENSE file in the root of the source
|
|
||||||
* tree. An additional intellectual property rights grant can be found
|
|
||||||
* in the file PATENTS. All contributing project authors may
|
|
||||||
* be found in the AUTHORS file in the root of the source tree.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <math.h>
|
|
||||||
#include <stdlib.h>
|
|
||||||
#include <string.h>
|
|
||||||
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
|
||||||
|
|
||||||
#include "./vp9_rtcd.h"
|
|
||||||
#include "./vpx_dsp_rtcd.h"
|
|
||||||
#include "test/acm_random.h"
|
|
||||||
#include "test/clear_system_state.h"
|
|
||||||
#include "test/register_state_check.h"
|
|
||||||
#include "test/util.h"
|
|
||||||
#include "vp9/common/vp9_entropy.h"
|
|
||||||
#include "vpx/vpx_codec.h"
|
|
||||||
#include "vpx/vpx_integer.h"
|
|
||||||
#include "vpx_ports/mem.h"
|
|
||||||
|
|
||||||
using libvpx_test::ACMRandom;
|
|
||||||
|
|
||||||
namespace {
|
|
||||||
const int kNumCoeffs = 16;
|
|
||||||
typedef void (*FdctFunc)(const int16_t *in, tran_low_t *out, int stride);
|
|
||||||
typedef void (*IdctFunc)(const tran_low_t *in, uint8_t *out, int stride);
|
|
||||||
typedef void (*FhtFunc)(const int16_t *in, tran_low_t *out, int stride,
|
|
||||||
int tx_type);
|
|
||||||
typedef void (*IhtFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
|
||||||
int tx_type);
|
|
||||||
|
|
||||||
typedef std::tr1::tuple<FdctFunc, IdctFunc, int, vpx_bit_depth_t> Dct4x4Param;
|
|
||||||
typedef std::tr1::tuple<FhtFunc, IhtFunc, int, vpx_bit_depth_t> Ht4x4Param;
|
|
||||||
|
|
||||||
void fdct4x4_ref(const int16_t *in, tran_low_t *out, int stride,
|
|
||||||
int /*tx_type*/) {
|
|
||||||
vpx_fdct4x4_c(in, out, stride);
|
|
||||||
}
|
|
||||||
|
|
||||||
void fht4x4_ref(const int16_t *in, tran_low_t *out, int stride, int tx_type) {
|
|
||||||
vp9_fht4x4_c(in, out, stride, tx_type);
|
|
||||||
}
|
|
||||||
|
|
||||||
void fwht4x4_ref(const int16_t *in, tran_low_t *out, int stride,
|
|
||||||
int /*tx_type*/) {
|
|
||||||
vp9_fwht4x4_c(in, out, stride);
|
|
||||||
}
|
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
void idct4x4_10(const tran_low_t *in, uint8_t *out, int stride) {
|
|
||||||
vpx_highbd_idct4x4_16_add_c(in, out, stride, 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
void idct4x4_12(const tran_low_t *in, uint8_t *out, int stride) {
|
|
||||||
vpx_highbd_idct4x4_16_add_c(in, out, stride, 12);
|
|
||||||
}
|
|
||||||
|
|
||||||
void iht4x4_10(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
|
||||||
vp9_highbd_iht4x4_16_add_c(in, out, stride, tx_type, 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
void iht4x4_12(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
|
||||||
vp9_highbd_iht4x4_16_add_c(in, out, stride, tx_type, 12);
|
|
||||||
}
|
|
||||||
|
|
||||||
void iwht4x4_10(const tran_low_t *in, uint8_t *out, int stride) {
|
|
||||||
vpx_highbd_iwht4x4_16_add_c(in, out, stride, 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
void iwht4x4_12(const tran_low_t *in, uint8_t *out, int stride) {
|
|
||||||
vpx_highbd_iwht4x4_16_add_c(in, out, stride, 12);
|
|
||||||
}
|
|
||||||
|
|
||||||
#if HAVE_SSE2
|
|
||||||
void idct4x4_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
|
||||||
vpx_highbd_idct4x4_16_add_sse2(in, out, stride, 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
void idct4x4_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
|
||||||
vpx_highbd_idct4x4_16_add_sse2(in, out, stride, 12);
|
|
||||||
}
|
|
||||||
#endif // HAVE_SSE2
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
|
|
||||||
class Trans4x4TestBase {
|
|
||||||
public:
|
|
||||||
virtual ~Trans4x4TestBase() {}
|
|
||||||
|
|
||||||
protected:
|
|
||||||
virtual void RunFwdTxfm(const int16_t *in, tran_low_t *out, int stride) = 0;
|
|
||||||
|
|
||||||
virtual void RunInvTxfm(const tran_low_t *out, uint8_t *dst, int stride) = 0;
|
|
||||||
|
|
||||||
void RunAccuracyCheck(int limit) {
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
uint32_t max_error = 0;
|
|
||||||
int64_t total_error = 0;
|
|
||||||
const int count_test_block = 10000;
|
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
|
||||||
DECLARE_ALIGNED(16, int16_t, test_input_block[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, test_temp_block[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, uint8_t, dst[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, uint8_t, src[kNumCoeffs]);
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
DECLARE_ALIGNED(16, uint16_t, dst16[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, uint16_t, src16[kNumCoeffs]);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// Initialize a test block with input range [-255, 255].
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
if (bit_depth_ == VPX_BITS_8) {
|
|
||||||
src[j] = rnd.Rand8();
|
|
||||||
dst[j] = rnd.Rand8();
|
|
||||||
test_input_block[j] = src[j] - dst[j];
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
} else {
|
|
||||||
src16[j] = rnd.Rand16() & mask_;
|
|
||||||
dst16[j] = rnd.Rand16() & mask_;
|
|
||||||
test_input_block[j] = src16[j] - dst16[j];
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(
|
|
||||||
RunFwdTxfm(test_input_block, test_temp_block, pitch_));
|
|
||||||
if (bit_depth_ == VPX_BITS_8) {
|
|
||||||
ASM_REGISTER_STATE_CHECK(RunInvTxfm(test_temp_block, dst, pitch_));
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
} else {
|
|
||||||
ASM_REGISTER_STATE_CHECK(
|
|
||||||
RunInvTxfm(test_temp_block, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int diff =
|
|
||||||
bit_depth_ == VPX_BITS_8 ? dst[j] - src[j] : dst16[j] - src16[j];
|
|
||||||
#else
|
|
||||||
ASSERT_EQ(VPX_BITS_8, bit_depth_);
|
|
||||||
const int diff = dst[j] - src[j];
|
|
||||||
#endif
|
|
||||||
const uint32_t error = diff * diff;
|
|
||||||
if (max_error < error) max_error = error;
|
|
||||||
total_error += error;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPECT_GE(static_cast<uint32_t>(limit), max_error)
|
|
||||||
<< "Error: 4x4 FHT/IHT has an individual round trip error > " << limit;
|
|
||||||
|
|
||||||
EXPECT_GE(count_test_block * limit, total_error)
|
|
||||||
<< "Error: 4x4 FHT/IHT has average round trip error > " << limit
|
|
||||||
<< " per block";
|
|
||||||
}
|
|
||||||
|
|
||||||
void RunCoeffCheck() {
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
const int count_test_block = 5000;
|
|
||||||
DECLARE_ALIGNED(16, int16_t, input_block[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output_ref_block[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output_block[kNumCoeffs]);
|
|
||||||
|
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
|
||||||
// Initialize a test block with input range [-mask_, mask_].
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
input_block[j] = (rnd.Rand16() & mask_) - (rnd.Rand16() & mask_);
|
|
||||||
}
|
|
||||||
|
|
||||||
fwd_txfm_ref(input_block, output_ref_block, pitch_, tx_type_);
|
|
||||||
ASM_REGISTER_STATE_CHECK(RunFwdTxfm(input_block, output_block, pitch_));
|
|
||||||
|
|
||||||
// The minimum quant value is 4.
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j)
|
|
||||||
EXPECT_EQ(output_block[j], output_ref_block[j]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void RunMemCheck() {
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
const int count_test_block = 5000;
|
|
||||||
DECLARE_ALIGNED(16, int16_t, input_extreme_block[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output_ref_block[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, output_block[kNumCoeffs]);
|
|
||||||
|
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
|
||||||
// Initialize a test block with input range [-mask_, mask_].
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
input_extreme_block[j] = rnd.Rand8() % 2 ? mask_ : -mask_;
|
|
||||||
}
|
|
||||||
if (i == 0) {
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) input_extreme_block[j] = mask_;
|
|
||||||
} else if (i == 1) {
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) input_extreme_block[j] = -mask_;
|
|
||||||
}
|
|
||||||
|
|
||||||
fwd_txfm_ref(input_extreme_block, output_ref_block, pitch_, tx_type_);
|
|
||||||
ASM_REGISTER_STATE_CHECK(
|
|
||||||
RunFwdTxfm(input_extreme_block, output_block, pitch_));
|
|
||||||
|
|
||||||
// The minimum quant value is 4.
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
EXPECT_EQ(output_block[j], output_ref_block[j]);
|
|
||||||
EXPECT_GE(4 * DCT_MAX_VALUE << (bit_depth_ - 8), abs(output_block[j]))
|
|
||||||
<< "Error: 4x4 FDCT has coefficient larger than 4*DCT_MAX_VALUE";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void RunInvAccuracyCheck(int limit) {
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
const int count_test_block = 1000;
|
|
||||||
DECLARE_ALIGNED(16, int16_t, in[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, uint8_t, dst[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, uint8_t, src[kNumCoeffs]);
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
DECLARE_ALIGNED(16, uint16_t, dst16[kNumCoeffs]);
|
|
||||||
DECLARE_ALIGNED(16, uint16_t, src16[kNumCoeffs]);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
|
||||||
// Initialize a test block with input range [-mask_, mask_].
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
if (bit_depth_ == VPX_BITS_8) {
|
|
||||||
src[j] = rnd.Rand8();
|
|
||||||
dst[j] = rnd.Rand8();
|
|
||||||
in[j] = src[j] - dst[j];
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
} else {
|
|
||||||
src16[j] = rnd.Rand16() & mask_;
|
|
||||||
dst16[j] = rnd.Rand16() & mask_;
|
|
||||||
in[j] = src16[j] - dst16[j];
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fwd_txfm_ref(in, coeff, pitch_, tx_type_);
|
|
||||||
|
|
||||||
if (bit_depth_ == VPX_BITS_8) {
|
|
||||||
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, pitch_));
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
} else {
|
|
||||||
ASM_REGISTER_STATE_CHECK(
|
|
||||||
RunInvTxfm(coeff, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int j = 0; j < kNumCoeffs; ++j) {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int diff =
|
|
||||||
bit_depth_ == VPX_BITS_8 ? dst[j] - src[j] : dst16[j] - src16[j];
|
|
||||||
#else
|
|
||||||
const int diff = dst[j] - src[j];
|
|
||||||
#endif
|
|
||||||
const uint32_t error = diff * diff;
|
|
||||||
EXPECT_GE(static_cast<uint32_t>(limit), error)
|
|
||||||
<< "Error: 4x4 IDCT has error " << error << " at index " << j;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int pitch_;
|
|
||||||
int tx_type_;
|
|
||||||
FhtFunc fwd_txfm_ref;
|
|
||||||
vpx_bit_depth_t bit_depth_;
|
|
||||||
int mask_;
|
|
||||||
};
|
|
||||||
|
|
||||||
class Trans4x4DCT : public Trans4x4TestBase,
|
|
||||||
public ::testing::TestWithParam<Dct4x4Param> {
|
|
||||||
public:
|
|
||||||
virtual ~Trans4x4DCT() {}
|
|
||||||
|
|
||||||
virtual void SetUp() {
|
|
||||||
fwd_txfm_ = GET_PARAM(0);
|
|
||||||
inv_txfm_ = GET_PARAM(1);
|
|
||||||
tx_type_ = GET_PARAM(2);
|
|
||||||
pitch_ = 4;
|
|
||||||
fwd_txfm_ref = fdct4x4_ref;
|
|
||||||
bit_depth_ = GET_PARAM(3);
|
|
||||||
mask_ = (1 << bit_depth_) - 1;
|
|
||||||
}
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
|
||||||
|
|
||||||
protected:
|
|
||||||
void RunFwdTxfm(const int16_t *in, tran_low_t *out, int stride) {
|
|
||||||
fwd_txfm_(in, out, stride);
|
|
||||||
}
|
|
||||||
void RunInvTxfm(const tran_low_t *out, uint8_t *dst, int stride) {
|
|
||||||
inv_txfm_(out, dst, stride);
|
|
||||||
}
|
|
||||||
|
|
||||||
FdctFunc fwd_txfm_;
|
|
||||||
IdctFunc inv_txfm_;
|
|
||||||
};
|
|
||||||
|
|
||||||
TEST_P(Trans4x4DCT, AccuracyCheck) { RunAccuracyCheck(1); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4DCT, CoeffCheck) { RunCoeffCheck(); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4DCT, MemCheck) { RunMemCheck(); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4DCT, InvAccuracyCheck) { RunInvAccuracyCheck(1); }
|
|
||||||
|
|
||||||
class Trans4x4HT : public Trans4x4TestBase,
|
|
||||||
public ::testing::TestWithParam<Ht4x4Param> {
|
|
||||||
public:
|
|
||||||
virtual ~Trans4x4HT() {}
|
|
||||||
|
|
||||||
virtual void SetUp() {
|
|
||||||
fwd_txfm_ = GET_PARAM(0);
|
|
||||||
inv_txfm_ = GET_PARAM(1);
|
|
||||||
tx_type_ = GET_PARAM(2);
|
|
||||||
pitch_ = 4;
|
|
||||||
fwd_txfm_ref = fht4x4_ref;
|
|
||||||
bit_depth_ = GET_PARAM(3);
|
|
||||||
mask_ = (1 << bit_depth_) - 1;
|
|
||||||
}
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
|
||||||
|
|
||||||
protected:
|
|
||||||
void RunFwdTxfm(const int16_t *in, tran_low_t *out, int stride) {
|
|
||||||
fwd_txfm_(in, out, stride, tx_type_);
|
|
||||||
}
|
|
||||||
|
|
||||||
void RunInvTxfm(const tran_low_t *out, uint8_t *dst, int stride) {
|
|
||||||
inv_txfm_(out, dst, stride, tx_type_);
|
|
||||||
}
|
|
||||||
|
|
||||||
FhtFunc fwd_txfm_;
|
|
||||||
IhtFunc inv_txfm_;
|
|
||||||
};
|
|
||||||
|
|
||||||
TEST_P(Trans4x4HT, AccuracyCheck) { RunAccuracyCheck(1); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4HT, CoeffCheck) { RunCoeffCheck(); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4HT, MemCheck) { RunMemCheck(); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4HT, InvAccuracyCheck) { RunInvAccuracyCheck(1); }
|
|
||||||
|
|
||||||
class Trans4x4WHT : public Trans4x4TestBase,
|
|
||||||
public ::testing::TestWithParam<Dct4x4Param> {
|
|
||||||
public:
|
|
||||||
virtual ~Trans4x4WHT() {}
|
|
||||||
|
|
||||||
virtual void SetUp() {
|
|
||||||
fwd_txfm_ = GET_PARAM(0);
|
|
||||||
inv_txfm_ = GET_PARAM(1);
|
|
||||||
tx_type_ = GET_PARAM(2);
|
|
||||||
pitch_ = 4;
|
|
||||||
fwd_txfm_ref = fwht4x4_ref;
|
|
||||||
bit_depth_ = GET_PARAM(3);
|
|
||||||
mask_ = (1 << bit_depth_) - 1;
|
|
||||||
}
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
|
||||||
|
|
||||||
protected:
|
|
||||||
void RunFwdTxfm(const int16_t *in, tran_low_t *out, int stride) {
|
|
||||||
fwd_txfm_(in, out, stride);
|
|
||||||
}
|
|
||||||
void RunInvTxfm(const tran_low_t *out, uint8_t *dst, int stride) {
|
|
||||||
inv_txfm_(out, dst, stride);
|
|
||||||
}
|
|
||||||
|
|
||||||
FdctFunc fwd_txfm_;
|
|
||||||
IdctFunc inv_txfm_;
|
|
||||||
};
|
|
||||||
|
|
||||||
TEST_P(Trans4x4WHT, AccuracyCheck) { RunAccuracyCheck(0); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4WHT, CoeffCheck) { RunCoeffCheck(); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4WHT, MemCheck) { RunMemCheck(); }
|
|
||||||
|
|
||||||
TEST_P(Trans4x4WHT, InvAccuracyCheck) { RunInvAccuracyCheck(0); }
|
|
||||||
using std::tr1::make_tuple;
|
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
C, Trans4x4DCT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vpx_highbd_fdct4x4_c, &idct4x4_10, 0, VPX_BITS_10),
|
|
||||||
make_tuple(&vpx_highbd_fdct4x4_c, &idct4x4_12, 0, VPX_BITS_12),
|
|
||||||
make_tuple(&vpx_fdct4x4_c, &vpx_idct4x4_16_add_c, 0, VPX_BITS_8)));
|
|
||||||
#else
|
|
||||||
INSTANTIATE_TEST_CASE_P(C, Trans4x4DCT,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct4x4_c,
|
|
||||||
&vpx_idct4x4_16_add_c, 0,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
C, Trans4x4HT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_10, 0, VPX_BITS_10),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_10, 1, VPX_BITS_10),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_10, 2, VPX_BITS_10),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_10, 3, VPX_BITS_10),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_12, 0, VPX_BITS_12),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_12, 1, VPX_BITS_12),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_12, 2, VPX_BITS_12),
|
|
||||||
make_tuple(&vp9_highbd_fht4x4_c, &iht4x4_12, 3, VPX_BITS_12),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 1, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 2, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 3, VPX_BITS_8)));
|
|
||||||
#else
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
C, Trans4x4HT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 1, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 2, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_c, 3, VPX_BITS_8)));
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
C, Trans4x4WHT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_highbd_fwht4x4_c, &iwht4x4_10, 0, VPX_BITS_10),
|
|
||||||
make_tuple(&vp9_highbd_fwht4x4_c, &iwht4x4_12, 0, VPX_BITS_12),
|
|
||||||
make_tuple(&vp9_fwht4x4_c, &vpx_iwht4x4_16_add_c, 0, VPX_BITS_8)));
|
|
||||||
#else
|
|
||||||
INSTANTIATE_TEST_CASE_P(C, Trans4x4WHT,
|
|
||||||
::testing::Values(make_tuple(&vp9_fwht4x4_c,
|
|
||||||
&vpx_iwht4x4_16_add_c, 0,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
|
|
||||||
#if HAVE_NEON_ASM && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
INSTANTIATE_TEST_CASE_P(NEON, Trans4x4DCT,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct4x4_c,
|
|
||||||
&vpx_idct4x4_16_add_neon,
|
|
||||||
0, VPX_BITS_8)));
|
|
||||||
#endif // HAVE_NEON_ASM && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
|
|
||||||
#if HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
NEON, Trans4x4HT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_neon, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_neon, 1, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_neon, 2, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_c, &vp9_iht4x4_16_add_neon, 3, VPX_BITS_8)));
|
|
||||||
#endif // HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
|
|
||||||
#if HAVE_SSE2 && !CONFIG_EMULATE_HARDWARE
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
SSE2, Trans4x4WHT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_fwht4x4_sse2, &vpx_iwht4x4_16_add_c, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fwht4x4_c, &vpx_iwht4x4_16_add_sse2, 0, VPX_BITS_8)));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, Trans4x4DCT,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct4x4_sse2,
|
|
||||||
&vpx_idct4x4_16_add_sse2,
|
|
||||||
0, VPX_BITS_8)));
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
SSE2, Trans4x4HT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_sse2, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_sse2, 1, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_sse2, 2, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_sse2, 3, VPX_BITS_8)));
|
|
||||||
#endif // HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
|
|
||||||
#if HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
SSE2, Trans4x4DCT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vpx_highbd_fdct4x4_c, &idct4x4_10_sse2, 0, VPX_BITS_10),
|
|
||||||
make_tuple(&vpx_highbd_fdct4x4_sse2, &idct4x4_10_sse2, 0, VPX_BITS_10),
|
|
||||||
make_tuple(&vpx_highbd_fdct4x4_c, &idct4x4_12_sse2, 0, VPX_BITS_12),
|
|
||||||
make_tuple(&vpx_highbd_fdct4x4_sse2, &idct4x4_12_sse2, 0, VPX_BITS_12),
|
|
||||||
make_tuple(&vpx_fdct4x4_sse2, &vpx_idct4x4_16_add_c, 0, VPX_BITS_8)));
|
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
SSE2, Trans4x4HT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_c, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_c, 1, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_c, 2, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_sse2, &vp9_iht4x4_16_add_c, 3, VPX_BITS_8)));
|
|
||||||
#endif // HAVE_SSE2 && CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
|
|
||||||
#if HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
INSTANTIATE_TEST_CASE_P(MSA, Trans4x4DCT,
|
|
||||||
::testing::Values(make_tuple(&vpx_fdct4x4_msa,
|
|
||||||
&vpx_idct4x4_16_add_msa, 0,
|
|
||||||
VPX_BITS_8)));
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
|
||||||
MSA, Trans4x4HT,
|
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_fht4x4_msa, &vp9_iht4x4_16_add_msa, 0, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_msa, &vp9_iht4x4_16_add_msa, 1, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_msa, &vp9_iht4x4_16_add_msa, 2, VPX_BITS_8),
|
|
||||||
make_tuple(&vp9_fht4x4_msa, &vp9_iht4x4_16_add_msa, 3, VPX_BITS_8)));
|
|
||||||
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
} // namespace
|
|
@ -43,9 +43,9 @@ typedef void (*FhtFunc)(const int16_t *in, tran_low_t *out, int stride,
|
|||||||
typedef void (*IhtFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
typedef void (*IhtFunc)(const tran_low_t *in, uint8_t *out, int stride,
|
||||||
int tx_type);
|
int tx_type);
|
||||||
|
|
||||||
typedef std::tr1::tuple<FdctFunc, IdctFunc, int, vpx_bit_depth_t> Dct8x8Param;
|
typedef ::testing::tuple<FdctFunc, IdctFunc, int, vpx_bit_depth_t> Dct8x8Param;
|
||||||
typedef std::tr1::tuple<FhtFunc, IhtFunc, int, vpx_bit_depth_t> Ht8x8Param;
|
typedef ::testing::tuple<FhtFunc, IhtFunc, int, vpx_bit_depth_t> Ht8x8Param;
|
||||||
typedef std::tr1::tuple<IdctFunc, IdctFunc, int, vpx_bit_depth_t> Idct8x8Param;
|
typedef ::testing::tuple<IdctFunc, IdctFunc, int, vpx_bit_depth_t> Idct8x8Param;
|
||||||
|
|
||||||
void reference_8x8_dct_1d(const double in[8], double out[8]) {
|
void reference_8x8_dct_1d(const double in[8], double out[8]) {
|
||||||
const double kInvSqrt2 = 0.707106781186547524400844362104;
|
const double kInvSqrt2 = 0.707106781186547524400844362104;
|
||||||
@ -88,45 +88,45 @@ void fht8x8_ref(const int16_t *in, tran_low_t *out, int stride, int tx_type) {
|
|||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
void idct8x8_10(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_10(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_64_add_c(in, out, stride, 10);
|
vpx_highbd_idct8x8_64_add_c(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct8x8_12(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_12(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_64_add_c(in, out, stride, 12);
|
vpx_highbd_idct8x8_64_add_c(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
void iht8x8_10(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
void iht8x8_10(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
||||||
vp9_highbd_iht8x8_64_add_c(in, out, stride, tx_type, 10);
|
vp9_highbd_iht8x8_64_add_c(in, CAST_TO_SHORTPTR(out), stride, tx_type, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void iht8x8_12(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
void iht8x8_12(const tran_low_t *in, uint8_t *out, int stride, int tx_type) {
|
||||||
vp9_highbd_iht8x8_64_add_c(in, out, stride, tx_type, 12);
|
vp9_highbd_iht8x8_64_add_c(in, CAST_TO_SHORTPTR(out), stride, tx_type, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
|
|
||||||
void idct8x8_12_add_10_c(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_12_add_10_c(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_12_add_c(in, out, stride, 10);
|
vpx_highbd_idct8x8_12_add_c(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct8x8_12_add_12_c(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_12_add_12_c(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_12_add_c(in, out, stride, 12);
|
vpx_highbd_idct8x8_12_add_c(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct8x8_12_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_12_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_12_add_sse2(in, out, stride, 10);
|
vpx_highbd_idct8x8_12_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct8x8_12_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_12_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_12_add_sse2(in, out, stride, 12);
|
vpx_highbd_idct8x8_12_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct8x8_64_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_64_add_10_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_64_add_sse2(in, out, stride, 10);
|
vpx_highbd_idct8x8_64_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
void idct8x8_64_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
void idct8x8_64_add_12_sse2(const tran_low_t *in, uint8_t *out, int stride) {
|
||||||
vpx_highbd_idct8x8_64_add_sse2(in, out, stride, 12);
|
vpx_highbd_idct8x8_64_add_sse2(in, CAST_TO_SHORTPTR(out), stride, 12);
|
||||||
}
|
}
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
@ -257,7 +257,7 @@ class FwdTrans8x8TestBase {
|
|||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(test_temp_block, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(test_temp_block, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -340,7 +340,7 @@ class FwdTrans8x8TestBase {
|
|||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(test_temp_block, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(test_temp_block, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -413,7 +413,7 @@ class FwdTrans8x8TestBase {
|
|||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(coeff, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(coeff, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -497,9 +497,9 @@ class FwdTrans8x8TestBase {
|
|||||||
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, pitch_));
|
ASM_REGISTER_STATE_CHECK(RunInvTxfm(coeff, dst, pitch_));
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
} else {
|
} else {
|
||||||
ref_txfm(coeff, CONVERT_TO_BYTEPTR(ref16), pitch_);
|
ref_txfm(coeff, CAST_TO_BYTEPTR(ref16), pitch_);
|
||||||
ASM_REGISTER_STATE_CHECK(
|
ASM_REGISTER_STATE_CHECK(
|
||||||
RunInvTxfm(coeff, CONVERT_TO_BYTEPTR(dst16), pitch_));
|
RunInvTxfm(coeff, CAST_TO_BYTEPTR(dst16), pitch_));
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -511,8 +511,8 @@ class FwdTrans8x8TestBase {
|
|||||||
const int diff = dst[j] - ref[j];
|
const int diff = dst[j] - ref[j];
|
||||||
#endif
|
#endif
|
||||||
const uint32_t error = diff * diff;
|
const uint32_t error = diff * diff;
|
||||||
EXPECT_EQ(0u, error) << "Error: 8x8 IDCT has error " << error
|
EXPECT_EQ(0u, error)
|
||||||
<< " at index " << j;
|
<< "Error: 8x8 IDCT has error " << error << " at index " << j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -628,7 +628,7 @@ TEST_P(InvTrans8x8DCT, CompareReference) {
|
|||||||
CompareInvReference(ref_txfm_, thresh_);
|
CompareInvReference(ref_txfm_, thresh_);
|
||||||
}
|
}
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -670,14 +670,13 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_c, 3, VPX_BITS_8)));
|
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_c, 3, VPX_BITS_8)));
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
#if HAVE_NEON_ASM && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_NEON && !CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(NEON, FwdTrans8x8DCT,
|
INSTANTIATE_TEST_CASE_P(NEON, FwdTrans8x8DCT,
|
||||||
::testing::Values(make_tuple(&vpx_fdct8x8_neon,
|
::testing::Values(make_tuple(&vpx_fdct8x8_neon,
|
||||||
&vpx_idct8x8_64_add_neon,
|
&vpx_idct8x8_64_add_neon,
|
||||||
0, VPX_BITS_8)));
|
0, VPX_BITS_8)));
|
||||||
#endif // HAVE_NEON_ASM && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
|
||||||
|
|
||||||
#if HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if !CONFIG_VP9_HIGHBITDEPTH
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
NEON, FwdTrans8x8HT,
|
NEON, FwdTrans8x8HT,
|
||||||
::testing::Values(
|
::testing::Values(
|
||||||
@ -685,7 +684,8 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_neon, 1, VPX_BITS_8),
|
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_neon, 1, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_neon, 2, VPX_BITS_8),
|
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_neon, 2, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_neon, 3, VPX_BITS_8)));
|
make_tuple(&vp9_fht8x8_c, &vp9_iht8x8_64_add_neon, 3, VPX_BITS_8)));
|
||||||
#endif // HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_NEON && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#if HAVE_SSE2 && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, FwdTrans8x8DCT,
|
INSTANTIATE_TEST_CASE_P(SSE2, FwdTrans8x8DCT,
|
||||||
@ -740,7 +740,7 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
!CONFIG_EMULATE_HARDWARE
|
!CONFIG_EMULATE_HARDWARE
|
||||||
INSTANTIATE_TEST_CASE_P(SSSE3, FwdTrans8x8DCT,
|
INSTANTIATE_TEST_CASE_P(SSSE3, FwdTrans8x8DCT,
|
||||||
::testing::Values(make_tuple(&vpx_fdct8x8_ssse3,
|
::testing::Values(make_tuple(&vpx_fdct8x8_ssse3,
|
||||||
&vpx_idct8x8_64_add_ssse3,
|
&vpx_idct8x8_64_add_sse2,
|
||||||
0, VPX_BITS_8)));
|
0, VPX_BITS_8)));
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -757,4 +757,11 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp9_fht8x8_msa, &vp9_iht8x8_64_add_msa, 2, VPX_BITS_8),
|
make_tuple(&vp9_fht8x8_msa, &vp9_iht8x8_64_add_msa, 2, VPX_BITS_8),
|
||||||
make_tuple(&vp9_fht8x8_msa, &vp9_iht8x8_64_add_msa, 3, VPX_BITS_8)));
|
make_tuple(&vp9_fht8x8_msa, &vp9_iht8x8_64_add_msa, 3, VPX_BITS_8)));
|
||||||
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
#endif // HAVE_MSA && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
|
||||||
|
#if HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, FwdTrans8x8DCT,
|
||||||
|
::testing::Values(make_tuple(&vpx_fdct8x8_c,
|
||||||
|
&vpx_idct8x8_64_add_vsx, 0,
|
||||||
|
VPX_BITS_8)));
|
||||||
|
#endif // HAVE_VSX && !CONFIG_VP9_HIGHBITDEPTH && !CONFIG_EMULATE_HARDWARE
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -13,6 +13,7 @@
|
|||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
#include "./vpx_dsp_rtcd.h"
|
#include "./vpx_dsp_rtcd.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
#include "test/acm_random.h"
|
#include "test/acm_random.h"
|
||||||
#include "test/register_state_check.h"
|
#include "test/register_state_check.h"
|
||||||
@ -21,7 +22,8 @@ namespace {
|
|||||||
|
|
||||||
using ::libvpx_test::ACMRandom;
|
using ::libvpx_test::ACMRandom;
|
||||||
|
|
||||||
typedef void (*HadamardFunc)(const int16_t *a, int a_stride, int16_t *b);
|
typedef void (*HadamardFunc)(const int16_t *a, ptrdiff_t a_stride,
|
||||||
|
tran_low_t *b);
|
||||||
|
|
||||||
void hadamard_loop(const int16_t *a, int a_stride, int16_t *out) {
|
void hadamard_loop(const int16_t *a, int a_stride, int16_t *out) {
|
||||||
int16_t b[8];
|
int16_t b[8];
|
||||||
@ -46,18 +48,16 @@ void hadamard_loop(const int16_t *a, int a_stride, int16_t *out) {
|
|||||||
out[5] = c[3] - c[7];
|
out[5] = c[3] - c[7];
|
||||||
}
|
}
|
||||||
|
|
||||||
void reference_hadamard8x8(const int16_t *a, int a_stride, int16_t *b) {
|
void reference_hadamard8x8(const int16_t *a, int a_stride, tran_low_t *b) {
|
||||||
int16_t buf[64];
|
int16_t buf[64];
|
||||||
for (int i = 0; i < 8; ++i) {
|
int16_t buf2[64];
|
||||||
hadamard_loop(a + i, a_stride, buf + i * 8);
|
for (int i = 0; i < 8; ++i) hadamard_loop(a + i, a_stride, buf + i * 8);
|
||||||
|
for (int i = 0; i < 8; ++i) hadamard_loop(buf + i, 8, buf2 + i * 8);
|
||||||
|
|
||||||
|
for (int i = 0; i < 64; ++i) b[i] = (tran_low_t)buf2[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
for (int i = 0; i < 8; ++i) {
|
void reference_hadamard16x16(const int16_t *a, int a_stride, tran_low_t *b) {
|
||||||
hadamard_loop(buf + i, 8, b + i * 8);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void reference_hadamard16x16(const int16_t *a, int a_stride, int16_t *b) {
|
|
||||||
/* The source is a 16x16 block. The destination is rearranged to 8x32.
|
/* The source is a 16x16 block. The destination is rearranged to 8x32.
|
||||||
* Input is 9 bit. */
|
* Input is 9 bit. */
|
||||||
reference_hadamard8x8(a + 0 + 0 * a_stride, a_stride, b + 0);
|
reference_hadamard8x8(a + 0 + 0 * a_stride, a_stride, b + 0);
|
||||||
@ -68,16 +68,16 @@ void reference_hadamard16x16(const int16_t *a, int a_stride, int16_t *b) {
|
|||||||
/* Overlay the 8x8 blocks and combine. */
|
/* Overlay the 8x8 blocks and combine. */
|
||||||
for (int i = 0; i < 64; ++i) {
|
for (int i = 0; i < 64; ++i) {
|
||||||
/* 8x8 steps the range up to 15 bits. */
|
/* 8x8 steps the range up to 15 bits. */
|
||||||
const int16_t a0 = b[0];
|
const tran_low_t a0 = b[0];
|
||||||
const int16_t a1 = b[64];
|
const tran_low_t a1 = b[64];
|
||||||
const int16_t a2 = b[128];
|
const tran_low_t a2 = b[128];
|
||||||
const int16_t a3 = b[192];
|
const tran_low_t a3 = b[192];
|
||||||
|
|
||||||
/* Prevent the result from escaping int16_t. */
|
/* Prevent the result from escaping int16_t. */
|
||||||
const int16_t b0 = (a0 + a1) >> 1;
|
const tran_low_t b0 = (a0 + a1) >> 1;
|
||||||
const int16_t b1 = (a0 - a1) >> 1;
|
const tran_low_t b1 = (a0 - a1) >> 1;
|
||||||
const int16_t b2 = (a2 + a3) >> 1;
|
const tran_low_t b2 = (a2 + a3) >> 1;
|
||||||
const int16_t b3 = (a2 - a3) >> 1;
|
const tran_low_t b3 = (a2 - a3) >> 1;
|
||||||
|
|
||||||
/* Store a 16 bit value. */
|
/* Store a 16 bit value. */
|
||||||
b[0] = b0 + b2;
|
b[0] = b0 + b2;
|
||||||
@ -101,12 +101,35 @@ class HadamardTestBase : public ::testing::TestWithParam<HadamardFunc> {
|
|||||||
ACMRandom rnd_;
|
ACMRandom rnd_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
void HadamardSpeedTest(const char *name, HadamardFunc const func,
|
||||||
|
const int16_t *input, int stride, tran_low_t *output,
|
||||||
|
int times) {
|
||||||
|
int i;
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (i = 0; i < times; ++i) {
|
||||||
|
func(input, stride, output);
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("%s[%12d runs]: %d us\n", name, times, elapsed_time);
|
||||||
|
}
|
||||||
|
|
||||||
class Hadamard8x8Test : public HadamardTestBase {};
|
class Hadamard8x8Test : public HadamardTestBase {};
|
||||||
|
|
||||||
|
void HadamardSpeedTest8x8(HadamardFunc const func, int times) {
|
||||||
|
DECLARE_ALIGNED(16, int16_t, input[64]);
|
||||||
|
DECLARE_ALIGNED(16, tran_low_t, output[64]);
|
||||||
|
memset(input, 1, sizeof(input));
|
||||||
|
HadamardSpeedTest("Hadamard8x8", func, input, 8, output, times);
|
||||||
|
}
|
||||||
|
|
||||||
TEST_P(Hadamard8x8Test, CompareReferenceRandom) {
|
TEST_P(Hadamard8x8Test, CompareReferenceRandom) {
|
||||||
DECLARE_ALIGNED(16, int16_t, a[64]);
|
DECLARE_ALIGNED(16, int16_t, a[64]);
|
||||||
DECLARE_ALIGNED(16, int16_t, b[64]);
|
DECLARE_ALIGNED(16, tran_low_t, b[64]);
|
||||||
int16_t b_ref[64];
|
tran_low_t b_ref[64];
|
||||||
for (int i = 0; i < 64; ++i) {
|
for (int i = 0; i < 64; ++i) {
|
||||||
a[i] = rnd_.Rand9Signed();
|
a[i] = rnd_.Rand9Signed();
|
||||||
}
|
}
|
||||||
@ -124,8 +147,8 @@ TEST_P(Hadamard8x8Test, CompareReferenceRandom) {
|
|||||||
|
|
||||||
TEST_P(Hadamard8x8Test, VaryStride) {
|
TEST_P(Hadamard8x8Test, VaryStride) {
|
||||||
DECLARE_ALIGNED(16, int16_t, a[64 * 8]);
|
DECLARE_ALIGNED(16, int16_t, a[64 * 8]);
|
||||||
DECLARE_ALIGNED(16, int16_t, b[64]);
|
DECLARE_ALIGNED(16, tran_low_t, b[64]);
|
||||||
int16_t b_ref[64];
|
tran_low_t b_ref[64];
|
||||||
for (int i = 0; i < 64 * 8; ++i) {
|
for (int i = 0; i < 64 * 8; ++i) {
|
||||||
a[i] = rnd_.Rand9Signed();
|
a[i] = rnd_.Rand9Signed();
|
||||||
}
|
}
|
||||||
@ -144,6 +167,12 @@ TEST_P(Hadamard8x8Test, VaryStride) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_P(Hadamard8x8Test, DISABLED_Speed) {
|
||||||
|
HadamardSpeedTest8x8(h_func_, 10);
|
||||||
|
HadamardSpeedTest8x8(h_func_, 10000);
|
||||||
|
HadamardSpeedTest8x8(h_func_, 10000000);
|
||||||
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(C, Hadamard8x8Test,
|
INSTANTIATE_TEST_CASE_P(C, Hadamard8x8Test,
|
||||||
::testing::Values(&vpx_hadamard_8x8_c));
|
::testing::Values(&vpx_hadamard_8x8_c));
|
||||||
|
|
||||||
@ -162,12 +191,33 @@ INSTANTIATE_TEST_CASE_P(NEON, Hadamard8x8Test,
|
|||||||
::testing::Values(&vpx_hadamard_8x8_neon));
|
::testing::Values(&vpx_hadamard_8x8_neon));
|
||||||
#endif // HAVE_NEON
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
// TODO(jingning): Remove highbitdepth flag when the SIMD functions are
|
||||||
|
// in place and turn on the unit test.
|
||||||
|
#if !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#if HAVE_MSA
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, Hadamard8x8Test,
|
||||||
|
::testing::Values(&vpx_hadamard_8x8_msa));
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
#endif // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
#if HAVE_VSX
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, Hadamard8x8Test,
|
||||||
|
::testing::Values(&vpx_hadamard_8x8_vsx));
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
|
||||||
class Hadamard16x16Test : public HadamardTestBase {};
|
class Hadamard16x16Test : public HadamardTestBase {};
|
||||||
|
|
||||||
|
void HadamardSpeedTest16x16(HadamardFunc const func, int times) {
|
||||||
|
DECLARE_ALIGNED(16, int16_t, input[256]);
|
||||||
|
DECLARE_ALIGNED(16, tran_low_t, output[256]);
|
||||||
|
memset(input, 1, sizeof(input));
|
||||||
|
HadamardSpeedTest("Hadamard16x16", func, input, 16, output, times);
|
||||||
|
}
|
||||||
|
|
||||||
TEST_P(Hadamard16x16Test, CompareReferenceRandom) {
|
TEST_P(Hadamard16x16Test, CompareReferenceRandom) {
|
||||||
DECLARE_ALIGNED(16, int16_t, a[16 * 16]);
|
DECLARE_ALIGNED(16, int16_t, a[16 * 16]);
|
||||||
DECLARE_ALIGNED(16, int16_t, b[16 * 16]);
|
DECLARE_ALIGNED(16, tran_low_t, b[16 * 16]);
|
||||||
int16_t b_ref[16 * 16];
|
tran_low_t b_ref[16 * 16];
|
||||||
for (int i = 0; i < 16 * 16; ++i) {
|
for (int i = 0; i < 16 * 16; ++i) {
|
||||||
a[i] = rnd_.Rand9Signed();
|
a[i] = rnd_.Rand9Signed();
|
||||||
}
|
}
|
||||||
@ -185,8 +235,8 @@ TEST_P(Hadamard16x16Test, CompareReferenceRandom) {
|
|||||||
|
|
||||||
TEST_P(Hadamard16x16Test, VaryStride) {
|
TEST_P(Hadamard16x16Test, VaryStride) {
|
||||||
DECLARE_ALIGNED(16, int16_t, a[16 * 16 * 8]);
|
DECLARE_ALIGNED(16, int16_t, a[16 * 16 * 8]);
|
||||||
DECLARE_ALIGNED(16, int16_t, b[16 * 16]);
|
DECLARE_ALIGNED(16, tran_low_t, b[16 * 16]);
|
||||||
int16_t b_ref[16 * 16];
|
tran_low_t b_ref[16 * 16];
|
||||||
for (int i = 0; i < 16 * 16 * 8; ++i) {
|
for (int i = 0; i < 16 * 16 * 8; ++i) {
|
||||||
a[i] = rnd_.Rand9Signed();
|
a[i] = rnd_.Rand9Signed();
|
||||||
}
|
}
|
||||||
@ -205,6 +255,12 @@ TEST_P(Hadamard16x16Test, VaryStride) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_P(Hadamard16x16Test, DISABLED_Speed) {
|
||||||
|
HadamardSpeedTest16x16(h_func_, 10);
|
||||||
|
HadamardSpeedTest16x16(h_func_, 10000);
|
||||||
|
HadamardSpeedTest16x16(h_func_, 10000000);
|
||||||
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(C, Hadamard16x16Test,
|
INSTANTIATE_TEST_CASE_P(C, Hadamard16x16Test,
|
||||||
::testing::Values(&vpx_hadamard_16x16_c));
|
::testing::Values(&vpx_hadamard_16x16_c));
|
||||||
|
|
||||||
@ -213,8 +269,25 @@ INSTANTIATE_TEST_CASE_P(SSE2, Hadamard16x16Test,
|
|||||||
::testing::Values(&vpx_hadamard_16x16_sse2));
|
::testing::Values(&vpx_hadamard_16x16_sse2));
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_AVX2
|
||||||
|
INSTANTIATE_TEST_CASE_P(AVX2, Hadamard16x16Test,
|
||||||
|
::testing::Values(&vpx_hadamard_16x16_avx2));
|
||||||
|
#endif // HAVE_AVX2
|
||||||
|
|
||||||
|
#if HAVE_VSX
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, Hadamard16x16Test,
|
||||||
|
::testing::Values(&vpx_hadamard_16x16_vsx));
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
|
||||||
#if HAVE_NEON
|
#if HAVE_NEON
|
||||||
INSTANTIATE_TEST_CASE_P(NEON, Hadamard16x16Test,
|
INSTANTIATE_TEST_CASE_P(NEON, Hadamard16x16Test,
|
||||||
::testing::Values(&vpx_hadamard_16x16_neon));
|
::testing::Values(&vpx_hadamard_16x16_neon));
|
||||||
#endif // HAVE_NEON
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#if HAVE_MSA
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, Hadamard16x16Test,
|
||||||
|
::testing::Values(&vpx_hadamard_16x16_msa));
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
#endif // !CONFIG_VP9_HIGHBITDEPTH
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -13,6 +13,7 @@
|
|||||||
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "test/buffer.h"
|
||||||
#include "test/clear_system_state.h"
|
#include "test/clear_system_state.h"
|
||||||
#include "test/register_state_check.h"
|
#include "test/register_state_check.h"
|
||||||
#include "vpx/vpx_integer.h"
|
#include "vpx/vpx_integer.h"
|
||||||
@ -21,110 +22,156 @@ typedef void (*IdctFunc)(int16_t *input, unsigned char *pred_ptr,
|
|||||||
int pred_stride, unsigned char *dst_ptr,
|
int pred_stride, unsigned char *dst_ptr,
|
||||||
int dst_stride);
|
int dst_stride);
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
using libvpx_test::Buffer;
|
||||||
|
|
||||||
class IDCTTest : public ::testing::TestWithParam<IdctFunc> {
|
class IDCTTest : public ::testing::TestWithParam<IdctFunc> {
|
||||||
protected:
|
protected:
|
||||||
virtual void SetUp() {
|
virtual void SetUp() {
|
||||||
int i;
|
|
||||||
|
|
||||||
UUT = GetParam();
|
UUT = GetParam();
|
||||||
memset(input, 0, sizeof(input));
|
|
||||||
/* Set up guard blocks */
|
input = new Buffer<int16_t>(4, 4, 0);
|
||||||
for (i = 0; i < 256; i++) output[i] = ((i & 0xF) < 4 && (i < 64)) ? 0 : -1;
|
ASSERT_TRUE(input != NULL);
|
||||||
|
ASSERT_TRUE(input->Init());
|
||||||
|
predict = new Buffer<uint8_t>(4, 4, 3);
|
||||||
|
ASSERT_TRUE(predict != NULL);
|
||||||
|
ASSERT_TRUE(predict->Init());
|
||||||
|
output = new Buffer<uint8_t>(4, 4, 3);
|
||||||
|
ASSERT_TRUE(output != NULL);
|
||||||
|
ASSERT_TRUE(output->Init());
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
virtual void TearDown() {
|
||||||
|
delete input;
|
||||||
|
delete predict;
|
||||||
|
delete output;
|
||||||
|
libvpx_test::ClearSystemState();
|
||||||
|
}
|
||||||
|
|
||||||
IdctFunc UUT;
|
IdctFunc UUT;
|
||||||
int16_t input[16];
|
Buffer<int16_t> *input;
|
||||||
unsigned char output[256];
|
Buffer<uint8_t> *predict;
|
||||||
unsigned char predict[256];
|
Buffer<uint8_t> *output;
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST_P(IDCTTest, TestGuardBlocks) {
|
|
||||||
int i;
|
|
||||||
|
|
||||||
for (i = 0; i < 256; i++) {
|
|
||||||
if ((i & 0xF) < 4 && i < 64)
|
|
||||||
EXPECT_EQ(0, output[i]) << i;
|
|
||||||
else
|
|
||||||
EXPECT_EQ(255, output[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_P(IDCTTest, TestAllZeros) {
|
TEST_P(IDCTTest, TestAllZeros) {
|
||||||
int i;
|
// When the input is '0' the output will be '0'.
|
||||||
|
input->Set(0);
|
||||||
|
predict->Set(0);
|
||||||
|
output->Set(0);
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(UUT(input, output, 16, output, 16));
|
ASM_REGISTER_STATE_CHECK(UUT(input->TopLeftPixel(), predict->TopLeftPixel(),
|
||||||
|
predict->stride(), output->TopLeftPixel(),
|
||||||
|
output->stride()));
|
||||||
|
|
||||||
for (i = 0; i < 256; i++) {
|
ASSERT_TRUE(input->CheckValues(0));
|
||||||
if ((i & 0xF) < 4 && i < 64)
|
ASSERT_TRUE(input->CheckPadding());
|
||||||
EXPECT_EQ(0, output[i]) << "i==" << i;
|
ASSERT_TRUE(output->CheckValues(0));
|
||||||
else
|
ASSERT_TRUE(output->CheckPadding());
|
||||||
EXPECT_EQ(255, output[i]) << "i==" << i;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_P(IDCTTest, TestAllOnes) {
|
TEST_P(IDCTTest, TestAllOnes) {
|
||||||
int i;
|
input->Set(0);
|
||||||
|
// When the first element is '4' it will fill the output buffer with '1'.
|
||||||
|
input->TopLeftPixel()[0] = 4;
|
||||||
|
predict->Set(0);
|
||||||
|
output->Set(0);
|
||||||
|
|
||||||
input[0] = 4;
|
ASM_REGISTER_STATE_CHECK(UUT(input->TopLeftPixel(), predict->TopLeftPixel(),
|
||||||
ASM_REGISTER_STATE_CHECK(UUT(input, output, 16, output, 16));
|
predict->stride(), output->TopLeftPixel(),
|
||||||
|
output->stride()));
|
||||||
|
|
||||||
for (i = 0; i < 256; i++) {
|
ASSERT_TRUE(output->CheckValues(1));
|
||||||
if ((i & 0xF) < 4 && i < 64)
|
ASSERT_TRUE(output->CheckPadding());
|
||||||
EXPECT_EQ(1, output[i]) << "i==" << i;
|
|
||||||
else
|
|
||||||
EXPECT_EQ(255, output[i]) << "i==" << i;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_P(IDCTTest, TestAddOne) {
|
TEST_P(IDCTTest, TestAddOne) {
|
||||||
int i;
|
// Set the transform output to '1' and make sure it gets added to the
|
||||||
|
// prediction buffer.
|
||||||
|
input->Set(0);
|
||||||
|
input->TopLeftPixel()[0] = 4;
|
||||||
|
output->Set(0);
|
||||||
|
|
||||||
for (i = 0; i < 256; i++) predict[i] = i;
|
uint8_t *pred = predict->TopLeftPixel();
|
||||||
input[0] = 4;
|
for (int y = 0; y < 4; ++y) {
|
||||||
ASM_REGISTER_STATE_CHECK(UUT(input, predict, 16, output, 16));
|
for (int x = 0; x < 4; ++x) {
|
||||||
|
pred[y * predict->stride() + x] = y * 4 + x;
|
||||||
for (i = 0; i < 256; i++) {
|
|
||||||
if ((i & 0xF) < 4 && i < 64)
|
|
||||||
EXPECT_EQ(i + 1, output[i]) << "i==" << i;
|
|
||||||
else
|
|
||||||
EXPECT_EQ(255, output[i]) << "i==" << i;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ASM_REGISTER_STATE_CHECK(UUT(input->TopLeftPixel(), predict->TopLeftPixel(),
|
||||||
|
predict->stride(), output->TopLeftPixel(),
|
||||||
|
output->stride()));
|
||||||
|
|
||||||
|
uint8_t const *out = output->TopLeftPixel();
|
||||||
|
for (int y = 0; y < 4; ++y) {
|
||||||
|
for (int x = 0; x < 4; ++x) {
|
||||||
|
EXPECT_EQ(1 + y * 4 + x, out[y * output->stride() + x]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (HasFailure()) {
|
||||||
|
output->DumpBuffer();
|
||||||
|
}
|
||||||
|
|
||||||
|
ASSERT_TRUE(output->CheckPadding());
|
||||||
|
}
|
||||||
|
|
||||||
TEST_P(IDCTTest, TestWithData) {
|
TEST_P(IDCTTest, TestWithData) {
|
||||||
int i;
|
// Test a single known input.
|
||||||
|
predict->Set(0);
|
||||||
|
|
||||||
for (i = 0; i < 16; i++) input[i] = i;
|
int16_t *in = input->TopLeftPixel();
|
||||||
|
for (int y = 0; y < 4; ++y) {
|
||||||
ASM_REGISTER_STATE_CHECK(UUT(input, output, 16, output, 16));
|
for (int x = 0; x < 4; ++x) {
|
||||||
|
in[y * input->stride() + x] = y * 4 + x;
|
||||||
for (i = 0; i < 256; i++) {
|
|
||||||
if ((i & 0xF) > 3 || i > 63)
|
|
||||||
EXPECT_EQ(255, output[i]) << "i==" << i;
|
|
||||||
else if (i == 0)
|
|
||||||
EXPECT_EQ(11, output[i]) << "i==" << i;
|
|
||||||
else if (i == 34)
|
|
||||||
EXPECT_EQ(1, output[i]) << "i==" << i;
|
|
||||||
else if (i == 2 || i == 17 || i == 32)
|
|
||||||
EXPECT_EQ(3, output[i]) << "i==" << i;
|
|
||||||
else
|
|
||||||
EXPECT_EQ(0, output[i]) << "i==" << i;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ASM_REGISTER_STATE_CHECK(UUT(input->TopLeftPixel(), predict->TopLeftPixel(),
|
||||||
|
predict->stride(), output->TopLeftPixel(),
|
||||||
|
output->stride()));
|
||||||
|
|
||||||
|
uint8_t *out = output->TopLeftPixel();
|
||||||
|
for (int y = 0; y < 4; ++y) {
|
||||||
|
for (int x = 0; x < 4; ++x) {
|
||||||
|
switch (y * 4 + x) {
|
||||||
|
case 0: EXPECT_EQ(11, out[y * output->stride() + x]); break;
|
||||||
|
case 2:
|
||||||
|
case 5:
|
||||||
|
case 8: EXPECT_EQ(3, out[y * output->stride() + x]); break;
|
||||||
|
case 10: EXPECT_EQ(1, out[y * output->stride() + x]); break;
|
||||||
|
default: EXPECT_EQ(0, out[y * output->stride() + x]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (HasFailure()) {
|
||||||
|
output->DumpBuffer();
|
||||||
|
}
|
||||||
|
|
||||||
|
ASSERT_TRUE(output->CheckPadding());
|
||||||
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(C, IDCTTest, ::testing::Values(vp8_short_idct4x4llm_c));
|
INSTANTIATE_TEST_CASE_P(C, IDCTTest, ::testing::Values(vp8_short_idct4x4llm_c));
|
||||||
|
|
||||||
#if HAVE_NEON
|
#if HAVE_NEON
|
||||||
INSTANTIATE_TEST_CASE_P(NEON, IDCTTest,
|
INSTANTIATE_TEST_CASE_P(NEON, IDCTTest,
|
||||||
::testing::Values(vp8_short_idct4x4llm_neon));
|
::testing::Values(vp8_short_idct4x4llm_neon));
|
||||||
#endif
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
#if HAVE_MMX
|
#if HAVE_MMX
|
||||||
INSTANTIATE_TEST_CASE_P(MMX, IDCTTest,
|
INSTANTIATE_TEST_CASE_P(MMX, IDCTTest,
|
||||||
::testing::Values(vp8_short_idct4x4llm_mmx));
|
::testing::Values(vp8_short_idct4x4llm_mmx));
|
||||||
#endif
|
#endif // HAVE_MMX
|
||||||
|
|
||||||
#if HAVE_MSA
|
#if HAVE_MSA
|
||||||
INSTANTIATE_TEST_CASE_P(MSA, IDCTTest,
|
INSTANTIATE_TEST_CASE_P(MSA, IDCTTest,
|
||||||
::testing::Values(vp8_short_idct4x4llm_msa));
|
::testing::Values(vp8_short_idct4x4llm_msa));
|
||||||
#endif
|
#endif // HAVE_MSA
|
||||||
}
|
|
||||||
|
#if HAVE_MMI
|
||||||
|
INSTANTIATE_TEST_CASE_P(MMI, IDCTTest,
|
||||||
|
::testing::Values(vp8_short_idct4x4llm_mmi));
|
||||||
|
#endif // HAVE_MMI
|
||||||
|
} // namespace
|
||||||
|
@ -45,8 +45,8 @@ class InvalidFileTest : public ::libvpx_test::DecoderTest,
|
|||||||
|
|
||||||
void OpenResFile(const std::string &res_file_name_) {
|
void OpenResFile(const std::string &res_file_name_) {
|
||||||
res_file_ = libvpx_test::OpenTestDataFile(res_file_name_);
|
res_file_ = libvpx_test::OpenTestDataFile(res_file_name_);
|
||||||
ASSERT_TRUE(res_file_ != NULL) << "Result file open failed. Filename: "
|
ASSERT_TRUE(res_file_ != NULL)
|
||||||
<< res_file_name_;
|
<< "Result file open failed. Filename: " << res_file_name_;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual bool HandleDecodeResult(
|
virtual bool HandleDecodeResult(
|
||||||
@ -120,11 +120,24 @@ class InvalidFileTest : public ::libvpx_test::DecoderTest,
|
|||||||
|
|
||||||
TEST_P(InvalidFileTest, ReturnCode) { RunTest(); }
|
TEST_P(InvalidFileTest, ReturnCode) { RunTest(); }
|
||||||
|
|
||||||
|
#if CONFIG_VP8_DECODER
|
||||||
|
const DecodeParam kVP8InvalidFileTests[] = {
|
||||||
|
{ 1, "invalid-bug-1443.ivf" },
|
||||||
|
{ 1, "invalid-token-partition.ivf" },
|
||||||
|
};
|
||||||
|
|
||||||
|
VP8_INSTANTIATE_TEST_CASE(InvalidFileTest,
|
||||||
|
::testing::ValuesIn(kVP8InvalidFileTests));
|
||||||
|
#endif // CONFIG_VP8_DECODER
|
||||||
|
|
||||||
#if CONFIG_VP9_DECODER
|
#if CONFIG_VP9_DECODER
|
||||||
const DecodeParam kVP9InvalidFileTests[] = {
|
const DecodeParam kVP9InvalidFileTests[] = {
|
||||||
{ 1, "invalid-vp90-02-v2.webm" },
|
{ 1, "invalid-vp90-02-v2.webm" },
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
{ 1, "invalid-vp90-2-00-quantizer-00.webm.ivf.s5861_r01-05_b6-.v2.ivf" },
|
{ 1, "invalid-vp90-2-00-quantizer-00.webm.ivf.s5861_r01-05_b6-.v2.ivf" },
|
||||||
|
{ 1,
|
||||||
|
"invalid-vp90-2-21-resize_inter_320x180_5_3-4.webm.ivf.s45551_r01-05_b6-."
|
||||||
|
"ivf" },
|
||||||
#endif
|
#endif
|
||||||
{ 1, "invalid-vp90-03-v3.webm" },
|
{ 1, "invalid-vp90-03-v3.webm" },
|
||||||
{ 1, "invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-.ivf" },
|
{ 1, "invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-.ivf" },
|
||||||
@ -144,6 +157,7 @@ const DecodeParam kVP9InvalidFileTests[] = {
|
|||||||
{ 1, "invalid-vp90-2-03-size-202x210.webm.ivf.s113306_r01-05_b6-.ivf" },
|
{ 1, "invalid-vp90-2-03-size-202x210.webm.ivf.s113306_r01-05_b6-.ivf" },
|
||||||
{ 1,
|
{ 1,
|
||||||
"invalid-vp90-2-10-show-existing-frame.webm.ivf.s180315_r01-05_b6-.ivf" },
|
"invalid-vp90-2-10-show-existing-frame.webm.ivf.s180315_r01-05_b6-.ivf" },
|
||||||
|
{ 1, "invalid-crbug-667044.webm" },
|
||||||
};
|
};
|
||||||
|
|
||||||
VP9_INSTANTIATE_TEST_CASE(InvalidFileTest,
|
VP9_INSTANTIATE_TEST_CASE(InvalidFileTest,
|
||||||
@ -163,12 +177,12 @@ class InvalidFileInvalidPeekTest : public InvalidFileTest {
|
|||||||
TEST_P(InvalidFileInvalidPeekTest, ReturnCode) { RunTest(); }
|
TEST_P(InvalidFileInvalidPeekTest, ReturnCode) { RunTest(); }
|
||||||
|
|
||||||
#if CONFIG_VP8_DECODER
|
#if CONFIG_VP8_DECODER
|
||||||
const DecodeParam kVP8InvalidFileTests[] = {
|
const DecodeParam kVP8InvalidPeekTests[] = {
|
||||||
{ 1, "invalid-vp80-00-comprehensive-018.ivf.2kf_0x6.ivf" },
|
{ 1, "invalid-vp80-00-comprehensive-018.ivf.2kf_0x6.ivf" },
|
||||||
};
|
};
|
||||||
|
|
||||||
VP8_INSTANTIATE_TEST_CASE(InvalidFileInvalidPeekTest,
|
VP8_INSTANTIATE_TEST_CASE(InvalidFileInvalidPeekTest,
|
||||||
::testing::ValuesIn(kVP8InvalidFileTests));
|
::testing::ValuesIn(kVP8InvalidPeekTests));
|
||||||
#endif // CONFIG_VP8_DECODER
|
#endif // CONFIG_VP8_DECODER
|
||||||
|
|
||||||
#if CONFIG_VP9_DECODER
|
#if CONFIG_VP9_DECODER
|
||||||
|
@ -47,8 +47,8 @@ class IVFVideoSource : public CompressedVideoSource {
|
|||||||
|
|
||||||
virtual void Begin() {
|
virtual void Begin() {
|
||||||
input_file_ = OpenTestDataFile(file_name_);
|
input_file_ = OpenTestDataFile(file_name_);
|
||||||
ASSERT_TRUE(input_file_ != NULL) << "Input file open failed. Filename: "
|
ASSERT_TRUE(input_file_ != NULL)
|
||||||
<< file_name_;
|
<< "Input file open failed. Filename: " << file_name_;
|
||||||
|
|
||||||
// Read file header
|
// Read file header
|
||||||
uint8_t file_hdr[kIvfFileHdrSize];
|
uint8_t file_hdr[kIvfFileHdrSize];
|
||||||
|
@ -68,7 +68,9 @@ TEST_P(KeyframeTest, TestRandomVideoSource) {
|
|||||||
|
|
||||||
// In realtime mode - auto placed keyframes are exceedingly rare, don't
|
// In realtime mode - auto placed keyframes are exceedingly rare, don't
|
||||||
// bother with this check if(GetParam() > 0)
|
// bother with this check if(GetParam() > 0)
|
||||||
if (GET_PARAM(1) > 0) EXPECT_GT(kf_count_, 1);
|
if (GET_PARAM(1) > 0) {
|
||||||
|
EXPECT_GT(kf_count_, 1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_P(KeyframeTest, TestDisableKeyframes) {
|
TEST_P(KeyframeTest, TestDisableKeyframes) {
|
||||||
@ -128,15 +130,16 @@ TEST_P(KeyframeTest, TestAutoKeyframe) {
|
|||||||
|
|
||||||
// In realtime mode - auto placed keyframes are exceedingly rare, don't
|
// In realtime mode - auto placed keyframes are exceedingly rare, don't
|
||||||
// bother with this check
|
// bother with this check
|
||||||
if (GET_PARAM(1) > 0)
|
if (GET_PARAM(1) > 0) {
|
||||||
EXPECT_EQ(2u, kf_pts_list_.size()) << " Not the right number of keyframes ";
|
EXPECT_EQ(2u, kf_pts_list_.size()) << " Not the right number of keyframes ";
|
||||||
|
}
|
||||||
|
|
||||||
// Verify that keyframes match the file keyframes in the file.
|
// Verify that keyframes match the file keyframes in the file.
|
||||||
for (std::vector<vpx_codec_pts_t>::const_iterator iter = kf_pts_list_.begin();
|
for (std::vector<vpx_codec_pts_t>::const_iterator iter = kf_pts_list_.begin();
|
||||||
iter != kf_pts_list_.end(); ++iter) {
|
iter != kf_pts_list_.end(); ++iter) {
|
||||||
if (deadline_ == VPX_DL_REALTIME && *iter > 0)
|
if (deadline_ == VPX_DL_REALTIME && *iter > 0)
|
||||||
EXPECT_EQ(0, (*iter - 1) % 30) << "Unexpected keyframe at frame "
|
EXPECT_EQ(0, (*iter - 1) % 30)
|
||||||
<< *iter;
|
<< "Unexpected keyframe at frame " << *iter;
|
||||||
else
|
else
|
||||||
EXPECT_EQ(0, *iter % 30) << "Unexpected keyframe at frame " << *iter;
|
EXPECT_EQ(0, *iter % 30) << "Unexpected keyframe at frame " << *iter;
|
||||||
}
|
}
|
||||||
|
@ -66,6 +66,36 @@ class LevelTest
|
|||||||
int level_;
|
int level_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
TEST_P(LevelTest, TestTargetLevel11Large) {
|
||||||
|
ASSERT_NE(encoding_mode_, ::libvpx_test::kRealTime);
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_odd.yuv", 208, 144, 30, 1, 0,
|
||||||
|
60);
|
||||||
|
target_level_ = 11;
|
||||||
|
cfg_.rc_target_bitrate = 150;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(target_level_, level_);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(LevelTest, TestTargetLevel20Large) {
|
||||||
|
ASSERT_NE(encoding_mode_, ::libvpx_test::kRealTime);
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 60);
|
||||||
|
target_level_ = 20;
|
||||||
|
cfg_.rc_target_bitrate = 1200;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(target_level_, level_);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(LevelTest, TestTargetLevel31Large) {
|
||||||
|
ASSERT_NE(encoding_mode_, ::libvpx_test::kRealTime);
|
||||||
|
::libvpx_test::I420VideoSource video("niklas_1280_720_30.y4m", 1280, 720, 30,
|
||||||
|
1, 0, 60);
|
||||||
|
target_level_ = 31;
|
||||||
|
cfg_.rc_target_bitrate = 8000;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(target_level_, level_);
|
||||||
|
}
|
||||||
|
|
||||||
// Test for keeping level stats only
|
// Test for keeping level stats only
|
||||||
TEST_P(LevelTest, TestTargetLevel0) {
|
TEST_P(LevelTest, TestTargetLevel0) {
|
||||||
::libvpx_test::I420VideoSource video("hantro_odd.yuv", 208, 144, 30, 1, 0,
|
::libvpx_test::I420VideoSource video("hantro_odd.yuv", 208, 144, 30, 1, 0,
|
||||||
@ -73,11 +103,11 @@ TEST_P(LevelTest, TestTargetLevel0) {
|
|||||||
target_level_ = 0;
|
target_level_ = 0;
|
||||||
min_gf_internal_ = 4;
|
min_gf_internal_ = 4;
|
||||||
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
ASSERT_EQ(11, level_);
|
ASSERT_GE(11, level_);
|
||||||
|
|
||||||
cfg_.rc_target_bitrate = 1600;
|
cfg_.rc_target_bitrate = 1600;
|
||||||
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
ASSERT_EQ(20, level_);
|
ASSERT_GE(20, level_);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test for level control being turned off
|
// Test for level control being turned off
|
||||||
@ -94,12 +124,13 @@ TEST_P(LevelTest, TestTargetLevelApi) {
|
|||||||
vpx_codec_ctx_t enc;
|
vpx_codec_ctx_t enc;
|
||||||
vpx_codec_enc_cfg_t cfg;
|
vpx_codec_enc_cfg_t cfg;
|
||||||
EXPECT_EQ(VPX_CODEC_OK, vpx_codec_enc_config_default(codec, &cfg, 0));
|
EXPECT_EQ(VPX_CODEC_OK, vpx_codec_enc_config_default(codec, &cfg, 0));
|
||||||
|
cfg.rc_target_bitrate = 100;
|
||||||
EXPECT_EQ(VPX_CODEC_OK, vpx_codec_enc_init(&enc, codec, &cfg, 0));
|
EXPECT_EQ(VPX_CODEC_OK, vpx_codec_enc_init(&enc, codec, &cfg, 0));
|
||||||
for (int level = 0; level <= 256; ++level) {
|
for (int level = 0; level <= 256; ++level) {
|
||||||
if (level == 10 || level == 11 || level == 20 || level == 21 ||
|
if (level == 10 || level == 11 || level == 20 || level == 21 ||
|
||||||
level == 30 || level == 31 || level == 40 || level == 41 ||
|
level == 30 || level == 31 || level == 40 || level == 41 ||
|
||||||
level == 50 || level == 51 || level == 52 || level == 60 ||
|
level == 50 || level == 51 || level == 52 || level == 60 ||
|
||||||
level == 61 || level == 62 || level == 0 || level == 255)
|
level == 61 || level == 62 || level == 0 || level == 1 || level == 255)
|
||||||
EXPECT_EQ(VPX_CODEC_OK,
|
EXPECT_EQ(VPX_CODEC_OK,
|
||||||
vpx_codec_control(&enc, VP9E_SET_TARGET_LEVEL, level));
|
vpx_codec_control(&enc, VP9E_SET_TARGET_LEVEL, level));
|
||||||
else
|
else
|
||||||
|
@ -56,8 +56,8 @@ typedef void (*dual_loop_op_t)(Pixel *s, int p, const uint8_t *blimit0,
|
|||||||
const uint8_t *thresh1);
|
const uint8_t *thresh1);
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
typedef std::tr1::tuple<loop_op_t, loop_op_t, int> loop8_param_t;
|
typedef ::testing::tuple<loop_op_t, loop_op_t, int> loop8_param_t;
|
||||||
typedef std::tr1::tuple<dual_loop_op_t, dual_loop_op_t, int> dualloop8_param_t;
|
typedef ::testing::tuple<dual_loop_op_t, dual_loop_op_t, int> dualloop8_param_t;
|
||||||
|
|
||||||
void InitInput(Pixel *s, Pixel *ref_s, ACMRandom *rnd, const uint8_t limit,
|
void InitInput(Pixel *s, Pixel *ref_s, ACMRandom *rnd, const uint8_t limit,
|
||||||
const int mask, const int32_t p, const int i) {
|
const int mask, const int32_t p, const int i) {
|
||||||
@ -114,6 +114,18 @@ void InitInput(Pixel *s, Pixel *ref_s, ACMRandom *rnd, const uint8_t limit,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint8_t GetOuterThresh(ACMRandom *rnd) {
|
||||||
|
return static_cast<uint8_t>(rnd->RandRange(3 * MAX_LOOP_FILTER + 5));
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t GetInnerThresh(ACMRandom *rnd) {
|
||||||
|
return static_cast<uint8_t>(rnd->RandRange(MAX_LOOP_FILTER + 1));
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t GetHevThresh(ACMRandom *rnd) {
|
||||||
|
return static_cast<uint8_t>(rnd->RandRange(MAX_LOOP_FILTER + 1) >> 4);
|
||||||
|
}
|
||||||
|
|
||||||
class Loop8Test6Param : public ::testing::TestWithParam<loop8_param_t> {
|
class Loop8Test6Param : public ::testing::TestWithParam<loop8_param_t> {
|
||||||
public:
|
public:
|
||||||
virtual ~Loop8Test6Param() {}
|
virtual ~Loop8Test6Param() {}
|
||||||
@ -162,15 +174,15 @@ TEST_P(Loop8Test6Param, OperationCheck) {
|
|||||||
int first_failure = -1;
|
int first_failure = -1;
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
int err_count = 0;
|
int err_count = 0;
|
||||||
uint8_t tmp = static_cast<uint8_t>(rnd(3 * MAX_LOOP_FILTER + 4));
|
uint8_t tmp = GetOuterThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
blimit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
blimit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(MAX_LOOP_FILTER));
|
tmp = GetInnerThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
limit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
limit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = rnd.Rand8();
|
tmp = GetHevThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
thresh[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
thresh[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
@ -221,15 +233,15 @@ TEST_P(Loop8Test6Param, ValueCheck) {
|
|||||||
|
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
int err_count = 0;
|
int err_count = 0;
|
||||||
uint8_t tmp = static_cast<uint8_t>(rnd(3 * MAX_LOOP_FILTER + 4));
|
uint8_t tmp = GetOuterThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
blimit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
blimit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(MAX_LOOP_FILTER));
|
tmp = GetInnerThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
limit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
limit[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = rnd.Rand8();
|
tmp = GetHevThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
thresh[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
thresh[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
@ -271,27 +283,27 @@ TEST_P(Loop8Test9Param, OperationCheck) {
|
|||||||
int first_failure = -1;
|
int first_failure = -1;
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
int err_count = 0;
|
int err_count = 0;
|
||||||
uint8_t tmp = static_cast<uint8_t>(rnd(3 * MAX_LOOP_FILTER + 4));
|
uint8_t tmp = GetOuterThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
blimit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
blimit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(MAX_LOOP_FILTER));
|
tmp = GetInnerThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
limit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
limit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = rnd.Rand8();
|
tmp = GetHevThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
thresh0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
thresh0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(3 * MAX_LOOP_FILTER + 4));
|
tmp = GetOuterThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
blimit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
blimit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(MAX_LOOP_FILTER));
|
tmp = GetInnerThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
limit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
limit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = rnd.Rand8();
|
tmp = GetHevThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
thresh1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
thresh1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
@ -334,27 +346,27 @@ TEST_P(Loop8Test9Param, ValueCheck) {
|
|||||||
int first_failure = -1;
|
int first_failure = -1;
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
int err_count = 0;
|
int err_count = 0;
|
||||||
uint8_t tmp = static_cast<uint8_t>(rnd(3 * MAX_LOOP_FILTER + 4));
|
uint8_t tmp = GetOuterThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
blimit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
blimit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(MAX_LOOP_FILTER));
|
tmp = GetInnerThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
limit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
limit0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = rnd.Rand8();
|
tmp = GetHevThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
thresh0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
thresh0[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(3 * MAX_LOOP_FILTER + 4));
|
tmp = GetOuterThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
blimit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
blimit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = static_cast<uint8_t>(rnd(MAX_LOOP_FILTER));
|
tmp = GetInnerThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
limit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
limit1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
tmp = rnd.Rand8();
|
tmp = GetHevThresh(&rnd);
|
||||||
DECLARE_ALIGNED(16, const uint8_t,
|
DECLARE_ALIGNED(16, const uint8_t,
|
||||||
thresh1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
thresh1[16]) = { tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp,
|
||||||
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
tmp, tmp, tmp, tmp, tmp, tmp, tmp, tmp };
|
||||||
@ -390,7 +402,7 @@ TEST_P(Loop8Test9Param, ValueCheck) {
|
|||||||
<< "First failed at test case " << first_failure;
|
<< "First failed at test case " << first_failure;
|
||||||
}
|
}
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
@ -107,10 +107,10 @@ TEST_P(MinMaxTest, CompareReferenceAndVaryStride) {
|
|||||||
int min_ref, max_ref, min, max;
|
int min_ref, max_ref, min, max;
|
||||||
reference_minmax(a, a_stride, b, b_stride, &min_ref, &max_ref);
|
reference_minmax(a, a_stride, b, b_stride, &min_ref, &max_ref);
|
||||||
ASM_REGISTER_STATE_CHECK(mm_func_(a, a_stride, b, b_stride, &min, &max));
|
ASM_REGISTER_STATE_CHECK(mm_func_(a, a_stride, b, b_stride, &min, &max));
|
||||||
EXPECT_EQ(max_ref, max) << "when a_stride = " << a_stride
|
EXPECT_EQ(max_ref, max)
|
||||||
<< " and b_stride = " << b_stride;
|
<< "when a_stride = " << a_stride << " and b_stride = " << b_stride;
|
||||||
EXPECT_EQ(min_ref, min) << "when a_stride = " << a_stride
|
EXPECT_EQ(min_ref, min)
|
||||||
<< " and b_stride = " << b_stride;
|
<< "when a_stride = " << a_stride << " and b_stride = " << b_stride;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -127,4 +127,9 @@ INSTANTIATE_TEST_CASE_P(NEON, MinMaxTest,
|
|||||||
::testing::Values(&vpx_minmax_8x8_neon));
|
::testing::Values(&vpx_minmax_8x8_neon));
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if HAVE_MSA
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, MinMaxTest,
|
||||||
|
::testing::Values(&vpx_minmax_8x8_msa));
|
||||||
|
#endif
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -7,21 +7,40 @@
|
|||||||
* in the file PATENTS. All contributing project authors may
|
* in the file PATENTS. All contributing project authors may
|
||||||
* be found in the AUTHORS file in the root of the source tree.
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
*/
|
*/
|
||||||
|
#include <limits.h>
|
||||||
#include "./vpx_config.h"
|
#include "./vpx_config.h"
|
||||||
#include "./vpx_dsp_rtcd.h"
|
#include "./vpx_dsp_rtcd.h"
|
||||||
#include "test/acm_random.h"
|
#include "test/acm_random.h"
|
||||||
|
#include "test/buffer.h"
|
||||||
#include "test/clear_system_state.h"
|
#include "test/clear_system_state.h"
|
||||||
#include "test/register_state_check.h"
|
#include "test/register_state_check.h"
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
#include "vpx/vpx_integer.h"
|
#include "vpx/vpx_integer.h"
|
||||||
#include "vpx_mem/vpx_mem.h"
|
#include "vpx_mem/vpx_mem.h"
|
||||||
|
|
||||||
|
using libvpx_test::ACMRandom;
|
||||||
|
using libvpx_test::Buffer;
|
||||||
|
|
||||||
typedef void (*VpxPostProcDownAndAcrossMbRowFunc)(
|
typedef void (*VpxPostProcDownAndAcrossMbRowFunc)(
|
||||||
unsigned char *src_ptr, unsigned char *dst_ptr, int src_pixels_per_line,
|
unsigned char *src_ptr, unsigned char *dst_ptr, int src_pixels_per_line,
|
||||||
int dst_pixels_per_line, int cols, unsigned char *flimit, int size);
|
int dst_pixels_per_line, int cols, unsigned char *flimit, int size);
|
||||||
|
|
||||||
|
typedef void (*VpxMbPostProcAcrossIpFunc)(unsigned char *src, int pitch,
|
||||||
|
int rows, int cols, int flimit);
|
||||||
|
|
||||||
|
typedef void (*VpxMbPostProcDownFunc)(unsigned char *dst, int pitch, int rows,
|
||||||
|
int cols, int flimit);
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
// Compute the filter level used in post proc from the loop filter strength
|
||||||
|
int q2mbl(int x) {
|
||||||
|
if (x < 20) x = 20;
|
||||||
|
|
||||||
|
x = 50 + (x - 50) * 10 / 8;
|
||||||
|
return x * x / 3;
|
||||||
|
}
|
||||||
|
|
||||||
class VpxPostProcDownAndAcrossMbRowTest
|
class VpxPostProcDownAndAcrossMbRowTest
|
||||||
: public ::testing::TestWithParam<VpxPostProcDownAndAcrossMbRowFunc> {
|
: public ::testing::TestWithParam<VpxPostProcDownAndAcrossMbRowFunc> {
|
||||||
public:
|
public:
|
||||||
@ -37,25 +56,16 @@ TEST_P(VpxPostProcDownAndAcrossMbRowTest, CheckFilterOutput) {
|
|||||||
const int block_height = 16;
|
const int block_height = 16;
|
||||||
|
|
||||||
// 5-tap filter needs 2 padding rows above and below the block in the input.
|
// 5-tap filter needs 2 padding rows above and below the block in the input.
|
||||||
const int input_width = block_width;
|
Buffer<uint8_t> src_image = Buffer<uint8_t>(block_width, block_height, 2);
|
||||||
const int input_height = block_height + 4;
|
ASSERT_TRUE(src_image.Init());
|
||||||
const int input_stride = input_width;
|
|
||||||
const int input_size = input_width * input_height;
|
|
||||||
|
|
||||||
// Filter extends output block by 8 samples at left and right edges.
|
// Filter extends output block by 8 samples at left and right edges.
|
||||||
const int output_width = block_width + 16;
|
// Though the left padding is only 8 bytes, the assembly code tries to
|
||||||
const int output_height = block_height;
|
// read 16 bytes before the pointer.
|
||||||
const int output_stride = output_width;
|
Buffer<uint8_t> dst_image =
|
||||||
const int output_size = output_width * output_height;
|
Buffer<uint8_t>(block_width, block_height, 8, 16, 8, 8);
|
||||||
|
ASSERT_TRUE(dst_image.Init());
|
||||||
|
|
||||||
uint8_t *const src_image =
|
|
||||||
reinterpret_cast<uint8_t *>(vpx_calloc(input_size, 1));
|
|
||||||
uint8_t *const dst_image =
|
|
||||||
reinterpret_cast<uint8_t *>(vpx_calloc(output_size, 1));
|
|
||||||
|
|
||||||
// Pointers to top-left pixel of block in the input and output images.
|
|
||||||
uint8_t *const src_image_ptr = src_image + (input_stride << 1);
|
|
||||||
uint8_t *const dst_image_ptr = dst_image + 8;
|
|
||||||
uint8_t *const flimits =
|
uint8_t *const flimits =
|
||||||
reinterpret_cast<uint8_t *>(vpx_memalign(16, block_width));
|
reinterpret_cast<uint8_t *>(vpx_memalign(16, block_width));
|
||||||
(void)memset(flimits, 255, block_width);
|
(void)memset(flimits, 255, block_width);
|
||||||
@ -63,53 +73,412 @@ TEST_P(VpxPostProcDownAndAcrossMbRowTest, CheckFilterOutput) {
|
|||||||
// Initialize pixels in the input:
|
// Initialize pixels in the input:
|
||||||
// block pixels to value 1,
|
// block pixels to value 1,
|
||||||
// border pixels to value 10.
|
// border pixels to value 10.
|
||||||
(void)memset(src_image, 10, input_size);
|
src_image.SetPadding(10);
|
||||||
uint8_t *pixel_ptr = src_image_ptr;
|
src_image.Set(1);
|
||||||
for (int i = 0; i < block_height; ++i) {
|
|
||||||
for (int j = 0; j < block_width; ++j) {
|
|
||||||
pixel_ptr[j] = 1;
|
|
||||||
}
|
|
||||||
pixel_ptr += input_stride;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Initialize pixels in the output to 99.
|
// Initialize pixels in the output to 99.
|
||||||
(void)memset(dst_image, 99, output_size);
|
dst_image.Set(99);
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(GetParam()(src_image_ptr, dst_image_ptr,
|
ASM_REGISTER_STATE_CHECK(GetParam()(
|
||||||
input_stride, output_stride, block_width,
|
src_image.TopLeftPixel(), dst_image.TopLeftPixel(), src_image.stride(),
|
||||||
flimits, 16));
|
dst_image.stride(), block_width, flimits, 16));
|
||||||
|
|
||||||
static const uint8_t kExpectedOutput[block_height] = {
|
static const uint8_t kExpectedOutput[block_height] = {
|
||||||
4, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 4
|
4, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 4
|
||||||
};
|
};
|
||||||
|
|
||||||
pixel_ptr = dst_image_ptr;
|
uint8_t *pixel_ptr = dst_image.TopLeftPixel();
|
||||||
for (int i = 0; i < block_height; ++i) {
|
for (int i = 0; i < block_height; ++i) {
|
||||||
for (int j = 0; j < block_width; ++j) {
|
for (int j = 0; j < block_width; ++j) {
|
||||||
ASSERT_EQ(kExpectedOutput[i], pixel_ptr[j]);
|
ASSERT_EQ(kExpectedOutput[i], pixel_ptr[j])
|
||||||
|
<< "at (" << i << ", " << j << ")";
|
||||||
}
|
}
|
||||||
pixel_ptr += output_stride;
|
pixel_ptr += dst_image.stride();
|
||||||
}
|
}
|
||||||
|
|
||||||
vpx_free(src_image);
|
|
||||||
vpx_free(dst_image);
|
|
||||||
vpx_free(flimits);
|
vpx_free(flimits);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
TEST_P(VpxPostProcDownAndAcrossMbRowTest, CheckCvsAssembly) {
|
||||||
|
// Size of the underlying data block that will be filtered.
|
||||||
|
// Y blocks are always a multiple of 16 wide and exactly 16 high. U and V
|
||||||
|
// blocks are always a multiple of 8 wide and exactly 8 high.
|
||||||
|
const int block_width = 136;
|
||||||
|
const int block_height = 16;
|
||||||
|
|
||||||
|
// 5-tap filter needs 2 padding rows above and below the block in the input.
|
||||||
|
// SSE2 reads in blocks of 16. Pad an extra 8 in case the width is not %16.
|
||||||
|
Buffer<uint8_t> src_image =
|
||||||
|
Buffer<uint8_t>(block_width, block_height, 2, 2, 10, 2);
|
||||||
|
ASSERT_TRUE(src_image.Init());
|
||||||
|
|
||||||
|
// Filter extends output block by 8 samples at left and right edges.
|
||||||
|
// Though the left padding is only 8 bytes, there is 'above' padding as well
|
||||||
|
// so when the assembly code tries to read 16 bytes before the pointer it is
|
||||||
|
// not a problem.
|
||||||
|
// SSE2 reads in blocks of 16. Pad an extra 8 in case the width is not %16.
|
||||||
|
Buffer<uint8_t> dst_image =
|
||||||
|
Buffer<uint8_t>(block_width, block_height, 8, 8, 16, 8);
|
||||||
|
ASSERT_TRUE(dst_image.Init());
|
||||||
|
Buffer<uint8_t> dst_image_ref = Buffer<uint8_t>(block_width, block_height, 8);
|
||||||
|
ASSERT_TRUE(dst_image_ref.Init());
|
||||||
|
|
||||||
|
// Filter values are set in blocks of 16 for Y and 8 for U/V. Each macroblock
|
||||||
|
// can have a different filter. SSE2 assembly reads flimits in blocks of 16 so
|
||||||
|
// it must be padded out.
|
||||||
|
const int flimits_width = block_width % 16 ? block_width + 8 : block_width;
|
||||||
|
uint8_t *const flimits =
|
||||||
|
reinterpret_cast<uint8_t *>(vpx_memalign(16, flimits_width));
|
||||||
|
|
||||||
|
ACMRandom rnd;
|
||||||
|
rnd.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
// Initialize pixels in the input:
|
||||||
|
// block pixels to random values.
|
||||||
|
// border pixels to value 10.
|
||||||
|
src_image.SetPadding(10);
|
||||||
|
src_image.Set(&rnd, &ACMRandom::Rand8);
|
||||||
|
|
||||||
|
for (int blocks = 0; blocks < block_width; blocks += 8) {
|
||||||
|
(void)memset(flimits, 0, sizeof(*flimits) * flimits_width);
|
||||||
|
|
||||||
|
for (int f = 0; f < 255; f++) {
|
||||||
|
(void)memset(flimits + blocks, f, sizeof(*flimits) * 8);
|
||||||
|
|
||||||
|
dst_image.Set(0);
|
||||||
|
dst_image_ref.Set(0);
|
||||||
|
|
||||||
|
vpx_post_proc_down_and_across_mb_row_c(
|
||||||
|
src_image.TopLeftPixel(), dst_image_ref.TopLeftPixel(),
|
||||||
|
src_image.stride(), dst_image_ref.stride(), block_width, flimits,
|
||||||
|
block_height);
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
GetParam()(src_image.TopLeftPixel(), dst_image.TopLeftPixel(),
|
||||||
|
src_image.stride(), dst_image.stride(), block_width,
|
||||||
|
flimits, block_height));
|
||||||
|
|
||||||
|
ASSERT_TRUE(dst_image.CheckValues(dst_image_ref));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
vpx_free(flimits);
|
||||||
|
}
|
||||||
|
|
||||||
|
class VpxMbPostProcAcrossIpTest
|
||||||
|
: public ::testing::TestWithParam<VpxMbPostProcAcrossIpFunc> {
|
||||||
|
public:
|
||||||
|
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void SetCols(unsigned char *s, int rows, int cols, int src_width) {
|
||||||
|
for (int r = 0; r < rows; r++) {
|
||||||
|
for (int c = 0; c < cols; c++) {
|
||||||
|
s[c] = c;
|
||||||
|
}
|
||||||
|
s += src_width;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunComparison(const unsigned char *expected_output, unsigned char *src_c,
|
||||||
|
int rows, int cols, int src_pitch) {
|
||||||
|
for (int r = 0; r < rows; r++) {
|
||||||
|
for (int c = 0; c < cols; c++) {
|
||||||
|
ASSERT_EQ(expected_output[c], src_c[c])
|
||||||
|
<< "at (" << r << ", " << c << ")";
|
||||||
|
}
|
||||||
|
src_c += src_pitch;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunFilterLevel(unsigned char *s, int rows, int cols, int src_width,
|
||||||
|
int filter_level, const unsigned char *expected_output) {
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
GetParam()(s, src_width, rows, cols, filter_level));
|
||||||
|
RunComparison(expected_output, s, rows, cols, src_width);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcAcrossIpTest, CheckLowFilterOutput) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> src = Buffer<uint8_t>(cols, rows, 8, 8, 17, 8);
|
||||||
|
ASSERT_TRUE(src.Init());
|
||||||
|
src.SetPadding(10);
|
||||||
|
SetCols(src.TopLeftPixel(), rows, cols, src.stride());
|
||||||
|
|
||||||
|
Buffer<uint8_t> expected_output = Buffer<uint8_t>(cols, rows, 0);
|
||||||
|
ASSERT_TRUE(expected_output.Init());
|
||||||
|
SetCols(expected_output.TopLeftPixel(), rows, cols, expected_output.stride());
|
||||||
|
|
||||||
|
RunFilterLevel(src.TopLeftPixel(), rows, cols, src.stride(), q2mbl(0),
|
||||||
|
expected_output.TopLeftPixel());
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcAcrossIpTest, CheckMediumFilterOutput) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> src = Buffer<uint8_t>(cols, rows, 8, 8, 17, 8);
|
||||||
|
ASSERT_TRUE(src.Init());
|
||||||
|
src.SetPadding(10);
|
||||||
|
SetCols(src.TopLeftPixel(), rows, cols, src.stride());
|
||||||
|
|
||||||
|
static const unsigned char kExpectedOutput[cols] = {
|
||||||
|
2, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 13
|
||||||
|
};
|
||||||
|
|
||||||
|
RunFilterLevel(src.TopLeftPixel(), rows, cols, src.stride(), q2mbl(70),
|
||||||
|
kExpectedOutput);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcAcrossIpTest, CheckHighFilterOutput) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> src = Buffer<uint8_t>(cols, rows, 8, 8, 17, 8);
|
||||||
|
ASSERT_TRUE(src.Init());
|
||||||
|
src.SetPadding(10);
|
||||||
|
SetCols(src.TopLeftPixel(), rows, cols, src.stride());
|
||||||
|
|
||||||
|
static const unsigned char kExpectedOutput[cols] = {
|
||||||
|
2, 2, 3, 4, 4, 5, 6, 7, 8, 9, 10, 11, 11, 12, 13, 13
|
||||||
|
};
|
||||||
|
|
||||||
|
RunFilterLevel(src.TopLeftPixel(), rows, cols, src.stride(), INT_MAX,
|
||||||
|
kExpectedOutput);
|
||||||
|
|
||||||
|
SetCols(src.TopLeftPixel(), rows, cols, src.stride());
|
||||||
|
|
||||||
|
RunFilterLevel(src.TopLeftPixel(), rows, cols, src.stride(), q2mbl(100),
|
||||||
|
kExpectedOutput);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcAcrossIpTest, CheckCvsAssembly) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> c_mem = Buffer<uint8_t>(cols, rows, 8, 8, 17, 8);
|
||||||
|
ASSERT_TRUE(c_mem.Init());
|
||||||
|
Buffer<uint8_t> asm_mem = Buffer<uint8_t>(cols, rows, 8, 8, 17, 8);
|
||||||
|
ASSERT_TRUE(asm_mem.Init());
|
||||||
|
|
||||||
|
// When level >= 100, the filter behaves the same as the level = INT_MAX
|
||||||
|
// When level < 20, it behaves the same as the level = 0
|
||||||
|
for (int level = 0; level < 100; level++) {
|
||||||
|
c_mem.SetPadding(10);
|
||||||
|
asm_mem.SetPadding(10);
|
||||||
|
SetCols(c_mem.TopLeftPixel(), rows, cols, c_mem.stride());
|
||||||
|
SetCols(asm_mem.TopLeftPixel(), rows, cols, asm_mem.stride());
|
||||||
|
|
||||||
|
vpx_mbpost_proc_across_ip_c(c_mem.TopLeftPixel(), c_mem.stride(), rows,
|
||||||
|
cols, q2mbl(level));
|
||||||
|
ASM_REGISTER_STATE_CHECK(GetParam()(
|
||||||
|
asm_mem.TopLeftPixel(), asm_mem.stride(), rows, cols, q2mbl(level)));
|
||||||
|
|
||||||
|
ASSERT_TRUE(asm_mem.CheckValues(c_mem));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class VpxMbPostProcDownTest
|
||||||
|
: public ::testing::TestWithParam<VpxMbPostProcDownFunc> {
|
||||||
|
public:
|
||||||
|
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void SetRows(unsigned char *src_c, int rows, int cols, int src_width) {
|
||||||
|
for (int r = 0; r < rows; r++) {
|
||||||
|
memset(src_c, r, cols);
|
||||||
|
src_c += src_width;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunComparison(const unsigned char *expected_output, unsigned char *src_c,
|
||||||
|
int rows, int cols, int src_pitch) {
|
||||||
|
for (int r = 0; r < rows; r++) {
|
||||||
|
for (int c = 0; c < cols; c++) {
|
||||||
|
ASSERT_EQ(expected_output[r * rows + c], src_c[c])
|
||||||
|
<< "at (" << r << ", " << c << ")";
|
||||||
|
}
|
||||||
|
src_c += src_pitch;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunFilterLevel(unsigned char *s, int rows, int cols, int src_width,
|
||||||
|
int filter_level, const unsigned char *expected_output) {
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
GetParam()(s, src_width, rows, cols, filter_level));
|
||||||
|
RunComparison(expected_output, s, rows, cols, src_width);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcDownTest, CheckHighFilterOutput) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> src_c = Buffer<uint8_t>(cols, rows, 8, 8, 8, 17);
|
||||||
|
ASSERT_TRUE(src_c.Init());
|
||||||
|
src_c.SetPadding(10);
|
||||||
|
|
||||||
|
SetRows(src_c.TopLeftPixel(), rows, cols, src_c.stride());
|
||||||
|
|
||||||
|
static const unsigned char kExpectedOutput[rows * cols] = {
|
||||||
|
2, 2, 1, 1, 2, 2, 2, 2, 2, 2, 1, 1, 2, 2, 2, 2, 2, 2, 2,
|
||||||
|
2, 3, 2, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 3, 3, 3, 3, 3, 3,
|
||||||
|
3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 4, 3, 4, 4, 3, 3, 3,
|
||||||
|
4, 4, 3, 4, 4, 3, 3, 4, 5, 4, 4, 4, 4, 4, 4, 4, 5, 4, 4,
|
||||||
|
4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
|
||||||
|
5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 7,
|
||||||
|
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 8, 8, 8, 8, 8,
|
||||||
|
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 9, 8, 9, 9, 8, 8, 8, 9,
|
||||||
|
9, 8, 9, 9, 8, 8, 8, 9, 9, 10, 10, 9, 9, 9, 10, 10, 9, 10, 10,
|
||||||
|
9, 9, 9, 10, 10, 10, 11, 10, 10, 10, 11, 10, 11, 10, 11, 10, 10, 10, 11,
|
||||||
|
10, 11, 11, 11, 11, 11, 11, 11, 12, 11, 11, 11, 11, 11, 11, 11, 12, 11, 12,
|
||||||
|
12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 13, 12,
|
||||||
|
13, 12, 13, 12, 12, 12, 13, 12, 13, 12, 13, 12, 13, 13, 13, 14, 13, 13, 13,
|
||||||
|
13, 13, 13, 13, 14, 13, 13, 13, 13
|
||||||
|
};
|
||||||
|
|
||||||
|
RunFilterLevel(src_c.TopLeftPixel(), rows, cols, src_c.stride(), INT_MAX,
|
||||||
|
kExpectedOutput);
|
||||||
|
|
||||||
|
src_c.SetPadding(10);
|
||||||
|
SetRows(src_c.TopLeftPixel(), rows, cols, src_c.stride());
|
||||||
|
RunFilterLevel(src_c.TopLeftPixel(), rows, cols, src_c.stride(), q2mbl(100),
|
||||||
|
kExpectedOutput);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcDownTest, CheckMediumFilterOutput) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> src_c = Buffer<uint8_t>(cols, rows, 8, 8, 8, 17);
|
||||||
|
ASSERT_TRUE(src_c.Init());
|
||||||
|
src_c.SetPadding(10);
|
||||||
|
|
||||||
|
SetRows(src_c.TopLeftPixel(), rows, cols, src_c.stride());
|
||||||
|
|
||||||
|
static const unsigned char kExpectedOutput[rows * cols] = {
|
||||||
|
2, 2, 1, 1, 2, 2, 2, 2, 2, 2, 1, 1, 2, 2, 2, 2, 2, 2, 2,
|
||||||
|
2, 3, 2, 2, 2, 2, 2, 2, 2, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||||
|
2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3,
|
||||||
|
3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
|
||||||
|
4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
|
||||||
|
5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 7,
|
||||||
|
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 8, 8, 8, 8, 8,
|
||||||
|
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 9, 9, 9, 9, 9, 9, 9, 9,
|
||||||
|
9, 9, 9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10,
|
||||||
|
10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11,
|
||||||
|
11, 11, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 13,
|
||||||
|
13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 12, 12, 13, 12,
|
||||||
|
13, 12, 13, 12, 12, 12, 13, 12, 13, 12, 13, 12, 13, 13, 13, 14, 13, 13, 13,
|
||||||
|
13, 13, 13, 13, 14, 13, 13, 13, 13
|
||||||
|
};
|
||||||
|
|
||||||
|
RunFilterLevel(src_c.TopLeftPixel(), rows, cols, src_c.stride(), q2mbl(70),
|
||||||
|
kExpectedOutput);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcDownTest, CheckLowFilterOutput) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
Buffer<uint8_t> src_c = Buffer<uint8_t>(cols, rows, 8, 8, 8, 17);
|
||||||
|
ASSERT_TRUE(src_c.Init());
|
||||||
|
src_c.SetPadding(10);
|
||||||
|
|
||||||
|
SetRows(src_c.TopLeftPixel(), rows, cols, src_c.stride());
|
||||||
|
|
||||||
|
unsigned char *expected_output = new unsigned char[rows * cols];
|
||||||
|
ASSERT_TRUE(expected_output != NULL);
|
||||||
|
SetRows(expected_output, rows, cols, cols);
|
||||||
|
|
||||||
|
RunFilterLevel(src_c.TopLeftPixel(), rows, cols, src_c.stride(), q2mbl(0),
|
||||||
|
expected_output);
|
||||||
|
|
||||||
|
delete[] expected_output;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VpxMbPostProcDownTest, CheckCvsAssembly) {
|
||||||
|
const int rows = 16;
|
||||||
|
const int cols = 16;
|
||||||
|
|
||||||
|
ACMRandom rnd;
|
||||||
|
rnd.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
|
||||||
|
Buffer<uint8_t> src_c = Buffer<uint8_t>(cols, rows, 8, 8, 8, 17);
|
||||||
|
ASSERT_TRUE(src_c.Init());
|
||||||
|
Buffer<uint8_t> src_asm = Buffer<uint8_t>(cols, rows, 8, 8, 8, 17);
|
||||||
|
ASSERT_TRUE(src_asm.Init());
|
||||||
|
|
||||||
|
for (int level = 0; level < 100; level++) {
|
||||||
|
src_c.SetPadding(10);
|
||||||
|
src_asm.SetPadding(10);
|
||||||
|
src_c.Set(&rnd, &ACMRandom::Rand8);
|
||||||
|
src_asm.CopyFrom(src_c);
|
||||||
|
|
||||||
|
vpx_mbpost_proc_down_c(src_c.TopLeftPixel(), src_c.stride(), rows, cols,
|
||||||
|
q2mbl(level));
|
||||||
|
ASM_REGISTER_STATE_CHECK(GetParam()(
|
||||||
|
src_asm.TopLeftPixel(), src_asm.stride(), rows, cols, q2mbl(level)));
|
||||||
|
ASSERT_TRUE(src_asm.CheckValues(src_c));
|
||||||
|
|
||||||
|
src_c.SetPadding(10);
|
||||||
|
src_asm.SetPadding(10);
|
||||||
|
src_c.Set(&rnd, &ACMRandom::Rand8Extremes);
|
||||||
|
src_asm.CopyFrom(src_c);
|
||||||
|
|
||||||
|
vpx_mbpost_proc_down_c(src_c.TopLeftPixel(), src_c.stride(), rows, cols,
|
||||||
|
q2mbl(level));
|
||||||
|
ASM_REGISTER_STATE_CHECK(GetParam()(
|
||||||
|
src_asm.TopLeftPixel(), src_asm.stride(), rows, cols, q2mbl(level)));
|
||||||
|
ASSERT_TRUE(src_asm.CheckValues(src_c));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
C, VpxPostProcDownAndAcrossMbRowTest,
|
C, VpxPostProcDownAndAcrossMbRowTest,
|
||||||
::testing::Values(vpx_post_proc_down_and_across_mb_row_c));
|
::testing::Values(vpx_post_proc_down_and_across_mb_row_c));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(C, VpxMbPostProcAcrossIpTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_across_ip_c));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(C, VpxMbPostProcDownTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_down_c));
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2, VpxPostProcDownAndAcrossMbRowTest,
|
SSE2, VpxPostProcDownAndAcrossMbRowTest,
|
||||||
::testing::Values(vpx_post_proc_down_and_across_mb_row_sse2));
|
::testing::Values(vpx_post_proc_down_and_across_mb_row_sse2));
|
||||||
#endif
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, VpxMbPostProcAcrossIpTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_across_ip_sse2));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, VpxMbPostProcDownTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_down_sse2));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, VpxPostProcDownAndAcrossMbRowTest,
|
||||||
|
::testing::Values(vpx_post_proc_down_and_across_mb_row_neon));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(NEON, VpxMbPostProcAcrossIpTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_across_ip_neon));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(NEON, VpxMbPostProcDownTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_down_neon));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
#if HAVE_MSA
|
#if HAVE_MSA
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
MSA, VpxPostProcDownAndAcrossMbRowTest,
|
MSA, VpxPostProcDownAndAcrossMbRowTest,
|
||||||
::testing::Values(vpx_post_proc_down_and_across_mb_row_msa));
|
::testing::Values(vpx_post_proc_down_and_across_mb_row_msa));
|
||||||
#endif
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, VpxMbPostProcAcrossIpTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_across_ip_msa));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, VpxMbPostProcDownTest,
|
||||||
|
::testing::Values(vpx_mbpost_proc_down_msa));
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -24,14 +24,14 @@
|
|||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
using ::testing::make_tuple;
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
using std::tr1::make_tuple;
|
|
||||||
|
|
||||||
typedef void (*PredictFunc)(uint8_t *src_ptr, int src_pixels_per_line,
|
typedef void (*PredictFunc)(uint8_t *src_ptr, int src_pixels_per_line,
|
||||||
int xoffset, int yoffset, uint8_t *dst_ptr,
|
int xoffset, int yoffset, uint8_t *dst_ptr,
|
||||||
int dst_pitch);
|
int dst_pitch);
|
||||||
|
|
||||||
typedef std::tr1::tuple<int, int, PredictFunc> PredictParam;
|
typedef ::testing::tuple<int, int, PredictFunc> PredictParam;
|
||||||
|
|
||||||
class PredictTestBase : public ::testing::TestWithParam<PredictParam> {
|
class PredictTestBase : public ::testing::TestWithParam<PredictParam> {
|
||||||
public:
|
public:
|
||||||
@ -324,6 +324,15 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(4, 4, &vp8_sixtap_predict4x4_msa)));
|
make_tuple(4, 4, &vp8_sixtap_predict4x4_msa)));
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if HAVE_MMI
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MMI, SixtapPredictTest,
|
||||||
|
::testing::Values(make_tuple(16, 16, &vp8_sixtap_predict16x16_mmi),
|
||||||
|
make_tuple(8, 8, &vp8_sixtap_predict8x8_mmi),
|
||||||
|
make_tuple(8, 4, &vp8_sixtap_predict8x4_mmi),
|
||||||
|
make_tuple(4, 4, &vp8_sixtap_predict4x4_mmi)));
|
||||||
|
#endif
|
||||||
|
|
||||||
class BilinearPredictTest : public PredictTestBase {};
|
class BilinearPredictTest : public PredictTestBase {};
|
||||||
|
|
||||||
TEST_P(BilinearPredictTest, TestWithRandomData) {
|
TEST_P(BilinearPredictTest, TestWithRandomData) {
|
||||||
|
@ -33,10 +33,10 @@ const int kNumBlockEntries = 16;
|
|||||||
|
|
||||||
typedef void (*VP8Quantize)(BLOCK *b, BLOCKD *d);
|
typedef void (*VP8Quantize)(BLOCK *b, BLOCKD *d);
|
||||||
|
|
||||||
typedef std::tr1::tuple<VP8Quantize, VP8Quantize> VP8QuantizeParam;
|
typedef ::testing::tuple<VP8Quantize, VP8Quantize> VP8QuantizeParam;
|
||||||
|
|
||||||
|
using ::testing::make_tuple;
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
using std::tr1::make_tuple;
|
|
||||||
|
|
||||||
// Create and populate a VP8_COMP instance which has a complete set of
|
// Create and populate a VP8_COMP instance which has a complete set of
|
||||||
// quantization inputs as well as a second MACROBLOCKD for output.
|
// quantization inputs as well as a second MACROBLOCKD for output.
|
||||||
@ -200,4 +200,12 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
make_tuple(&vp8_fast_quantize_b_msa, &vp8_fast_quantize_b_c),
|
make_tuple(&vp8_fast_quantize_b_msa, &vp8_fast_quantize_b_c),
|
||||||
make_tuple(&vp8_regular_quantize_b_msa, &vp8_regular_quantize_b_c)));
|
make_tuple(&vp8_regular_quantize_b_msa, &vp8_regular_quantize_b_c)));
|
||||||
#endif // HAVE_MSA
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
|
#if HAVE_MMI
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MMI, QuantizeTest,
|
||||||
|
::testing::Values(
|
||||||
|
make_tuple(&vp8_fast_quantize_b_mmi, &vp8_fast_quantize_b_c),
|
||||||
|
make_tuple(&vp8_regular_quantize_b_mmi, &vp8_regular_quantize_b_c)));
|
||||||
|
#endif // HAVE_MMI
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -28,11 +28,13 @@
|
|||||||
// See platform implementations of RegisterStateCheckXXX for details.
|
// See platform implementations of RegisterStateCheckXXX for details.
|
||||||
//
|
//
|
||||||
|
|
||||||
#if defined(_WIN64)
|
#if defined(_WIN64) && ARCH_X86_64
|
||||||
|
|
||||||
#undef NOMINMAX
|
#undef NOMINMAX
|
||||||
#define NOMINMAX
|
#define NOMINMAX
|
||||||
|
#ifndef WIN32_LEAN_AND_MEAN
|
||||||
#define WIN32_LEAN_AND_MEAN
|
#define WIN32_LEAN_AND_MEAN
|
||||||
|
#endif
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <winnt.h>
|
#include <winnt.h>
|
||||||
|
|
||||||
@ -111,8 +113,8 @@ class RegisterStateCheck {
|
|||||||
int64_t post_store[8];
|
int64_t post_store[8];
|
||||||
vpx_push_neon(post_store);
|
vpx_push_neon(post_store);
|
||||||
for (int i = 0; i < 8; ++i) {
|
for (int i = 0; i < 8; ++i) {
|
||||||
EXPECT_EQ(pre_store_[i], post_store[i]) << "d" << i + 8
|
EXPECT_EQ(pre_store_[i], post_store[i])
|
||||||
<< " has been modified";
|
<< "d" << i + 8 << " has been modified";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -136,7 +138,7 @@ class RegisterStateCheck {};
|
|||||||
|
|
||||||
} // namespace libvpx_test
|
} // namespace libvpx_test
|
||||||
|
|
||||||
#endif // _WIN64
|
#endif // _WIN64 && ARCH_X86_64
|
||||||
|
|
||||||
#if ARCH_X86 || ARCH_X86_64
|
#if ARCH_X86 || ARCH_X86_64
|
||||||
#if defined(__GNUC__)
|
#if defined(__GNUC__)
|
||||||
|
@ -277,12 +277,29 @@ class ResizeTest
|
|||||||
SetMode(GET_PARAM(1));
|
SetMode(GET_PARAM(1));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual void FramePktHook(const vpx_codec_cx_pkt_t *pkt) {
|
||||||
|
ASSERT_NE(static_cast<int>(pkt->data.frame.width[0]), 0);
|
||||||
|
ASSERT_NE(static_cast<int>(pkt->data.frame.height[0]), 0);
|
||||||
|
encode_frame_width_.push_back(pkt->data.frame.width[0]);
|
||||||
|
encode_frame_height_.push_back(pkt->data.frame.height[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int GetFrameWidth(size_t idx) const {
|
||||||
|
return encode_frame_width_[idx];
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int GetFrameHeight(size_t idx) const {
|
||||||
|
return encode_frame_height_[idx];
|
||||||
|
}
|
||||||
|
|
||||||
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
||||||
vpx_codec_pts_t pts) {
|
vpx_codec_pts_t pts) {
|
||||||
frame_info_list_.push_back(FrameInfo(pts, img.d_w, img.d_h));
|
frame_info_list_.push_back(FrameInfo(pts, img.d_w, img.d_h));
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<FrameInfo> frame_info_list_;
|
std::vector<FrameInfo> frame_info_list_;
|
||||||
|
std::vector<unsigned int> encode_frame_width_;
|
||||||
|
std::vector<unsigned int> encode_frame_height_;
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST_P(ResizeTest, TestExternalResizeWorks) {
|
TEST_P(ResizeTest, TestExternalResizeWorks) {
|
||||||
@ -296,12 +313,15 @@ TEST_P(ResizeTest, TestExternalResizeWorks) {
|
|||||||
const unsigned int frame = static_cast<unsigned>(info->pts);
|
const unsigned int frame = static_cast<unsigned>(info->pts);
|
||||||
unsigned int expected_w;
|
unsigned int expected_w;
|
||||||
unsigned int expected_h;
|
unsigned int expected_h;
|
||||||
|
const size_t idx = info - frame_info_list_.begin();
|
||||||
|
ASSERT_EQ(info->w, GetFrameWidth(idx));
|
||||||
|
ASSERT_EQ(info->h, GetFrameHeight(idx));
|
||||||
ScaleForFrameNumber(frame, kInitialWidth, kInitialHeight, &expected_w,
|
ScaleForFrameNumber(frame, kInitialWidth, kInitialHeight, &expected_w,
|
||||||
&expected_h, 0);
|
&expected_h, 0);
|
||||||
EXPECT_EQ(expected_w, info->w) << "Frame " << frame
|
EXPECT_EQ(expected_w, info->w)
|
||||||
<< " had unexpected width";
|
<< "Frame " << frame << " had unexpected width";
|
||||||
EXPECT_EQ(expected_h, info->h) << "Frame " << frame
|
EXPECT_EQ(expected_h, info->h)
|
||||||
<< " had unexpected height";
|
<< "Frame " << frame << " had unexpected height";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -464,8 +484,23 @@ class ResizeRealtimeTest
|
|||||||
++mismatch_nframes_;
|
++mismatch_nframes_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual void FramePktHook(const vpx_codec_cx_pkt_t *pkt) {
|
||||||
|
ASSERT_NE(static_cast<int>(pkt->data.frame.width[0]), 0);
|
||||||
|
ASSERT_NE(static_cast<int>(pkt->data.frame.height[0]), 0);
|
||||||
|
encode_frame_width_.push_back(pkt->data.frame.width[0]);
|
||||||
|
encode_frame_height_.push_back(pkt->data.frame.height[0]);
|
||||||
|
}
|
||||||
|
|
||||||
unsigned int GetMismatchFrames() { return mismatch_nframes_; }
|
unsigned int GetMismatchFrames() { return mismatch_nframes_; }
|
||||||
|
|
||||||
|
unsigned int GetFrameWidth(size_t idx) const {
|
||||||
|
return encode_frame_width_[idx];
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int GetFrameHeight(size_t idx) const {
|
||||||
|
return encode_frame_height_[idx];
|
||||||
|
}
|
||||||
|
|
||||||
void DefaultConfig() {
|
void DefaultConfig() {
|
||||||
cfg_.rc_buf_initial_sz = 500;
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
cfg_.rc_buf_optimal_sz = 600;
|
cfg_.rc_buf_optimal_sz = 600;
|
||||||
@ -493,6 +528,8 @@ class ResizeRealtimeTest
|
|||||||
bool change_bitrate_;
|
bool change_bitrate_;
|
||||||
double mismatch_psnr_;
|
double mismatch_psnr_;
|
||||||
int mismatch_nframes_;
|
int mismatch_nframes_;
|
||||||
|
std::vector<unsigned int> encode_frame_width_;
|
||||||
|
std::vector<unsigned int> encode_frame_height_;
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST_P(ResizeRealtimeTest, TestExternalResizeWorks) {
|
TEST_P(ResizeRealtimeTest, TestExternalResizeWorks) {
|
||||||
@ -513,10 +550,10 @@ TEST_P(ResizeRealtimeTest, TestExternalResizeWorks) {
|
|||||||
unsigned int expected_h;
|
unsigned int expected_h;
|
||||||
ScaleForFrameNumber(frame, kInitialWidth, kInitialHeight, &expected_w,
|
ScaleForFrameNumber(frame, kInitialWidth, kInitialHeight, &expected_w,
|
||||||
&expected_h, 1);
|
&expected_h, 1);
|
||||||
EXPECT_EQ(expected_w, info->w) << "Frame " << frame
|
EXPECT_EQ(expected_w, info->w)
|
||||||
<< " had unexpected width";
|
<< "Frame " << frame << " had unexpected width";
|
||||||
EXPECT_EQ(expected_h, info->h) << "Frame " << frame
|
EXPECT_EQ(expected_h, info->h)
|
||||||
<< " had unexpected height";
|
<< "Frame " << frame << " had unexpected height";
|
||||||
EXPECT_EQ(static_cast<unsigned int>(0), GetMismatchFrames());
|
EXPECT_EQ(static_cast<unsigned int>(0), GetMismatchFrames());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -582,6 +619,9 @@ TEST_P(ResizeRealtimeTest, TestInternalResizeDownUpChangeBitRate) {
|
|||||||
int resize_count = 0;
|
int resize_count = 0;
|
||||||
for (std::vector<FrameInfo>::const_iterator info = frame_info_list_.begin();
|
for (std::vector<FrameInfo>::const_iterator info = frame_info_list_.begin();
|
||||||
info != frame_info_list_.end(); ++info) {
|
info != frame_info_list_.end(); ++info) {
|
||||||
|
const size_t idx = info - frame_info_list_.begin();
|
||||||
|
ASSERT_EQ(info->w, GetFrameWidth(idx));
|
||||||
|
ASSERT_EQ(info->h, GetFrameHeight(idx));
|
||||||
if (info->w != last_w || info->h != last_h) {
|
if (info->w != last_w || info->h != last_h) {
|
||||||
resize_count++;
|
resize_count++;
|
||||||
if (resize_count == 1) {
|
if (resize_count == 1) {
|
||||||
|
170
test/sad_test.cc
170
test/sad_test.cc
@ -23,6 +23,7 @@
|
|||||||
#include "vpx/vpx_codec.h"
|
#include "vpx/vpx_codec.h"
|
||||||
#include "vpx_mem/vpx_mem.h"
|
#include "vpx_mem/vpx_mem.h"
|
||||||
#include "vpx_ports/mem.h"
|
#include "vpx_ports/mem.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
template <typename Function>
|
template <typename Function>
|
||||||
struct TestParams {
|
struct TestParams {
|
||||||
@ -84,7 +85,7 @@ class SADTestBase : public ::testing::TestWithParam<ParamType> {
|
|||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
}
|
}
|
||||||
mask_ = (1 << bit_depth_) - 1;
|
mask_ = (1 << bit_depth_) - 1;
|
||||||
source_stride_ = (params_.width + 31) & ~31;
|
source_stride_ = (params_.width + 63) & ~63;
|
||||||
reference_stride_ = params_.width * 2;
|
reference_stride_ = params_.width * 2;
|
||||||
rnd_.Reset(ACMRandom::DeterministicSeed());
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
}
|
}
|
||||||
@ -108,7 +109,7 @@ class SADTestBase : public ::testing::TestWithParam<ParamType> {
|
|||||||
|
|
||||||
protected:
|
protected:
|
||||||
// Handle blocks up to 4 blocks 64x64 with stride up to 128
|
// Handle blocks up to 4 blocks 64x64 with stride up to 128
|
||||||
static const int kDataAlignment = 16;
|
static const int kDataAlignment = 32;
|
||||||
static const int kDataBlockSize = 64 * 128;
|
static const int kDataBlockSize = 64 * 128;
|
||||||
static const int kDataBufferSize = 4 * kDataBlockSize;
|
static const int kDataBufferSize = 4 * kDataBlockSize;
|
||||||
|
|
||||||
@ -463,6 +464,38 @@ TEST_P(SADx4Test, SrcAlignedByWidth) {
|
|||||||
source_data_ = tmp_source_data;
|
source_data_ = tmp_source_data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_P(SADx4Test, DISABLED_Speed) {
|
||||||
|
int tmp_stride = reference_stride_;
|
||||||
|
reference_stride_ -= 1;
|
||||||
|
FillRandom(source_data_, source_stride_);
|
||||||
|
FillRandom(GetReference(0), reference_stride_);
|
||||||
|
FillRandom(GetReference(1), reference_stride_);
|
||||||
|
FillRandom(GetReference(2), reference_stride_);
|
||||||
|
FillRandom(GetReference(3), reference_stride_);
|
||||||
|
const int kCountSpeedTestBlock = 500000000 / (params_.width * params_.height);
|
||||||
|
uint32_t reference_sad[4], exp_sad[4];
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
|
||||||
|
memset(reference_sad, 0, sizeof(reference_sad));
|
||||||
|
SADs(exp_sad);
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int i = 0; i < kCountSpeedTestBlock; ++i) {
|
||||||
|
for (int block = 0; block < 4; ++block) {
|
||||||
|
reference_sad[block] = ReferenceSAD(block);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
for (int block = 0; block < 4; ++block) {
|
||||||
|
EXPECT_EQ(reference_sad[block], exp_sad[block]) << "block " << block;
|
||||||
|
}
|
||||||
|
const int elapsed_time =
|
||||||
|
static_cast<int>(vpx_usec_timer_elapsed(&timer) / 1000);
|
||||||
|
printf("sad%dx%dx4 (%2dbit) time: %5d ms\n", params_.width, params_.height,
|
||||||
|
bit_depth_, elapsed_time);
|
||||||
|
|
||||||
|
reference_stride_ = tmp_stride;
|
||||||
|
}
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
// C functions
|
// C functions
|
||||||
const SadMxNParam c_tests[] = {
|
const SadMxNParam c_tests[] = {
|
||||||
@ -644,19 +677,50 @@ INSTANTIATE_TEST_CASE_P(C, SADx4Test, ::testing::ValuesIn(x4d_c_tests));
|
|||||||
#if HAVE_NEON
|
#if HAVE_NEON
|
||||||
const SadMxNParam neon_tests[] = {
|
const SadMxNParam neon_tests[] = {
|
||||||
SadMxNParam(64, 64, &vpx_sad64x64_neon),
|
SadMxNParam(64, 64, &vpx_sad64x64_neon),
|
||||||
|
SadMxNParam(64, 32, &vpx_sad64x32_neon),
|
||||||
SadMxNParam(32, 32, &vpx_sad32x32_neon),
|
SadMxNParam(32, 32, &vpx_sad32x32_neon),
|
||||||
|
SadMxNParam(16, 32, &vpx_sad16x32_neon),
|
||||||
SadMxNParam(16, 16, &vpx_sad16x16_neon),
|
SadMxNParam(16, 16, &vpx_sad16x16_neon),
|
||||||
SadMxNParam(16, 8, &vpx_sad16x8_neon),
|
SadMxNParam(16, 8, &vpx_sad16x8_neon),
|
||||||
SadMxNParam(8, 16, &vpx_sad8x16_neon),
|
SadMxNParam(8, 16, &vpx_sad8x16_neon),
|
||||||
SadMxNParam(8, 8, &vpx_sad8x8_neon),
|
SadMxNParam(8, 8, &vpx_sad8x8_neon),
|
||||||
|
SadMxNParam(8, 4, &vpx_sad8x4_neon),
|
||||||
|
SadMxNParam(4, 8, &vpx_sad4x8_neon),
|
||||||
SadMxNParam(4, 4, &vpx_sad4x4_neon),
|
SadMxNParam(4, 4, &vpx_sad4x4_neon),
|
||||||
};
|
};
|
||||||
INSTANTIATE_TEST_CASE_P(NEON, SADTest, ::testing::ValuesIn(neon_tests));
|
INSTANTIATE_TEST_CASE_P(NEON, SADTest, ::testing::ValuesIn(neon_tests));
|
||||||
|
|
||||||
|
const SadMxNAvgParam avg_neon_tests[] = {
|
||||||
|
SadMxNAvgParam(64, 64, &vpx_sad64x64_avg_neon),
|
||||||
|
SadMxNAvgParam(64, 32, &vpx_sad64x32_avg_neon),
|
||||||
|
SadMxNAvgParam(32, 64, &vpx_sad32x64_avg_neon),
|
||||||
|
SadMxNAvgParam(32, 32, &vpx_sad32x32_avg_neon),
|
||||||
|
SadMxNAvgParam(32, 16, &vpx_sad32x16_avg_neon),
|
||||||
|
SadMxNAvgParam(16, 32, &vpx_sad16x32_avg_neon),
|
||||||
|
SadMxNAvgParam(16, 16, &vpx_sad16x16_avg_neon),
|
||||||
|
SadMxNAvgParam(16, 8, &vpx_sad16x8_avg_neon),
|
||||||
|
SadMxNAvgParam(8, 16, &vpx_sad8x16_avg_neon),
|
||||||
|
SadMxNAvgParam(8, 8, &vpx_sad8x8_avg_neon),
|
||||||
|
SadMxNAvgParam(8, 4, &vpx_sad8x4_avg_neon),
|
||||||
|
SadMxNAvgParam(4, 8, &vpx_sad4x8_avg_neon),
|
||||||
|
SadMxNAvgParam(4, 4, &vpx_sad4x4_avg_neon),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(NEON, SADavgTest, ::testing::ValuesIn(avg_neon_tests));
|
||||||
|
|
||||||
const SadMxNx4Param x4d_neon_tests[] = {
|
const SadMxNx4Param x4d_neon_tests[] = {
|
||||||
SadMxNx4Param(64, 64, &vpx_sad64x64x4d_neon),
|
SadMxNx4Param(64, 64, &vpx_sad64x64x4d_neon),
|
||||||
|
SadMxNx4Param(64, 32, &vpx_sad64x32x4d_neon),
|
||||||
|
SadMxNx4Param(32, 64, &vpx_sad32x64x4d_neon),
|
||||||
SadMxNx4Param(32, 32, &vpx_sad32x32x4d_neon),
|
SadMxNx4Param(32, 32, &vpx_sad32x32x4d_neon),
|
||||||
|
SadMxNx4Param(32, 16, &vpx_sad32x16x4d_neon),
|
||||||
|
SadMxNx4Param(16, 32, &vpx_sad16x32x4d_neon),
|
||||||
SadMxNx4Param(16, 16, &vpx_sad16x16x4d_neon),
|
SadMxNx4Param(16, 16, &vpx_sad16x16x4d_neon),
|
||||||
|
SadMxNx4Param(16, 8, &vpx_sad16x8x4d_neon),
|
||||||
|
SadMxNx4Param(8, 16, &vpx_sad8x16x4d_neon),
|
||||||
|
SadMxNx4Param(8, 8, &vpx_sad8x8x4d_neon),
|
||||||
|
SadMxNx4Param(8, 4, &vpx_sad8x4x4d_neon),
|
||||||
|
SadMxNx4Param(4, 8, &vpx_sad4x8x4d_neon),
|
||||||
|
SadMxNx4Param(4, 4, &vpx_sad4x4x4d_neon),
|
||||||
};
|
};
|
||||||
INSTANTIATE_TEST_CASE_P(NEON, SADx4Test, ::testing::ValuesIn(x4d_neon_tests));
|
INSTANTIATE_TEST_CASE_P(NEON, SADx4Test, ::testing::ValuesIn(x4d_neon_tests));
|
||||||
#endif // HAVE_NEON
|
#endif // HAVE_NEON
|
||||||
@ -865,6 +929,14 @@ const SadMxNx4Param x4d_avx2_tests[] = {
|
|||||||
INSTANTIATE_TEST_CASE_P(AVX2, SADx4Test, ::testing::ValuesIn(x4d_avx2_tests));
|
INSTANTIATE_TEST_CASE_P(AVX2, SADx4Test, ::testing::ValuesIn(x4d_avx2_tests));
|
||||||
#endif // HAVE_AVX2
|
#endif // HAVE_AVX2
|
||||||
|
|
||||||
|
#if HAVE_AVX512
|
||||||
|
const SadMxNx4Param x4d_avx512_tests[] = {
|
||||||
|
SadMxNx4Param(64, 64, &vpx_sad64x64x4d_avx512),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(AVX512, SADx4Test,
|
||||||
|
::testing::ValuesIn(x4d_avx512_tests));
|
||||||
|
#endif // HAVE_AVX512
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
// MIPS functions
|
// MIPS functions
|
||||||
#if HAVE_MSA
|
#if HAVE_MSA
|
||||||
@ -920,4 +992,98 @@ const SadMxNx4Param x4d_msa_tests[] = {
|
|||||||
INSTANTIATE_TEST_CASE_P(MSA, SADx4Test, ::testing::ValuesIn(x4d_msa_tests));
|
INSTANTIATE_TEST_CASE_P(MSA, SADx4Test, ::testing::ValuesIn(x4d_msa_tests));
|
||||||
#endif // HAVE_MSA
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
|
//------------------------------------------------------------------------------
|
||||||
|
// VSX functions
|
||||||
|
#if HAVE_VSX
|
||||||
|
const SadMxNParam vsx_tests[] = {
|
||||||
|
SadMxNParam(64, 64, &vpx_sad64x64_vsx),
|
||||||
|
SadMxNParam(64, 32, &vpx_sad64x32_vsx),
|
||||||
|
SadMxNParam(32, 64, &vpx_sad32x64_vsx),
|
||||||
|
SadMxNParam(32, 32, &vpx_sad32x32_vsx),
|
||||||
|
SadMxNParam(32, 16, &vpx_sad32x16_vsx),
|
||||||
|
SadMxNParam(16, 32, &vpx_sad16x32_vsx),
|
||||||
|
SadMxNParam(16, 16, &vpx_sad16x16_vsx),
|
||||||
|
SadMxNParam(16, 8, &vpx_sad16x8_vsx),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, SADTest, ::testing::ValuesIn(vsx_tests));
|
||||||
|
|
||||||
|
const SadMxNAvgParam avg_vsx_tests[] = {
|
||||||
|
SadMxNAvgParam(64, 64, &vpx_sad64x64_avg_vsx),
|
||||||
|
SadMxNAvgParam(64, 32, &vpx_sad64x32_avg_vsx),
|
||||||
|
SadMxNAvgParam(32, 64, &vpx_sad32x64_avg_vsx),
|
||||||
|
SadMxNAvgParam(32, 32, &vpx_sad32x32_avg_vsx),
|
||||||
|
SadMxNAvgParam(32, 16, &vpx_sad32x16_avg_vsx),
|
||||||
|
SadMxNAvgParam(16, 32, &vpx_sad16x32_avg_vsx),
|
||||||
|
SadMxNAvgParam(16, 16, &vpx_sad16x16_avg_vsx),
|
||||||
|
SadMxNAvgParam(16, 8, &vpx_sad16x8_avg_vsx),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, SADavgTest, ::testing::ValuesIn(avg_vsx_tests));
|
||||||
|
|
||||||
|
const SadMxNx4Param x4d_vsx_tests[] = {
|
||||||
|
SadMxNx4Param(64, 64, &vpx_sad64x64x4d_vsx),
|
||||||
|
SadMxNx4Param(64, 32, &vpx_sad64x32x4d_vsx),
|
||||||
|
SadMxNx4Param(32, 64, &vpx_sad32x64x4d_vsx),
|
||||||
|
SadMxNx4Param(32, 32, &vpx_sad32x32x4d_vsx),
|
||||||
|
SadMxNx4Param(32, 16, &vpx_sad32x16x4d_vsx),
|
||||||
|
SadMxNx4Param(16, 32, &vpx_sad16x32x4d_vsx),
|
||||||
|
SadMxNx4Param(16, 16, &vpx_sad16x16x4d_vsx),
|
||||||
|
SadMxNx4Param(16, 8, &vpx_sad16x8x4d_vsx),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(VSX, SADx4Test, ::testing::ValuesIn(x4d_vsx_tests));
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
|
||||||
|
//------------------------------------------------------------------------------
|
||||||
|
// Loongson functions
|
||||||
|
#if HAVE_MMI
|
||||||
|
const SadMxNParam mmi_tests[] = {
|
||||||
|
SadMxNParam(64, 64, &vpx_sad64x64_mmi),
|
||||||
|
SadMxNParam(64, 32, &vpx_sad64x32_mmi),
|
||||||
|
SadMxNParam(32, 64, &vpx_sad32x64_mmi),
|
||||||
|
SadMxNParam(32, 32, &vpx_sad32x32_mmi),
|
||||||
|
SadMxNParam(32, 16, &vpx_sad32x16_mmi),
|
||||||
|
SadMxNParam(16, 32, &vpx_sad16x32_mmi),
|
||||||
|
SadMxNParam(16, 16, &vpx_sad16x16_mmi),
|
||||||
|
SadMxNParam(16, 8, &vpx_sad16x8_mmi),
|
||||||
|
SadMxNParam(8, 16, &vpx_sad8x16_mmi),
|
||||||
|
SadMxNParam(8, 8, &vpx_sad8x8_mmi),
|
||||||
|
SadMxNParam(8, 4, &vpx_sad8x4_mmi),
|
||||||
|
SadMxNParam(4, 8, &vpx_sad4x8_mmi),
|
||||||
|
SadMxNParam(4, 4, &vpx_sad4x4_mmi),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(MMI, SADTest, ::testing::ValuesIn(mmi_tests));
|
||||||
|
|
||||||
|
const SadMxNAvgParam avg_mmi_tests[] = {
|
||||||
|
SadMxNAvgParam(64, 64, &vpx_sad64x64_avg_mmi),
|
||||||
|
SadMxNAvgParam(64, 32, &vpx_sad64x32_avg_mmi),
|
||||||
|
SadMxNAvgParam(32, 64, &vpx_sad32x64_avg_mmi),
|
||||||
|
SadMxNAvgParam(32, 32, &vpx_sad32x32_avg_mmi),
|
||||||
|
SadMxNAvgParam(32, 16, &vpx_sad32x16_avg_mmi),
|
||||||
|
SadMxNAvgParam(16, 32, &vpx_sad16x32_avg_mmi),
|
||||||
|
SadMxNAvgParam(16, 16, &vpx_sad16x16_avg_mmi),
|
||||||
|
SadMxNAvgParam(16, 8, &vpx_sad16x8_avg_mmi),
|
||||||
|
SadMxNAvgParam(8, 16, &vpx_sad8x16_avg_mmi),
|
||||||
|
SadMxNAvgParam(8, 8, &vpx_sad8x8_avg_mmi),
|
||||||
|
SadMxNAvgParam(8, 4, &vpx_sad8x4_avg_mmi),
|
||||||
|
SadMxNAvgParam(4, 8, &vpx_sad4x8_avg_mmi),
|
||||||
|
SadMxNAvgParam(4, 4, &vpx_sad4x4_avg_mmi),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(MMI, SADavgTest, ::testing::ValuesIn(avg_mmi_tests));
|
||||||
|
|
||||||
|
const SadMxNx4Param x4d_mmi_tests[] = {
|
||||||
|
SadMxNx4Param(64, 64, &vpx_sad64x64x4d_mmi),
|
||||||
|
SadMxNx4Param(64, 32, &vpx_sad64x32x4d_mmi),
|
||||||
|
SadMxNx4Param(32, 64, &vpx_sad32x64x4d_mmi),
|
||||||
|
SadMxNx4Param(32, 32, &vpx_sad32x32x4d_mmi),
|
||||||
|
SadMxNx4Param(32, 16, &vpx_sad32x16x4d_mmi),
|
||||||
|
SadMxNx4Param(16, 32, &vpx_sad16x32x4d_mmi),
|
||||||
|
SadMxNx4Param(16, 16, &vpx_sad16x16x4d_mmi),
|
||||||
|
SadMxNx4Param(16, 8, &vpx_sad16x8x4d_mmi),
|
||||||
|
SadMxNx4Param(8, 16, &vpx_sad8x16x4d_mmi),
|
||||||
|
SadMxNx4Param(8, 8, &vpx_sad8x8x4d_mmi),
|
||||||
|
SadMxNx4Param(8, 4, &vpx_sad8x4x4d_mmi),
|
||||||
|
SadMxNx4Param(4, 8, &vpx_sad4x8x4d_mmi),
|
||||||
|
SadMxNx4Param(4, 4, &vpx_sad4x4x4d_mmi),
|
||||||
|
};
|
||||||
|
INSTANTIATE_TEST_CASE_P(MMI, SADx4Test, ::testing::ValuesIn(x4d_mmi_tests));
|
||||||
|
#endif // HAVE_MMI
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -146,14 +146,6 @@ TEST(VP8RoiMapTest, ParameterCheck) {
|
|||||||
if (deltas_valid != roi_retval) break;
|
if (deltas_valid != roi_retval) break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test that we report and error if cyclic refresh is enabled.
|
|
||||||
cpi.cyclic_refresh_mode_enabled = 1;
|
|
||||||
roi_retval =
|
|
||||||
vp8_set_roimap(&cpi, roi_map, cpi.common.mb_rows, cpi.common.mb_cols,
|
|
||||||
delta_q, delta_lf, threshold);
|
|
||||||
EXPECT_EQ(-1, roi_retval) << "cyclic refresh check error";
|
|
||||||
cpi.cyclic_refresh_mode_enabled = 0;
|
|
||||||
|
|
||||||
// Test invalid number of rows or colums.
|
// Test invalid number of rows or colums.
|
||||||
roi_retval =
|
roi_retval =
|
||||||
vp8_set_roimap(&cpi, roi_map, cpi.common.mb_rows + 1,
|
vp8_set_roimap(&cpi, roi_map, cpi.common.mb_rows + 1,
|
||||||
|
169
test/stress.sh
Executable file
169
test/stress.sh
Executable file
@ -0,0 +1,169 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
##
|
||||||
|
## Copyright (c) 2016 The WebM project authors. All Rights Reserved.
|
||||||
|
##
|
||||||
|
## Use of this source code is governed by a BSD-style license
|
||||||
|
## that can be found in the LICENSE file in the root of the source
|
||||||
|
## tree. An additional intellectual property rights grant can be found
|
||||||
|
## in the file PATENTS. All contributing project authors may
|
||||||
|
## be found in the AUTHORS file in the root of the source tree.
|
||||||
|
##
|
||||||
|
## This file performs a stress test. It runs (STRESS_ONEPASS_MAX_JOBS,
|
||||||
|
## default=5) one, (STRESS_TWOPASS_MAX_JOBS, default=5) two pass &
|
||||||
|
## (STRESS_RT_MAX_JOBS, default=5) encodes and (STRESS_<codec>_DECODE_MAX_JOBS,
|
||||||
|
## default=30) decodes in parallel.
|
||||||
|
|
||||||
|
. $(dirname $0)/tools_common.sh
|
||||||
|
|
||||||
|
YUV="${LIBVPX_TEST_DATA_PATH}/niklas_1280_720_30.yuv"
|
||||||
|
VP8="${LIBVPX_TEST_DATA_PATH}/tos_vp8.webm"
|
||||||
|
VP9="${LIBVPX_TEST_DATA_PATH}/vp90-2-sintel_1920x818_tile_1x4_fpm_2279kbps.webm"
|
||||||
|
DATA_URL="http://downloads.webmproject.org/test_data/libvpx/"
|
||||||
|
SHA1_FILE="$(dirname $0)/test-data.sha1"
|
||||||
|
|
||||||
|
# Set sha1sum to proper sha program (sha1sum, shasum, sha1). This code is
|
||||||
|
# cribbed from libs.mk.
|
||||||
|
[ -x "$(which sha1sum)" ] && sha1sum=sha1sum
|
||||||
|
[ -x "$(which shasum)" ] && sha1sum=shasum
|
||||||
|
[ -x "$(which sha1)" ] && sha1sum=sha1
|
||||||
|
|
||||||
|
# Download a file from the url and check its sha1sum.
|
||||||
|
download_and_check_file() {
|
||||||
|
# Get the file from the file path.
|
||||||
|
local readonly root="${1#${LIBVPX_TEST_DATA_PATH}/}"
|
||||||
|
|
||||||
|
# Download the file using curl. Trap to insure non partial file.
|
||||||
|
(trap "rm -f $1" INT TERM \
|
||||||
|
&& eval "curl --retry 1 -L -o $1 ${DATA_URL}${root} ${devnull}")
|
||||||
|
|
||||||
|
# Check the sha1 sum of the file.
|
||||||
|
if [ -n "${sha1sum}" ]; then
|
||||||
|
set -e
|
||||||
|
grep ${root} ${SHA1_FILE} \
|
||||||
|
| (cd ${LIBVPX_TEST_DATA_PATH}; ${sha1sum} -c);
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Environment check: Make sure input is available.
|
||||||
|
stress_verify_environment() {
|
||||||
|
if [ ! -e "${SHA1_FILE}" ] ; then
|
||||||
|
echo "Missing ${SHA1_FILE}"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
for file in "${YUV}" "${VP8}" "${VP9}"; do
|
||||||
|
if [ ! -e "${file}" ] ; then
|
||||||
|
download_and_check_file "${file}"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
if [ ! -e "${YUV}" ] || [ ! -e "${VP8}" ] || [ ! -e "${VP9}" ] ; then
|
||||||
|
elog "Libvpx test data must exist in LIBVPX_TEST_DATA_PATH."
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
if [ -z "$(vpx_tool_path vpxenc)" ]; then
|
||||||
|
elog "vpxenc not found. It must exist in LIBVPX_BIN_PATH or its parent."
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
if [ -z "$(vpx_tool_path vpxdec)" ]; then
|
||||||
|
elog "vpxdec not found. It must exist in LIBVPX_BIN_PATH or its parent."
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# This function runs tests on libvpx that run multiple encodes and decodes
|
||||||
|
# in parallel in hopes of catching synchronization and/or threading issues.
|
||||||
|
stress() {
|
||||||
|
local readonly decoder="$(vpx_tool_path vpxdec)"
|
||||||
|
local readonly encoder="$(vpx_tool_path vpxenc)"
|
||||||
|
local readonly codec="$1"
|
||||||
|
local readonly webm="$2"
|
||||||
|
local readonly decode_count="$3"
|
||||||
|
local readonly threads="$4"
|
||||||
|
local readonly enc_args="$5"
|
||||||
|
local pids=""
|
||||||
|
local rt_max_jobs=${STRESS_RT_MAX_JOBS:-5}
|
||||||
|
local onepass_max_jobs=${STRESS_ONEPASS_MAX_JOBS:-5}
|
||||||
|
local twopass_max_jobs=${STRESS_TWOPASS_MAX_JOBS:-5}
|
||||||
|
|
||||||
|
# Enable job control, so we can run multiple processes.
|
||||||
|
set -m
|
||||||
|
|
||||||
|
# Start $onepass_max_jobs encode jobs in parallel.
|
||||||
|
for i in $(seq ${onepass_max_jobs}); do
|
||||||
|
bitrate=$(($i * 20 + 300))
|
||||||
|
eval "${VPX_TEST_PREFIX}" "${encoder}" "--codec=${codec} -w 1280 -h 720" \
|
||||||
|
"${YUV}" "-t ${threads} --limit=150 --test-decode=fatal --passes=1" \
|
||||||
|
"--target-bitrate=${bitrate} -o ${VPX_TEST_OUTPUT_DIR}/${i}.1pass.webm" \
|
||||||
|
"${enc_args}" ${devnull} &
|
||||||
|
pids="${pids} $!"
|
||||||
|
done
|
||||||
|
|
||||||
|
# Start $twopass_max_jobs encode jobs in parallel.
|
||||||
|
for i in $(seq ${twopass_max_jobs}); do
|
||||||
|
bitrate=$(($i * 20 + 300))
|
||||||
|
eval "${VPX_TEST_PREFIX}" "${encoder}" "--codec=${codec} -w 1280 -h 720" \
|
||||||
|
"${YUV}" "-t ${threads} --limit=150 --test-decode=fatal --passes=2" \
|
||||||
|
"--target-bitrate=${bitrate} -o ${VPX_TEST_OUTPUT_DIR}/${i}.2pass.webm" \
|
||||||
|
"${enc_args}" ${devnull} &
|
||||||
|
pids="${pids} $!"
|
||||||
|
done
|
||||||
|
|
||||||
|
# Start $rt_max_jobs rt encode jobs in parallel.
|
||||||
|
for i in $(seq ${rt_max_jobs}); do
|
||||||
|
bitrate=$(($i * 20 + 300))
|
||||||
|
eval "${VPX_TEST_PREFIX}" "${encoder}" "--codec=${codec} -w 1280 -h 720" \
|
||||||
|
"${YUV}" "-t ${threads} --limit=150 --test-decode=fatal " \
|
||||||
|
"--target-bitrate=${bitrate} --lag-in-frames=0 --error-resilient=1" \
|
||||||
|
"--kf-min-dist=3000 --kf-max-dist=3000 --cpu-used=-6 --static-thresh=1" \
|
||||||
|
"--end-usage=cbr --min-q=2 --max-q=56 --undershoot-pct=100" \
|
||||||
|
"--overshoot-pct=15 --buf-sz=1000 --buf-initial-sz=500" \
|
||||||
|
"--buf-optimal-sz=600 --max-intra-rate=900 --resize-allowed=0" \
|
||||||
|
"--drop-frame=0 --passes=1 --rt --noise-sensitivity=4" \
|
||||||
|
"-o ${VPX_TEST_OUTPUT_DIR}/${i}.rt.webm" ${devnull} &
|
||||||
|
pids="${pids} $!"
|
||||||
|
done
|
||||||
|
|
||||||
|
# Start $decode_count decode jobs in parallel.
|
||||||
|
for i in $(seq "${decode_count}"); do
|
||||||
|
eval "${decoder}" "-t ${threads}" "${webm}" "--noblit" ${devnull} &
|
||||||
|
pids="${pids} $!"
|
||||||
|
done
|
||||||
|
|
||||||
|
# Wait for all parallel jobs to finish.
|
||||||
|
fail=0
|
||||||
|
for job in "${pids}"; do
|
||||||
|
wait $job || fail=$(($fail + 1))
|
||||||
|
done
|
||||||
|
return $fail
|
||||||
|
}
|
||||||
|
|
||||||
|
vp8_stress_test() {
|
||||||
|
local vp8_max_jobs=${STRESS_VP8_DECODE_MAX_JOBS:-40}
|
||||||
|
if [ "$(vp8_decode_available)" = "yes" -a \
|
||||||
|
"$(vp8_encode_available)" = "yes" ]; then
|
||||||
|
stress vp8 "${VP8}" "${vp8_max_jobs}" 4
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
vp9_stress() {
|
||||||
|
local vp9_max_jobs=${STRESS_VP9_DECODE_MAX_JOBS:-25}
|
||||||
|
|
||||||
|
if [ "$(vp9_decode_available)" = "yes" -a \
|
||||||
|
"$(vp9_encode_available)" = "yes" ]; then
|
||||||
|
stress vp9 "${VP9}" "${vp9_max_jobs}" "$@"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
vp9_stress_test() {
|
||||||
|
for threads in 4 8 100; do
|
||||||
|
vp9_stress "$threads" "--row-mt=0"
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
|
vp9_stress_test_row_mt() {
|
||||||
|
for threads in 4 8 100; do
|
||||||
|
vp9_stress "$threads" "--row-mt=1"
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
|
run_tests stress_verify_environment \
|
||||||
|
"vp8_stress_test vp9_stress_test vp9_stress_test_row_mt"
|
@ -28,7 +28,7 @@ namespace {
|
|||||||
const int kNumIterations = 10000;
|
const int kNumIterations = 10000;
|
||||||
|
|
||||||
typedef uint64_t (*SSI16Func)(const int16_t *src, int stride, int size);
|
typedef uint64_t (*SSI16Func)(const int16_t *src, int stride, int size);
|
||||||
typedef std::tr1::tuple<SSI16Func, SSI16Func> SumSquaresParam;
|
typedef ::testing::tuple<SSI16Func, SSI16Func> SumSquaresParam;
|
||||||
|
|
||||||
class SumSquaresTest : public ::testing::TestWithParam<SumSquaresParam> {
|
class SumSquaresTest : public ::testing::TestWithParam<SumSquaresParam> {
|
||||||
public:
|
public:
|
||||||
@ -102,7 +102,7 @@ TEST_P(SumSquaresTest, ExtremeValues) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
@ -110,4 +110,11 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
::testing::Values(make_tuple(&vpx_sum_squares_2d_i16_c,
|
::testing::Values(make_tuple(&vpx_sum_squares_2d_i16_c,
|
||||||
&vpx_sum_squares_2d_i16_sse2)));
|
&vpx_sum_squares_2d_i16_sse2)));
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_MSA
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MSA, SumSquaresTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_sum_squares_2d_i16_c,
|
||||||
|
&vpx_sum_squares_2d_i16_msa)));
|
||||||
|
#endif // HAVE_MSA
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -18,7 +18,7 @@ namespace {
|
|||||||
|
|
||||||
const int kTestMode = 0;
|
const int kTestMode = 0;
|
||||||
|
|
||||||
typedef std::tr1::tuple<libvpx_test::TestMode, int> SuperframeTestParam;
|
typedef ::testing::tuple<libvpx_test::TestMode, int> SuperframeTestParam;
|
||||||
|
|
||||||
class SuperframeTest
|
class SuperframeTest
|
||||||
: public ::libvpx_test::EncoderTest,
|
: public ::libvpx_test::EncoderTest,
|
||||||
@ -31,7 +31,7 @@ class SuperframeTest
|
|||||||
virtual void SetUp() {
|
virtual void SetUp() {
|
||||||
InitializeConfig();
|
InitializeConfig();
|
||||||
const SuperframeTestParam input = GET_PARAM(1);
|
const SuperframeTestParam input = GET_PARAM(1);
|
||||||
const libvpx_test::TestMode mode = std::tr1::get<kTestMode>(input);
|
const libvpx_test::TestMode mode = ::testing::get<kTestMode>(input);
|
||||||
SetMode(mode);
|
SetMode(mode);
|
||||||
sf_count_ = 0;
|
sf_count_ = 0;
|
||||||
sf_count_max_ = INT_MAX;
|
sf_count_max_ = INT_MAX;
|
||||||
|
1084
test/svc_datarate_test.cc
Normal file
1084
test/svc_datarate_test.cc
Normal file
File diff suppressed because it is too large
Load Diff
789
test/svc_test.cc
789
test/svc_test.cc
@ -1,789 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (c) 2013 The WebM project authors. All Rights Reserved.
|
|
||||||
*
|
|
||||||
* Use of this source code is governed by a BSD-style license
|
|
||||||
* that can be found in the LICENSE file in the root of the source
|
|
||||||
* tree. An additional intellectual property rights grant can be found
|
|
||||||
* in the file PATENTS. All contributing project authors may
|
|
||||||
* be found in the AUTHORS file in the root of the source tree.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <string>
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
|
||||||
#include "test/codec_factory.h"
|
|
||||||
#include "test/decode_test_driver.h"
|
|
||||||
#include "test/i420_video_source.h"
|
|
||||||
|
|
||||||
#include "vp9/decoder/vp9_decoder.h"
|
|
||||||
|
|
||||||
#include "vpx/svc_context.h"
|
|
||||||
#include "vpx/vp8cx.h"
|
|
||||||
#include "vpx/vpx_encoder.h"
|
|
||||||
|
|
||||||
namespace {
|
|
||||||
|
|
||||||
using libvpx_test::CodecFactory;
|
|
||||||
using libvpx_test::Decoder;
|
|
||||||
using libvpx_test::DxDataIterator;
|
|
||||||
using libvpx_test::VP9CodecFactory;
|
|
||||||
|
|
||||||
class SvcTest : public ::testing::Test {
|
|
||||||
protected:
|
|
||||||
static const uint32_t kWidth = 352;
|
|
||||||
static const uint32_t kHeight = 288;
|
|
||||||
|
|
||||||
SvcTest()
|
|
||||||
: codec_iface_(0), test_file_name_("hantro_collage_w352h288.yuv"),
|
|
||||||
codec_initialized_(false), decoder_(0) {
|
|
||||||
memset(&svc_, 0, sizeof(svc_));
|
|
||||||
memset(&codec_, 0, sizeof(codec_));
|
|
||||||
memset(&codec_enc_, 0, sizeof(codec_enc_));
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual ~SvcTest() {}
|
|
||||||
|
|
||||||
virtual void SetUp() {
|
|
||||||
svc_.log_level = SVC_LOG_DEBUG;
|
|
||||||
svc_.log_print = 0;
|
|
||||||
|
|
||||||
codec_iface_ = vpx_codec_vp9_cx();
|
|
||||||
const vpx_codec_err_t res =
|
|
||||||
vpx_codec_enc_config_default(codec_iface_, &codec_enc_, 0);
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
|
|
||||||
codec_enc_.g_w = kWidth;
|
|
||||||
codec_enc_.g_h = kHeight;
|
|
||||||
codec_enc_.g_timebase.num = 1;
|
|
||||||
codec_enc_.g_timebase.den = 60;
|
|
||||||
codec_enc_.kf_min_dist = 100;
|
|
||||||
codec_enc_.kf_max_dist = 100;
|
|
||||||
|
|
||||||
vpx_codec_dec_cfg_t dec_cfg = vpx_codec_dec_cfg_t();
|
|
||||||
VP9CodecFactory codec_factory;
|
|
||||||
decoder_ = codec_factory.CreateDecoder(dec_cfg, 0);
|
|
||||||
|
|
||||||
tile_columns_ = 0;
|
|
||||||
tile_rows_ = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void TearDown() {
|
|
||||||
ReleaseEncoder();
|
|
||||||
delete (decoder_);
|
|
||||||
}
|
|
||||||
|
|
||||||
void InitializeEncoder() {
|
|
||||||
const vpx_codec_err_t res =
|
|
||||||
vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
vpx_codec_control(&codec_, VP8E_SET_CPUUSED, 4); // Make the test faster
|
|
||||||
vpx_codec_control(&codec_, VP9E_SET_TILE_COLUMNS, tile_columns_);
|
|
||||||
vpx_codec_control(&codec_, VP9E_SET_TILE_ROWS, tile_rows_);
|
|
||||||
codec_initialized_ = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ReleaseEncoder() {
|
|
||||||
vpx_svc_release(&svc_);
|
|
||||||
if (codec_initialized_) vpx_codec_destroy(&codec_);
|
|
||||||
codec_initialized_ = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GetStatsData(std::string *const stats_buf) {
|
|
||||||
vpx_codec_iter_t iter = NULL;
|
|
||||||
const vpx_codec_cx_pkt_t *cx_pkt;
|
|
||||||
|
|
||||||
while ((cx_pkt = vpx_codec_get_cx_data(&codec_, &iter)) != NULL) {
|
|
||||||
if (cx_pkt->kind == VPX_CODEC_STATS_PKT) {
|
|
||||||
EXPECT_GT(cx_pkt->data.twopass_stats.sz, 0U);
|
|
||||||
ASSERT_TRUE(cx_pkt->data.twopass_stats.buf != NULL);
|
|
||||||
stats_buf->append(static_cast<char *>(cx_pkt->data.twopass_stats.buf),
|
|
||||||
cx_pkt->data.twopass_stats.sz);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Pass1EncodeNFrames(const int n, const int layers,
|
|
||||||
std::string *const stats_buf) {
|
|
||||||
vpx_codec_err_t res;
|
|
||||||
|
|
||||||
ASSERT_GT(n, 0);
|
|
||||||
ASSERT_GT(layers, 0);
|
|
||||||
svc_.spatial_layers = layers;
|
|
||||||
codec_enc_.g_pass = VPX_RC_FIRST_PASS;
|
|
||||||
InitializeEncoder();
|
|
||||||
|
|
||||||
libvpx_test::I420VideoSource video(
|
|
||||||
test_file_name_, codec_enc_.g_w, codec_enc_.g_h,
|
|
||||||
codec_enc_.g_timebase.den, codec_enc_.g_timebase.num, 0, 30);
|
|
||||||
video.Begin();
|
|
||||||
|
|
||||||
for (int i = 0; i < n; ++i) {
|
|
||||||
res = vpx_svc_encode(&svc_, &codec_, video.img(), video.pts(),
|
|
||||||
video.duration(), VPX_DL_GOOD_QUALITY);
|
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res);
|
|
||||||
GetStatsData(stats_buf);
|
|
||||||
video.Next();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Flush encoder and test EOS packet.
|
|
||||||
res = vpx_svc_encode(&svc_, &codec_, NULL, video.pts(), video.duration(),
|
|
||||||
VPX_DL_GOOD_QUALITY);
|
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res);
|
|
||||||
GetStatsData(stats_buf);
|
|
||||||
|
|
||||||
ReleaseEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
void StoreFrames(const size_t max_frame_received,
|
|
||||||
struct vpx_fixed_buf *const outputs,
|
|
||||||
size_t *const frame_received) {
|
|
||||||
vpx_codec_iter_t iter = NULL;
|
|
||||||
const vpx_codec_cx_pkt_t *cx_pkt;
|
|
||||||
|
|
||||||
while ((cx_pkt = vpx_codec_get_cx_data(&codec_, &iter)) != NULL) {
|
|
||||||
if (cx_pkt->kind == VPX_CODEC_CX_FRAME_PKT) {
|
|
||||||
const size_t frame_size = cx_pkt->data.frame.sz;
|
|
||||||
|
|
||||||
EXPECT_GT(frame_size, 0U);
|
|
||||||
ASSERT_TRUE(cx_pkt->data.frame.buf != NULL);
|
|
||||||
ASSERT_LT(*frame_received, max_frame_received);
|
|
||||||
|
|
||||||
if (*frame_received == 0)
|
|
||||||
EXPECT_EQ(1, !!(cx_pkt->data.frame.flags & VPX_FRAME_IS_KEY));
|
|
||||||
|
|
||||||
outputs[*frame_received].buf = malloc(frame_size + 16);
|
|
||||||
ASSERT_TRUE(outputs[*frame_received].buf != NULL);
|
|
||||||
memcpy(outputs[*frame_received].buf, cx_pkt->data.frame.buf,
|
|
||||||
frame_size);
|
|
||||||
outputs[*frame_received].sz = frame_size;
|
|
||||||
++(*frame_received);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Pass2EncodeNFrames(std::string *const stats_buf, const int n,
|
|
||||||
const int layers,
|
|
||||||
struct vpx_fixed_buf *const outputs) {
|
|
||||||
vpx_codec_err_t res;
|
|
||||||
size_t frame_received = 0;
|
|
||||||
|
|
||||||
ASSERT_TRUE(outputs != NULL);
|
|
||||||
ASSERT_GT(n, 0);
|
|
||||||
ASSERT_GT(layers, 0);
|
|
||||||
svc_.spatial_layers = layers;
|
|
||||||
codec_enc_.rc_target_bitrate = 500;
|
|
||||||
if (codec_enc_.g_pass == VPX_RC_LAST_PASS) {
|
|
||||||
ASSERT_TRUE(stats_buf != NULL);
|
|
||||||
ASSERT_GT(stats_buf->size(), 0U);
|
|
||||||
codec_enc_.rc_twopass_stats_in.buf = &(*stats_buf)[0];
|
|
||||||
codec_enc_.rc_twopass_stats_in.sz = stats_buf->size();
|
|
||||||
}
|
|
||||||
InitializeEncoder();
|
|
||||||
|
|
||||||
libvpx_test::I420VideoSource video(
|
|
||||||
test_file_name_, codec_enc_.g_w, codec_enc_.g_h,
|
|
||||||
codec_enc_.g_timebase.den, codec_enc_.g_timebase.num, 0, 30);
|
|
||||||
video.Begin();
|
|
||||||
|
|
||||||
for (int i = 0; i < n; ++i) {
|
|
||||||
res = vpx_svc_encode(&svc_, &codec_, video.img(), video.pts(),
|
|
||||||
video.duration(), VPX_DL_GOOD_QUALITY);
|
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res);
|
|
||||||
StoreFrames(n, outputs, &frame_received);
|
|
||||||
video.Next();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Flush encoder.
|
|
||||||
res = vpx_svc_encode(&svc_, &codec_, NULL, 0, video.duration(),
|
|
||||||
VPX_DL_GOOD_QUALITY);
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
StoreFrames(n, outputs, &frame_received);
|
|
||||||
|
|
||||||
EXPECT_EQ(frame_received, static_cast<size_t>(n));
|
|
||||||
|
|
||||||
ReleaseEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecodeNFrames(const struct vpx_fixed_buf *const inputs, const int n) {
|
|
||||||
int decoded_frames = 0;
|
|
||||||
int received_frames = 0;
|
|
||||||
|
|
||||||
ASSERT_TRUE(inputs != NULL);
|
|
||||||
ASSERT_GT(n, 0);
|
|
||||||
|
|
||||||
for (int i = 0; i < n; ++i) {
|
|
||||||
ASSERT_TRUE(inputs[i].buf != NULL);
|
|
||||||
ASSERT_GT(inputs[i].sz, 0U);
|
|
||||||
const vpx_codec_err_t res_dec = decoder_->DecodeFrame(
|
|
||||||
static_cast<const uint8_t *>(inputs[i].buf), inputs[i].sz);
|
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res_dec) << decoder_->DecodeError();
|
|
||||||
++decoded_frames;
|
|
||||||
|
|
||||||
DxDataIterator dec_iter = decoder_->GetDxData();
|
|
||||||
while (dec_iter.Next() != NULL) {
|
|
||||||
++received_frames;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
EXPECT_EQ(decoded_frames, n);
|
|
||||||
EXPECT_EQ(received_frames, n);
|
|
||||||
}
|
|
||||||
|
|
||||||
void DropEnhancementLayers(struct vpx_fixed_buf *const inputs,
|
|
||||||
const int num_super_frames,
|
|
||||||
const int remained_spatial_layers) {
|
|
||||||
ASSERT_TRUE(inputs != NULL);
|
|
||||||
ASSERT_GT(num_super_frames, 0);
|
|
||||||
ASSERT_GT(remained_spatial_layers, 0);
|
|
||||||
|
|
||||||
for (int i = 0; i < num_super_frames; ++i) {
|
|
||||||
uint32_t frame_sizes[8] = { 0 };
|
|
||||||
int frame_count = 0;
|
|
||||||
int frames_found = 0;
|
|
||||||
int frame;
|
|
||||||
ASSERT_TRUE(inputs[i].buf != NULL);
|
|
||||||
ASSERT_GT(inputs[i].sz, 0U);
|
|
||||||
|
|
||||||
vpx_codec_err_t res = vp9_parse_superframe_index(
|
|
||||||
static_cast<const uint8_t *>(inputs[i].buf), inputs[i].sz,
|
|
||||||
frame_sizes, &frame_count, NULL, NULL);
|
|
||||||
ASSERT_EQ(VPX_CODEC_OK, res);
|
|
||||||
|
|
||||||
if (frame_count == 0) {
|
|
||||||
// There's no super frame but only a single frame.
|
|
||||||
ASSERT_EQ(1, remained_spatial_layers);
|
|
||||||
} else {
|
|
||||||
// Found a super frame.
|
|
||||||
uint8_t *frame_data = static_cast<uint8_t *>(inputs[i].buf);
|
|
||||||
uint8_t *frame_start = frame_data;
|
|
||||||
for (frame = 0; frame < frame_count; ++frame) {
|
|
||||||
// Looking for a visible frame.
|
|
||||||
if (frame_data[0] & 0x02) {
|
|
||||||
++frames_found;
|
|
||||||
if (frames_found == remained_spatial_layers) break;
|
|
||||||
}
|
|
||||||
frame_data += frame_sizes[frame];
|
|
||||||
}
|
|
||||||
ASSERT_LT(frame, frame_count)
|
|
||||||
<< "Couldn't find a visible frame. "
|
|
||||||
<< "remained_spatial_layers: " << remained_spatial_layers
|
|
||||||
<< " super_frame: " << i;
|
|
||||||
if (frame == frame_count - 1) continue;
|
|
||||||
|
|
||||||
frame_data += frame_sizes[frame];
|
|
||||||
|
|
||||||
// We need to add one more frame for multiple frame contexts.
|
|
||||||
uint8_t marker =
|
|
||||||
static_cast<const uint8_t *>(inputs[i].buf)[inputs[i].sz - 1];
|
|
||||||
const uint32_t mag = ((marker >> 3) & 0x3) + 1;
|
|
||||||
const size_t index_sz = 2 + mag * frame_count;
|
|
||||||
const size_t new_index_sz = 2 + mag * (frame + 1);
|
|
||||||
marker &= 0x0f8;
|
|
||||||
marker |= frame;
|
|
||||||
|
|
||||||
// Copy existing frame sizes.
|
|
||||||
memmove(frame_data + 1, frame_start + inputs[i].sz - index_sz + 1,
|
|
||||||
new_index_sz - 2);
|
|
||||||
// New marker.
|
|
||||||
frame_data[0] = marker;
|
|
||||||
frame_data += (mag * (frame + 1) + 1);
|
|
||||||
|
|
||||||
*frame_data++ = marker;
|
|
||||||
inputs[i].sz = frame_data - frame_start;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void FreeBitstreamBuffers(struct vpx_fixed_buf *const inputs, const int n) {
|
|
||||||
ASSERT_TRUE(inputs != NULL);
|
|
||||||
ASSERT_GT(n, 0);
|
|
||||||
|
|
||||||
for (int i = 0; i < n; ++i) {
|
|
||||||
free(inputs[i].buf);
|
|
||||||
inputs[i].buf = NULL;
|
|
||||||
inputs[i].sz = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
SvcContext svc_;
|
|
||||||
vpx_codec_ctx_t codec_;
|
|
||||||
struct vpx_codec_enc_cfg codec_enc_;
|
|
||||||
vpx_codec_iface_t *codec_iface_;
|
|
||||||
std::string test_file_name_;
|
|
||||||
bool codec_initialized_;
|
|
||||||
Decoder *decoder_;
|
|
||||||
int tile_columns_;
|
|
||||||
int tile_rows_;
|
|
||||||
};
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SvcInit) {
|
|
||||||
// test missing parameters
|
|
||||||
vpx_codec_err_t res = vpx_svc_init(NULL, &codec_, codec_iface_, &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
res = vpx_svc_init(&svc_, NULL, codec_iface_, &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, NULL, &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, codec_iface_, NULL);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
svc_.spatial_layers = 6; // too many layers
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, codec_iface_, &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
svc_.spatial_layers = 0; // use default layers
|
|
||||||
InitializeEncoder();
|
|
||||||
EXPECT_EQ(VPX_SS_DEFAULT_LAYERS, svc_.spatial_layers);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, InitTwoLayers) {
|
|
||||||
svc_.spatial_layers = 2;
|
|
||||||
InitializeEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, InvalidOptions) {
|
|
||||||
vpx_codec_err_t res = vpx_svc_set_options(&svc_, NULL);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "not-an-option=1");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SetLayersOption) {
|
|
||||||
vpx_codec_err_t res = vpx_svc_set_options(&svc_, "spatial-layers=3");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
InitializeEncoder();
|
|
||||||
EXPECT_EQ(3, svc_.spatial_layers);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SetMultipleOptions) {
|
|
||||||
vpx_codec_err_t res =
|
|
||||||
vpx_svc_set_options(&svc_, "spatial-layers=2 scale-factors=1/3,2/3");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
InitializeEncoder();
|
|
||||||
EXPECT_EQ(2, svc_.spatial_layers);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SetScaleFactorsOption) {
|
|
||||||
svc_.spatial_layers = 2;
|
|
||||||
vpx_codec_err_t res =
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=not-scale-factors");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "scale-factors=1/3, 3*3");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "scale-factors=1/3");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "scale-factors=1/3,2/3");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
InitializeEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SetQuantizersOption) {
|
|
||||||
svc_.spatial_layers = 2;
|
|
||||||
vpx_codec_err_t res = vpx_svc_set_options(&svc_, "max-quantizers=nothing");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "min-quantizers=nothing");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "max-quantizers=40");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "min-quantizers=40");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "max-quantizers=30,30 min-quantizers=40,40");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "max-quantizers=40,40 min-quantizers=30,30");
|
|
||||||
InitializeEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SetAutoAltRefOption) {
|
|
||||||
svc_.spatial_layers = 5;
|
|
||||||
vpx_codec_err_t res = vpx_svc_set_options(&svc_, "auto-alt-refs=none");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
res = vpx_svc_set_options(&svc_, "auto-alt-refs=1,1,1,1,0");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=0,1,1,1,0");
|
|
||||||
InitializeEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Test that decoder can handle an SVC frame as the first frame in a sequence.
|
|
||||||
TEST_F(SvcTest, OnePassEncodeOneFrame) {
|
|
||||||
codec_enc_.g_pass = VPX_RC_ONE_PASS;
|
|
||||||
vpx_fixed_buf output = { 0 };
|
|
||||||
Pass2EncodeNFrames(NULL, 1, 2, &output);
|
|
||||||
DecodeNFrames(&output, 1);
|
|
||||||
FreeBitstreamBuffers(&output, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, OnePassEncodeThreeFrames) {
|
|
||||||
codec_enc_.g_pass = VPX_RC_ONE_PASS;
|
|
||||||
codec_enc_.g_lag_in_frames = 0;
|
|
||||||
vpx_fixed_buf outputs[3];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(NULL, 3, 2, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 3);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 3);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode10Frames) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
Pass1EncodeNFrames(10, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 2, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode20FramesWithAltRef) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
Pass1EncodeNFrames(20, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1,1");
|
|
||||||
vpx_fixed_buf outputs[20];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 20, 2, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 20);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 20);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2SpatialLayersDecodeBaseLayerOnly) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
Pass1EncodeNFrames(10, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1,1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 2, &outputs[0]);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 1);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode5SpatialLayersDecode54321Layers) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
Pass1EncodeNFrames(10, 5, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=0,1,1,1,0");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 5, &outputs[0]);
|
|
||||||
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 4);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 3);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 2);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 1);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2SNRLayers) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1,1/1");
|
|
||||||
Pass1EncodeNFrames(20, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1,1 scale-factors=1/1,1/1");
|
|
||||||
vpx_fixed_buf outputs[20];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 20, 2, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 20);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 20);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode3SNRLayersDecode321Layers) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1,1/1,1/1");
|
|
||||||
Pass1EncodeNFrames(20, 3, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1,1,1 scale-factors=1/1,1/1,1/1");
|
|
||||||
vpx_fixed_buf outputs[20];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 20, 3, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 20);
|
|
||||||
DropEnhancementLayers(&outputs[0], 20, 2);
|
|
||||||
DecodeNFrames(&outputs[0], 20);
|
|
||||||
DropEnhancementLayers(&outputs[0], 20, 1);
|
|
||||||
DecodeNFrames(&outputs[0], 20);
|
|
||||||
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 20);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, SetMultipleFrameContextsOption) {
|
|
||||||
svc_.spatial_layers = 5;
|
|
||||||
vpx_codec_err_t res = vpx_svc_set_options(&svc_, "multi-frame-contexts=1");
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res);
|
|
||||||
res = vpx_svc_init(&svc_, &codec_, vpx_codec_vp9_cx(), &codec_enc_);
|
|
||||||
EXPECT_EQ(VPX_CODEC_INVALID_PARAM, res);
|
|
||||||
|
|
||||||
svc_.spatial_layers = 2;
|
|
||||||
res = vpx_svc_set_options(&svc_, "multi-frame-contexts=1");
|
|
||||||
InitializeEncoder();
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2SpatialLayersWithMultipleFrameContexts) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
Pass1EncodeNFrames(10, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1,1 multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 2, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest,
|
|
||||||
TwoPassEncode2SpatialLayersWithMultipleFrameContextsDecodeBaselayer) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
Pass1EncodeNFrames(10, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1,1 multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 2, &outputs[0]);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 1);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2SNRLayersWithMultipleFrameContexts) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1,1/1");
|
|
||||||
Pass1EncodeNFrames(10, 2, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
vpx_svc_set_options(&svc_,
|
|
||||||
"auto-alt-refs=1,1 scale-factors=1/1,1/1 "
|
|
||||||
"multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 2, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest,
|
|
||||||
TwoPassEncode3SNRLayersWithMultipleFrameContextsDecode321Layer) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1,1/1,1/1");
|
|
||||||
Pass1EncodeNFrames(10, 3, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
vpx_svc_set_options(&svc_,
|
|
||||||
"auto-alt-refs=1,1,1 scale-factors=1/1,1/1,1/1 "
|
|
||||||
"multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 3, &outputs[0]);
|
|
||||||
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 2);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
DropEnhancementLayers(&outputs[0], 10, 1);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2TemporalLayers) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1");
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
Pass1EncodeNFrames(10, 1, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1 scale-factors=1/1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 1, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2TemporalLayersWithMultipleFrameContexts) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1");
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
Pass1EncodeNFrames(10, 1, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
vpx_svc_set_options(&svc_,
|
|
||||||
"auto-alt-refs=1 scale-factors=1/1 "
|
|
||||||
"multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 1, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2TemporalLayersDecodeBaseLayer) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1");
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
Pass1EncodeNFrames(10, 1, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1 scale-factors=1/1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 1, &outputs[0]);
|
|
||||||
|
|
||||||
vpx_fixed_buf base_layer[5];
|
|
||||||
for (int i = 0; i < 5; ++i) base_layer[i] = outputs[i * 2];
|
|
||||||
|
|
||||||
DecodeNFrames(&base_layer[0], 5);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest,
|
|
||||||
TwoPassEncode2TemporalLayersWithMultipleFrameContextsDecodeBaseLayer) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1");
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
Pass1EncodeNFrames(10, 1, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
vpx_svc_set_options(&svc_,
|
|
||||||
"auto-alt-refs=1 scale-factors=1/1 "
|
|
||||||
"multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 1, &outputs[0]);
|
|
||||||
|
|
||||||
vpx_fixed_buf base_layer[5];
|
|
||||||
for (int i = 0; i < 5; ++i) base_layer[i] = outputs[i * 2];
|
|
||||||
|
|
||||||
DecodeNFrames(&base_layer[0], 5);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2TemporalLayersWithTiles) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1");
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
Pass1EncodeNFrames(10, 1, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
vpx_svc_set_options(&svc_, "auto-alt-refs=1 scale-factors=1/1");
|
|
||||||
codec_enc_.g_w = 704;
|
|
||||||
codec_enc_.g_h = 144;
|
|
||||||
tile_columns_ = 1;
|
|
||||||
tile_rows_ = 1;
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 1, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_F(SvcTest, TwoPassEncode2TemporalLayersWithMultipleFrameContextsAndTiles) {
|
|
||||||
// First pass encode
|
|
||||||
std::string stats_buf;
|
|
||||||
vpx_svc_set_options(&svc_, "scale-factors=1/1");
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
Pass1EncodeNFrames(10, 1, &stats_buf);
|
|
||||||
|
|
||||||
// Second pass encode
|
|
||||||
codec_enc_.g_pass = VPX_RC_LAST_PASS;
|
|
||||||
svc_.temporal_layers = 2;
|
|
||||||
codec_enc_.g_error_resilient = 0;
|
|
||||||
codec_enc_.g_w = 704;
|
|
||||||
codec_enc_.g_h = 144;
|
|
||||||
tile_columns_ = 1;
|
|
||||||
tile_rows_ = 1;
|
|
||||||
vpx_svc_set_options(&svc_,
|
|
||||||
"auto-alt-refs=1 scale-factors=1/1 "
|
|
||||||
"multi-frame-contexts=1");
|
|
||||||
vpx_fixed_buf outputs[10];
|
|
||||||
memset(&outputs[0], 0, sizeof(outputs));
|
|
||||||
Pass2EncodeNFrames(&stats_buf, 10, 1, &outputs[0]);
|
|
||||||
DecodeNFrames(&outputs[0], 10);
|
|
||||||
FreeBitstreamBuffers(&outputs[0], 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
|
277
test/temporal_filter_test.cc
Normal file
277
test/temporal_filter_test.cc
Normal file
@ -0,0 +1,277 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <limits>
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vp9_rtcd.h"
|
||||||
|
#include "test/acm_random.h"
|
||||||
|
#include "test/buffer.h"
|
||||||
|
#include "test/register_state_check.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
using ::libvpx_test::ACMRandom;
|
||||||
|
using ::libvpx_test::Buffer;
|
||||||
|
|
||||||
|
typedef void (*TemporalFilterFunc)(const uint8_t *a, unsigned int stride,
|
||||||
|
const uint8_t *b, unsigned int w,
|
||||||
|
unsigned int h, int filter_strength,
|
||||||
|
int filter_weight, unsigned int *accumulator,
|
||||||
|
uint16_t *count);
|
||||||
|
|
||||||
|
// Calculate the difference between 'a' and 'b', sum in blocks of 9, and apply
|
||||||
|
// filter based on strength and weight. Store the resulting filter amount in
|
||||||
|
// 'count' and apply it to 'b' and store it in 'accumulator'.
|
||||||
|
void reference_filter(const Buffer<uint8_t> &a, const Buffer<uint8_t> &b, int w,
|
||||||
|
int h, int filter_strength, int filter_weight,
|
||||||
|
Buffer<unsigned int> *accumulator,
|
||||||
|
Buffer<uint16_t> *count) {
|
||||||
|
Buffer<int> diff_sq = Buffer<int>(w, h, 0);
|
||||||
|
ASSERT_TRUE(diff_sq.Init());
|
||||||
|
diff_sq.Set(0);
|
||||||
|
|
||||||
|
int rounding = 0;
|
||||||
|
if (filter_strength > 0) {
|
||||||
|
rounding = 1 << (filter_strength - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calculate all the differences. Avoids re-calculating a bunch of extra
|
||||||
|
// values.
|
||||||
|
for (int height = 0; height < h; ++height) {
|
||||||
|
for (int width = 0; width < w; ++width) {
|
||||||
|
int diff = a.TopLeftPixel()[height * a.stride() + width] -
|
||||||
|
b.TopLeftPixel()[height * b.stride() + width];
|
||||||
|
diff_sq.TopLeftPixel()[height * diff_sq.stride() + width] = diff * diff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// For any given point, sum the neighboring values and calculate the
|
||||||
|
// modifier.
|
||||||
|
for (int height = 0; height < h; ++height) {
|
||||||
|
for (int width = 0; width < w; ++width) {
|
||||||
|
// Determine how many values are being summed.
|
||||||
|
int summed_values = 9;
|
||||||
|
|
||||||
|
if (height == 0 || height == (h - 1)) {
|
||||||
|
summed_values -= 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (width == 0 || width == (w - 1)) {
|
||||||
|
if (summed_values == 6) { // corner
|
||||||
|
summed_values -= 2;
|
||||||
|
} else {
|
||||||
|
summed_values -= 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Sum the diff_sq of the surrounding values.
|
||||||
|
int sum = 0;
|
||||||
|
for (int idy = -1; idy <= 1; ++idy) {
|
||||||
|
for (int idx = -1; idx <= 1; ++idx) {
|
||||||
|
const int y = height + idy;
|
||||||
|
const int x = width + idx;
|
||||||
|
|
||||||
|
// If inside the border.
|
||||||
|
if (y >= 0 && y < h && x >= 0 && x < w) {
|
||||||
|
sum += diff_sq.TopLeftPixel()[y * diff_sq.stride() + x];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
sum *= 3;
|
||||||
|
sum /= summed_values;
|
||||||
|
sum += rounding;
|
||||||
|
sum >>= filter_strength;
|
||||||
|
|
||||||
|
// Clamp the value and invert it.
|
||||||
|
if (sum > 16) sum = 16;
|
||||||
|
sum = 16 - sum;
|
||||||
|
|
||||||
|
sum *= filter_weight;
|
||||||
|
|
||||||
|
count->TopLeftPixel()[height * count->stride() + width] += sum;
|
||||||
|
accumulator->TopLeftPixel()[height * accumulator->stride() + width] +=
|
||||||
|
sum * b.TopLeftPixel()[height * b.stride() + width];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class TemporalFilterTest : public ::testing::TestWithParam<TemporalFilterFunc> {
|
||||||
|
public:
|
||||||
|
virtual void SetUp() {
|
||||||
|
filter_func_ = GetParam();
|
||||||
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
TemporalFilterFunc filter_func_;
|
||||||
|
ACMRandom rnd_;
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(TemporalFilterTest, SizeCombinations) {
|
||||||
|
// Depending on subsampling this function may be called with values of 8 or 16
|
||||||
|
// for width and height, in any combination.
|
||||||
|
Buffer<uint8_t> a = Buffer<uint8_t>(16, 16, 8);
|
||||||
|
ASSERT_TRUE(a.Init());
|
||||||
|
|
||||||
|
const int filter_weight = 2;
|
||||||
|
const int filter_strength = 6;
|
||||||
|
|
||||||
|
for (int width = 8; width <= 16; width += 8) {
|
||||||
|
for (int height = 8; height <= 16; height += 8) {
|
||||||
|
// The second buffer must not have any border.
|
||||||
|
Buffer<uint8_t> b = Buffer<uint8_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(b.Init());
|
||||||
|
Buffer<unsigned int> accum_ref = Buffer<unsigned int>(width, height, 0);
|
||||||
|
ASSERT_TRUE(accum_ref.Init());
|
||||||
|
Buffer<unsigned int> accum_chk = Buffer<unsigned int>(width, height, 0);
|
||||||
|
ASSERT_TRUE(accum_chk.Init());
|
||||||
|
Buffer<uint16_t> count_ref = Buffer<uint16_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(count_ref.Init());
|
||||||
|
Buffer<uint16_t> count_chk = Buffer<uint16_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(count_chk.Init());
|
||||||
|
|
||||||
|
// The difference between the buffers must be small to pass the threshold
|
||||||
|
// to apply the filter.
|
||||||
|
a.Set(&rnd_, 0, 7);
|
||||||
|
b.Set(&rnd_, 0, 7);
|
||||||
|
|
||||||
|
accum_ref.Set(rnd_.Rand8());
|
||||||
|
accum_chk.CopyFrom(accum_ref);
|
||||||
|
count_ref.Set(rnd_.Rand8());
|
||||||
|
count_chk.CopyFrom(count_ref);
|
||||||
|
reference_filter(a, b, width, height, filter_strength, filter_weight,
|
||||||
|
&accum_ref, &count_ref);
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
filter_func_(a.TopLeftPixel(), a.stride(), b.TopLeftPixel(), width,
|
||||||
|
height, filter_strength, filter_weight,
|
||||||
|
accum_chk.TopLeftPixel(), count_chk.TopLeftPixel()));
|
||||||
|
EXPECT_TRUE(accum_chk.CheckValues(accum_ref));
|
||||||
|
EXPECT_TRUE(count_chk.CheckValues(count_ref));
|
||||||
|
if (HasFailure()) {
|
||||||
|
printf("Width: %d Height: %d\n", width, height);
|
||||||
|
count_chk.PrintDifference(count_ref);
|
||||||
|
accum_chk.PrintDifference(accum_ref);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(TemporalFilterTest, CompareReferenceRandom) {
|
||||||
|
for (int width = 8; width <= 16; width += 8) {
|
||||||
|
for (int height = 8; height <= 16; height += 8) {
|
||||||
|
Buffer<uint8_t> a = Buffer<uint8_t>(width, height, 8);
|
||||||
|
ASSERT_TRUE(a.Init());
|
||||||
|
// The second buffer must not have any border.
|
||||||
|
Buffer<uint8_t> b = Buffer<uint8_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(b.Init());
|
||||||
|
Buffer<unsigned int> accum_ref = Buffer<unsigned int>(width, height, 0);
|
||||||
|
ASSERT_TRUE(accum_ref.Init());
|
||||||
|
Buffer<unsigned int> accum_chk = Buffer<unsigned int>(width, height, 0);
|
||||||
|
ASSERT_TRUE(accum_chk.Init());
|
||||||
|
Buffer<uint16_t> count_ref = Buffer<uint16_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(count_ref.Init());
|
||||||
|
Buffer<uint16_t> count_chk = Buffer<uint16_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(count_chk.Init());
|
||||||
|
|
||||||
|
for (int filter_strength = 0; filter_strength <= 6; ++filter_strength) {
|
||||||
|
for (int filter_weight = 0; filter_weight <= 2; ++filter_weight) {
|
||||||
|
for (int repeat = 0; repeat < 100; ++repeat) {
|
||||||
|
if (repeat < 50) {
|
||||||
|
a.Set(&rnd_, 0, 7);
|
||||||
|
b.Set(&rnd_, 0, 7);
|
||||||
|
} else {
|
||||||
|
// Check large (but close) values as well.
|
||||||
|
a.Set(&rnd_, std::numeric_limits<uint8_t>::max() - 7,
|
||||||
|
std::numeric_limits<uint8_t>::max());
|
||||||
|
b.Set(&rnd_, std::numeric_limits<uint8_t>::max() - 7,
|
||||||
|
std::numeric_limits<uint8_t>::max());
|
||||||
|
}
|
||||||
|
|
||||||
|
accum_ref.Set(rnd_.Rand8());
|
||||||
|
accum_chk.CopyFrom(accum_ref);
|
||||||
|
count_ref.Set(rnd_.Rand8());
|
||||||
|
count_chk.CopyFrom(count_ref);
|
||||||
|
reference_filter(a, b, width, height, filter_strength,
|
||||||
|
filter_weight, &accum_ref, &count_ref);
|
||||||
|
ASM_REGISTER_STATE_CHECK(filter_func_(
|
||||||
|
a.TopLeftPixel(), a.stride(), b.TopLeftPixel(), width, height,
|
||||||
|
filter_strength, filter_weight, accum_chk.TopLeftPixel(),
|
||||||
|
count_chk.TopLeftPixel()));
|
||||||
|
EXPECT_TRUE(accum_chk.CheckValues(accum_ref));
|
||||||
|
EXPECT_TRUE(count_chk.CheckValues(count_ref));
|
||||||
|
if (HasFailure()) {
|
||||||
|
printf("Weight: %d Strength: %d\n", filter_weight,
|
||||||
|
filter_strength);
|
||||||
|
count_chk.PrintDifference(count_ref);
|
||||||
|
accum_chk.PrintDifference(accum_ref);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(TemporalFilterTest, DISABLED_Speed) {
|
||||||
|
Buffer<uint8_t> a = Buffer<uint8_t>(16, 16, 8);
|
||||||
|
ASSERT_TRUE(a.Init());
|
||||||
|
|
||||||
|
const int filter_weight = 2;
|
||||||
|
const int filter_strength = 6;
|
||||||
|
|
||||||
|
for (int width = 8; width <= 16; width += 8) {
|
||||||
|
for (int height = 8; height <= 16; height += 8) {
|
||||||
|
// The second buffer must not have any border.
|
||||||
|
Buffer<uint8_t> b = Buffer<uint8_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(b.Init());
|
||||||
|
Buffer<unsigned int> accum_ref = Buffer<unsigned int>(width, height, 0);
|
||||||
|
ASSERT_TRUE(accum_ref.Init());
|
||||||
|
Buffer<unsigned int> accum_chk = Buffer<unsigned int>(width, height, 0);
|
||||||
|
ASSERT_TRUE(accum_chk.Init());
|
||||||
|
Buffer<uint16_t> count_ref = Buffer<uint16_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(count_ref.Init());
|
||||||
|
Buffer<uint16_t> count_chk = Buffer<uint16_t>(width, height, 0);
|
||||||
|
ASSERT_TRUE(count_chk.Init());
|
||||||
|
|
||||||
|
a.Set(&rnd_, 0, 7);
|
||||||
|
b.Set(&rnd_, 0, 7);
|
||||||
|
|
||||||
|
accum_chk.Set(0);
|
||||||
|
count_chk.Set(0);
|
||||||
|
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int i = 0; i < 10000; ++i) {
|
||||||
|
filter_func_(a.TopLeftPixel(), a.stride(), b.TopLeftPixel(), width,
|
||||||
|
height, filter_strength, filter_weight,
|
||||||
|
accum_chk.TopLeftPixel(), count_chk.TopLeftPixel());
|
||||||
|
}
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
|
printf("Temporal filter %dx%d time: %5d us\n", width, height,
|
||||||
|
elapsed_time);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(C, TemporalFilterTest,
|
||||||
|
::testing::Values(&vp9_temporal_filter_apply_c));
|
||||||
|
|
||||||
|
#if HAVE_SSE4_1
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE4_1, TemporalFilterTest,
|
||||||
|
::testing::Values(&vp9_temporal_filter_apply_sse4_1));
|
||||||
|
#endif // HAVE_SSE4_1
|
||||||
|
} // namespace
|
@ -20,8 +20,10 @@ LIBVPX_TEST_DATA-$(CONFIG_ENCODERS) += park_joy_90p_8_440.yuv
|
|||||||
|
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += desktop_credits.y4m
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += desktop_credits.y4m
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += niklas_1280_720_30.y4m
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += niklas_1280_720_30.y4m
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += noisy_clip_640_360.y4m
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += rush_hour_444.y4m
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += rush_hour_444.y4m
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += screendata.y4m
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += screendata.y4m
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += niklas_640_480_30.yuv
|
||||||
|
|
||||||
# Test vectors
|
# Test vectors
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += vp80-00-comprehensive-001.ivf
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += vp80-00-comprehensive-001.ivf
|
||||||
@ -730,6 +732,10 @@ LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp93-2-20-12bit-yuv444.webm.md5
|
|||||||
endif # CONFIG_VP9_HIGHBITDEPTH
|
endif # CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
# Invalid files for testing libvpx error checking.
|
# Invalid files for testing libvpx error checking.
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-bug-1443.ivf
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-bug-1443.ivf.res
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-token-partition.ivf
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-token-partition.ivf.res
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-vp80-00-comprehensive-018.ivf.2kf_0x6.ivf
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-vp80-00-comprehensive-018.ivf.2kf_0x6.ivf
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-vp80-00-comprehensive-018.ivf.2kf_0x6.ivf.res
|
LIBVPX_TEST_DATA-$(CONFIG_VP8_DECODER) += invalid-vp80-00-comprehensive-018.ivf.2kf_0x6.ivf.res
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-01-v3.webm
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-01-v3.webm
|
||||||
@ -770,6 +776,8 @@ LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s367
|
|||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s3676_r01-05_b6-.ivf.res
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s3676_r01-05_b6-.ivf.res
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s73804_r01-05_b6-.ivf
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s73804_r01-05_b6-.ivf
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s73804_r01-05_b6-.ivf.res
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-12-droppable_1.ivf.s73804_r01-05_b6-.ivf.res
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-21-resize_inter_320x180_5_3-4.webm.ivf.s45551_r01-05_b6-.ivf
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-21-resize_inter_320x180_5_3-4.webm.ivf.s45551_r01-05_b6-.ivf.res
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp91-2-mixedrefcsp-444to420.ivf
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp91-2-mixedrefcsp-444to420.ivf
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp91-2-mixedrefcsp-444to420.ivf.res
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp91-2-mixedrefcsp-444to420.ivf.res
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-07-frame_parallel-1.webm
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-07-frame_parallel-1.webm
|
||||||
@ -777,6 +785,8 @@ LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-07-frame_parallel-2.web
|
|||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-07-frame_parallel-3.webm
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-vp90-2-07-frame_parallel-3.webm
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-crbug-629481.webm
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-crbug-629481.webm
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-crbug-629481.webm.res
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-crbug-629481.webm.res
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-crbug-667044.webm
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += invalid-crbug-667044.webm.res
|
||||||
|
|
||||||
ifeq ($(CONFIG_DECODE_PERF_TESTS),yes)
|
ifeq ($(CONFIG_DECODE_PERF_TESTS),yes)
|
||||||
# Encode / Decode test
|
# Encode / Decode test
|
||||||
@ -811,7 +821,6 @@ LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += kirland_640_480_30.yuv
|
|||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += macmarcomoving_640_480_30.yuv
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += macmarcomoving_640_480_30.yuv
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += macmarcostationary_640_480_30.yuv
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += macmarcostationary_640_480_30.yuv
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += niklas_1280_720_30.yuv
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += niklas_1280_720_30.yuv
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += niklas_640_480_30.yuv
|
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += tacomanarrows_640_480_30.yuv
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += tacomanarrows_640_480_30.yuv
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += tacomasmallcameramovement_640_480_30.yuv
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += tacomasmallcameramovement_640_480_30.yuv
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += thaloundeskmtg_640_480_30.yuv
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER) += thaloundeskmtg_640_480_30.yuv
|
||||||
@ -871,3 +880,5 @@ LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-21-resize_inter_1920x1080_7_3-4
|
|||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-21-resize_inter_1920x1080_7_3-4.webm.md5
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-21-resize_inter_1920x1080_7_3-4.webm.md5
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-22-svc_1280x720_3.ivf
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-22-svc_1280x720_3.ivf
|
||||||
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-22-svc_1280x720_3.ivf.md5
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-22-svc_1280x720_3.ivf.md5
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-22-svc_1280x720_1.webm
|
||||||
|
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-22-svc_1280x720_1.webm.md5
|
||||||
|
@ -6,6 +6,8 @@ b87815bf86020c592ccc7a846ba2e28ec8043902 *hantro_odd.yuv
|
|||||||
456d1493e52d32a5c30edf44a27debc1fa6b253a *invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-.ivf.res
|
456d1493e52d32a5c30edf44a27debc1fa6b253a *invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-.ivf.res
|
||||||
c123d1f9f02fb4143abb5e271916e3a3080de8f6 *invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-z.ivf
|
c123d1f9f02fb4143abb5e271916e3a3080de8f6 *invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-z.ivf
|
||||||
456d1493e52d32a5c30edf44a27debc1fa6b253a *invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-z.ivf.res
|
456d1493e52d32a5c30edf44a27debc1fa6b253a *invalid-vp90-2-00-quantizer-11.webm.ivf.s52984_r01-05_b6-z.ivf.res
|
||||||
|
efafb92b7567bc04c3f1432ea6c268c1c31affd5 *invalid-vp90-2-21-resize_inter_320x180_5_3-4.webm.ivf.s45551_r01-05_b6-.ivf
|
||||||
|
5d9474c0309b7ca09a182d888f73b37a8fe1362c *invalid-vp90-2-21-resize_inter_320x180_5_3-4.webm.ivf.s45551_r01-05_b6-.ivf.res
|
||||||
fe346136b9b8c1e6f6084cc106485706915795e4 *invalid-vp90-01-v3.webm
|
fe346136b9b8c1e6f6084cc106485706915795e4 *invalid-vp90-01-v3.webm
|
||||||
5d9474c0309b7ca09a182d888f73b37a8fe1362c *invalid-vp90-01-v3.webm.res
|
5d9474c0309b7ca09a182d888f73b37a8fe1362c *invalid-vp90-01-v3.webm.res
|
||||||
d78e2fceba5ac942246503ec8366f879c4775ca5 *invalid-vp90-02-v2.webm
|
d78e2fceba5ac942246503ec8366f879c4775ca5 *invalid-vp90-02-v2.webm
|
||||||
@ -14,6 +16,7 @@ df1a1453feb3c00d7d89746c7003b4163523bff3 *invalid-vp90-03-v3.webm
|
|||||||
4935c62becc68c13642a03db1e6d3e2331c1c612 *invalid-vp90-03-v3.webm.res
|
4935c62becc68c13642a03db1e6d3e2331c1c612 *invalid-vp90-03-v3.webm.res
|
||||||
d637297561dd904eb2c97a9015deeb31c4a1e8d2 *invalid-vp90-2-08-tile_1x4_frame_parallel_all_key.webm
|
d637297561dd904eb2c97a9015deeb31c4a1e8d2 *invalid-vp90-2-08-tile_1x4_frame_parallel_all_key.webm
|
||||||
3a204bdbeaa3c6458b77bcebb8366d107267f55d *invalid-vp90-2-08-tile_1x4_frame_parallel_all_key.webm.res
|
3a204bdbeaa3c6458b77bcebb8366d107267f55d *invalid-vp90-2-08-tile_1x4_frame_parallel_all_key.webm.res
|
||||||
|
9aa21d8b2cb9d39abe8a7bb6032dc66955fb4342 *noisy_clip_640_360.y4m
|
||||||
a432f96ff0a787268e2f94a8092ab161a18d1b06 *park_joy_90p_10_420.y4m
|
a432f96ff0a787268e2f94a8092ab161a18d1b06 *park_joy_90p_10_420.y4m
|
||||||
0b194cc312c3a2e84d156a221b0a5eb615dfddc5 *park_joy_90p_10_422.y4m
|
0b194cc312c3a2e84d156a221b0a5eb615dfddc5 *park_joy_90p_10_422.y4m
|
||||||
ff0e0a21dc2adc95b8c1b37902713700655ced17 *park_joy_90p_10_444.y4m
|
ff0e0a21dc2adc95b8c1b37902713700655ced17 *park_joy_90p_10_444.y4m
|
||||||
@ -844,3 +847,12 @@ a000d568431d07379dd5a8ec066061c07e560b47 *invalid-vp90-2-00-quantizer-63.ivf.kf_
|
|||||||
5d9474c0309b7ca09a182d888f73b37a8fe1362c *invalid-crbug-629481.webm.res
|
5d9474c0309b7ca09a182d888f73b37a8fe1362c *invalid-crbug-629481.webm.res
|
||||||
7602e00378161ca36ae93cc6ee12dd30b5ba1e1d *vp90-2-22-svc_1280x720_3.ivf
|
7602e00378161ca36ae93cc6ee12dd30b5ba1e1d *vp90-2-22-svc_1280x720_3.ivf
|
||||||
02e53e3eefbf25ec0929047fe50876acdeb040bd *vp90-2-22-svc_1280x720_3.ivf.md5
|
02e53e3eefbf25ec0929047fe50876acdeb040bd *vp90-2-22-svc_1280x720_3.ivf.md5
|
||||||
|
6fa3d3ac306a3d9ce1d610b78441dc00d2c2d4b9 *tos_vp8.webm
|
||||||
|
e402cbbf9e550ae017a1e9f1f73931c1d18474e8 *invalid-crbug-667044.webm
|
||||||
|
d3964f9dad9f60363c81b688324d95b4ec7c8038 *invalid-crbug-667044.webm.res
|
||||||
|
fd9df7f3f6992af1d7a9dde975c9a0d6f28c053d *invalid-bug-1443.ivf
|
||||||
|
fd3020fa6e9ca5966206738654c97dec313b0a95 *invalid-bug-1443.ivf.res
|
||||||
|
1a0e405606939f2febab1a21b30c37cb8f2c8cb1 *invalid-token-partition.ivf
|
||||||
|
90a8a95e7024f015b87f5483a65036609b3d1b74 *invalid-token-partition.ivf.res
|
||||||
|
17696cd21e875f1d6e5d418cbf89feab02c8850a *vp90-2-22-svc_1280x720_1.webm
|
||||||
|
e2f9e1e47a791b4e939a9bdc50bf7a25b3761f77 *vp90-2-22-svc_1280x720_1.webm.md5
|
||||||
|
21
test/test.mk
21
test/test.mk
@ -1,4 +1,5 @@
|
|||||||
LIBVPX_TEST_SRCS-yes += acm_random.h
|
LIBVPX_TEST_SRCS-yes += acm_random.h
|
||||||
|
LIBVPX_TEST_SRCS-yes += buffer.h
|
||||||
LIBVPX_TEST_SRCS-yes += clear_system_state.h
|
LIBVPX_TEST_SRCS-yes += clear_system_state.h
|
||||||
LIBVPX_TEST_SRCS-yes += codec_factory.h
|
LIBVPX_TEST_SRCS-yes += codec_factory.h
|
||||||
LIBVPX_TEST_SRCS-yes += md5_helper.h
|
LIBVPX_TEST_SRCS-yes += md5_helper.h
|
||||||
@ -21,7 +22,9 @@ LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += ../y4minput.h ../y4minput.c
|
|||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += altref_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += altref_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += aq_segment_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += aq_segment_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += alt_ref_aq_segment_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += alt_ref_aq_segment_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += datarate_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += vp8_datarate_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += vp9_datarate_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += svc_datarate_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += encode_api_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += encode_api_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += error_resilience_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += error_resilience_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += i420_video_source.h
|
LIBVPX_TEST_SRCS-$(CONFIG_ENCODERS) += i420_video_source.h
|
||||||
@ -38,7 +41,6 @@ LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += byte_alignment_test.cc
|
|||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += decode_svc_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += decode_svc_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += external_frame_buffer_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += external_frame_buffer_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += user_priv_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += user_priv_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += vp9_frame_parallel_test.cc
|
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += active_map_refresh_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += active_map_refresh_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += active_map_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += active_map_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += borders_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += borders_test.cc
|
||||||
@ -47,6 +49,7 @@ LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += frame_size_tests.cc
|
|||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_lossless_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_lossless_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_end_to_end_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_end_to_end_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_ethread_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_ethread_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_motion_vector_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += level_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += level_test.cc
|
||||||
|
|
||||||
LIBVPX_TEST_SRCS-yes += decode_test_driver.cc
|
LIBVPX_TEST_SRCS-yes += decode_test_driver.cc
|
||||||
@ -122,6 +125,7 @@ LIBVPX_TEST_SRCS-$(CONFIG_VP8_ENCODER) += vp8_fdct4x4_test.cc
|
|||||||
LIBVPX_TEST_SRCS-yes += idct_test.cc
|
LIBVPX_TEST_SRCS-yes += idct_test.cc
|
||||||
LIBVPX_TEST_SRCS-yes += predict_test.cc
|
LIBVPX_TEST_SRCS-yes += predict_test.cc
|
||||||
LIBVPX_TEST_SRCS-yes += vpx_scale_test.cc
|
LIBVPX_TEST_SRCS-yes += vpx_scale_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-yes += vpx_scale_test.h
|
||||||
|
|
||||||
ifeq ($(CONFIG_VP8_ENCODER)$(CONFIG_TEMPORAL_DENOISING),yesyes)
|
ifeq ($(CONFIG_VP8_ENCODER)$(CONFIG_TEMPORAL_DENOISING),yesyes)
|
||||||
LIBVPX_TEST_SRCS-$(HAVE_SSE2) += vp8_denoiser_sse2_test.cc
|
LIBVPX_TEST_SRCS-$(HAVE_SSE2) += vp8_denoiser_sse2_test.cc
|
||||||
@ -149,25 +153,30 @@ LIBVPX_TEST_SRCS-yes += vp9_intrapred_test.cc
|
|||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += vp9_decrypt_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += vp9_decrypt_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += vp9_thread_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_DECODER) += vp9_thread_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += avg_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += avg_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += comp_avg_pred_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += dct16x16_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += dct16x16_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += dct32x32_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += dct32x32_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += fdct4x4_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += dct_partial_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += dct_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += fdct8x8_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += fdct8x8_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += hadamard_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += hadamard_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += minmax_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += minmax_test.cc
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_scale_test.cc
|
||||||
|
ifneq ($(CONFIG_REALTIME_ONLY),yes)
|
||||||
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += temporal_filter_test.cc
|
||||||
|
endif
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += variance_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += variance_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_error_block_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_block_error_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_quantize_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_quantize_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_subtract_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_subtract_test.cc
|
||||||
|
|
||||||
ifeq ($(CONFIG_VP9_ENCODER),yes)
|
ifeq ($(CONFIG_VP9_ENCODER),yes)
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_SPATIAL_SVC) += svc_test.cc
|
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_INTERNAL_STATS) += blockiness_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_INTERNAL_STATS) += blockiness_test.cc
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_INTERNAL_STATS) += consistency_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_INTERNAL_STATS) += consistency_test.cc
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(CONFIG_VP9_ENCODER)$(CONFIG_VP9_TEMPORAL_DENOISING),yesyes)
|
ifeq ($(CONFIG_VP9_ENCODER)$(CONFIG_VP9_TEMPORAL_DENOISING),yesyes)
|
||||||
LIBVPX_TEST_SRCS-$(HAVE_SSE2) += vp9_denoiser_sse2_test.cc
|
LIBVPX_TEST_SRCS-yes += vp9_denoiser_test.cc
|
||||||
endif
|
endif
|
||||||
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_arf_freq_test.cc
|
LIBVPX_TEST_SRCS-$(CONFIG_VP9_ENCODER) += vp9_arf_freq_test.cc
|
||||||
|
|
||||||
|
@ -270,19 +270,22 @@ INTRA_PRED_TEST(NEON, TestIntraPred4, vpx_dc_predictor_4x4_neon,
|
|||||||
INTRA_PRED_TEST(NEON, TestIntraPred8, vpx_dc_predictor_8x8_neon,
|
INTRA_PRED_TEST(NEON, TestIntraPred8, vpx_dc_predictor_8x8_neon,
|
||||||
vpx_dc_left_predictor_8x8_neon, vpx_dc_top_predictor_8x8_neon,
|
vpx_dc_left_predictor_8x8_neon, vpx_dc_top_predictor_8x8_neon,
|
||||||
vpx_dc_128_predictor_8x8_neon, vpx_v_predictor_8x8_neon,
|
vpx_dc_128_predictor_8x8_neon, vpx_v_predictor_8x8_neon,
|
||||||
vpx_h_predictor_8x8_neon, vpx_d45_predictor_8x8_neon, NULL,
|
vpx_h_predictor_8x8_neon, vpx_d45_predictor_8x8_neon,
|
||||||
NULL, NULL, NULL, NULL, vpx_tm_predictor_8x8_neon)
|
vpx_d135_predictor_8x8_neon, NULL, NULL, NULL, NULL,
|
||||||
|
vpx_tm_predictor_8x8_neon)
|
||||||
INTRA_PRED_TEST(NEON, TestIntraPred16, vpx_dc_predictor_16x16_neon,
|
INTRA_PRED_TEST(NEON, TestIntraPred16, vpx_dc_predictor_16x16_neon,
|
||||||
vpx_dc_left_predictor_16x16_neon,
|
vpx_dc_left_predictor_16x16_neon,
|
||||||
vpx_dc_top_predictor_16x16_neon,
|
vpx_dc_top_predictor_16x16_neon,
|
||||||
vpx_dc_128_predictor_16x16_neon, vpx_v_predictor_16x16_neon,
|
vpx_dc_128_predictor_16x16_neon, vpx_v_predictor_16x16_neon,
|
||||||
vpx_h_predictor_16x16_neon, vpx_d45_predictor_16x16_neon, NULL,
|
vpx_h_predictor_16x16_neon, vpx_d45_predictor_16x16_neon,
|
||||||
NULL, NULL, NULL, NULL, vpx_tm_predictor_16x16_neon)
|
vpx_d135_predictor_16x16_neon, NULL, NULL, NULL, NULL,
|
||||||
|
vpx_tm_predictor_16x16_neon)
|
||||||
INTRA_PRED_TEST(NEON, TestIntraPred32, vpx_dc_predictor_32x32_neon,
|
INTRA_PRED_TEST(NEON, TestIntraPred32, vpx_dc_predictor_32x32_neon,
|
||||||
vpx_dc_left_predictor_32x32_neon,
|
vpx_dc_left_predictor_32x32_neon,
|
||||||
vpx_dc_top_predictor_32x32_neon,
|
vpx_dc_top_predictor_32x32_neon,
|
||||||
vpx_dc_128_predictor_32x32_neon, vpx_v_predictor_32x32_neon,
|
vpx_dc_128_predictor_32x32_neon, vpx_v_predictor_32x32_neon,
|
||||||
vpx_h_predictor_32x32_neon, NULL, NULL, NULL, NULL, NULL, NULL,
|
vpx_h_predictor_32x32_neon, vpx_d45_predictor_32x32_neon,
|
||||||
|
vpx_d135_predictor_32x32_neon, NULL, NULL, NULL, NULL,
|
||||||
vpx_tm_predictor_32x32_neon)
|
vpx_tm_predictor_32x32_neon)
|
||||||
#endif // HAVE_NEON
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
@ -309,6 +312,31 @@ INTRA_PRED_TEST(MSA, TestIntraPred32, vpx_dc_predictor_32x32_msa,
|
|||||||
vpx_tm_predictor_32x32_msa)
|
vpx_tm_predictor_32x32_msa)
|
||||||
#endif // HAVE_MSA
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
|
#if HAVE_VSX
|
||||||
|
INTRA_PRED_TEST(VSX, TestIntraPred4, NULL, NULL, NULL, NULL, NULL,
|
||||||
|
vpx_h_predictor_4x4_vsx, NULL, NULL, NULL, NULL, NULL, NULL,
|
||||||
|
vpx_tm_predictor_4x4_vsx)
|
||||||
|
|
||||||
|
INTRA_PRED_TEST(VSX, TestIntraPred8, vpx_dc_predictor_8x8_vsx, NULL, NULL, NULL,
|
||||||
|
NULL, vpx_h_predictor_8x8_vsx, vpx_d45_predictor_8x8_vsx, NULL,
|
||||||
|
NULL, NULL, NULL, vpx_d63_predictor_8x8_vsx,
|
||||||
|
vpx_tm_predictor_8x8_vsx)
|
||||||
|
|
||||||
|
INTRA_PRED_TEST(VSX, TestIntraPred16, vpx_dc_predictor_16x16_vsx,
|
||||||
|
vpx_dc_left_predictor_16x16_vsx, vpx_dc_top_predictor_16x16_vsx,
|
||||||
|
vpx_dc_128_predictor_16x16_vsx, vpx_v_predictor_16x16_vsx,
|
||||||
|
vpx_h_predictor_16x16_vsx, vpx_d45_predictor_16x16_vsx, NULL,
|
||||||
|
NULL, NULL, NULL, vpx_d63_predictor_16x16_vsx,
|
||||||
|
vpx_tm_predictor_16x16_vsx)
|
||||||
|
|
||||||
|
INTRA_PRED_TEST(VSX, TestIntraPred32, vpx_dc_predictor_32x32_vsx,
|
||||||
|
vpx_dc_left_predictor_32x32_vsx, vpx_dc_top_predictor_32x32_vsx,
|
||||||
|
vpx_dc_128_predictor_32x32_vsx, vpx_v_predictor_32x32_vsx,
|
||||||
|
vpx_h_predictor_32x32_vsx, vpx_d45_predictor_32x32_vsx, NULL,
|
||||||
|
NULL, NULL, NULL, vpx_d63_predictor_32x32_vsx,
|
||||||
|
vpx_tm_predictor_32x32_vsx)
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
@ -452,29 +480,107 @@ HIGHBD_INTRA_PRED_TEST(
|
|||||||
vpx_highbd_d63_predictor_32x32_c, vpx_highbd_tm_predictor_32x32_c)
|
vpx_highbd_d63_predictor_32x32_c, vpx_highbd_tm_predictor_32x32_c)
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred4,
|
HIGHBD_INTRA_PRED_TEST(
|
||||||
vpx_highbd_dc_predictor_4x4_sse2, NULL, NULL, NULL,
|
SSE2, TestHighbdIntraPred4, vpx_highbd_dc_predictor_4x4_sse2,
|
||||||
vpx_highbd_v_predictor_4x4_sse2, NULL, NULL, NULL, NULL,
|
vpx_highbd_dc_left_predictor_4x4_sse2, vpx_highbd_dc_top_predictor_4x4_sse2,
|
||||||
NULL, NULL, NULL, vpx_highbd_tm_predictor_4x4_c)
|
vpx_highbd_dc_128_predictor_4x4_sse2, vpx_highbd_v_predictor_4x4_sse2,
|
||||||
|
vpx_highbd_h_predictor_4x4_sse2, NULL, vpx_highbd_d135_predictor_4x4_sse2,
|
||||||
|
vpx_highbd_d117_predictor_4x4_sse2, vpx_highbd_d153_predictor_4x4_sse2,
|
||||||
|
vpx_highbd_d207_predictor_4x4_sse2, vpx_highbd_d63_predictor_4x4_sse2,
|
||||||
|
vpx_highbd_tm_predictor_4x4_c)
|
||||||
|
|
||||||
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred8,
|
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred8,
|
||||||
vpx_highbd_dc_predictor_8x8_sse2, NULL, NULL, NULL,
|
vpx_highbd_dc_predictor_8x8_sse2,
|
||||||
vpx_highbd_v_predictor_8x8_sse2, NULL, NULL, NULL, NULL,
|
vpx_highbd_dc_left_predictor_8x8_sse2,
|
||||||
NULL, NULL, NULL, vpx_highbd_tm_predictor_8x8_sse2)
|
vpx_highbd_dc_top_predictor_8x8_sse2,
|
||||||
|
vpx_highbd_dc_128_predictor_8x8_sse2,
|
||||||
|
vpx_highbd_v_predictor_8x8_sse2,
|
||||||
|
vpx_highbd_h_predictor_8x8_sse2, NULL, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, vpx_highbd_tm_predictor_8x8_sse2)
|
||||||
|
|
||||||
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred16,
|
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred16,
|
||||||
vpx_highbd_dc_predictor_16x16_sse2, NULL, NULL, NULL,
|
vpx_highbd_dc_predictor_16x16_sse2,
|
||||||
vpx_highbd_v_predictor_16x16_sse2, NULL, NULL, NULL,
|
vpx_highbd_dc_left_predictor_16x16_sse2,
|
||||||
NULL, NULL, NULL, NULL,
|
vpx_highbd_dc_top_predictor_16x16_sse2,
|
||||||
vpx_highbd_tm_predictor_16x16_sse2)
|
vpx_highbd_dc_128_predictor_16x16_sse2,
|
||||||
|
vpx_highbd_v_predictor_16x16_sse2,
|
||||||
|
vpx_highbd_h_predictor_16x16_sse2, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, NULL, vpx_highbd_tm_predictor_16x16_sse2)
|
||||||
|
|
||||||
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred32,
|
HIGHBD_INTRA_PRED_TEST(SSE2, TestHighbdIntraPred32,
|
||||||
vpx_highbd_dc_predictor_32x32_sse2, NULL, NULL, NULL,
|
vpx_highbd_dc_predictor_32x32_sse2,
|
||||||
vpx_highbd_v_predictor_32x32_sse2, NULL, NULL, NULL,
|
vpx_highbd_dc_left_predictor_32x32_sse2,
|
||||||
NULL, NULL, NULL, NULL,
|
vpx_highbd_dc_top_predictor_32x32_sse2,
|
||||||
vpx_highbd_tm_predictor_32x32_sse2)
|
vpx_highbd_dc_128_predictor_32x32_sse2,
|
||||||
|
vpx_highbd_v_predictor_32x32_sse2,
|
||||||
|
vpx_highbd_h_predictor_32x32_sse2, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, NULL, vpx_highbd_tm_predictor_32x32_sse2)
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_SSSE3
|
||||||
|
HIGHBD_INTRA_PRED_TEST(SSSE3, TestHighbdIntraPred4, NULL, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, vpx_highbd_d45_predictor_4x4_ssse3, NULL,
|
||||||
|
NULL, NULL, NULL, NULL, NULL)
|
||||||
|
HIGHBD_INTRA_PRED_TEST(SSSE3, TestHighbdIntraPred8, NULL, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, vpx_highbd_d45_predictor_8x8_ssse3,
|
||||||
|
vpx_highbd_d135_predictor_8x8_ssse3,
|
||||||
|
vpx_highbd_d117_predictor_8x8_ssse3,
|
||||||
|
vpx_highbd_d153_predictor_8x8_ssse3,
|
||||||
|
vpx_highbd_d207_predictor_8x8_ssse3,
|
||||||
|
vpx_highbd_d63_predictor_8x8_ssse3, NULL)
|
||||||
|
HIGHBD_INTRA_PRED_TEST(SSSE3, TestHighbdIntraPred16, NULL, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, vpx_highbd_d45_predictor_16x16_ssse3,
|
||||||
|
vpx_highbd_d135_predictor_16x16_ssse3,
|
||||||
|
vpx_highbd_d117_predictor_16x16_ssse3,
|
||||||
|
vpx_highbd_d153_predictor_16x16_ssse3,
|
||||||
|
vpx_highbd_d207_predictor_16x16_ssse3,
|
||||||
|
vpx_highbd_d63_predictor_16x16_ssse3, NULL)
|
||||||
|
HIGHBD_INTRA_PRED_TEST(SSSE3, TestHighbdIntraPred32, NULL, NULL, NULL, NULL,
|
||||||
|
NULL, NULL, vpx_highbd_d45_predictor_32x32_ssse3,
|
||||||
|
vpx_highbd_d135_predictor_32x32_ssse3,
|
||||||
|
vpx_highbd_d117_predictor_32x32_ssse3,
|
||||||
|
vpx_highbd_d153_predictor_32x32_ssse3,
|
||||||
|
vpx_highbd_d207_predictor_32x32_ssse3,
|
||||||
|
vpx_highbd_d63_predictor_32x32_ssse3, NULL)
|
||||||
|
#endif // HAVE_SSSE3
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
HIGHBD_INTRA_PRED_TEST(
|
||||||
|
NEON, TestHighbdIntraPred4, vpx_highbd_dc_predictor_4x4_neon,
|
||||||
|
vpx_highbd_dc_left_predictor_4x4_neon, vpx_highbd_dc_top_predictor_4x4_neon,
|
||||||
|
vpx_highbd_dc_128_predictor_4x4_neon, vpx_highbd_v_predictor_4x4_neon,
|
||||||
|
vpx_highbd_h_predictor_4x4_neon, vpx_highbd_d45_predictor_4x4_neon,
|
||||||
|
vpx_highbd_d135_predictor_4x4_neon, NULL, NULL, NULL, NULL,
|
||||||
|
vpx_highbd_tm_predictor_4x4_neon)
|
||||||
|
HIGHBD_INTRA_PRED_TEST(
|
||||||
|
NEON, TestHighbdIntraPred8, vpx_highbd_dc_predictor_8x8_neon,
|
||||||
|
vpx_highbd_dc_left_predictor_8x8_neon, vpx_highbd_dc_top_predictor_8x8_neon,
|
||||||
|
vpx_highbd_dc_128_predictor_8x8_neon, vpx_highbd_v_predictor_8x8_neon,
|
||||||
|
vpx_highbd_h_predictor_8x8_neon, vpx_highbd_d45_predictor_8x8_neon,
|
||||||
|
vpx_highbd_d135_predictor_8x8_neon, NULL, NULL, NULL, NULL,
|
||||||
|
vpx_highbd_tm_predictor_8x8_neon)
|
||||||
|
HIGHBD_INTRA_PRED_TEST(NEON, TestHighbdIntraPred16,
|
||||||
|
vpx_highbd_dc_predictor_16x16_neon,
|
||||||
|
vpx_highbd_dc_left_predictor_16x16_neon,
|
||||||
|
vpx_highbd_dc_top_predictor_16x16_neon,
|
||||||
|
vpx_highbd_dc_128_predictor_16x16_neon,
|
||||||
|
vpx_highbd_v_predictor_16x16_neon,
|
||||||
|
vpx_highbd_h_predictor_16x16_neon,
|
||||||
|
vpx_highbd_d45_predictor_16x16_neon,
|
||||||
|
vpx_highbd_d135_predictor_16x16_neon, NULL, NULL, NULL,
|
||||||
|
NULL, vpx_highbd_tm_predictor_16x16_neon)
|
||||||
|
HIGHBD_INTRA_PRED_TEST(NEON, TestHighbdIntraPred32,
|
||||||
|
vpx_highbd_dc_predictor_32x32_neon,
|
||||||
|
vpx_highbd_dc_left_predictor_32x32_neon,
|
||||||
|
vpx_highbd_dc_top_predictor_32x32_neon,
|
||||||
|
vpx_highbd_dc_128_predictor_32x32_neon,
|
||||||
|
vpx_highbd_v_predictor_32x32_neon,
|
||||||
|
vpx_highbd_h_predictor_32x32_neon,
|
||||||
|
vpx_highbd_d45_predictor_32x32_neon,
|
||||||
|
vpx_highbd_d135_predictor_32x32_neon, NULL, NULL, NULL,
|
||||||
|
NULL, vpx_highbd_tm_predictor_32x32_neon)
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
#include "test/test_libvpx.cc"
|
#include "test/test_libvpx.cc"
|
||||||
|
@ -53,12 +53,14 @@ int main(int argc, char **argv) {
|
|||||||
}
|
}
|
||||||
if (!(simd_caps & HAS_AVX)) append_negative_gtest_filter(":AVX.*:AVX/*");
|
if (!(simd_caps & HAS_AVX)) append_negative_gtest_filter(":AVX.*:AVX/*");
|
||||||
if (!(simd_caps & HAS_AVX2)) append_negative_gtest_filter(":AVX2.*:AVX2/*");
|
if (!(simd_caps & HAS_AVX2)) append_negative_gtest_filter(":AVX2.*:AVX2/*");
|
||||||
|
if (!(simd_caps & HAS_AVX512)) {
|
||||||
|
append_negative_gtest_filter(":AVX512.*:AVX512/*");
|
||||||
|
}
|
||||||
#endif // ARCH_X86 || ARCH_X86_64
|
#endif // ARCH_X86 || ARCH_X86_64
|
||||||
|
|
||||||
#if !CONFIG_SHARED
|
#if !CONFIG_SHARED
|
||||||
// Shared library builds don't support whitebox tests
|
// Shared library builds don't support whitebox tests
|
||||||
// that exercise internal symbols.
|
// that exercise internal symbols.
|
||||||
|
|
||||||
#if CONFIG_VP8
|
#if CONFIG_VP8
|
||||||
vp8_rtcd();
|
vp8_rtcd();
|
||||||
#endif // CONFIG_VP8
|
#endif // CONFIG_VP8
|
||||||
|
@ -28,13 +28,10 @@
|
|||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
enum DecodeMode { kSerialMode, kFrameParallelMode };
|
const int kThreads = 0;
|
||||||
|
const int kFileName = 1;
|
||||||
|
|
||||||
const int kDecodeMode = 0;
|
typedef ::testing::tuple<int, const char *> DecodeParam;
|
||||||
const int kThreads = 1;
|
|
||||||
const int kFileName = 2;
|
|
||||||
|
|
||||||
typedef std::tr1::tuple<int, int, const char *> DecodeParam;
|
|
||||||
|
|
||||||
class TestVectorTest : public ::libvpx_test::DecoderTest,
|
class TestVectorTest : public ::libvpx_test::DecoderTest,
|
||||||
public ::libvpx_test::CodecTestWithParam<DecodeParam> {
|
public ::libvpx_test::CodecTestWithParam<DecodeParam> {
|
||||||
@ -53,8 +50,8 @@ class TestVectorTest : public ::libvpx_test::DecoderTest,
|
|||||||
|
|
||||||
void OpenMD5File(const std::string &md5_file_name_) {
|
void OpenMD5File(const std::string &md5_file_name_) {
|
||||||
md5_file_ = libvpx_test::OpenTestDataFile(md5_file_name_);
|
md5_file_ = libvpx_test::OpenTestDataFile(md5_file_name_);
|
||||||
ASSERT_TRUE(md5_file_ != NULL) << "Md5 file open failed. Filename: "
|
ASSERT_TRUE(md5_file_ != NULL)
|
||||||
<< md5_file_name_;
|
<< "Md5 file open failed. Filename: " << md5_file_name_;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
||||||
@ -91,30 +88,15 @@ class TestVectorTest : public ::libvpx_test::DecoderTest,
|
|||||||
// the test failed.
|
// the test failed.
|
||||||
TEST_P(TestVectorTest, MD5Match) {
|
TEST_P(TestVectorTest, MD5Match) {
|
||||||
const DecodeParam input = GET_PARAM(1);
|
const DecodeParam input = GET_PARAM(1);
|
||||||
const std::string filename = std::tr1::get<kFileName>(input);
|
const std::string filename = ::testing::get<kFileName>(input);
|
||||||
const int threads = std::tr1::get<kThreads>(input);
|
|
||||||
const int mode = std::tr1::get<kDecodeMode>(input);
|
|
||||||
vpx_codec_flags_t flags = 0;
|
vpx_codec_flags_t flags = 0;
|
||||||
vpx_codec_dec_cfg_t cfg = vpx_codec_dec_cfg_t();
|
vpx_codec_dec_cfg_t cfg = vpx_codec_dec_cfg_t();
|
||||||
char str[256];
|
char str[256];
|
||||||
|
|
||||||
if (mode == kFrameParallelMode) {
|
cfg.threads = ::testing::get<kThreads>(input);
|
||||||
flags |= VPX_CODEC_USE_FRAME_THREADING;
|
|
||||||
#if CONFIG_VP9_DECODER
|
|
||||||
// TODO(hkuang): Fix frame parallel decode bug. See issue 1086.
|
|
||||||
if (resize_clips_.find(filename) != resize_clips_.end()) {
|
|
||||||
printf("Skipping the test file: %s, due to frame parallel decode bug.\n",
|
|
||||||
filename.c_str());
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
cfg.threads = threads;
|
snprintf(str, sizeof(str) / sizeof(str[0]) - 1, "file: %s threads: %d",
|
||||||
|
filename.c_str(), cfg.threads);
|
||||||
snprintf(str, sizeof(str) / sizeof(str[0]) - 1,
|
|
||||||
"file: %s mode: %s threads: %d", filename.c_str(),
|
|
||||||
mode == 0 ? "Serial" : "Parallel", threads);
|
|
||||||
SCOPED_TRACE(str);
|
SCOPED_TRACE(str);
|
||||||
|
|
||||||
// Open compressed video file.
|
// Open compressed video file.
|
||||||
@ -145,38 +127,44 @@ TEST_P(TestVectorTest, MD5Match) {
|
|||||||
ASSERT_NO_FATAL_FAILURE(RunLoop(video.get(), cfg));
|
ASSERT_NO_FATAL_FAILURE(RunLoop(video.get(), cfg));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test VP8 decode in serial mode with single thread.
|
|
||||||
// NOTE: VP8 only support serial mode.
|
|
||||||
#if CONFIG_VP8_DECODER
|
#if CONFIG_VP8_DECODER
|
||||||
VP8_INSTANTIATE_TEST_CASE(
|
VP8_INSTANTIATE_TEST_CASE(
|
||||||
TestVectorTest,
|
TestVectorTest,
|
||||||
::testing::Combine(
|
::testing::Combine(
|
||||||
::testing::Values(0), // Serial Mode.
|
|
||||||
::testing::Values(1), // Single thread.
|
::testing::Values(1), // Single thread.
|
||||||
::testing::ValuesIn(libvpx_test::kVP8TestVectors,
|
::testing::ValuesIn(libvpx_test::kVP8TestVectors,
|
||||||
libvpx_test::kVP8TestVectors +
|
libvpx_test::kVP8TestVectors +
|
||||||
libvpx_test::kNumVP8TestVectors)));
|
libvpx_test::kNumVP8TestVectors)));
|
||||||
|
|
||||||
|
// Test VP8 decode in with different numbers of threads.
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
VP8MultiThreaded, TestVectorTest,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Values(
|
||||||
|
static_cast<const libvpx_test::CodecFactory *>(&libvpx_test::kVP8)),
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Range(2, 9), // With 2 ~ 8 threads.
|
||||||
|
::testing::ValuesIn(libvpx_test::kVP8TestVectors,
|
||||||
|
libvpx_test::kVP8TestVectors +
|
||||||
|
libvpx_test::kNumVP8TestVectors))));
|
||||||
|
|
||||||
#endif // CONFIG_VP8_DECODER
|
#endif // CONFIG_VP8_DECODER
|
||||||
|
|
||||||
// Test VP9 decode in serial mode with single thread.
|
|
||||||
#if CONFIG_VP9_DECODER
|
#if CONFIG_VP9_DECODER
|
||||||
VP9_INSTANTIATE_TEST_CASE(
|
VP9_INSTANTIATE_TEST_CASE(
|
||||||
TestVectorTest,
|
TestVectorTest,
|
||||||
::testing::Combine(
|
::testing::Combine(
|
||||||
::testing::Values(0), // Serial Mode.
|
|
||||||
::testing::Values(1), // Single thread.
|
::testing::Values(1), // Single thread.
|
||||||
::testing::ValuesIn(libvpx_test::kVP9TestVectors,
|
::testing::ValuesIn(libvpx_test::kVP9TestVectors,
|
||||||
libvpx_test::kVP9TestVectors +
|
libvpx_test::kVP9TestVectors +
|
||||||
libvpx_test::kNumVP9TestVectors)));
|
libvpx_test::kNumVP9TestVectors)));
|
||||||
|
|
||||||
// Test VP9 decode in frame parallel mode with different number of threads.
|
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
VP9MultiThreadedFrameParallel, TestVectorTest,
|
VP9MultiThreaded, TestVectorTest,
|
||||||
::testing::Combine(
|
::testing::Combine(
|
||||||
::testing::Values(
|
::testing::Values(
|
||||||
static_cast<const libvpx_test::CodecFactory *>(&libvpx_test::kVP9)),
|
static_cast<const libvpx_test::CodecFactory *>(&libvpx_test::kVP9)),
|
||||||
::testing::Combine(
|
::testing::Combine(
|
||||||
::testing::Values(1), // Frame Parallel mode.
|
|
||||||
::testing::Range(2, 9), // With 2 ~ 8 threads.
|
::testing::Range(2, 9), // With 2 ~ 8 threads.
|
||||||
::testing::ValuesIn(libvpx_test::kVP9TestVectors,
|
::testing::ValuesIn(libvpx_test::kVP9TestVectors,
|
||||||
libvpx_test::kVP9TestVectors +
|
libvpx_test::kVP9TestVectors +
|
||||||
|
@ -371,6 +371,7 @@ const char *const kVP9TestVectors[] = {
|
|||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
"vp90-2-20-big_superframe-01.webm",
|
"vp90-2-20-big_superframe-01.webm",
|
||||||
"vp90-2-20-big_superframe-02.webm",
|
"vp90-2-20-big_superframe-02.webm",
|
||||||
|
"vp90-2-22-svc_1280x720_1.webm",
|
||||||
RESIZE_TEST_VECTORS
|
RESIZE_TEST_VECTORS
|
||||||
};
|
};
|
||||||
const char *const kVP9TestVectorsSvc[] = { "vp90-2-22-svc_1280x720_3.ivf" };
|
const char *const kVP9TestVectorsSvc[] = { "vp90-2-22-svc_1280x720_3.ivf" };
|
||||||
|
@ -54,7 +54,10 @@ twopass_encoder_vp9() {
|
|||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if [ "$(vpx_config_option_enabled CONFIG_REALTIME_ONLY)" != "yes" ]; then
|
||||||
twopass_encoder_tests="twopass_encoder_vp8
|
twopass_encoder_tests="twopass_encoder_vp8
|
||||||
twopass_encoder_vp9"
|
twopass_encoder_vp9"
|
||||||
|
|
||||||
run_tests twopass_encoder_verify_environment "${twopass_encoder_tests}"
|
run_tests twopass_encoder_verify_environment "${twopass_encoder_tests}"
|
||||||
|
fi
|
||||||
|
@ -27,8 +27,8 @@
|
|||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
using std::string;
|
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
|
using std::string;
|
||||||
|
|
||||||
#if CONFIG_WEBM_IO
|
#if CONFIG_WEBM_IO
|
||||||
|
|
||||||
|
@ -17,7 +17,7 @@
|
|||||||
#include "vpx/vpx_image.h"
|
#include "vpx/vpx_image.h"
|
||||||
|
|
||||||
// Macros
|
// Macros
|
||||||
#define GET_PARAM(k) std::tr1::get<k>(GetParam())
|
#define GET_PARAM(k) ::testing::get<k>(GetParam())
|
||||||
|
|
||||||
inline double compute_psnr(const vpx_image_t *img1, const vpx_image_t *img2) {
|
inline double compute_psnr(const vpx_image_t *img1, const vpx_image_t *img2) {
|
||||||
assert((img1->fmt == img2->fmt) && (img1->d_w == img2->d_w) &&
|
assert((img1->fmt == img2->fmt) && (img1->d_w == img2->d_w) &&
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -13,7 +13,9 @@
|
|||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
#undef NOMINMAX
|
#undef NOMINMAX
|
||||||
#define NOMINMAX
|
#define NOMINMAX
|
||||||
|
#ifndef WIN32_LEAN_AND_MEAN
|
||||||
#define WIN32_LEAN_AND_MEAN
|
#define WIN32_LEAN_AND_MEAN
|
||||||
|
#endif
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#endif
|
#endif
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
|
513
test/vp8_datarate_test.cc
Normal file
513
test/vp8_datarate_test.cc
Normal file
@ -0,0 +1,513 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2012 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
#include "./vpx_config.h"
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
#include "test/codec_factory.h"
|
||||||
|
#include "test/encode_test_driver.h"
|
||||||
|
#include "test/i420_video_source.h"
|
||||||
|
#include "test/util.h"
|
||||||
|
#include "test/y4m_video_source.h"
|
||||||
|
#include "vpx/vpx_codec.h"
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
class DatarateTestLarge
|
||||||
|
: public ::libvpx_test::EncoderTest,
|
||||||
|
public ::libvpx_test::CodecTestWith2Params<libvpx_test::TestMode, int> {
|
||||||
|
public:
|
||||||
|
DatarateTestLarge() : EncoderTest(GET_PARAM(0)) {}
|
||||||
|
|
||||||
|
virtual ~DatarateTestLarge() {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() {
|
||||||
|
InitializeConfig();
|
||||||
|
SetMode(GET_PARAM(1));
|
||||||
|
set_cpu_used_ = GET_PARAM(2);
|
||||||
|
ResetModel();
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void ResetModel() {
|
||||||
|
last_pts_ = 0;
|
||||||
|
bits_in_buffer_model_ = cfg_.rc_target_bitrate * cfg_.rc_buf_initial_sz;
|
||||||
|
frame_number_ = 0;
|
||||||
|
first_drop_ = 0;
|
||||||
|
bits_total_ = 0;
|
||||||
|
duration_ = 0.0;
|
||||||
|
denoiser_offon_test_ = 0;
|
||||||
|
denoiser_offon_period_ = -1;
|
||||||
|
gf_boost_ = 0;
|
||||||
|
use_roi_ = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void PreEncodeFrameHook(::libvpx_test::VideoSource *video,
|
||||||
|
::libvpx_test::Encoder *encoder) {
|
||||||
|
if (video->frame() == 0) {
|
||||||
|
encoder->Control(VP8E_SET_NOISE_SENSITIVITY, denoiser_on_);
|
||||||
|
encoder->Control(VP8E_SET_CPUUSED, set_cpu_used_);
|
||||||
|
encoder->Control(VP8E_SET_GF_CBR_BOOST_PCT, gf_boost_);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (use_roi_) {
|
||||||
|
encoder->Control(VP8E_SET_ROI_MAP, &roi_);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (denoiser_offon_test_) {
|
||||||
|
ASSERT_GT(denoiser_offon_period_, 0)
|
||||||
|
<< "denoiser_offon_period_ is not positive.";
|
||||||
|
if ((video->frame() + 1) % denoiser_offon_period_ == 0) {
|
||||||
|
// Flip denoiser_on_ periodically
|
||||||
|
denoiser_on_ ^= 1;
|
||||||
|
}
|
||||||
|
encoder->Control(VP8E_SET_NOISE_SENSITIVITY, denoiser_on_);
|
||||||
|
}
|
||||||
|
|
||||||
|
const vpx_rational_t tb = video->timebase();
|
||||||
|
timebase_ = static_cast<double>(tb.num) / tb.den;
|
||||||
|
duration_ = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void FramePktHook(const vpx_codec_cx_pkt_t *pkt) {
|
||||||
|
// Time since last timestamp = duration.
|
||||||
|
vpx_codec_pts_t duration = pkt->data.frame.pts - last_pts_;
|
||||||
|
|
||||||
|
// TODO(jimbankoski): Remove these lines when the issue:
|
||||||
|
// http://code.google.com/p/webm/issues/detail?id=496 is fixed.
|
||||||
|
// For now the codec assumes buffer starts at starting buffer rate
|
||||||
|
// plus one frame's time.
|
||||||
|
if (last_pts_ == 0) duration = 1;
|
||||||
|
|
||||||
|
// Add to the buffer the bits we'd expect from a constant bitrate server.
|
||||||
|
bits_in_buffer_model_ += static_cast<int64_t>(
|
||||||
|
duration * timebase_ * cfg_.rc_target_bitrate * 1000);
|
||||||
|
|
||||||
|
/* Test the buffer model here before subtracting the frame. Do so because
|
||||||
|
* the way the leaky bucket model works in libvpx is to allow the buffer to
|
||||||
|
* empty - and then stop showing frames until we've got enough bits to
|
||||||
|
* show one. As noted in comment below (issue 495), this does not currently
|
||||||
|
* apply to key frames. For now exclude key frames in condition below. */
|
||||||
|
const bool key_frame =
|
||||||
|
(pkt->data.frame.flags & VPX_FRAME_IS_KEY) ? true : false;
|
||||||
|
if (!key_frame) {
|
||||||
|
ASSERT_GE(bits_in_buffer_model_, 0)
|
||||||
|
<< "Buffer Underrun at frame " << pkt->data.frame.pts;
|
||||||
|
}
|
||||||
|
|
||||||
|
const int64_t frame_size_in_bits = pkt->data.frame.sz * 8;
|
||||||
|
|
||||||
|
// Subtract from the buffer the bits associated with a played back frame.
|
||||||
|
bits_in_buffer_model_ -= frame_size_in_bits;
|
||||||
|
|
||||||
|
// Update the running total of bits for end of test datarate checks.
|
||||||
|
bits_total_ += frame_size_in_bits;
|
||||||
|
|
||||||
|
// If first drop not set and we have a drop set it to this time.
|
||||||
|
if (!first_drop_ && duration > 1) first_drop_ = last_pts_ + 1;
|
||||||
|
|
||||||
|
// Update the most recent pts.
|
||||||
|
last_pts_ = pkt->data.frame.pts;
|
||||||
|
|
||||||
|
// We update this so that we can calculate the datarate minus the last
|
||||||
|
// frame encoded in the file.
|
||||||
|
bits_in_last_frame_ = frame_size_in_bits;
|
||||||
|
|
||||||
|
++frame_number_;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void EndPassHook(void) {
|
||||||
|
if (bits_total_) {
|
||||||
|
const double file_size_in_kb = bits_total_ / 1000.; // bits per kilobit
|
||||||
|
|
||||||
|
duration_ = (last_pts_ + 1) * timebase_;
|
||||||
|
|
||||||
|
// Effective file datarate includes the time spent prebuffering.
|
||||||
|
effective_datarate_ = (bits_total_ - bits_in_last_frame_) / 1000.0 /
|
||||||
|
(cfg_.rc_buf_initial_sz / 1000.0 + duration_);
|
||||||
|
|
||||||
|
file_datarate_ = file_size_in_kb / duration_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
vpx_codec_pts_t last_pts_;
|
||||||
|
int64_t bits_in_buffer_model_;
|
||||||
|
double timebase_;
|
||||||
|
int frame_number_;
|
||||||
|
vpx_codec_pts_t first_drop_;
|
||||||
|
int64_t bits_total_;
|
||||||
|
double duration_;
|
||||||
|
double file_datarate_;
|
||||||
|
double effective_datarate_;
|
||||||
|
int64_t bits_in_last_frame_;
|
||||||
|
int denoiser_on_;
|
||||||
|
int denoiser_offon_test_;
|
||||||
|
int denoiser_offon_period_;
|
||||||
|
int set_cpu_used_;
|
||||||
|
int gf_boost_;
|
||||||
|
bool use_roi_;
|
||||||
|
vpx_roi_map_t roi_;
|
||||||
|
};
|
||||||
|
|
||||||
|
#if CONFIG_TEMPORAL_DENOISING
|
||||||
|
// Check basic datarate targeting, for a single bitrate, but loop over the
|
||||||
|
// various denoiser settings.
|
||||||
|
TEST_P(DatarateTestLarge, DenoiserLevels) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
for (int j = 1; j < 5; ++j) {
|
||||||
|
// Run over the denoiser levels.
|
||||||
|
// For the temporal denoiser (#if CONFIG_TEMPORAL_DENOISING) the level j
|
||||||
|
// refers to the 4 denoiser modes: denoiserYonly, denoiserOnYUV,
|
||||||
|
// denoiserOnAggressive, and denoiserOnAdaptive.
|
||||||
|
denoiser_on_ = j;
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic datarate targeting, for a single bitrate, when denoiser is off
|
||||||
|
// and on.
|
||||||
|
TEST_P(DatarateTestLarge, DenoiserOffOn) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 299);
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
// The denoiser is off by default.
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
// Set the offon test flag.
|
||||||
|
denoiser_offon_test_ = 1;
|
||||||
|
denoiser_offon_period_ = 100;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
#endif // CONFIG_TEMPORAL_DENOISING
|
||||||
|
|
||||||
|
TEST_P(DatarateTestLarge, BasicBufferModel) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
// 2 pass cbr datarate control has a bug hidden by the small # of
|
||||||
|
// frames selected in this encode. The problem is that even if the buffer is
|
||||||
|
// negative we produce a keyframe on a cutscene. Ignoring datarate
|
||||||
|
// constraints
|
||||||
|
// TODO(jimbankoski): ( Fix when issue
|
||||||
|
// http://code.google.com/p/webm/issues/detail?id=495 is addressed. )
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
|
||||||
|
// There is an issue for low bitrates in real-time mode, where the
|
||||||
|
// effective_datarate slightly overshoots the target bitrate.
|
||||||
|
// This is same the issue as noted about (#495).
|
||||||
|
// TODO(jimbankoski/marpan): Update test to run for lower bitrates (< 100),
|
||||||
|
// when the issue is resolved.
|
||||||
|
for (int i = 100; i < 800; i += 200) {
|
||||||
|
cfg_.rc_target_bitrate = i;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(DatarateTestLarge, ChangingDropFrameThresh) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_max_quantizer = 36;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
cfg_.kf_mode = VPX_KF_DISABLED;
|
||||||
|
|
||||||
|
const int frame_count = 40;
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, frame_count);
|
||||||
|
|
||||||
|
// Here we check that the first dropped frame gets earlier and earlier
|
||||||
|
// as the drop frame threshold is increased.
|
||||||
|
|
||||||
|
const int kDropFrameThreshTestStep = 30;
|
||||||
|
vpx_codec_pts_t last_drop = frame_count;
|
||||||
|
for (int i = 1; i < 91; i += kDropFrameThreshTestStep) {
|
||||||
|
cfg_.rc_dropframe_thresh = i;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_LE(first_drop_, last_drop)
|
||||||
|
<< " The first dropped frame for drop_thresh " << i
|
||||||
|
<< " > first dropped frame for drop_thresh "
|
||||||
|
<< i - kDropFrameThreshTestStep;
|
||||||
|
last_drop = first_drop_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(DatarateTestLarge, DropFramesMultiThreads) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 30;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
|
||||||
|
class DatarateTestRealTime : public DatarateTestLarge {
|
||||||
|
public:
|
||||||
|
virtual ~DatarateTestRealTime() {}
|
||||||
|
};
|
||||||
|
|
||||||
|
#if CONFIG_TEMPORAL_DENOISING
|
||||||
|
// Check basic datarate targeting, for a single bitrate, but loop over the
|
||||||
|
// various denoiser settings.
|
||||||
|
TEST_P(DatarateTestRealTime, DenoiserLevels) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
for (int j = 1; j < 5; ++j) {
|
||||||
|
// Run over the denoiser levels.
|
||||||
|
// For the temporal denoiser (#if CONFIG_TEMPORAL_DENOISING) the level j
|
||||||
|
// refers to the 4 denoiser modes: denoiserYonly, denoiserOnYUV,
|
||||||
|
// denoiserOnAggressive, and denoiserOnAdaptive.
|
||||||
|
denoiser_on_ = j;
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic datarate targeting, for a single bitrate, when denoiser is off
|
||||||
|
// and on.
|
||||||
|
TEST_P(DatarateTestRealTime, DenoiserOffOn) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 299);
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
// The denoiser is off by default.
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
// Set the offon test flag.
|
||||||
|
denoiser_offon_test_ = 1;
|
||||||
|
denoiser_offon_period_ = 100;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
#endif // CONFIG_TEMPORAL_DENOISING
|
||||||
|
|
||||||
|
TEST_P(DatarateTestRealTime, BasicBufferModel) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
// 2 pass cbr datarate control has a bug hidden by the small # of
|
||||||
|
// frames selected in this encode. The problem is that even if the buffer is
|
||||||
|
// negative we produce a keyframe on a cutscene, ignoring datarate
|
||||||
|
// constraints
|
||||||
|
// TODO(jimbankoski): Fix when issue
|
||||||
|
// http://bugs.chromium.org/p/webm/issues/detail?id=495 is addressed.
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
|
||||||
|
// There is an issue for low bitrates in real-time mode, where the
|
||||||
|
// effective_datarate slightly overshoots the target bitrate.
|
||||||
|
// This is same the issue as noted above (#495).
|
||||||
|
// TODO(jimbankoski/marpan): Update test to run for lower bitrates (< 100),
|
||||||
|
// when the issue is resolved.
|
||||||
|
for (int i = 100; i <= 700; i += 200) {
|
||||||
|
cfg_.rc_target_bitrate = i;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(DatarateTestRealTime, ChangingDropFrameThresh) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_max_quantizer = 36;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
cfg_.kf_mode = VPX_KF_DISABLED;
|
||||||
|
|
||||||
|
const int frame_count = 40;
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, frame_count);
|
||||||
|
|
||||||
|
// Check that the first dropped frame gets earlier and earlier
|
||||||
|
// as the drop frame threshold is increased.
|
||||||
|
|
||||||
|
const int kDropFrameThreshTestStep = 30;
|
||||||
|
vpx_codec_pts_t last_drop = frame_count;
|
||||||
|
for (int i = 1; i < 91; i += kDropFrameThreshTestStep) {
|
||||||
|
cfg_.rc_dropframe_thresh = i;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_LE(first_drop_, last_drop)
|
||||||
|
<< " The first dropped frame for drop_thresh " << i
|
||||||
|
<< " > first dropped frame for drop_thresh "
|
||||||
|
<< i - kDropFrameThreshTestStep;
|
||||||
|
last_drop = first_drop_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(DatarateTestRealTime, DropFramesMultiThreads) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 30;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
// Encode using multiple threads.
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(DatarateTestRealTime, RegionOfInterest) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 0;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
// Encode using multiple threads.
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 300);
|
||||||
|
cfg_.rc_target_bitrate = 450;
|
||||||
|
cfg_.g_w = 352;
|
||||||
|
cfg_.g_h = 288;
|
||||||
|
|
||||||
|
ResetModel();
|
||||||
|
|
||||||
|
// Set ROI parameters
|
||||||
|
use_roi_ = true;
|
||||||
|
memset(&roi_, 0, sizeof(roi_));
|
||||||
|
|
||||||
|
roi_.rows = (cfg_.g_h + 15) / 16;
|
||||||
|
roi_.cols = (cfg_.g_w + 15) / 16;
|
||||||
|
|
||||||
|
roi_.delta_q[0] = 0;
|
||||||
|
roi_.delta_q[1] = -20;
|
||||||
|
roi_.delta_q[2] = 0;
|
||||||
|
roi_.delta_q[3] = 0;
|
||||||
|
|
||||||
|
roi_.delta_lf[0] = 0;
|
||||||
|
roi_.delta_lf[1] = -20;
|
||||||
|
roi_.delta_lf[2] = 0;
|
||||||
|
roi_.delta_lf[3] = 0;
|
||||||
|
|
||||||
|
roi_.static_threshold[0] = 0;
|
||||||
|
roi_.static_threshold[1] = 1000;
|
||||||
|
roi_.static_threshold[2] = 0;
|
||||||
|
roi_.static_threshold[3] = 0;
|
||||||
|
|
||||||
|
// Use 2 states: 1 is center square, 0 is the rest.
|
||||||
|
roi_.roi_map =
|
||||||
|
(uint8_t *)calloc(roi_.rows * roi_.cols, sizeof(*roi_.roi_map));
|
||||||
|
for (unsigned int i = 0; i < roi_.rows; ++i) {
|
||||||
|
for (unsigned int j = 0; j < roi_.cols; ++j) {
|
||||||
|
if (i > (roi_.rows >> 2) && i < ((roi_.rows * 3) >> 2) &&
|
||||||
|
j > (roi_.cols >> 2) && j < ((roi_.cols * 3) >> 2)) {
|
||||||
|
roi_.roi_map[i * roi_.cols + j] = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
|
||||||
|
free(roi_.roi_map);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(DatarateTestRealTime, GFBoost) {
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_dropframe_thresh = 0;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_error_resilient = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 300);
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
// Apply a gf boost.
|
||||||
|
gf_boost_ = 50;
|
||||||
|
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_ * 0.95)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, file_datarate_ * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
}
|
||||||
|
|
||||||
|
VP8_INSTANTIATE_TEST_CASE(DatarateTestLarge, ALL_TEST_MODES,
|
||||||
|
::testing::Values(0));
|
||||||
|
VP8_INSTANTIATE_TEST_CASE(DatarateTestRealTime,
|
||||||
|
::testing::Values(::libvpx_test::kRealTime),
|
||||||
|
::testing::Values(-6, -12));
|
||||||
|
} // namespace
|
@ -17,12 +17,16 @@
|
|||||||
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vpx_config.h"
|
||||||
#include "./vp8_rtcd.h"
|
#include "./vp8_rtcd.h"
|
||||||
#include "test/acm_random.h"
|
#include "test/acm_random.h"
|
||||||
#include "vpx/vpx_integer.h"
|
#include "vpx/vpx_integer.h"
|
||||||
|
#include "vpx_ports/mem.h"
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
typedef void (*FdctFunc)(int16_t *a, int16_t *b, int a_stride);
|
||||||
|
|
||||||
const int cospi8sqrt2minus1 = 20091;
|
const int cospi8sqrt2minus1 = 20091;
|
||||||
const int sinpi8sqrt2 = 35468;
|
const int sinpi8sqrt2 = 35468;
|
||||||
|
|
||||||
@ -68,10 +72,21 @@ void reference_idct4x4(const int16_t *input, int16_t *output) {
|
|||||||
|
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
|
|
||||||
TEST(VP8FdctTest, SignBiasCheck) {
|
class FdctTest : public ::testing::TestWithParam<FdctFunc> {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
public:
|
||||||
|
virtual void SetUp() {
|
||||||
|
fdct_func_ = GetParam();
|
||||||
|
rnd_.Reset(ACMRandom::DeterministicSeed());
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
FdctFunc fdct_func_;
|
||||||
|
ACMRandom rnd_;
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(FdctTest, SignBiasCheck) {
|
||||||
int16_t test_input_block[16];
|
int16_t test_input_block[16];
|
||||||
int16_t test_output_block[16];
|
DECLARE_ALIGNED(16, int16_t, test_output_block[16]);
|
||||||
const int pitch = 8;
|
const int pitch = 8;
|
||||||
int count_sign_block[16][2];
|
int count_sign_block[16][2];
|
||||||
const int count_test_block = 1000000;
|
const int count_test_block = 1000000;
|
||||||
@ -81,10 +96,10 @@ TEST(VP8FdctTest, SignBiasCheck) {
|
|||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
// Initialize a test block with input range [-255, 255].
|
// Initialize a test block with input range [-255, 255].
|
||||||
for (int j = 0; j < 16; ++j) {
|
for (int j = 0; j < 16; ++j) {
|
||||||
test_input_block[j] = rnd.Rand8() - rnd.Rand8();
|
test_input_block[j] = rnd_.Rand8() - rnd_.Rand8();
|
||||||
}
|
}
|
||||||
|
|
||||||
vp8_short_fdct4x4_c(test_input_block, test_output_block, pitch);
|
fdct_func_(test_input_block, test_output_block, pitch);
|
||||||
|
|
||||||
for (int j = 0; j < 16; ++j) {
|
for (int j = 0; j < 16; ++j) {
|
||||||
if (test_output_block[j] < 0) {
|
if (test_output_block[j] < 0) {
|
||||||
@ -110,10 +125,10 @@ TEST(VP8FdctTest, SignBiasCheck) {
|
|||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
// Initialize a test block with input range [-15, 15].
|
// Initialize a test block with input range [-15, 15].
|
||||||
for (int j = 0; j < 16; ++j) {
|
for (int j = 0; j < 16; ++j) {
|
||||||
test_input_block[j] = (rnd.Rand8() >> 4) - (rnd.Rand8() >> 4);
|
test_input_block[j] = (rnd_.Rand8() >> 4) - (rnd_.Rand8() >> 4);
|
||||||
}
|
}
|
||||||
|
|
||||||
vp8_short_fdct4x4_c(test_input_block, test_output_block, pitch);
|
fdct_func_(test_input_block, test_output_block, pitch);
|
||||||
|
|
||||||
for (int j = 0; j < 16; ++j) {
|
for (int j = 0; j < 16; ++j) {
|
||||||
if (test_output_block[j] < 0) {
|
if (test_output_block[j] < 0) {
|
||||||
@ -135,23 +150,22 @@ TEST(VP8FdctTest, SignBiasCheck) {
|
|||||||
<< "Error: 4x4 FDCT has a sign bias > 10% for input range [-15, 15]";
|
<< "Error: 4x4 FDCT has a sign bias > 10% for input range [-15, 15]";
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST(VP8FdctTest, RoundTripErrorCheck) {
|
TEST_P(FdctTest, RoundTripErrorCheck) {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
int max_error = 0;
|
int max_error = 0;
|
||||||
double total_error = 0;
|
double total_error = 0;
|
||||||
const int count_test_block = 1000000;
|
const int count_test_block = 1000000;
|
||||||
for (int i = 0; i < count_test_block; ++i) {
|
for (int i = 0; i < count_test_block; ++i) {
|
||||||
int16_t test_input_block[16];
|
int16_t test_input_block[16];
|
||||||
int16_t test_temp_block[16];
|
|
||||||
int16_t test_output_block[16];
|
int16_t test_output_block[16];
|
||||||
|
DECLARE_ALIGNED(16, int16_t, test_temp_block[16]);
|
||||||
|
|
||||||
// Initialize a test block with input range [-255, 255].
|
// Initialize a test block with input range [-255, 255].
|
||||||
for (int j = 0; j < 16; ++j) {
|
for (int j = 0; j < 16; ++j) {
|
||||||
test_input_block[j] = rnd.Rand8() - rnd.Rand8();
|
test_input_block[j] = rnd_.Rand8() - rnd_.Rand8();
|
||||||
}
|
}
|
||||||
|
|
||||||
const int pitch = 8;
|
const int pitch = 8;
|
||||||
vp8_short_fdct4x4_c(test_input_block, test_temp_block, pitch);
|
fdct_func_(test_input_block, test_temp_block, pitch);
|
||||||
reference_idct4x4(test_temp_block, test_output_block);
|
reference_idct4x4(test_temp_block, test_output_block);
|
||||||
|
|
||||||
for (int j = 0; j < 16; ++j) {
|
for (int j = 0; j < 16; ++j) {
|
||||||
@ -169,4 +183,24 @@ TEST(VP8FdctTest, RoundTripErrorCheck) {
|
|||||||
<< "Error: FDCT/IDCT has average roundtrip error > 1 per block";
|
<< "Error: FDCT/IDCT has average roundtrip error > 1 per block";
|
||||||
};
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(C, FdctTest, ::testing::Values(vp8_short_fdct4x4_c));
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
INSTANTIATE_TEST_CASE_P(NEON, FdctTest,
|
||||||
|
::testing::Values(vp8_short_fdct4x4_neon));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if HAVE_SSE2
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, FdctTest,
|
||||||
|
::testing::Values(vp8_short_fdct4x4_sse2));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_MSA
|
||||||
|
INSTANTIATE_TEST_CASE_P(MSA, FdctTest,
|
||||||
|
::testing::Values(vp8_short_fdct4x4_msa));
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
#if HAVE_MMI
|
||||||
|
INSTANTIATE_TEST_CASE_P(MMI, FdctTest,
|
||||||
|
::testing::Values(vp8_short_fdct4x4_mmi));
|
||||||
|
#endif // HAVE_MMI
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -23,36 +23,36 @@
|
|||||||
#include "vp9/common/vp9_entropy.h"
|
#include "vp9/common/vp9_entropy.h"
|
||||||
#include "vpx/vpx_codec.h"
|
#include "vpx/vpx_codec.h"
|
||||||
#include "vpx/vpx_integer.h"
|
#include "vpx/vpx_integer.h"
|
||||||
|
#include "vpx_dsp/vpx_dsp_common.h"
|
||||||
|
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int kNumIterations = 1000;
|
const int kNumIterations = 1000;
|
||||||
|
|
||||||
typedef int64_t (*ErrorBlockFunc)(const tran_low_t *coeff,
|
typedef int64_t (*HBDBlockErrorFunc)(const tran_low_t *coeff,
|
||||||
const tran_low_t *dqcoeff,
|
|
||||||
intptr_t block_size, int64_t *ssz, int bps);
|
|
||||||
|
|
||||||
typedef std::tr1::tuple<ErrorBlockFunc, ErrorBlockFunc, vpx_bit_depth_t>
|
|
||||||
ErrorBlockParam;
|
|
||||||
|
|
||||||
// wrapper for 8-bit block error functions without a 'bps' param.
|
|
||||||
typedef int64_t (*HighBdBlockError8bit)(const tran_low_t *coeff,
|
|
||||||
const tran_low_t *dqcoeff,
|
|
||||||
intptr_t block_size, int64_t *ssz);
|
|
||||||
template <HighBdBlockError8bit fn>
|
|
||||||
int64_t HighBdBlockError8bitWrapper(const tran_low_t *coeff,
|
|
||||||
const tran_low_t *dqcoeff,
|
const tran_low_t *dqcoeff,
|
||||||
intptr_t block_size, int64_t *ssz,
|
intptr_t block_size, int64_t *ssz,
|
||||||
int bps) {
|
int bps);
|
||||||
EXPECT_EQ(8, bps);
|
|
||||||
|
typedef ::testing::tuple<HBDBlockErrorFunc, HBDBlockErrorFunc, vpx_bit_depth_t>
|
||||||
|
BlockErrorParam;
|
||||||
|
|
||||||
|
typedef int64_t (*BlockErrorFunc)(const tran_low_t *coeff,
|
||||||
|
const tran_low_t *dqcoeff,
|
||||||
|
intptr_t block_size, int64_t *ssz);
|
||||||
|
|
||||||
|
template <BlockErrorFunc fn>
|
||||||
|
int64_t BlockError8BitWrapper(const tran_low_t *coeff,
|
||||||
|
const tran_low_t *dqcoeff, intptr_t block_size,
|
||||||
|
int64_t *ssz, int bps) {
|
||||||
|
EXPECT_EQ(bps, 8);
|
||||||
return fn(coeff, dqcoeff, block_size, ssz);
|
return fn(coeff, dqcoeff, block_size, ssz);
|
||||||
}
|
}
|
||||||
|
|
||||||
class ErrorBlockTest : public ::testing::TestWithParam<ErrorBlockParam> {
|
class BlockErrorTest : public ::testing::TestWithParam<BlockErrorParam> {
|
||||||
public:
|
public:
|
||||||
virtual ~ErrorBlockTest() {}
|
virtual ~BlockErrorTest() {}
|
||||||
virtual void SetUp() {
|
virtual void SetUp() {
|
||||||
error_block_op_ = GET_PARAM(0);
|
error_block_op_ = GET_PARAM(0);
|
||||||
ref_error_block_op_ = GET_PARAM(1);
|
ref_error_block_op_ = GET_PARAM(1);
|
||||||
@ -63,11 +63,11 @@ class ErrorBlockTest : public ::testing::TestWithParam<ErrorBlockParam> {
|
|||||||
|
|
||||||
protected:
|
protected:
|
||||||
vpx_bit_depth_t bit_depth_;
|
vpx_bit_depth_t bit_depth_;
|
||||||
ErrorBlockFunc error_block_op_;
|
HBDBlockErrorFunc error_block_op_;
|
||||||
ErrorBlockFunc ref_error_block_op_;
|
HBDBlockErrorFunc ref_error_block_op_;
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST_P(ErrorBlockTest, OperationCheck) {
|
TEST_P(BlockErrorTest, OperationCheck) {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff[4096]);
|
DECLARE_ALIGNED(16, tran_low_t, coeff[4096]);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, dqcoeff[4096]);
|
DECLARE_ALIGNED(16, tran_low_t, dqcoeff[4096]);
|
||||||
@ -110,7 +110,7 @@ TEST_P(ErrorBlockTest, OperationCheck) {
|
|||||||
<< "First failed at test case " << first_failure;
|
<< "First failed at test case " << first_failure;
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_P(ErrorBlockTest, ExtremeValues) {
|
TEST_P(BlockErrorTest, ExtremeValues) {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff[4096]);
|
DECLARE_ALIGNED(16, tran_low_t, coeff[4096]);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, dqcoeff[4096]);
|
DECLARE_ALIGNED(16, tran_low_t, dqcoeff[4096]);
|
||||||
@ -168,32 +168,31 @@ TEST_P(ErrorBlockTest, ExtremeValues) {
|
|||||||
<< "First failed at test case " << first_failure;
|
<< "First failed at test case " << first_failure;
|
||||||
}
|
}
|
||||||
|
|
||||||
using std::tr1::make_tuple;
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
INSTANTIATE_TEST_CASE_P(
|
const BlockErrorParam sse2_block_error_tests[] = {
|
||||||
SSE2, ErrorBlockTest,
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
::testing::Values(
|
|
||||||
make_tuple(&vp9_highbd_block_error_sse2, &vp9_highbd_block_error_c,
|
make_tuple(&vp9_highbd_block_error_sse2, &vp9_highbd_block_error_c,
|
||||||
VPX_BITS_10),
|
VPX_BITS_10),
|
||||||
make_tuple(&vp9_highbd_block_error_sse2, &vp9_highbd_block_error_c,
|
make_tuple(&vp9_highbd_block_error_sse2, &vp9_highbd_block_error_c,
|
||||||
VPX_BITS_12),
|
VPX_BITS_12),
|
||||||
make_tuple(&vp9_highbd_block_error_sse2, &vp9_highbd_block_error_c,
|
make_tuple(&vp9_highbd_block_error_sse2, &vp9_highbd_block_error_c,
|
||||||
VPX_BITS_8),
|
VPX_BITS_8),
|
||||||
make_tuple(
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
&HighBdBlockError8bitWrapper<vp9_highbd_block_error_8bit_sse2>,
|
make_tuple(&BlockError8BitWrapper<vp9_block_error_sse2>,
|
||||||
&HighBdBlockError8bitWrapper<vp9_highbd_block_error_8bit_c>,
|
&BlockError8BitWrapper<vp9_block_error_c>, VPX_BITS_8)
|
||||||
VPX_BITS_8)));
|
};
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSE2, BlockErrorTest,
|
||||||
|
::testing::ValuesIn(sse2_block_error_tests));
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
#if HAVE_AVX
|
#if HAVE_AVX2
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
AVX, ErrorBlockTest,
|
AVX2, BlockErrorTest,
|
||||||
::testing::Values(make_tuple(
|
::testing::Values(make_tuple(&BlockError8BitWrapper<vp9_block_error_avx2>,
|
||||||
&HighBdBlockError8bitWrapper<vp9_highbd_block_error_8bit_avx>,
|
&BlockError8BitWrapper<vp9_block_error_c>,
|
||||||
&HighBdBlockError8bitWrapper<vp9_highbd_block_error_8bit_c>,
|
|
||||||
VPX_BITS_8)));
|
VPX_BITS_8)));
|
||||||
#endif // HAVE_AVX
|
#endif // HAVE_AVX2
|
||||||
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
} // namespace
|
} // namespace
|
839
test/vp9_datarate_test.cc
Normal file
839
test/vp9_datarate_test.cc
Normal file
@ -0,0 +1,839 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2012 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
#include "./vpx_config.h"
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
#include "test/codec_factory.h"
|
||||||
|
#include "test/encode_test_driver.h"
|
||||||
|
#include "test/i420_video_source.h"
|
||||||
|
#include "test/util.h"
|
||||||
|
#include "test/y4m_video_source.h"
|
||||||
|
#include "vpx/vpx_codec.h"
|
||||||
|
#include "vpx_ports/bitops.h"
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
class DatarateTestVP9 : public ::libvpx_test::EncoderTest {
|
||||||
|
public:
|
||||||
|
explicit DatarateTestVP9(const ::libvpx_test::CodecFactory *codec)
|
||||||
|
: EncoderTest(codec) {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual ~DatarateTestVP9() {}
|
||||||
|
|
||||||
|
virtual void ResetModel() {
|
||||||
|
last_pts_ = 0;
|
||||||
|
bits_in_buffer_model_ = cfg_.rc_target_bitrate * cfg_.rc_buf_initial_sz;
|
||||||
|
frame_number_ = 0;
|
||||||
|
tot_frame_number_ = 0;
|
||||||
|
first_drop_ = 0;
|
||||||
|
num_drops_ = 0;
|
||||||
|
// Denoiser is off by default.
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
// For testing up to 3 layers.
|
||||||
|
for (int i = 0; i < 3; ++i) {
|
||||||
|
bits_total_[i] = 0;
|
||||||
|
}
|
||||||
|
denoiser_offon_test_ = 0;
|
||||||
|
denoiser_offon_period_ = -1;
|
||||||
|
frame_parallel_decoding_mode_ = 1;
|
||||||
|
use_roi_ = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// Frame flags and layer id for temporal layers.
|
||||||
|
//
|
||||||
|
|
||||||
|
// For two layers, test pattern is:
|
||||||
|
// 1 3
|
||||||
|
// 0 2 .....
|
||||||
|
// For three layers, test pattern is:
|
||||||
|
// 1 3 5 7
|
||||||
|
// 2 6
|
||||||
|
// 0 4 ....
|
||||||
|
// LAST is always update on base/layer 0, GOLDEN is updated on layer 1.
|
||||||
|
// For this 3 layer example, the 2nd enhancement layer (layer 2) updates
|
||||||
|
// the altref frame.
|
||||||
|
static int GetFrameFlags(int frame_num, int num_temp_layers) {
|
||||||
|
int frame_flags = 0;
|
||||||
|
if (num_temp_layers == 2) {
|
||||||
|
if (frame_num % 2 == 0) {
|
||||||
|
// Layer 0: predict from L and ARF, update L.
|
||||||
|
frame_flags =
|
||||||
|
VP8_EFLAG_NO_REF_GF | VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_ARF;
|
||||||
|
} else {
|
||||||
|
// Layer 1: predict from L, G and ARF, and update G.
|
||||||
|
frame_flags = VP8_EFLAG_NO_UPD_ARF | VP8_EFLAG_NO_UPD_LAST |
|
||||||
|
VP8_EFLAG_NO_UPD_ENTROPY;
|
||||||
|
}
|
||||||
|
} else if (num_temp_layers == 3) {
|
||||||
|
if (frame_num % 4 == 0) {
|
||||||
|
// Layer 0: predict from L and ARF; update L.
|
||||||
|
frame_flags =
|
||||||
|
VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_ARF | VP8_EFLAG_NO_REF_GF;
|
||||||
|
} else if ((frame_num - 2) % 4 == 0) {
|
||||||
|
// Layer 1: predict from L, G, ARF; update G.
|
||||||
|
frame_flags = VP8_EFLAG_NO_UPD_ARF | VP8_EFLAG_NO_UPD_LAST;
|
||||||
|
} else if ((frame_num - 1) % 2 == 0) {
|
||||||
|
// Layer 2: predict from L, G, ARF; update ARF.
|
||||||
|
frame_flags = VP8_EFLAG_NO_UPD_GF | VP8_EFLAG_NO_UPD_LAST;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return frame_flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int SetLayerId(int frame_num, int num_temp_layers) {
|
||||||
|
int layer_id = 0;
|
||||||
|
if (num_temp_layers == 2) {
|
||||||
|
if (frame_num % 2 == 0) {
|
||||||
|
layer_id = 0;
|
||||||
|
} else {
|
||||||
|
layer_id = 1;
|
||||||
|
}
|
||||||
|
} else if (num_temp_layers == 3) {
|
||||||
|
if (frame_num % 4 == 0) {
|
||||||
|
layer_id = 0;
|
||||||
|
} else if ((frame_num - 2) % 4 == 0) {
|
||||||
|
layer_id = 1;
|
||||||
|
} else if ((frame_num - 1) % 2 == 0) {
|
||||||
|
layer_id = 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return layer_id;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void PreEncodeFrameHook(::libvpx_test::VideoSource *video,
|
||||||
|
::libvpx_test::Encoder *encoder) {
|
||||||
|
if (video->frame() == 0) encoder->Control(VP8E_SET_CPUUSED, set_cpu_used_);
|
||||||
|
|
||||||
|
if (denoiser_offon_test_) {
|
||||||
|
ASSERT_GT(denoiser_offon_period_, 0)
|
||||||
|
<< "denoiser_offon_period_ is not positive.";
|
||||||
|
if ((video->frame() + 1) % denoiser_offon_period_ == 0) {
|
||||||
|
// Flip denoiser_on_ periodically
|
||||||
|
denoiser_on_ ^= 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
encoder->Control(VP9E_SET_NOISE_SENSITIVITY, denoiser_on_);
|
||||||
|
encoder->Control(VP9E_SET_TILE_COLUMNS, get_msb(cfg_.g_threads));
|
||||||
|
encoder->Control(VP9E_SET_FRAME_PARALLEL_DECODING,
|
||||||
|
frame_parallel_decoding_mode_);
|
||||||
|
|
||||||
|
if (use_roi_) {
|
||||||
|
encoder->Control(VP9E_SET_ROI_MAP, &roi_);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (cfg_.ts_number_layers > 1) {
|
||||||
|
if (video->frame() == 0) {
|
||||||
|
encoder->Control(VP9E_SET_SVC, 1);
|
||||||
|
}
|
||||||
|
vpx_svc_layer_id_t layer_id;
|
||||||
|
layer_id.spatial_layer_id = 0;
|
||||||
|
frame_flags_ = GetFrameFlags(video->frame(), cfg_.ts_number_layers);
|
||||||
|
layer_id.temporal_layer_id =
|
||||||
|
SetLayerId(video->frame(), cfg_.ts_number_layers);
|
||||||
|
encoder->Control(VP9E_SET_SVC_LAYER_ID, &layer_id);
|
||||||
|
}
|
||||||
|
const vpx_rational_t tb = video->timebase();
|
||||||
|
timebase_ = static_cast<double>(tb.num) / tb.den;
|
||||||
|
duration_ = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void FramePktHook(const vpx_codec_cx_pkt_t *pkt) {
|
||||||
|
// Time since last timestamp = duration.
|
||||||
|
vpx_codec_pts_t duration = pkt->data.frame.pts - last_pts_;
|
||||||
|
|
||||||
|
if (duration > 1) {
|
||||||
|
// If first drop not set and we have a drop set it to this time.
|
||||||
|
if (!first_drop_) first_drop_ = last_pts_ + 1;
|
||||||
|
// Update the number of frame drops.
|
||||||
|
num_drops_ += static_cast<int>(duration - 1);
|
||||||
|
// Update counter for total number of frames (#frames input to encoder).
|
||||||
|
// Needed for setting the proper layer_id below.
|
||||||
|
tot_frame_number_ += static_cast<int>(duration - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
int layer = SetLayerId(tot_frame_number_, cfg_.ts_number_layers);
|
||||||
|
|
||||||
|
// Add to the buffer the bits we'd expect from a constant bitrate server.
|
||||||
|
bits_in_buffer_model_ += static_cast<int64_t>(
|
||||||
|
duration * timebase_ * cfg_.rc_target_bitrate * 1000);
|
||||||
|
|
||||||
|
// Buffer should not go negative.
|
||||||
|
ASSERT_GE(bits_in_buffer_model_, 0)
|
||||||
|
<< "Buffer Underrun at frame " << pkt->data.frame.pts;
|
||||||
|
|
||||||
|
const size_t frame_size_in_bits = pkt->data.frame.sz * 8;
|
||||||
|
|
||||||
|
// Update the total encoded bits. For temporal layers, update the cumulative
|
||||||
|
// encoded bits per layer.
|
||||||
|
for (int i = layer; i < static_cast<int>(cfg_.ts_number_layers); ++i) {
|
||||||
|
bits_total_[i] += frame_size_in_bits;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Update the most recent pts.
|
||||||
|
last_pts_ = pkt->data.frame.pts;
|
||||||
|
++frame_number_;
|
||||||
|
++tot_frame_number_;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void EndPassHook(void) {
|
||||||
|
for (int layer = 0; layer < static_cast<int>(cfg_.ts_number_layers);
|
||||||
|
++layer) {
|
||||||
|
duration_ = (last_pts_ + 1) * timebase_;
|
||||||
|
if (bits_total_[layer]) {
|
||||||
|
// Effective file datarate:
|
||||||
|
effective_datarate_[layer] = (bits_total_[layer] / 1000.0) / duration_;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
vpx_codec_pts_t last_pts_;
|
||||||
|
double timebase_;
|
||||||
|
int frame_number_; // Counter for number of non-dropped/encoded frames.
|
||||||
|
int tot_frame_number_; // Counter for total number of input frames.
|
||||||
|
int64_t bits_total_[3];
|
||||||
|
double duration_;
|
||||||
|
double effective_datarate_[3];
|
||||||
|
int set_cpu_used_;
|
||||||
|
int64_t bits_in_buffer_model_;
|
||||||
|
vpx_codec_pts_t first_drop_;
|
||||||
|
int num_drops_;
|
||||||
|
int denoiser_on_;
|
||||||
|
int denoiser_offon_test_;
|
||||||
|
int denoiser_offon_period_;
|
||||||
|
int frame_parallel_decoding_mode_;
|
||||||
|
bool use_roi_;
|
||||||
|
vpx_roi_map_t roi_;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Params: test mode, speed setting and index for bitrate array.
|
||||||
|
class DatarateTestVP9Large
|
||||||
|
: public DatarateTestVP9,
|
||||||
|
public ::libvpx_test::CodecTestWith3Params<libvpx_test::TestMode, int,
|
||||||
|
int> {
|
||||||
|
public:
|
||||||
|
DatarateTestVP9Large() : DatarateTestVP9(GET_PARAM(0)) {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() {
|
||||||
|
InitializeConfig();
|
||||||
|
SetMode(GET_PARAM(1));
|
||||||
|
set_cpu_used_ = GET_PARAM(2);
|
||||||
|
ResetModel();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Params: test mode, speed setting.
|
||||||
|
class DatarateTestVP9LargeOneBR
|
||||||
|
: public DatarateTestVP9,
|
||||||
|
public ::libvpx_test::CodecTestWith2Params<libvpx_test::TestMode, int> {
|
||||||
|
public:
|
||||||
|
DatarateTestVP9LargeOneBR() : DatarateTestVP9(GET_PARAM(0)) {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() {
|
||||||
|
InitializeConfig();
|
||||||
|
SetMode(GET_PARAM(1));
|
||||||
|
set_cpu_used_ = GET_PARAM(2);
|
||||||
|
ResetModel();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Check basic rate targeting for VBR mode with 0 lag.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargetingVBRLagZero) {
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.g_error_resilient = 0;
|
||||||
|
cfg_.rc_end_usage = VPX_VBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 300);
|
||||||
|
|
||||||
|
const int bitrates[2] = { 400, 800 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
if (bitrate_index > 1) return;
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.75)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.35)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for VBR mode with non-zero lag.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargetingVBRLagNonZero) {
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.g_error_resilient = 0;
|
||||||
|
cfg_.rc_end_usage = VPX_VBR;
|
||||||
|
// For non-zero lag, rate control will work (be within bounds) for
|
||||||
|
// real-time mode.
|
||||||
|
if (deadline_ == VPX_DL_REALTIME) {
|
||||||
|
cfg_.g_lag_in_frames = 15;
|
||||||
|
} else {
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 300);
|
||||||
|
const int bitrates[2] = { 400, 800 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
if (bitrate_index > 1) return;
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.75)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.30)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for VBR mode with non-zero lag, with
|
||||||
|
// frame_parallel_decoding_mode off. This enables the adapt_coeff/mode/mv probs
|
||||||
|
// since error_resilience is off.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargetingVBRLagNonZeroFrameParDecOff) {
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.g_error_resilient = 0;
|
||||||
|
cfg_.rc_end_usage = VPX_VBR;
|
||||||
|
// For non-zero lag, rate control will work (be within bounds) for
|
||||||
|
// real-time mode.
|
||||||
|
if (deadline_ == VPX_DL_REALTIME) {
|
||||||
|
cfg_.g_lag_in_frames = 15;
|
||||||
|
} else {
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 300);
|
||||||
|
const int bitrates[2] = { 400, 800 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
if (bitrate_index > 1) return;
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
frame_parallel_decoding_mode_ = 0;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.75)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.35)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for CBR mode.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargeting) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
const int bitrates[4] = { 150, 350, 550, 750 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for CBR mode, with frame_parallel_decoding_mode
|
||||||
|
// off( and error_resilience off).
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargetingFrameParDecOff) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
cfg_.g_error_resilient = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
const int bitrates[4] = { 150, 350, 550, 750 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
frame_parallel_decoding_mode_ = 0;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for CBR mode, with 2 threads and dropped frames.
|
||||||
|
TEST_P(DatarateTestVP9LargeOneBR, BasicRateTargetingDropFramesMultiThreads) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 30;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
// Encode using multiple threads.
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for CBR.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargeting444) {
|
||||||
|
::libvpx_test::Y4mVideoSource video("rush_hour_444.y4m", 0, 140);
|
||||||
|
|
||||||
|
cfg_.g_profile = 1;
|
||||||
|
cfg_.g_timebase = video.timebase();
|
||||||
|
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
const int bitrates[4] = { 250, 450, 650, 850 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(static_cast<double>(cfg_.rc_target_bitrate),
|
||||||
|
effective_datarate_[0] * 0.80)
|
||||||
|
<< " The datarate for the file exceeds the target by too much!";
|
||||||
|
ASSERT_LE(static_cast<double>(cfg_.rc_target_bitrate),
|
||||||
|
effective_datarate_[0] * 1.15)
|
||||||
|
<< " The datarate for the file missed the target!"
|
||||||
|
<< cfg_.rc_target_bitrate << " " << effective_datarate_;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check that (1) the first dropped frame gets earlier and earlier
|
||||||
|
// as the drop frame threshold is increased, and (2) that the total number of
|
||||||
|
// frame drops does not decrease as we increase frame drop threshold.
|
||||||
|
// Use a lower qp-max to force some frame drops.
|
||||||
|
TEST_P(DatarateTestVP9Large, ChangingDropFrameThresh) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_undershoot_pct = 20;
|
||||||
|
cfg_.rc_undershoot_pct = 20;
|
||||||
|
cfg_.rc_dropframe_thresh = 10;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 50;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
// TODO(marpan): Investigate datarate target failures with a smaller keyframe
|
||||||
|
// interval (128).
|
||||||
|
cfg_.kf_max_dist = 9999;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
|
||||||
|
const int kDropFrameThreshTestStep = 30;
|
||||||
|
const int bitrates[2] = { 50, 150 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
if (bitrate_index > 1) return;
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
vpx_codec_pts_t last_drop = 140;
|
||||||
|
int last_num_drops = 0;
|
||||||
|
for (int i = 10; i < 100; i += kDropFrameThreshTestStep) {
|
||||||
|
cfg_.rc_dropframe_thresh = i;
|
||||||
|
ResetModel();
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.25)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
ASSERT_LE(first_drop_, last_drop)
|
||||||
|
<< " The first dropped frame for drop_thresh " << i
|
||||||
|
<< " > first dropped frame for drop_thresh "
|
||||||
|
<< i - kDropFrameThreshTestStep;
|
||||||
|
ASSERT_GE(num_drops_, last_num_drops * 0.85)
|
||||||
|
<< " The number of dropped frames for drop_thresh " << i
|
||||||
|
<< " < number of dropped frames for drop_thresh "
|
||||||
|
<< i - kDropFrameThreshTestStep;
|
||||||
|
last_drop = first_drop_;
|
||||||
|
last_num_drops = num_drops_;
|
||||||
|
}
|
||||||
|
} // namespace
|
||||||
|
|
||||||
|
// Check basic rate targeting for 2 temporal layers.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargeting2TemporalLayers) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
// 2 Temporal layers, no spatial layers: Framerate decimation (2, 1).
|
||||||
|
cfg_.ss_number_layers = 1;
|
||||||
|
cfg_.ts_number_layers = 2;
|
||||||
|
cfg_.ts_rate_decimator[0] = 2;
|
||||||
|
cfg_.ts_rate_decimator[1] = 1;
|
||||||
|
|
||||||
|
cfg_.temporal_layering_mode = VP9E_TEMPORAL_LAYERING_MODE_BYPASS;
|
||||||
|
|
||||||
|
if (deadline_ == VPX_DL_REALTIME) cfg_.g_error_resilient = 1;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 200);
|
||||||
|
const int bitrates[4] = { 200, 400, 600, 800 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
// 60-40 bitrate allocation for 2 temporal layers.
|
||||||
|
cfg_.layer_target_bitrate[0] = 60 * cfg_.rc_target_bitrate / 100;
|
||||||
|
cfg_.layer_target_bitrate[1] = cfg_.rc_target_bitrate;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
for (int j = 0; j < static_cast<int>(cfg_.ts_number_layers); ++j) {
|
||||||
|
ASSERT_GE(effective_datarate_[j], cfg_.layer_target_bitrate[j] * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much, "
|
||||||
|
"for layer: "
|
||||||
|
<< j;
|
||||||
|
ASSERT_LE(effective_datarate_[j], cfg_.layer_target_bitrate[j] * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much, "
|
||||||
|
"for layer: "
|
||||||
|
<< j;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for 3 temporal layers.
|
||||||
|
TEST_P(DatarateTestVP9Large, BasicRateTargeting3TemporalLayers) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
// 3 Temporal layers, no spatial layers: Framerate decimation (4, 2, 1).
|
||||||
|
cfg_.ss_number_layers = 1;
|
||||||
|
cfg_.ts_number_layers = 3;
|
||||||
|
cfg_.ts_rate_decimator[0] = 4;
|
||||||
|
cfg_.ts_rate_decimator[1] = 2;
|
||||||
|
cfg_.ts_rate_decimator[2] = 1;
|
||||||
|
|
||||||
|
cfg_.temporal_layering_mode = VP9E_TEMPORAL_LAYERING_MODE_BYPASS;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 200);
|
||||||
|
const int bitrates[4] = { 200, 400, 600, 800 };
|
||||||
|
const int bitrate_index = GET_PARAM(3);
|
||||||
|
cfg_.rc_target_bitrate = bitrates[bitrate_index];
|
||||||
|
ResetModel();
|
||||||
|
// 40-20-40 bitrate allocation for 3 temporal layers.
|
||||||
|
cfg_.layer_target_bitrate[0] = 40 * cfg_.rc_target_bitrate / 100;
|
||||||
|
cfg_.layer_target_bitrate[1] = 60 * cfg_.rc_target_bitrate / 100;
|
||||||
|
cfg_.layer_target_bitrate[2] = cfg_.rc_target_bitrate;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
for (int j = 0; j < static_cast<int>(cfg_.ts_number_layers); ++j) {
|
||||||
|
// TODO(yaowu): Work out more stable rc control strategy and
|
||||||
|
// Adjust the thresholds to be tighter than .75.
|
||||||
|
ASSERT_GE(effective_datarate_[j], cfg_.layer_target_bitrate[j] * 0.75)
|
||||||
|
<< " The datarate for the file is lower than target by too much, "
|
||||||
|
"for layer: "
|
||||||
|
<< j;
|
||||||
|
// TODO(yaowu): Work out more stable rc control strategy and
|
||||||
|
// Adjust the thresholds to be tighter than 1.25.
|
||||||
|
ASSERT_LE(effective_datarate_[j], cfg_.layer_target_bitrate[j] * 1.25)
|
||||||
|
<< " The datarate for the file is greater than target by too much, "
|
||||||
|
"for layer: "
|
||||||
|
<< j;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic rate targeting for 3 temporal layers, with frame dropping.
|
||||||
|
// Only for one (low) bitrate with lower max_quantizer, and somewhat higher
|
||||||
|
// frame drop threshold, to force frame dropping.
|
||||||
|
TEST_P(DatarateTestVP9LargeOneBR,
|
||||||
|
BasicRateTargeting3TemporalLayersFrameDropping) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
// Set frame drop threshold and rc_max_quantizer to force some frame drops.
|
||||||
|
cfg_.rc_dropframe_thresh = 20;
|
||||||
|
cfg_.rc_max_quantizer = 45;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
// 3 Temporal layers, no spatial layers: Framerate decimation (4, 2, 1).
|
||||||
|
cfg_.ss_number_layers = 1;
|
||||||
|
cfg_.ts_number_layers = 3;
|
||||||
|
cfg_.ts_rate_decimator[0] = 4;
|
||||||
|
cfg_.ts_rate_decimator[1] = 2;
|
||||||
|
cfg_.ts_rate_decimator[2] = 1;
|
||||||
|
|
||||||
|
cfg_.temporal_layering_mode = VP9E_TEMPORAL_LAYERING_MODE_BYPASS;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 200);
|
||||||
|
cfg_.rc_target_bitrate = 200;
|
||||||
|
ResetModel();
|
||||||
|
// 40-20-40 bitrate allocation for 3 temporal layers.
|
||||||
|
cfg_.layer_target_bitrate[0] = 40 * cfg_.rc_target_bitrate / 100;
|
||||||
|
cfg_.layer_target_bitrate[1] = 60 * cfg_.rc_target_bitrate / 100;
|
||||||
|
cfg_.layer_target_bitrate[2] = cfg_.rc_target_bitrate;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
for (int j = 0; j < static_cast<int>(cfg_.ts_number_layers); ++j) {
|
||||||
|
ASSERT_GE(effective_datarate_[j], cfg_.layer_target_bitrate[j] * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much, "
|
||||||
|
"for layer: "
|
||||||
|
<< j;
|
||||||
|
ASSERT_LE(effective_datarate_[j], cfg_.layer_target_bitrate[j] * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much, "
|
||||||
|
"for layer: "
|
||||||
|
<< j;
|
||||||
|
// Expect some frame drops in this test: for this 200 frames test,
|
||||||
|
// expect at least 10% and not more than 60% drops.
|
||||||
|
ASSERT_GE(num_drops_, 20);
|
||||||
|
ASSERT_LE(num_drops_, 130);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Params: speed setting.
|
||||||
|
class DatarateTestVP9RealTime : public DatarateTestVP9,
|
||||||
|
public ::libvpx_test::CodecTestWithParam<int> {
|
||||||
|
public:
|
||||||
|
DatarateTestVP9RealTime() : DatarateTestVP9(GET_PARAM(0)) {}
|
||||||
|
virtual ~DatarateTestVP9RealTime() {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() {
|
||||||
|
InitializeConfig();
|
||||||
|
SetMode(::libvpx_test::kRealTime);
|
||||||
|
set_cpu_used_ = GET_PARAM(1);
|
||||||
|
ResetModel();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Check VP9 region of interest feature.
|
||||||
|
TEST_P(DatarateTestVP9RealTime, RegionOfInterest) {
|
||||||
|
if (deadline_ != VPX_DL_REALTIME || set_cpu_used_ < 5) return;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 0;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
cfg_.rc_max_quantizer = 63;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 300);
|
||||||
|
|
||||||
|
cfg_.rc_target_bitrate = 450;
|
||||||
|
cfg_.g_w = 352;
|
||||||
|
cfg_.g_h = 288;
|
||||||
|
|
||||||
|
ResetModel();
|
||||||
|
|
||||||
|
// Set ROI parameters
|
||||||
|
use_roi_ = true;
|
||||||
|
memset(&roi_, 0, sizeof(roi_));
|
||||||
|
|
||||||
|
roi_.rows = (cfg_.g_h + 7) / 8;
|
||||||
|
roi_.cols = (cfg_.g_w + 7) / 8;
|
||||||
|
|
||||||
|
roi_.delta_q[1] = -20;
|
||||||
|
roi_.delta_lf[1] = -20;
|
||||||
|
memset(roi_.ref_frame, -1, sizeof(roi_.ref_frame));
|
||||||
|
roi_.ref_frame[1] = 1;
|
||||||
|
|
||||||
|
// Use 2 states: 1 is center square, 0 is the rest.
|
||||||
|
roi_.roi_map = reinterpret_cast<uint8_t *>(
|
||||||
|
calloc(roi_.rows * roi_.cols, sizeof(*roi_.roi_map)));
|
||||||
|
ASSERT_TRUE(roi_.roi_map != NULL);
|
||||||
|
|
||||||
|
for (unsigned int i = 0; i < roi_.rows; ++i) {
|
||||||
|
for (unsigned int j = 0; j < roi_.cols; ++j) {
|
||||||
|
if (i > (roi_.rows >> 2) && i < ((roi_.rows * 3) >> 2) &&
|
||||||
|
j > (roi_.cols >> 2) && j < ((roi_.cols * 3) >> 2)) {
|
||||||
|
roi_.roi_map[i * roi_.cols + j] = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(cfg_.rc_target_bitrate, effective_datarate_[0] * 0.90)
|
||||||
|
<< " The datarate for the file exceeds the target!";
|
||||||
|
|
||||||
|
ASSERT_LE(cfg_.rc_target_bitrate, effective_datarate_[0] * 1.4)
|
||||||
|
<< " The datarate for the file missed the target!";
|
||||||
|
|
||||||
|
free(roi_.roi_map);
|
||||||
|
}
|
||||||
|
|
||||||
|
#if CONFIG_VP9_TEMPORAL_DENOISING
|
||||||
|
// Params: speed setting.
|
||||||
|
class DatarateTestVP9LargeDenoiser : public DatarateTestVP9RealTime {
|
||||||
|
public:
|
||||||
|
virtual ~DatarateTestVP9LargeDenoiser() {}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Check basic datarate targeting, for a single bitrate, when denoiser is on.
|
||||||
|
TEST_P(DatarateTestVP9LargeDenoiser, LowNoise) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 2;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 140);
|
||||||
|
|
||||||
|
// For the temporal denoiser (#if CONFIG_VP9_TEMPORAL_DENOISING),
|
||||||
|
// there is only one denoiser mode: denoiserYonly(which is 1),
|
||||||
|
// but may add more modes in the future.
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
// Turn on the denoiser.
|
||||||
|
denoiser_on_ = 1;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic datarate targeting, for a single bitrate, when denoiser is on,
|
||||||
|
// for clip with high noise level. Use 2 threads.
|
||||||
|
TEST_P(DatarateTestVP9LargeDenoiser, HighNoise) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 2;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
|
||||||
|
::libvpx_test::Y4mVideoSource video("noisy_clip_640_360.y4m", 0, 200);
|
||||||
|
|
||||||
|
// For the temporal denoiser (#if CONFIG_VP9_TEMPORAL_DENOISING),
|
||||||
|
// there is only one denoiser mode: kDenoiserOnYOnly(which is 1),
|
||||||
|
// but may add more modes in the future.
|
||||||
|
cfg_.rc_target_bitrate = 1000;
|
||||||
|
ResetModel();
|
||||||
|
// Turn on the denoiser.
|
||||||
|
denoiser_on_ = 1;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic datarate targeting, for a single bitrate, when denoiser is on,
|
||||||
|
// for 1280x720 clip with 4 threads.
|
||||||
|
TEST_P(DatarateTestVP9LargeDenoiser, 4threads) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 2;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
cfg_.g_threads = 4;
|
||||||
|
|
||||||
|
::libvpx_test::Y4mVideoSource video("niklas_1280_720_30.y4m", 0, 300);
|
||||||
|
|
||||||
|
// For the temporal denoiser (#if CONFIG_VP9_TEMPORAL_DENOISING),
|
||||||
|
// there is only one denoiser mode: denoiserYonly(which is 1),
|
||||||
|
// but may add more modes in the future.
|
||||||
|
cfg_.rc_target_bitrate = 1000;
|
||||||
|
ResetModel();
|
||||||
|
// Turn on the denoiser.
|
||||||
|
denoiser_on_ = 1;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.29)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check basic datarate targeting, for a single bitrate, when denoiser is off
|
||||||
|
// and on.
|
||||||
|
TEST_P(DatarateTestVP9LargeDenoiser, DenoiserOffOn) {
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 500;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_dropframe_thresh = 1;
|
||||||
|
cfg_.rc_min_quantizer = 2;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
|
||||||
|
::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
|
||||||
|
30, 1, 0, 299);
|
||||||
|
|
||||||
|
// For the temporal denoiser (#if CONFIG_VP9_TEMPORAL_DENOISING),
|
||||||
|
// there is only one denoiser mode: denoiserYonly(which is 1),
|
||||||
|
// but may add more modes in the future.
|
||||||
|
cfg_.rc_target_bitrate = 300;
|
||||||
|
ResetModel();
|
||||||
|
// The denoiser is off by default.
|
||||||
|
denoiser_on_ = 0;
|
||||||
|
// Set the offon test flag.
|
||||||
|
denoiser_offon_test_ = 1;
|
||||||
|
denoiser_offon_period_ = 100;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
ASSERT_GE(effective_datarate_[0], cfg_.rc_target_bitrate * 0.85)
|
||||||
|
<< " The datarate for the file is lower than target by too much!";
|
||||||
|
ASSERT_LE(effective_datarate_[0], cfg_.rc_target_bitrate * 1.15)
|
||||||
|
<< " The datarate for the file is greater than target by too much!";
|
||||||
|
}
|
||||||
|
#endif // CONFIG_VP9_TEMPORAL_DENOISING
|
||||||
|
|
||||||
|
VP9_INSTANTIATE_TEST_CASE(DatarateTestVP9Large,
|
||||||
|
::testing::Values(::libvpx_test::kOnePassGood,
|
||||||
|
::libvpx_test::kRealTime),
|
||||||
|
::testing::Range(2, 9), ::testing::Range(0, 4));
|
||||||
|
|
||||||
|
VP9_INSTANTIATE_TEST_CASE(DatarateTestVP9LargeOneBR,
|
||||||
|
::testing::Values(::libvpx_test::kOnePassGood,
|
||||||
|
::libvpx_test::kRealTime),
|
||||||
|
::testing::Range(2, 9));
|
||||||
|
|
||||||
|
VP9_INSTANTIATE_TEST_CASE(DatarateTestVP9RealTime, ::testing::Range(5, 9));
|
||||||
|
|
||||||
|
#if CONFIG_VP9_TEMPORAL_DENOISING
|
||||||
|
VP9_INSTANTIATE_TEST_CASE(DatarateTestVP9LargeDenoiser, ::testing::Range(5, 9));
|
||||||
|
#endif
|
||||||
|
} // namespace
|
@ -29,11 +29,22 @@ using libvpx_test::ACMRandom;
|
|||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
const int kNumPixels = 64 * 64;
|
const int kNumPixels = 64 * 64;
|
||||||
class VP9DenoiserTest : public ::testing::TestWithParam<BLOCK_SIZE> {
|
|
||||||
|
typedef int (*Vp9DenoiserFilterFunc)(const uint8_t *sig, int sig_stride,
|
||||||
|
const uint8_t *mc_avg, int mc_avg_stride,
|
||||||
|
uint8_t *avg, int avg_stride,
|
||||||
|
int increase_denoising, BLOCK_SIZE bs,
|
||||||
|
int motion_magnitude);
|
||||||
|
typedef ::testing::tuple<Vp9DenoiserFilterFunc, BLOCK_SIZE>
|
||||||
|
VP9DenoiserTestParam;
|
||||||
|
|
||||||
|
class VP9DenoiserTest
|
||||||
|
: public ::testing::Test,
|
||||||
|
public ::testing::WithParamInterface<VP9DenoiserTestParam> {
|
||||||
public:
|
public:
|
||||||
virtual ~VP9DenoiserTest() {}
|
virtual ~VP9DenoiserTest() {}
|
||||||
|
|
||||||
virtual void SetUp() { bs_ = GetParam(); }
|
virtual void SetUp() { bs_ = GET_PARAM(1); }
|
||||||
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
||||||
|
|
||||||
@ -76,8 +87,8 @@ TEST_P(VP9DenoiserTest, BitexactCheck) {
|
|||||||
64, avg_block_c, 64, 0, bs_,
|
64, avg_block_c, 64, 0, bs_,
|
||||||
motion_magnitude_random));
|
motion_magnitude_random));
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(vp9_denoiser_filter_sse2(
|
ASM_REGISTER_STATE_CHECK(GET_PARAM(0)(sig_block, 64, mc_avg_block, 64,
|
||||||
sig_block, 64, mc_avg_block, 64, avg_block_sse2, 64, 0, bs_,
|
avg_block_sse2, 64, 0, bs_,
|
||||||
motion_magnitude_random));
|
motion_magnitude_random));
|
||||||
|
|
||||||
// Test bitexactness.
|
// Test bitexactness.
|
||||||
@ -89,10 +100,36 @@ TEST_P(VP9DenoiserTest, BitexactCheck) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
using ::testing::make_tuple;
|
||||||
|
|
||||||
// Test for all block size.
|
// Test for all block size.
|
||||||
INSTANTIATE_TEST_CASE_P(SSE2, VP9DenoiserTest,
|
#if HAVE_SSE2
|
||||||
::testing::Values(BLOCK_8X8, BLOCK_8X16, BLOCK_16X8,
|
INSTANTIATE_TEST_CASE_P(
|
||||||
BLOCK_16X16, BLOCK_16X32, BLOCK_32X16,
|
SSE2, VP9DenoiserTest,
|
||||||
BLOCK_32X32, BLOCK_32X64, BLOCK_64X32,
|
::testing::Values(make_tuple(&vp9_denoiser_filter_sse2, BLOCK_8X8),
|
||||||
BLOCK_64X64));
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_8X16),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_16X8),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_16X16),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_16X32),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_32X16),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_32X32),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_32X64),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_64X32),
|
||||||
|
make_tuple(&vp9_denoiser_filter_sse2, BLOCK_64X64)));
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, VP9DenoiserTest,
|
||||||
|
::testing::Values(make_tuple(&vp9_denoiser_filter_neon, BLOCK_8X8),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_8X16),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_16X8),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_16X16),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_16X32),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_32X16),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_32X32),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_32X64),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_64X32),
|
||||||
|
make_tuple(&vp9_denoiser_filter_neon, BLOCK_64X64)));
|
||||||
|
#endif
|
||||||
} // namespace
|
} // namespace
|
@ -99,9 +99,7 @@ class VpxEncoderParmsGetToDecoder
|
|||||||
vpx_codec_ctx_t *const vp9_decoder = decoder->GetDecoder();
|
vpx_codec_ctx_t *const vp9_decoder = decoder->GetDecoder();
|
||||||
vpx_codec_alg_priv_t *const priv =
|
vpx_codec_alg_priv_t *const priv =
|
||||||
reinterpret_cast<vpx_codec_alg_priv_t *>(vp9_decoder->priv);
|
reinterpret_cast<vpx_codec_alg_priv_t *>(vp9_decoder->priv);
|
||||||
FrameWorkerData *const worker_data =
|
VP9_COMMON *const common = &priv->pbi->common;
|
||||||
reinterpret_cast<FrameWorkerData *>(priv->frame_workers[0].data1);
|
|
||||||
VP9_COMMON *const common = &worker_data->pbi->common;
|
|
||||||
|
|
||||||
if (encode_parms.lossless) {
|
if (encode_parms.lossless) {
|
||||||
EXPECT_EQ(0, common->base_qindex);
|
EXPECT_EQ(0, common->base_qindex);
|
||||||
|
@ -59,7 +59,7 @@ const TestVideoParam kTestVectors[] = {
|
|||||||
// Encoding modes tested
|
// Encoding modes tested
|
||||||
const libvpx_test::TestMode kEncodingModeVectors[] = {
|
const libvpx_test::TestMode kEncodingModeVectors[] = {
|
||||||
::libvpx_test::kTwoPassGood, ::libvpx_test::kOnePassGood,
|
::libvpx_test::kTwoPassGood, ::libvpx_test::kOnePassGood,
|
||||||
::libvpx_test::kRealTime,
|
::libvpx_test::kRealTime
|
||||||
};
|
};
|
||||||
|
|
||||||
// Speed settings tested
|
// Speed settings tested
|
||||||
|
@ -16,8 +16,207 @@
|
|||||||
#include "test/md5_helper.h"
|
#include "test/md5_helper.h"
|
||||||
#include "test/util.h"
|
#include "test/util.h"
|
||||||
#include "test/y4m_video_source.h"
|
#include "test/y4m_video_source.h"
|
||||||
|
#include "vp9/encoder/vp9_firstpass.h"
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
// FIRSTPASS_STATS struct:
|
||||||
|
// {
|
||||||
|
// 25 double members;
|
||||||
|
// 1 int64_t member;
|
||||||
|
// }
|
||||||
|
// Whenever FIRSTPASS_STATS struct is modified, the following constants need to
|
||||||
|
// be revisited.
|
||||||
|
const int kDbl = 25;
|
||||||
|
const int kInt = 1;
|
||||||
|
const size_t kFirstPassStatsSz = kDbl * sizeof(double) + kInt * sizeof(int64_t);
|
||||||
|
|
||||||
|
class VPxFirstPassEncoderThreadTest
|
||||||
|
: public ::libvpx_test::EncoderTest,
|
||||||
|
public ::libvpx_test::CodecTestWith2Params<libvpx_test::TestMode, int> {
|
||||||
|
protected:
|
||||||
|
VPxFirstPassEncoderThreadTest()
|
||||||
|
: EncoderTest(GET_PARAM(0)), encoder_initialized_(false), tiles_(0),
|
||||||
|
encoding_mode_(GET_PARAM(1)), set_cpu_used_(GET_PARAM(2)) {
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
first_pass_only_ = true;
|
||||||
|
firstpass_stats_.buf = NULL;
|
||||||
|
firstpass_stats_.sz = 0;
|
||||||
|
}
|
||||||
|
virtual ~VPxFirstPassEncoderThreadTest() { free(firstpass_stats_.buf); }
|
||||||
|
|
||||||
|
virtual void SetUp() {
|
||||||
|
InitializeConfig();
|
||||||
|
SetMode(encoding_mode_);
|
||||||
|
|
||||||
|
cfg_.rc_end_usage = VPX_VBR;
|
||||||
|
cfg_.rc_2pass_vbr_minsection_pct = 5;
|
||||||
|
cfg_.rc_2pass_vbr_maxsection_pct = 2000;
|
||||||
|
cfg_.rc_max_quantizer = 56;
|
||||||
|
cfg_.rc_min_quantizer = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void BeginPassHook(unsigned int /*pass*/) {
|
||||||
|
encoder_initialized_ = false;
|
||||||
|
abort_ = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void EndPassHook() {
|
||||||
|
// For first pass stats test, only run first pass encoder.
|
||||||
|
if (first_pass_only_ && cfg_.g_pass == VPX_RC_FIRST_PASS)
|
||||||
|
abort_ |= first_pass_only_;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void PreEncodeFrameHook(::libvpx_test::VideoSource * /*video*/,
|
||||||
|
::libvpx_test::Encoder *encoder) {
|
||||||
|
if (!encoder_initialized_) {
|
||||||
|
// Encode in 2-pass mode.
|
||||||
|
encoder->Control(VP9E_SET_TILE_COLUMNS, tiles_);
|
||||||
|
encoder->Control(VP8E_SET_CPUUSED, set_cpu_used_);
|
||||||
|
encoder->Control(VP8E_SET_ENABLEAUTOALTREF, 1);
|
||||||
|
encoder->Control(VP8E_SET_ARNR_MAXFRAMES, 7);
|
||||||
|
encoder->Control(VP8E_SET_ARNR_STRENGTH, 5);
|
||||||
|
encoder->Control(VP8E_SET_ARNR_TYPE, 3);
|
||||||
|
encoder->Control(VP9E_SET_FRAME_PARALLEL_DECODING, 0);
|
||||||
|
|
||||||
|
if (encoding_mode_ == ::libvpx_test::kTwoPassGood)
|
||||||
|
encoder->Control(VP9E_SET_ROW_MT, row_mt_mode_);
|
||||||
|
|
||||||
|
encoder_initialized_ = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void StatsPktHook(const vpx_codec_cx_pkt_t *pkt) {
|
||||||
|
const uint8_t *const pkt_buf =
|
||||||
|
reinterpret_cast<uint8_t *>(pkt->data.twopass_stats.buf);
|
||||||
|
const size_t pkt_size = pkt->data.twopass_stats.sz;
|
||||||
|
|
||||||
|
// First pass stats size equals sizeof(FIRSTPASS_STATS)
|
||||||
|
EXPECT_EQ(pkt_size, kFirstPassStatsSz)
|
||||||
|
<< "Error: First pass stats size doesn't equal kFirstPassStatsSz";
|
||||||
|
|
||||||
|
firstpass_stats_.buf =
|
||||||
|
realloc(firstpass_stats_.buf, firstpass_stats_.sz + pkt_size);
|
||||||
|
memcpy((uint8_t *)firstpass_stats_.buf + firstpass_stats_.sz, pkt_buf,
|
||||||
|
pkt_size);
|
||||||
|
firstpass_stats_.sz += pkt_size;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool encoder_initialized_;
|
||||||
|
int tiles_;
|
||||||
|
::libvpx_test::TestMode encoding_mode_;
|
||||||
|
int set_cpu_used_;
|
||||||
|
int row_mt_mode_;
|
||||||
|
bool first_pass_only_;
|
||||||
|
vpx_fixed_buf_t firstpass_stats_;
|
||||||
|
};
|
||||||
|
|
||||||
|
static void compare_fp_stats(vpx_fixed_buf_t *fp_stats, double factor) {
|
||||||
|
// fp_stats consists of 2 set of first pass encoding stats. These 2 set of
|
||||||
|
// stats are compared to check if the stats match or at least are very close.
|
||||||
|
FIRSTPASS_STATS *stats1 = reinterpret_cast<FIRSTPASS_STATS *>(fp_stats->buf);
|
||||||
|
int nframes_ = (int)(fp_stats->sz / sizeof(FIRSTPASS_STATS));
|
||||||
|
FIRSTPASS_STATS *stats2 = stats1 + nframes_ / 2;
|
||||||
|
int i, j;
|
||||||
|
|
||||||
|
// The total stats are also output and included in the first pass stats. Here
|
||||||
|
// ignore that in the comparison.
|
||||||
|
for (i = 0; i < (nframes_ / 2 - 1); ++i) {
|
||||||
|
const double *frame_stats1 = reinterpret_cast<double *>(stats1);
|
||||||
|
const double *frame_stats2 = reinterpret_cast<double *>(stats2);
|
||||||
|
|
||||||
|
for (j = 0; j < kDbl; ++j) {
|
||||||
|
ASSERT_LE(fabs(*frame_stats1 - *frame_stats2),
|
||||||
|
fabs(*frame_stats1) / factor)
|
||||||
|
<< "First failure @ frame #" << i << " stat #" << j << " ("
|
||||||
|
<< *frame_stats1 << " vs. " << *frame_stats2 << ")";
|
||||||
|
frame_stats1++;
|
||||||
|
frame_stats2++;
|
||||||
|
}
|
||||||
|
|
||||||
|
stats1++;
|
||||||
|
stats2++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Reset firstpass_stats_ to 0.
|
||||||
|
memset((uint8_t *)fp_stats->buf, 0, fp_stats->sz);
|
||||||
|
fp_stats->sz = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void compare_fp_stats_md5(vpx_fixed_buf_t *fp_stats) {
|
||||||
|
// fp_stats consists of 2 set of first pass encoding stats. These 2 set of
|
||||||
|
// stats are compared to check if the stats match.
|
||||||
|
uint8_t *stats1 = reinterpret_cast<uint8_t *>(fp_stats->buf);
|
||||||
|
uint8_t *stats2 = stats1 + fp_stats->sz / 2;
|
||||||
|
::libvpx_test::MD5 md5_row_mt_0, md5_row_mt_1;
|
||||||
|
|
||||||
|
md5_row_mt_0.Add(stats1, fp_stats->sz / 2);
|
||||||
|
const char *md5_row_mt_0_str = md5_row_mt_0.Get();
|
||||||
|
|
||||||
|
md5_row_mt_1.Add(stats2, fp_stats->sz / 2);
|
||||||
|
const char *md5_row_mt_1_str = md5_row_mt_1.Get();
|
||||||
|
|
||||||
|
// Check md5 match.
|
||||||
|
ASSERT_STREQ(md5_row_mt_0_str, md5_row_mt_1_str)
|
||||||
|
<< "MD5 checksums don't match";
|
||||||
|
|
||||||
|
// Reset firstpass_stats_ to 0.
|
||||||
|
memset((uint8_t *)fp_stats->buf, 0, fp_stats->sz);
|
||||||
|
fp_stats->sz = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_P(VPxFirstPassEncoderThreadTest, FirstPassStatsTest) {
|
||||||
|
::libvpx_test::Y4mVideoSource video("niklas_1280_720_30.y4m", 0, 60);
|
||||||
|
|
||||||
|
first_pass_only_ = true;
|
||||||
|
cfg_.rc_target_bitrate = 1000;
|
||||||
|
|
||||||
|
// Test row_mt_mode: 0 vs 1 at single thread case(threads = 1, tiles_ = 0)
|
||||||
|
tiles_ = 0;
|
||||||
|
cfg_.g_threads = 1;
|
||||||
|
|
||||||
|
row_mt_mode_ = 0;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
|
||||||
|
// Compare to check if using or not using row-mt generates close stats.
|
||||||
|
ASSERT_NO_FATAL_FAILURE(compare_fp_stats(&firstpass_stats_, 1000.0));
|
||||||
|
|
||||||
|
// Test single thread vs multiple threads
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
tiles_ = 0;
|
||||||
|
|
||||||
|
cfg_.g_threads = 1;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
|
||||||
|
cfg_.g_threads = 4;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
|
||||||
|
// Compare to check if single-thread and multi-thread stats are close enough.
|
||||||
|
ASSERT_NO_FATAL_FAILURE(compare_fp_stats(&firstpass_stats_, 1000.0));
|
||||||
|
|
||||||
|
// Bit exact test in row_mt mode.
|
||||||
|
// When row_mt_mode_=1 and using >1 threads, the encoder generates bit exact
|
||||||
|
// result.
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
tiles_ = 2;
|
||||||
|
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
|
||||||
|
cfg_.g_threads = 8;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
|
||||||
|
// Compare to check if stats match with row-mt=0/1.
|
||||||
|
compare_fp_stats_md5(&firstpass_stats_);
|
||||||
|
}
|
||||||
|
|
||||||
class VPxEncoderThreadTest
|
class VPxEncoderThreadTest
|
||||||
: public ::libvpx_test::EncoderTest,
|
: public ::libvpx_test::EncoderTest,
|
||||||
public ::libvpx_test::CodecTestWith4Params<libvpx_test::TestMode, int,
|
public ::libvpx_test::CodecTestWith4Params<libvpx_test::TestMode, int,
|
||||||
@ -29,6 +228,9 @@ class VPxEncoderThreadTest
|
|||||||
encoding_mode_(GET_PARAM(1)), set_cpu_used_(GET_PARAM(2)) {
|
encoding_mode_(GET_PARAM(1)), set_cpu_used_(GET_PARAM(2)) {
|
||||||
init_flags_ = VPX_CODEC_USE_PSNR;
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
md5_.clear();
|
md5_.clear();
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
psnr_ = 0.0;
|
||||||
|
nframes_ = 0;
|
||||||
}
|
}
|
||||||
virtual ~VPxEncoderThreadTest() {}
|
virtual ~VPxEncoderThreadTest() {}
|
||||||
|
|
||||||
@ -37,7 +239,6 @@ class VPxEncoderThreadTest
|
|||||||
SetMode(encoding_mode_);
|
SetMode(encoding_mode_);
|
||||||
|
|
||||||
if (encoding_mode_ != ::libvpx_test::kRealTime) {
|
if (encoding_mode_ != ::libvpx_test::kRealTime) {
|
||||||
cfg_.g_lag_in_frames = 3;
|
|
||||||
cfg_.rc_end_usage = VPX_VBR;
|
cfg_.rc_end_usage = VPX_VBR;
|
||||||
cfg_.rc_2pass_vbr_minsection_pct = 5;
|
cfg_.rc_2pass_vbr_minsection_pct = 5;
|
||||||
cfg_.rc_2pass_vbr_maxsection_pct = 2000;
|
cfg_.rc_2pass_vbr_maxsection_pct = 2000;
|
||||||
@ -52,6 +253,8 @@ class VPxEncoderThreadTest
|
|||||||
|
|
||||||
virtual void BeginPassHook(unsigned int /*pass*/) {
|
virtual void BeginPassHook(unsigned int /*pass*/) {
|
||||||
encoder_initialized_ = false;
|
encoder_initialized_ = false;
|
||||||
|
psnr_ = 0.0;
|
||||||
|
nframes_ = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void PreEncodeFrameHook(::libvpx_test::VideoSource * /*video*/,
|
virtual void PreEncodeFrameHook(::libvpx_test::VideoSource * /*video*/,
|
||||||
@ -70,10 +273,17 @@ class VPxEncoderThreadTest
|
|||||||
encoder->Control(VP8E_SET_ENABLEAUTOALTREF, 0);
|
encoder->Control(VP8E_SET_ENABLEAUTOALTREF, 0);
|
||||||
encoder->Control(VP9E_SET_AQ_MODE, 3);
|
encoder->Control(VP9E_SET_AQ_MODE, 3);
|
||||||
}
|
}
|
||||||
|
encoder->Control(VP9E_SET_ROW_MT, row_mt_mode_);
|
||||||
|
|
||||||
encoder_initialized_ = true;
|
encoder_initialized_ = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual void PSNRPktHook(const vpx_codec_cx_pkt_t *pkt) {
|
||||||
|
psnr_ += pkt->data.psnr.psnr[0];
|
||||||
|
nframes_++;
|
||||||
|
}
|
||||||
|
|
||||||
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
virtual void DecompressedFrameHook(const vpx_image_t &img,
|
||||||
vpx_codec_pts_t /*pts*/) {
|
vpx_codec_pts_t /*pts*/) {
|
||||||
::libvpx_test::MD5 md5_res;
|
::libvpx_test::MD5 md5_res;
|
||||||
@ -92,43 +302,127 @@ class VPxEncoderThreadTest
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
double GetAveragePsnr() const { return nframes_ ? (psnr_ / nframes_) : 0.0; }
|
||||||
|
|
||||||
bool encoder_initialized_;
|
bool encoder_initialized_;
|
||||||
int tiles_;
|
int tiles_;
|
||||||
int threads_;
|
int threads_;
|
||||||
::libvpx_test::TestMode encoding_mode_;
|
::libvpx_test::TestMode encoding_mode_;
|
||||||
int set_cpu_used_;
|
int set_cpu_used_;
|
||||||
|
int row_mt_mode_;
|
||||||
|
double psnr_;
|
||||||
|
unsigned int nframes_;
|
||||||
std::vector<std::string> md5_;
|
std::vector<std::string> md5_;
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST_P(VPxEncoderThreadTest, EncoderResultTest) {
|
TEST_P(VPxEncoderThreadTest, EncoderResultTest) {
|
||||||
std::vector<std::string> single_thr_md5, multi_thr_md5;
|
|
||||||
|
|
||||||
::libvpx_test::Y4mVideoSource video("niklas_1280_720_30.y4m", 15, 20);
|
::libvpx_test::Y4mVideoSource video("niklas_1280_720_30.y4m", 15, 20);
|
||||||
|
|
||||||
cfg_.rc_target_bitrate = 1000;
|
cfg_.rc_target_bitrate = 1000;
|
||||||
|
|
||||||
|
// Part 1: Bit exact test for row_mt_mode_ = 0.
|
||||||
|
// This part keeps original unit tests done before row-mt code is checked in.
|
||||||
|
row_mt_mode_ = 0;
|
||||||
|
|
||||||
// Encode using single thread.
|
// Encode using single thread.
|
||||||
cfg_.g_threads = 1;
|
cfg_.g_threads = 1;
|
||||||
init_flags_ = VPX_CODEC_USE_PSNR;
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
single_thr_md5 = md5_;
|
const std::vector<std::string> single_thr_md5 = md5_;
|
||||||
md5_.clear();
|
md5_.clear();
|
||||||
|
|
||||||
// Encode using multiple threads.
|
// Encode using multiple threads.
|
||||||
cfg_.g_threads = threads_;
|
cfg_.g_threads = threads_;
|
||||||
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
multi_thr_md5 = md5_;
|
const std::vector<std::string> multi_thr_md5 = md5_;
|
||||||
md5_.clear();
|
md5_.clear();
|
||||||
|
|
||||||
// Compare to check if two vectors are equal.
|
// Compare to check if two vectors are equal.
|
||||||
ASSERT_EQ(single_thr_md5, multi_thr_md5);
|
ASSERT_EQ(single_thr_md5, multi_thr_md5);
|
||||||
|
|
||||||
|
// Part 2: row_mt_mode_ = 0 vs row_mt_mode_ = 1 single thread bit exact test.
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
|
||||||
|
// Encode using single thread
|
||||||
|
cfg_.g_threads = 1;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
std::vector<std::string> row_mt_single_thr_md5 = md5_;
|
||||||
|
md5_.clear();
|
||||||
|
|
||||||
|
ASSERT_EQ(single_thr_md5, row_mt_single_thr_md5);
|
||||||
|
|
||||||
|
// Part 3: Bit exact test with row-mt on
|
||||||
|
// When row_mt_mode_=1 and using >1 threads, the encoder generates bit exact
|
||||||
|
// result.
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
row_mt_single_thr_md5.clear();
|
||||||
|
|
||||||
|
// Encode using 2 threads.
|
||||||
|
cfg_.g_threads = 2;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
row_mt_single_thr_md5 = md5_;
|
||||||
|
md5_.clear();
|
||||||
|
|
||||||
|
// Encode using multiple threads.
|
||||||
|
cfg_.g_threads = threads_;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
const std::vector<std::string> row_mt_multi_thr_md5 = md5_;
|
||||||
|
md5_.clear();
|
||||||
|
|
||||||
|
// Compare to check if two vectors are equal.
|
||||||
|
ASSERT_EQ(row_mt_single_thr_md5, row_mt_multi_thr_md5);
|
||||||
|
|
||||||
|
// Part 4: PSNR test with bit_match_mode_ = 0
|
||||||
|
row_mt_mode_ = 1;
|
||||||
|
|
||||||
|
// Encode using single thread.
|
||||||
|
cfg_.g_threads = 1;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
const double single_thr_psnr = GetAveragePsnr();
|
||||||
|
|
||||||
|
// Encode using multiple threads.
|
||||||
|
cfg_.g_threads = threads_;
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
|
||||||
|
const double multi_thr_psnr = GetAveragePsnr();
|
||||||
|
|
||||||
|
EXPECT_NEAR(single_thr_psnr, multi_thr_psnr, 0.1);
|
||||||
}
|
}
|
||||||
|
|
||||||
VP9_INSTANTIATE_TEST_CASE(VPxEncoderThreadTest,
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
VP9, VPxFirstPassEncoderThreadTest,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Values(
|
||||||
|
static_cast<const libvpx_test::CodecFactory *>(&libvpx_test::kVP9)),
|
||||||
|
::testing::Values(::libvpx_test::kTwoPassGood),
|
||||||
|
::testing::Range(0, 4))); // cpu_used
|
||||||
|
|
||||||
|
// Split this into two instantiations so that we can distinguish
|
||||||
|
// between very slow runs ( ie cpu_speed 0 ) vs ones that can be
|
||||||
|
// run nightly by adding Large to the title.
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
VP9, VPxEncoderThreadTest,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Values(
|
||||||
|
static_cast<const libvpx_test::CodecFactory *>(&libvpx_test::kVP9)),
|
||||||
::testing::Values(::libvpx_test::kTwoPassGood,
|
::testing::Values(::libvpx_test::kTwoPassGood,
|
||||||
::libvpx_test::kOnePassGood,
|
::libvpx_test::kOnePassGood,
|
||||||
::libvpx_test::kRealTime),
|
::libvpx_test::kRealTime),
|
||||||
::testing::Range(0, 9), // cpu_used
|
::testing::Range(3, 9), // cpu_used
|
||||||
::testing::Range(0, 3), // tile_columns
|
::testing::Range(0, 3), // tile_columns
|
||||||
::testing::Range(2, 5)); // threads
|
::testing::Range(2, 5))); // threads
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
VP9Large, VPxEncoderThreadTest,
|
||||||
|
::testing::Combine(
|
||||||
|
::testing::Values(
|
||||||
|
static_cast<const libvpx_test::CodecFactory *>(&libvpx_test::kVP9)),
|
||||||
|
::testing::Values(::libvpx_test::kTwoPassGood,
|
||||||
|
::libvpx_test::kOnePassGood,
|
||||||
|
::libvpx_test::kRealTime),
|
||||||
|
::testing::Range(0, 3), // cpu_used
|
||||||
|
::testing::Range(0, 3), // tile_columns
|
||||||
|
::testing::Range(2, 5))); // threads
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
@ -1,217 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (c) 2014 The WebM project authors. All Rights Reserved.
|
|
||||||
*
|
|
||||||
* Use of this source code is governed by a BSD-style license
|
|
||||||
* that can be found in the LICENSE file in the root of the source
|
|
||||||
* tree. An additional intellectual property rights grant can be found
|
|
||||||
* in the file PATENTS. All contributing project authors may
|
|
||||||
* be found in the AUTHORS file in the root of the source tree.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <cstdio>
|
|
||||||
#include <cstdlib>
|
|
||||||
#include <string>
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
|
||||||
#include "./vpx_config.h"
|
|
||||||
#include "test/codec_factory.h"
|
|
||||||
#include "test/decode_test_driver.h"
|
|
||||||
#include "test/ivf_video_source.h"
|
|
||||||
#include "test/md5_helper.h"
|
|
||||||
#include "test/util.h"
|
|
||||||
#if CONFIG_WEBM_IO
|
|
||||||
#include "test/webm_video_source.h"
|
|
||||||
#endif
|
|
||||||
#include "vpx_mem/vpx_mem.h"
|
|
||||||
|
|
||||||
namespace {
|
|
||||||
|
|
||||||
using std::string;
|
|
||||||
|
|
||||||
#if CONFIG_WEBM_IO
|
|
||||||
|
|
||||||
struct PauseFileList {
|
|
||||||
const char *name;
|
|
||||||
// md5 sum for decoded frames which does not include skipped frames.
|
|
||||||
const char *expected_md5;
|
|
||||||
const int pause_frame_num;
|
|
||||||
};
|
|
||||||
|
|
||||||
// Decodes |filename| with |num_threads|. Pause at the specified frame_num,
|
|
||||||
// seek to next key frame and then continue decoding until the end. Return
|
|
||||||
// the md5 of the decoded frames which does not include skipped frames.
|
|
||||||
string DecodeFileWithPause(const string &filename, int num_threads,
|
|
||||||
int pause_num) {
|
|
||||||
libvpx_test::WebMVideoSource video(filename);
|
|
||||||
video.Init();
|
|
||||||
int in_frames = 0;
|
|
||||||
int out_frames = 0;
|
|
||||||
|
|
||||||
vpx_codec_dec_cfg_t cfg = vpx_codec_dec_cfg_t();
|
|
||||||
cfg.threads = num_threads;
|
|
||||||
vpx_codec_flags_t flags = 0;
|
|
||||||
flags |= VPX_CODEC_USE_FRAME_THREADING;
|
|
||||||
libvpx_test::VP9Decoder decoder(cfg, flags);
|
|
||||||
|
|
||||||
libvpx_test::MD5 md5;
|
|
||||||
video.Begin();
|
|
||||||
|
|
||||||
do {
|
|
||||||
++in_frames;
|
|
||||||
const vpx_codec_err_t res =
|
|
||||||
decoder.DecodeFrame(video.cxdata(), video.frame_size());
|
|
||||||
if (res != VPX_CODEC_OK) {
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res) << decoder.DecodeError();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Pause at specified frame number.
|
|
||||||
if (in_frames == pause_num) {
|
|
||||||
// Flush the decoder and then seek to next key frame.
|
|
||||||
decoder.DecodeFrame(NULL, 0);
|
|
||||||
video.SeekToNextKeyFrame();
|
|
||||||
} else {
|
|
||||||
video.Next();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Flush the decoder at the end of the video.
|
|
||||||
if (!video.cxdata()) decoder.DecodeFrame(NULL, 0);
|
|
||||||
|
|
||||||
libvpx_test::DxDataIterator dec_iter = decoder.GetDxData();
|
|
||||||
const vpx_image_t *img;
|
|
||||||
|
|
||||||
// Get decompressed data
|
|
||||||
while ((img = dec_iter.Next())) {
|
|
||||||
++out_frames;
|
|
||||||
md5.Add(img);
|
|
||||||
}
|
|
||||||
} while (video.cxdata() != NULL);
|
|
||||||
|
|
||||||
EXPECT_EQ(in_frames, out_frames)
|
|
||||||
<< "Input frame count does not match output frame count";
|
|
||||||
|
|
||||||
return string(md5.Get());
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecodeFilesWithPause(const PauseFileList files[]) {
|
|
||||||
for (const PauseFileList *iter = files; iter->name != NULL; ++iter) {
|
|
||||||
SCOPED_TRACE(iter->name);
|
|
||||||
for (int t = 2; t <= 8; ++t) {
|
|
||||||
EXPECT_EQ(iter->expected_md5,
|
|
||||||
DecodeFileWithPause(iter->name, t, iter->pause_frame_num))
|
|
||||||
<< "threads = " << t;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST(VP9MultiThreadedFrameParallel, PauseSeekResume) {
|
|
||||||
// vp90-2-07-frame_parallel-1.webm is a 40 frame video file with
|
|
||||||
// one key frame for every ten frames.
|
|
||||||
static const PauseFileList files[] = {
|
|
||||||
{ "vp90-2-07-frame_parallel-1.webm", "6ea7c3875d67252e7caf2bc6e75b36b1",
|
|
||||||
6 },
|
|
||||||
{ "vp90-2-07-frame_parallel-1.webm", "4bb634160c7356a8d7d4299b6dc83a45",
|
|
||||||
12 },
|
|
||||||
{ "vp90-2-07-frame_parallel-1.webm", "89772591e6ef461f9fa754f916c78ed8",
|
|
||||||
26 },
|
|
||||||
{ NULL, NULL, 0 },
|
|
||||||
};
|
|
||||||
DecodeFilesWithPause(files);
|
|
||||||
}
|
|
||||||
|
|
||||||
struct FileList {
|
|
||||||
const char *name;
|
|
||||||
// md5 sum for decoded frames which does not include corrupted frames.
|
|
||||||
const char *expected_md5;
|
|
||||||
// Expected number of decoded frames which does not include corrupted frames.
|
|
||||||
const int expected_frame_count;
|
|
||||||
};
|
|
||||||
|
|
||||||
// Decodes |filename| with |num_threads|. Return the md5 of the decoded
|
|
||||||
// frames which does not include corrupted frames.
|
|
||||||
string DecodeFile(const string &filename, int num_threads,
|
|
||||||
int expected_frame_count) {
|
|
||||||
libvpx_test::WebMVideoSource video(filename);
|
|
||||||
video.Init();
|
|
||||||
|
|
||||||
vpx_codec_dec_cfg_t cfg = vpx_codec_dec_cfg_t();
|
|
||||||
cfg.threads = num_threads;
|
|
||||||
const vpx_codec_flags_t flags = VPX_CODEC_USE_FRAME_THREADING;
|
|
||||||
libvpx_test::VP9Decoder decoder(cfg, flags);
|
|
||||||
|
|
||||||
libvpx_test::MD5 md5;
|
|
||||||
video.Begin();
|
|
||||||
|
|
||||||
int out_frames = 0;
|
|
||||||
do {
|
|
||||||
const vpx_codec_err_t res =
|
|
||||||
decoder.DecodeFrame(video.cxdata(), video.frame_size());
|
|
||||||
// TODO(hkuang): frame parallel mode should return an error on corruption.
|
|
||||||
if (res != VPX_CODEC_OK) {
|
|
||||||
EXPECT_EQ(VPX_CODEC_OK, res) << decoder.DecodeError();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
video.Next();
|
|
||||||
|
|
||||||
// Flush the decoder at the end of the video.
|
|
||||||
if (!video.cxdata()) decoder.DecodeFrame(NULL, 0);
|
|
||||||
|
|
||||||
libvpx_test::DxDataIterator dec_iter = decoder.GetDxData();
|
|
||||||
const vpx_image_t *img;
|
|
||||||
|
|
||||||
// Get decompressed data
|
|
||||||
while ((img = dec_iter.Next())) {
|
|
||||||
++out_frames;
|
|
||||||
md5.Add(img);
|
|
||||||
}
|
|
||||||
} while (video.cxdata() != NULL);
|
|
||||||
|
|
||||||
EXPECT_EQ(expected_frame_count, out_frames)
|
|
||||||
<< "Input frame count does not match expected output frame count";
|
|
||||||
|
|
||||||
return string(md5.Get());
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecodeFiles(const FileList files[]) {
|
|
||||||
for (const FileList *iter = files; iter->name != NULL; ++iter) {
|
|
||||||
SCOPED_TRACE(iter->name);
|
|
||||||
for (int t = 2; t <= 8; ++t) {
|
|
||||||
EXPECT_EQ(iter->expected_md5,
|
|
||||||
DecodeFile(iter->name, t, iter->expected_frame_count))
|
|
||||||
<< "threads = " << t;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST(VP9MultiThreadedFrameParallel, InvalidFileTest) {
|
|
||||||
static const FileList files[] = {
|
|
||||||
// invalid-vp90-2-07-frame_parallel-1.webm is a 40 frame video file with
|
|
||||||
// one key frame for every ten frames. The 11th frame has corrupted data.
|
|
||||||
{ "invalid-vp90-2-07-frame_parallel-1.webm",
|
|
||||||
"0549d0f45f60deaef8eb708e6c0eb6cb", 30 },
|
|
||||||
// invalid-vp90-2-07-frame_parallel-2.webm is a 40 frame video file with
|
|
||||||
// one key frame for every ten frames. The 1st and 31st frames have
|
|
||||||
// corrupted data.
|
|
||||||
{ "invalid-vp90-2-07-frame_parallel-2.webm",
|
|
||||||
"6a1f3cf6f9e7a364212fadb9580d525e", 20 },
|
|
||||||
// invalid-vp90-2-07-frame_parallel-3.webm is a 40 frame video file with
|
|
||||||
// one key frame for every ten frames. The 5th and 13th frames have
|
|
||||||
// corrupted data.
|
|
||||||
{ "invalid-vp90-2-07-frame_parallel-3.webm",
|
|
||||||
"8256544308de926b0681e04685b98677", 27 },
|
|
||||||
{ NULL, NULL, 0 },
|
|
||||||
};
|
|
||||||
DecodeFiles(files);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST(VP9MultiThreadedFrameParallel, ValidFileTest) {
|
|
||||||
static const FileList files[] = {
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
{ "vp92-2-20-10bit-yuv420.webm", "a16b99df180c584e8db2ffeda987d293", 10 },
|
|
||||||
#endif
|
|
||||||
{ NULL, NULL, 0 },
|
|
||||||
};
|
|
||||||
DecodeFiles(files);
|
|
||||||
}
|
|
||||||
#endif // CONFIG_WEBM_IO
|
|
||||||
} // namespace
|
|
@ -235,8 +235,16 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
8),
|
8),
|
||||||
IntraPredParam(&vpx_d45_predictor_16x16_neon,
|
IntraPredParam(&vpx_d45_predictor_16x16_neon,
|
||||||
&vpx_d45_predictor_16x16_c, 16, 8),
|
&vpx_d45_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_d45_predictor_32x32_neon,
|
||||||
|
&vpx_d45_predictor_32x32_c, 32, 8),
|
||||||
IntraPredParam(&vpx_d135_predictor_4x4_neon, &vpx_d135_predictor_4x4_c,
|
IntraPredParam(&vpx_d135_predictor_4x4_neon, &vpx_d135_predictor_4x4_c,
|
||||||
4, 8),
|
4, 8),
|
||||||
|
IntraPredParam(&vpx_d135_predictor_8x8_neon, &vpx_d135_predictor_8x8_c,
|
||||||
|
8, 8),
|
||||||
|
IntraPredParam(&vpx_d135_predictor_16x16_neon,
|
||||||
|
&vpx_d135_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_d135_predictor_32x32_neon,
|
||||||
|
&vpx_d135_predictor_32x32_c, 32, 8),
|
||||||
IntraPredParam(&vpx_dc_128_predictor_4x4_neon,
|
IntraPredParam(&vpx_dc_128_predictor_4x4_neon,
|
||||||
&vpx_dc_128_predictor_4x4_c, 4, 8),
|
&vpx_dc_128_predictor_4x4_c, 4, 8),
|
||||||
IntraPredParam(&vpx_dc_128_predictor_8x8_neon,
|
IntraPredParam(&vpx_dc_128_predictor_8x8_neon,
|
||||||
@ -291,6 +299,139 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
32, 8)));
|
32, 8)));
|
||||||
#endif // HAVE_NEON
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
#if HAVE_DSPR2
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
DSPR2, VP9IntraPredTest,
|
||||||
|
::testing::Values(IntraPredParam(&vpx_dc_predictor_4x4_dspr2,
|
||||||
|
&vpx_dc_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_8x8_dspr2,
|
||||||
|
&vpx_dc_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_16x16_dspr2,
|
||||||
|
&vpx_dc_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_4x4_dspr2,
|
||||||
|
&vpx_h_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_8x8_dspr2,
|
||||||
|
&vpx_h_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_16x16_dspr2,
|
||||||
|
&vpx_h_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_4x4_dspr2,
|
||||||
|
&vpx_tm_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_8x8_dspr2,
|
||||||
|
&vpx_tm_predictor_8x8_c, 8, 8)));
|
||||||
|
#endif // HAVE_DSPR2
|
||||||
|
|
||||||
|
#if HAVE_MSA
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
MSA, VP9IntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
IntraPredParam(&vpx_dc_128_predictor_4x4_msa,
|
||||||
|
&vpx_dc_128_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_dc_128_predictor_8x8_msa,
|
||||||
|
&vpx_dc_128_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_dc_128_predictor_16x16_msa,
|
||||||
|
&vpx_dc_128_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_128_predictor_32x32_msa,
|
||||||
|
&vpx_dc_128_predictor_32x32_c, 32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_left_predictor_4x4_msa,
|
||||||
|
&vpx_dc_left_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_dc_left_predictor_8x8_msa,
|
||||||
|
&vpx_dc_left_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_dc_left_predictor_16x16_msa,
|
||||||
|
&vpx_dc_left_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_left_predictor_32x32_msa,
|
||||||
|
&vpx_dc_left_predictor_32x32_c, 32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_4x4_msa, &vpx_dc_predictor_4x4_c, 4,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_8x8_msa, &vpx_dc_predictor_8x8_c, 8,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_16x16_msa, &vpx_dc_predictor_16x16_c,
|
||||||
|
16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_32x32_msa, &vpx_dc_predictor_32x32_c,
|
||||||
|
32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_top_predictor_4x4_msa,
|
||||||
|
&vpx_dc_top_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_dc_top_predictor_8x8_msa,
|
||||||
|
&vpx_dc_top_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_dc_top_predictor_16x16_msa,
|
||||||
|
&vpx_dc_top_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_top_predictor_32x32_msa,
|
||||||
|
&vpx_dc_top_predictor_32x32_c, 32, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_4x4_msa, &vpx_h_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_8x8_msa, &vpx_h_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_16x16_msa, &vpx_h_predictor_16x16_c, 16,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_32x32_msa, &vpx_h_predictor_32x32_c, 32,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_4x4_msa, &vpx_tm_predictor_4x4_c, 4,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_8x8_msa, &vpx_tm_predictor_8x8_c, 8,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_16x16_msa, &vpx_tm_predictor_16x16_c,
|
||||||
|
16, 8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_32x32_msa, &vpx_tm_predictor_32x32_c,
|
||||||
|
32, 8),
|
||||||
|
IntraPredParam(&vpx_v_predictor_4x4_msa, &vpx_v_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_v_predictor_8x8_msa, &vpx_v_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_v_predictor_16x16_msa, &vpx_v_predictor_16x16_c, 16,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_v_predictor_32x32_msa, &vpx_v_predictor_32x32_c, 32,
|
||||||
|
8)));
|
||||||
|
#endif // HAVE_MSA
|
||||||
|
|
||||||
|
#if HAVE_VSX
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
VSX, VP9IntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
IntraPredParam(&vpx_d45_predictor_8x8_vsx, &vpx_d45_predictor_8x8_c, 8,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_d45_predictor_16x16_vsx, &vpx_d45_predictor_16x16_c,
|
||||||
|
16, 8),
|
||||||
|
IntraPredParam(&vpx_d45_predictor_32x32_vsx, &vpx_d45_predictor_32x32_c,
|
||||||
|
32, 8),
|
||||||
|
IntraPredParam(&vpx_d63_predictor_8x8_vsx, &vpx_d63_predictor_8x8_c, 8,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_d63_predictor_16x16_vsx, &vpx_d63_predictor_16x16_c,
|
||||||
|
16, 8),
|
||||||
|
IntraPredParam(&vpx_d63_predictor_32x32_vsx, &vpx_d63_predictor_32x32_c,
|
||||||
|
32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_128_predictor_16x16_vsx,
|
||||||
|
&vpx_dc_128_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_128_predictor_32x32_vsx,
|
||||||
|
&vpx_dc_128_predictor_32x32_c, 32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_left_predictor_16x16_vsx,
|
||||||
|
&vpx_dc_left_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_left_predictor_32x32_vsx,
|
||||||
|
&vpx_dc_left_predictor_32x32_c, 32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_8x8_vsx, &vpx_dc_predictor_8x8_c, 8,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_16x16_vsx, &vpx_dc_predictor_16x16_c,
|
||||||
|
16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_predictor_32x32_vsx, &vpx_dc_predictor_32x32_c,
|
||||||
|
32, 8),
|
||||||
|
IntraPredParam(&vpx_dc_top_predictor_16x16_vsx,
|
||||||
|
&vpx_dc_top_predictor_16x16_c, 16, 8),
|
||||||
|
IntraPredParam(&vpx_dc_top_predictor_32x32_vsx,
|
||||||
|
&vpx_dc_top_predictor_32x32_c, 32, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_4x4_vsx, &vpx_h_predictor_4x4_c, 4, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_8x8_vsx, &vpx_h_predictor_8x8_c, 8, 8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_16x16_vsx, &vpx_h_predictor_16x16_c, 16,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_h_predictor_32x32_vsx, &vpx_h_predictor_32x32_c, 32,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_4x4_vsx, &vpx_tm_predictor_4x4_c, 4,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_8x8_vsx, &vpx_tm_predictor_8x8_c, 8,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_16x16_vsx, &vpx_tm_predictor_16x16_c,
|
||||||
|
16, 8),
|
||||||
|
IntraPredParam(&vpx_tm_predictor_32x32_vsx, &vpx_tm_predictor_32x32_c,
|
||||||
|
32, 8),
|
||||||
|
IntraPredParam(&vpx_v_predictor_16x16_vsx, &vpx_v_predictor_16x16_c, 16,
|
||||||
|
8),
|
||||||
|
IntraPredParam(&vpx_v_predictor_32x32_vsx, &vpx_v_predictor_32x32_c, 32,
|
||||||
|
8)));
|
||||||
|
#endif // HAVE_VSX
|
||||||
|
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
typedef void (*HighbdIntraPred)(uint16_t *dst, ptrdiff_t stride,
|
typedef void (*HighbdIntraPred)(uint16_t *dst, ptrdiff_t stride,
|
||||||
const uint16_t *above, const uint16_t *left,
|
const uint16_t *above, const uint16_t *left,
|
||||||
@ -326,10 +467,164 @@ TEST_P(VP9HighbdIntraPredTest, HighbdIntraPredTests) {
|
|||||||
RunTest(left_col, above_data, dst, ref_dst);
|
RunTest(left_col, above_data, dst, ref_dst);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if HAVE_SSSE3
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSSE3_TO_C_8, VP9HighbdIntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_4x4_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d63_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d63_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_32x32_c,
|
||||||
|
&vpx_highbd_d63_predictor_32x32_ssse3, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d117_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d117_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_32x32_c,
|
||||||
|
&vpx_highbd_d117_predictor_32x32_ssse3, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_32x32_c, 32, 8)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSSE3_TO_C_10, VP9HighbdIntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_4x4_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d63_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d63_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_32x32_c,
|
||||||
|
&vpx_highbd_d63_predictor_32x32_ssse3, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d117_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d117_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_32x32_c,
|
||||||
|
&vpx_highbd_d117_predictor_32x32_ssse3, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_32x32_c, 32, 10)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSSE3_TO_C_12, VP9HighbdIntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_4x4_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d45_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d63_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d63_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_32x32_c,
|
||||||
|
&vpx_highbd_d63_predictor_32x32_ssse3, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d117_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d117_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_32x32_c,
|
||||||
|
&vpx_highbd_d117_predictor_32x32_ssse3, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d135_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d153_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_8x8_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_16x16_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_32x32_ssse3,
|
||||||
|
&vpx_highbd_d207_predictor_32x32_c, 32, 12)));
|
||||||
|
#endif // HAVE_SSSE3
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2_TO_C_8, VP9HighbdIntraPredTest,
|
SSE2_TO_C_8, VP9HighbdIntraPredTest,
|
||||||
::testing::Values(
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d63_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d117_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d135_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d153_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d207_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_32x32_c, 32, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_sse2,
|
||||||
&vpx_highbd_dc_predictor_4x4_c, 4, 8),
|
&vpx_highbd_dc_predictor_4x4_c, 4, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_sse2,
|
||||||
@ -338,6 +633,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_dc_predictor_16x16_c, 16, 8),
|
&vpx_highbd_dc_predictor_16x16_c, 16, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_sse2,
|
||||||
&vpx_highbd_dc_predictor_32x32_c, 32, 8),
|
&vpx_highbd_dc_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_32x32_c, 32, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_sse2,
|
||||||
&vpx_highbd_tm_predictor_4x4_c, 4, 8),
|
&vpx_highbd_tm_predictor_4x4_c, 4, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_sse2,
|
||||||
@ -346,6 +649,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_tm_predictor_16x16_c, 16, 8),
|
&vpx_highbd_tm_predictor_16x16_c, 16, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_sse2,
|
||||||
&vpx_highbd_tm_predictor_32x32_c, 32, 8),
|
&vpx_highbd_tm_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_h_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_h_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_h_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_h_predictor_32x32_c, 32, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_sse2,
|
||||||
&vpx_highbd_v_predictor_4x4_c, 4, 8),
|
&vpx_highbd_v_predictor_4x4_c, 4, 8),
|
||||||
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_sse2,
|
||||||
@ -358,6 +669,32 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2_TO_C_10, VP9HighbdIntraPredTest,
|
SSE2_TO_C_10, VP9HighbdIntraPredTest,
|
||||||
::testing::Values(
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d63_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d117_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d135_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d153_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d207_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_32x32_c, 32, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_sse2,
|
||||||
&vpx_highbd_dc_predictor_4x4_c, 4, 10),
|
&vpx_highbd_dc_predictor_4x4_c, 4, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_sse2,
|
||||||
@ -366,6 +703,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_dc_predictor_16x16_c, 16, 10),
|
&vpx_highbd_dc_predictor_16x16_c, 16, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_sse2,
|
||||||
&vpx_highbd_dc_predictor_32x32_c, 32, 10),
|
&vpx_highbd_dc_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_32x32_c, 32, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_sse2,
|
||||||
&vpx_highbd_tm_predictor_4x4_c, 4, 10),
|
&vpx_highbd_tm_predictor_4x4_c, 4, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_sse2,
|
||||||
@ -374,6 +719,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_tm_predictor_16x16_c, 16, 10),
|
&vpx_highbd_tm_predictor_16x16_c, 16, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_sse2,
|
||||||
&vpx_highbd_tm_predictor_32x32_c, 32, 10),
|
&vpx_highbd_tm_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_h_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_h_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_h_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_h_predictor_32x32_c, 32, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_sse2,
|
||||||
&vpx_highbd_v_predictor_4x4_c, 4, 10),
|
&vpx_highbd_v_predictor_4x4_c, 4, 10),
|
||||||
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_sse2,
|
||||||
@ -386,6 +739,32 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2_TO_C_12, VP9HighbdIntraPredTest,
|
SSE2_TO_C_12, VP9HighbdIntraPredTest,
|
||||||
::testing::Values(
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_128_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d63_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d63_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d117_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d117_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d135_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d153_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d153_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d207_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_d207_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_left_predictor_32x32_c, 32, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_sse2,
|
||||||
&vpx_highbd_dc_predictor_4x4_c, 4, 12),
|
&vpx_highbd_dc_predictor_4x4_c, 4, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_sse2,
|
||||||
@ -394,6 +773,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_dc_predictor_16x16_c, 16, 12),
|
&vpx_highbd_dc_predictor_16x16_c, 16, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_sse2,
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_sse2,
|
||||||
&vpx_highbd_dc_predictor_32x32_c, 32, 12),
|
&vpx_highbd_dc_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_dc_top_predictor_32x32_c, 32, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_sse2,
|
||||||
&vpx_highbd_tm_predictor_4x4_c, 4, 12),
|
&vpx_highbd_tm_predictor_4x4_c, 4, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_sse2,
|
||||||
@ -402,6 +789,14 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_tm_predictor_16x16_c, 16, 12),
|
&vpx_highbd_tm_predictor_16x16_c, 16, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_sse2,
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_sse2,
|
||||||
&vpx_highbd_tm_predictor_32x32_c, 32, 12),
|
&vpx_highbd_tm_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_4x4_sse2,
|
||||||
|
&vpx_highbd_h_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_8x8_sse2,
|
||||||
|
&vpx_highbd_h_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_16x16_sse2,
|
||||||
|
&vpx_highbd_h_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_32x32_sse2,
|
||||||
|
&vpx_highbd_h_predictor_32x32_c, 32, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_sse2,
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_sse2,
|
||||||
&vpx_highbd_v_predictor_4x4_c, 4, 12),
|
&vpx_highbd_v_predictor_4x4_c, 4, 12),
|
||||||
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_sse2,
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_sse2,
|
||||||
@ -412,5 +807,235 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
&vpx_highbd_v_predictor_32x32_c, 32, 12)));
|
&vpx_highbd_v_predictor_32x32_c, 32, 12)));
|
||||||
#endif // HAVE_SSE2
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON_TO_C_8, VP9HighbdIntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_d45_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_d45_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_d45_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_d45_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_d135_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_d135_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_d135_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_d135_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_h_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_h_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_h_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_h_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_tm_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_tm_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_tm_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_tm_predictor_32x32_c, 32, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_v_predictor_4x4_c, 4, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_v_predictor_8x8_c, 8, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_v_predictor_16x16_c, 16, 8),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_v_predictor_32x32_c, 32, 8)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON_TO_C_10, VP9HighbdIntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_d45_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_d45_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_d45_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_d45_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_d135_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_d135_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_d135_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_d135_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_h_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_h_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_h_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_h_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_tm_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_tm_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_tm_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_tm_predictor_32x32_c, 32, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_v_predictor_4x4_c, 4, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_v_predictor_8x8_c, 8, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_v_predictor_16x16_c, 16, 10),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_v_predictor_32x32_c, 32, 10)));
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON_TO_C_12, VP9HighbdIntraPredTest,
|
||||||
|
::testing::Values(
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_d45_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_d45_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_d45_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d45_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_d45_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_d135_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_d135_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_d135_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_d135_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_d135_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_128_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_128_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_left_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_left_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_dc_top_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_dc_top_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_h_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_h_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_h_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_h_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_h_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_tm_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_tm_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_tm_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_tm_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_tm_predictor_32x32_c, 32, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_4x4_neon,
|
||||||
|
&vpx_highbd_v_predictor_4x4_c, 4, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_8x8_neon,
|
||||||
|
&vpx_highbd_v_predictor_8x8_c, 8, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_16x16_neon,
|
||||||
|
&vpx_highbd_v_predictor_16x16_c, 16, 12),
|
||||||
|
HighbdIntraPredParam(&vpx_highbd_v_predictor_32x32_neon,
|
||||||
|
&vpx_highbd_v_predictor_32x32_c, 32, 12)));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
} // namespace
|
} // namespace
|
||||||
|
97
test/vp9_motion_vector_test.cc
Normal file
97
test/vp9_motion_vector_test.cc
Normal file
@ -0,0 +1,97 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2017 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "test/codec_factory.h"
|
||||||
|
#include "test/encode_test_driver.h"
|
||||||
|
#include "test/util.h"
|
||||||
|
#include "test/yuv_video_source.h"
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
#define MAX_EXTREME_MV 1
|
||||||
|
#define MIN_EXTREME_MV 2
|
||||||
|
|
||||||
|
// Encoding modes
|
||||||
|
const libvpx_test::TestMode kEncodingModeVectors[] = {
|
||||||
|
::libvpx_test::kTwoPassGood, ::libvpx_test::kOnePassGood,
|
||||||
|
::libvpx_test::kRealTime
|
||||||
|
};
|
||||||
|
|
||||||
|
// Encoding speeds
|
||||||
|
const int kCpuUsedVectors[] = { 0, 1, 2, 3, 4, 5, 6 };
|
||||||
|
|
||||||
|
// MV test modes: 1 - always use maximum MV; 2 - always use minimum MV.
|
||||||
|
const int kMVTestModes[] = { MAX_EXTREME_MV, MIN_EXTREME_MV };
|
||||||
|
|
||||||
|
class MotionVectorTestLarge
|
||||||
|
: public ::libvpx_test::EncoderTest,
|
||||||
|
public ::libvpx_test::CodecTestWith3Params<libvpx_test::TestMode, int,
|
||||||
|
int> {
|
||||||
|
protected:
|
||||||
|
MotionVectorTestLarge()
|
||||||
|
: EncoderTest(GET_PARAM(0)), encoding_mode_(GET_PARAM(1)),
|
||||||
|
cpu_used_(GET_PARAM(2)), mv_test_mode_(GET_PARAM(3)) {}
|
||||||
|
|
||||||
|
virtual ~MotionVectorTestLarge() {}
|
||||||
|
|
||||||
|
virtual void SetUp() {
|
||||||
|
InitializeConfig();
|
||||||
|
SetMode(encoding_mode_);
|
||||||
|
if (encoding_mode_ != ::libvpx_test::kRealTime) {
|
||||||
|
cfg_.g_lag_in_frames = 3;
|
||||||
|
cfg_.rc_end_usage = VPX_VBR;
|
||||||
|
} else {
|
||||||
|
cfg_.g_lag_in_frames = 0;
|
||||||
|
cfg_.rc_end_usage = VPX_CBR;
|
||||||
|
cfg_.rc_buf_sz = 1000;
|
||||||
|
cfg_.rc_buf_initial_sz = 500;
|
||||||
|
cfg_.rc_buf_optimal_sz = 600;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void PreEncodeFrameHook(::libvpx_test::VideoSource *video,
|
||||||
|
::libvpx_test::Encoder *encoder) {
|
||||||
|
if (video->frame() == 1) {
|
||||||
|
encoder->Control(VP8E_SET_CPUUSED, cpu_used_);
|
||||||
|
encoder->Control(VP9E_ENABLE_MOTION_VECTOR_UNIT_TEST, mv_test_mode_);
|
||||||
|
if (encoding_mode_ != ::libvpx_test::kRealTime) {
|
||||||
|
encoder->Control(VP8E_SET_ENABLEAUTOALTREF, 1);
|
||||||
|
encoder->Control(VP8E_SET_ARNR_MAXFRAMES, 7);
|
||||||
|
encoder->Control(VP8E_SET_ARNR_STRENGTH, 5);
|
||||||
|
encoder->Control(VP8E_SET_ARNR_TYPE, 3);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
libvpx_test::TestMode encoding_mode_;
|
||||||
|
int cpu_used_;
|
||||||
|
int mv_test_mode_;
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(MotionVectorTestLarge, OverallTest) {
|
||||||
|
cfg_.rc_target_bitrate = 24000;
|
||||||
|
cfg_.g_profile = 0;
|
||||||
|
init_flags_ = VPX_CODEC_USE_PSNR;
|
||||||
|
|
||||||
|
testing::internal::scoped_ptr<libvpx_test::VideoSource> video;
|
||||||
|
video.reset(new libvpx_test::YUVVideoSource(
|
||||||
|
"niklas_640_480_30.yuv", VPX_IMG_FMT_I420, 3840, 2160, // 2048, 1080,
|
||||||
|
30, 1, 0, 5));
|
||||||
|
|
||||||
|
ASSERT_TRUE(video.get() != NULL);
|
||||||
|
ASSERT_NO_FATAL_FAILURE(RunLoop(video.get()));
|
||||||
|
}
|
||||||
|
|
||||||
|
VP9_INSTANTIATE_TEST_CASE(MotionVectorTestLarge,
|
||||||
|
::testing::ValuesIn(kEncodingModeVectors),
|
||||||
|
::testing::ValuesIn(kCpuUsedVectors),
|
||||||
|
::testing::ValuesIn(kMVTestModes));
|
||||||
|
} // namespace
|
@ -14,9 +14,11 @@
|
|||||||
|
|
||||||
#include "third_party/googletest/src/include/gtest/gtest.h"
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vp9_rtcd.h"
|
||||||
#include "./vpx_config.h"
|
#include "./vpx_config.h"
|
||||||
#include "./vpx_dsp_rtcd.h"
|
#include "./vpx_dsp_rtcd.h"
|
||||||
#include "test/acm_random.h"
|
#include "test/acm_random.h"
|
||||||
|
#include "test/buffer.h"
|
||||||
#include "test/clear_system_state.h"
|
#include "test/clear_system_state.h"
|
||||||
#include "test/register_state_check.h"
|
#include "test/register_state_check.h"
|
||||||
#include "test/util.h"
|
#include "test/util.h"
|
||||||
@ -24,11 +26,12 @@
|
|||||||
#include "vp9/common/vp9_scan.h"
|
#include "vp9/common/vp9_scan.h"
|
||||||
#include "vpx/vpx_codec.h"
|
#include "vpx/vpx_codec.h"
|
||||||
#include "vpx/vpx_integer.h"
|
#include "vpx/vpx_integer.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
|
||||||
using libvpx_test::ACMRandom;
|
using libvpx_test::ACMRandom;
|
||||||
|
using libvpx_test::Buffer;
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
#if CONFIG_VP9_HIGHBITDEPTH
|
|
||||||
const int number_of_iterations = 100;
|
const int number_of_iterations = 100;
|
||||||
|
|
||||||
typedef void (*QuantizeFunc)(const tran_low_t *coeff, intptr_t count,
|
typedef void (*QuantizeFunc)(const tran_low_t *coeff, intptr_t count,
|
||||||
@ -38,307 +41,537 @@ typedef void (*QuantizeFunc)(const tran_low_t *coeff, intptr_t count,
|
|||||||
tran_low_t *dqcoeff, const int16_t *dequant,
|
tran_low_t *dqcoeff, const int16_t *dequant,
|
||||||
uint16_t *eob, const int16_t *scan,
|
uint16_t *eob, const int16_t *scan,
|
||||||
const int16_t *iscan);
|
const int16_t *iscan);
|
||||||
typedef std::tr1::tuple<QuantizeFunc, QuantizeFunc, vpx_bit_depth_t>
|
typedef ::testing::tuple<QuantizeFunc, QuantizeFunc, vpx_bit_depth_t,
|
||||||
|
int /*max_size*/, bool /*is_fp*/>
|
||||||
QuantizeParam;
|
QuantizeParam;
|
||||||
|
|
||||||
class VP9QuantizeTest : public ::testing::TestWithParam<QuantizeParam> {
|
// Wrapper for FP version which does not use zbin or quant_shift.
|
||||||
public:
|
typedef void (*QuantizeFPFunc)(const tran_low_t *coeff, intptr_t count,
|
||||||
virtual ~VP9QuantizeTest() {}
|
int skip_block, const int16_t *round,
|
||||||
virtual void SetUp() {
|
const int16_t *quant, tran_low_t *qcoeff,
|
||||||
quantize_op_ = GET_PARAM(0);
|
tran_low_t *dqcoeff, const int16_t *dequant,
|
||||||
ref_quantize_op_ = GET_PARAM(1);
|
uint16_t *eob, const int16_t *scan,
|
||||||
bit_depth_ = GET_PARAM(2);
|
const int16_t *iscan);
|
||||||
mask_ = (1 << bit_depth_) - 1;
|
|
||||||
|
template <QuantizeFPFunc fn>
|
||||||
|
void QuantFPWrapper(const tran_low_t *coeff, intptr_t count, int skip_block,
|
||||||
|
const int16_t *zbin, const int16_t *round,
|
||||||
|
const int16_t *quant, const int16_t *quant_shift,
|
||||||
|
tran_low_t *qcoeff, tran_low_t *dqcoeff,
|
||||||
|
const int16_t *dequant, uint16_t *eob, const int16_t *scan,
|
||||||
|
const int16_t *iscan) {
|
||||||
|
(void)zbin;
|
||||||
|
(void)quant_shift;
|
||||||
|
|
||||||
|
fn(coeff, count, skip_block, round, quant, qcoeff, dqcoeff, dequant, eob,
|
||||||
|
scan, iscan);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
class VP9QuantizeBase {
|
||||||
|
|
||||||
protected:
|
|
||||||
vpx_bit_depth_t bit_depth_;
|
|
||||||
int mask_;
|
|
||||||
QuantizeFunc quantize_op_;
|
|
||||||
QuantizeFunc ref_quantize_op_;
|
|
||||||
};
|
|
||||||
|
|
||||||
class VP9Quantize32Test : public ::testing::TestWithParam<QuantizeParam> {
|
|
||||||
public:
|
public:
|
||||||
virtual ~VP9Quantize32Test() {}
|
VP9QuantizeBase(vpx_bit_depth_t bit_depth, int max_size, bool is_fp)
|
||||||
virtual void SetUp() {
|
: bit_depth_(bit_depth), max_size_(max_size), is_fp_(is_fp) {
|
||||||
quantize_op_ = GET_PARAM(0);
|
max_value_ = (1 << bit_depth_) - 1;
|
||||||
ref_quantize_op_ = GET_PARAM(1);
|
zbin_ptr_ =
|
||||||
bit_depth_ = GET_PARAM(2);
|
reinterpret_cast<int16_t *>(vpx_memalign(16, 8 * sizeof(*zbin_ptr_)));
|
||||||
mask_ = (1 << bit_depth_) - 1;
|
round_fp_ptr_ = reinterpret_cast<int16_t *>(
|
||||||
|
vpx_memalign(16, 8 * sizeof(*round_fp_ptr_)));
|
||||||
|
quant_fp_ptr_ = reinterpret_cast<int16_t *>(
|
||||||
|
vpx_memalign(16, 8 * sizeof(*quant_fp_ptr_)));
|
||||||
|
round_ptr_ =
|
||||||
|
reinterpret_cast<int16_t *>(vpx_memalign(16, 8 * sizeof(*round_ptr_)));
|
||||||
|
quant_ptr_ =
|
||||||
|
reinterpret_cast<int16_t *>(vpx_memalign(16, 8 * sizeof(*quant_ptr_)));
|
||||||
|
quant_shift_ptr_ = reinterpret_cast<int16_t *>(
|
||||||
|
vpx_memalign(16, 8 * sizeof(*quant_shift_ptr_)));
|
||||||
|
dequant_ptr_ = reinterpret_cast<int16_t *>(
|
||||||
|
vpx_memalign(16, 8 * sizeof(*dequant_ptr_)));
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void TearDown() { libvpx_test::ClearSystemState(); }
|
~VP9QuantizeBase() {
|
||||||
|
vpx_free(zbin_ptr_);
|
||||||
|
vpx_free(round_fp_ptr_);
|
||||||
|
vpx_free(quant_fp_ptr_);
|
||||||
|
vpx_free(round_ptr_);
|
||||||
|
vpx_free(quant_ptr_);
|
||||||
|
vpx_free(quant_shift_ptr_);
|
||||||
|
vpx_free(dequant_ptr_);
|
||||||
|
zbin_ptr_ = NULL;
|
||||||
|
round_fp_ptr_ = NULL;
|
||||||
|
quant_fp_ptr_ = NULL;
|
||||||
|
round_ptr_ = NULL;
|
||||||
|
quant_ptr_ = NULL;
|
||||||
|
quant_shift_ptr_ = NULL;
|
||||||
|
dequant_ptr_ = NULL;
|
||||||
|
libvpx_test::ClearSystemState();
|
||||||
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
vpx_bit_depth_t bit_depth_;
|
int16_t *zbin_ptr_;
|
||||||
int mask_;
|
int16_t *round_fp_ptr_;
|
||||||
QuantizeFunc quantize_op_;
|
int16_t *quant_fp_ptr_;
|
||||||
QuantizeFunc ref_quantize_op_;
|
int16_t *round_ptr_;
|
||||||
|
int16_t *quant_ptr_;
|
||||||
|
int16_t *quant_shift_ptr_;
|
||||||
|
int16_t *dequant_ptr_;
|
||||||
|
const vpx_bit_depth_t bit_depth_;
|
||||||
|
int max_value_;
|
||||||
|
const int max_size_;
|
||||||
|
const bool is_fp_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class VP9QuantizeTest : public VP9QuantizeBase,
|
||||||
|
public ::testing::TestWithParam<QuantizeParam> {
|
||||||
|
public:
|
||||||
|
VP9QuantizeTest()
|
||||||
|
: VP9QuantizeBase(GET_PARAM(2), GET_PARAM(3), GET_PARAM(4)),
|
||||||
|
quantize_op_(GET_PARAM(0)), ref_quantize_op_(GET_PARAM(1)) {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
const QuantizeFunc quantize_op_;
|
||||||
|
const QuantizeFunc ref_quantize_op_;
|
||||||
|
};
|
||||||
|
|
||||||
|
// This quantizer compares the AC coefficients to the quantization step size to
|
||||||
|
// determine if further multiplication operations are needed.
|
||||||
|
// Based on vp9_quantize_fp_sse2().
|
||||||
|
inline void quant_fp_nz(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
|
||||||
|
int skip_block, const int16_t *round_ptr,
|
||||||
|
const int16_t *quant_ptr, tran_low_t *qcoeff_ptr,
|
||||||
|
tran_low_t *dqcoeff_ptr, const int16_t *dequant_ptr,
|
||||||
|
uint16_t *eob_ptr, const int16_t *scan,
|
||||||
|
const int16_t *iscan, int is_32x32) {
|
||||||
|
int i, eob = -1;
|
||||||
|
const int thr = dequant_ptr[1] >> (1 + is_32x32);
|
||||||
|
(void)iscan;
|
||||||
|
(void)skip_block;
|
||||||
|
assert(!skip_block);
|
||||||
|
|
||||||
|
// Quantization pass: All coefficients with index >= zero_flag are
|
||||||
|
// skippable. Note: zero_flag can be zero.
|
||||||
|
for (i = 0; i < n_coeffs; i += 16) {
|
||||||
|
int y;
|
||||||
|
int nzflag_cnt = 0;
|
||||||
|
int abs_coeff[16];
|
||||||
|
int coeff_sign[16];
|
||||||
|
|
||||||
|
// count nzflag for each row (16 tran_low_t)
|
||||||
|
for (y = 0; y < 16; ++y) {
|
||||||
|
const int rc = i + y;
|
||||||
|
const int coeff = coeff_ptr[rc];
|
||||||
|
coeff_sign[y] = (coeff >> 31);
|
||||||
|
abs_coeff[y] = (coeff ^ coeff_sign[y]) - coeff_sign[y];
|
||||||
|
// The first 16 are skipped in the sse2 code. Do the same here to match.
|
||||||
|
if (i >= 16 && (abs_coeff[y] <= thr)) {
|
||||||
|
nzflag_cnt++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (y = 0; y < 16; ++y) {
|
||||||
|
const int rc = i + y;
|
||||||
|
// If all of the AC coeffs in a row has magnitude less than the
|
||||||
|
// quantization step_size/2, quantize to zero.
|
||||||
|
if (nzflag_cnt < 16) {
|
||||||
|
int tmp;
|
||||||
|
int _round;
|
||||||
|
|
||||||
|
if (is_32x32) {
|
||||||
|
_round = ROUND_POWER_OF_TWO(round_ptr[rc != 0], 1);
|
||||||
|
} else {
|
||||||
|
_round = round_ptr[rc != 0];
|
||||||
|
}
|
||||||
|
tmp = clamp(abs_coeff[y] + _round, INT16_MIN, INT16_MAX);
|
||||||
|
tmp = (tmp * quant_ptr[rc != 0]) >> (16 - is_32x32);
|
||||||
|
qcoeff_ptr[rc] = (tmp ^ coeff_sign[y]) - coeff_sign[y];
|
||||||
|
dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0];
|
||||||
|
|
||||||
|
if (is_32x32) {
|
||||||
|
dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0] / 2;
|
||||||
|
} else {
|
||||||
|
dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0];
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
qcoeff_ptr[rc] = 0;
|
||||||
|
dqcoeff_ptr[rc] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Scan for eob.
|
||||||
|
for (i = 0; i < n_coeffs; i++) {
|
||||||
|
// Use the scan order to find the correct eob.
|
||||||
|
const int rc = scan[i];
|
||||||
|
if (qcoeff_ptr[rc]) {
|
||||||
|
eob = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*eob_ptr = eob + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void quantize_fp_nz_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
|
||||||
|
int skip_block, const int16_t *round_ptr,
|
||||||
|
const int16_t *quant_ptr, tran_low_t *qcoeff_ptr,
|
||||||
|
tran_low_t *dqcoeff_ptr, const int16_t *dequant_ptr,
|
||||||
|
uint16_t *eob_ptr, const int16_t *scan,
|
||||||
|
const int16_t *iscan) {
|
||||||
|
quant_fp_nz(coeff_ptr, n_coeffs, skip_block, round_ptr, quant_ptr, qcoeff_ptr,
|
||||||
|
dqcoeff_ptr, dequant_ptr, eob_ptr, scan, iscan, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
void quantize_fp_32x32_nz_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
|
||||||
|
int skip_block, const int16_t *round_ptr,
|
||||||
|
const int16_t *quant_ptr, tran_low_t *qcoeff_ptr,
|
||||||
|
tran_low_t *dqcoeff_ptr, const int16_t *dequant_ptr,
|
||||||
|
uint16_t *eob_ptr, const int16_t *scan,
|
||||||
|
const int16_t *iscan) {
|
||||||
|
quant_fp_nz(coeff_ptr, n_coeffs, skip_block, round_ptr, quant_ptr, qcoeff_ptr,
|
||||||
|
dqcoeff_ptr, dequant_ptr, eob_ptr, scan, iscan, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void GenerateHelperArrays(ACMRandom *rnd, int16_t *zbin, int16_t *round,
|
||||||
|
int16_t *quant, int16_t *quant_shift,
|
||||||
|
int16_t *dequant, int16_t *round_fp,
|
||||||
|
int16_t *quant_fp) {
|
||||||
|
// Max when q == 0. Otherwise, it is 48 for Y and 42 for U/V.
|
||||||
|
const int max_qrounding_factor_fp = 64;
|
||||||
|
|
||||||
|
for (int j = 0; j < 2; j++) {
|
||||||
|
// The range is 4 to 1828 in the VP9 tables.
|
||||||
|
const int qlookup = rnd->RandRange(1825) + 4;
|
||||||
|
round_fp[j] = (max_qrounding_factor_fp * qlookup) >> 7;
|
||||||
|
quant_fp[j] = (1 << 16) / qlookup;
|
||||||
|
|
||||||
|
// Values determined by deconstructing vp9_init_quantizer().
|
||||||
|
// zbin may be up to 1143 for 8 and 10 bit Y values, or 1200 for 12 bit Y
|
||||||
|
// values or U/V values of any bit depth. This is because y_delta is not
|
||||||
|
// factored into the vp9_ac_quant() call.
|
||||||
|
zbin[j] = rnd->RandRange(1200);
|
||||||
|
|
||||||
|
// round may be up to 685 for Y values or 914 for U/V.
|
||||||
|
round[j] = rnd->RandRange(914);
|
||||||
|
// quant ranges from 1 to -32703
|
||||||
|
quant[j] = static_cast<int>(rnd->RandRange(32704)) - 32703;
|
||||||
|
// quant_shift goes up to 1 << 16.
|
||||||
|
quant_shift[j] = rnd->RandRange(16384);
|
||||||
|
// dequant maxes out at 1828 for all cases.
|
||||||
|
dequant[j] = rnd->RandRange(1828);
|
||||||
|
}
|
||||||
|
for (int j = 2; j < 8; j++) {
|
||||||
|
zbin[j] = zbin[1];
|
||||||
|
round_fp[j] = round_fp[1];
|
||||||
|
quant_fp[j] = quant_fp[1];
|
||||||
|
round[j] = round[1];
|
||||||
|
quant[j] = quant[1];
|
||||||
|
quant_shift[j] = quant_shift[1];
|
||||||
|
dequant[j] = dequant[1];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
TEST_P(VP9QuantizeTest, OperationCheck) {
|
TEST_P(VP9QuantizeTest, OperationCheck) {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff_ptr[256]);
|
Buffer<tran_low_t> coeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 16);
|
||||||
DECLARE_ALIGNED(16, int16_t, zbin_ptr[2]);
|
ASSERT_TRUE(coeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, round_ptr[2]);
|
Buffer<tran_low_t> qcoeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_ptr[2]);
|
ASSERT_TRUE(qcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_shift_ptr[2]);
|
Buffer<tran_low_t> dqcoeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, qcoeff_ptr[256]);
|
ASSERT_TRUE(dqcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, dqcoeff_ptr[256]);
|
Buffer<tran_low_t> ref_qcoeff =
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_qcoeff_ptr[256]);
|
Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_dqcoeff_ptr[256]);
|
ASSERT_TRUE(ref_qcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, dequant_ptr[2]);
|
Buffer<tran_low_t> ref_dqcoeff =
|
||||||
DECLARE_ALIGNED(16, uint16_t, eob_ptr[1]);
|
Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, uint16_t, ref_eob_ptr[1]);
|
ASSERT_TRUE(ref_dqcoeff.Init());
|
||||||
int err_count_total = 0;
|
uint16_t eob, ref_eob;
|
||||||
int first_failure = -1;
|
|
||||||
for (int i = 0; i < number_of_iterations; ++i) {
|
|
||||||
const int skip_block = i == 0;
|
|
||||||
const TX_SIZE sz = (TX_SIZE)(i % 3); // TX_4X4, TX_8X8 TX_16X16
|
|
||||||
const TX_TYPE tx_type = (TX_TYPE)((i >> 2) % 3);
|
|
||||||
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
|
||||||
const int count = (4 << sz) * (4 << sz); // 16, 64, 256
|
|
||||||
int err_count = 0;
|
|
||||||
*eob_ptr = rnd.Rand16();
|
|
||||||
*ref_eob_ptr = *eob_ptr;
|
|
||||||
for (int j = 0; j < count; j++) {
|
|
||||||
coeff_ptr[j] = rnd.Rand16() & mask_;
|
|
||||||
}
|
|
||||||
for (int j = 0; j < 2; j++) {
|
|
||||||
zbin_ptr[j] = rnd.Rand16() & mask_;
|
|
||||||
round_ptr[j] = rnd.Rand16();
|
|
||||||
quant_ptr[j] = rnd.Rand16();
|
|
||||||
quant_shift_ptr[j] = rnd.Rand16();
|
|
||||||
dequant_ptr[j] = rnd.Rand16();
|
|
||||||
}
|
|
||||||
ref_quantize_op_(coeff_ptr, count, skip_block, zbin_ptr, round_ptr,
|
|
||||||
quant_ptr, quant_shift_ptr, ref_qcoeff_ptr,
|
|
||||||
ref_dqcoeff_ptr, dequant_ptr, ref_eob_ptr,
|
|
||||||
scan_order->scan, scan_order->iscan);
|
|
||||||
ASM_REGISTER_STATE_CHECK(quantize_op_(
|
|
||||||
coeff_ptr, count, skip_block, zbin_ptr, round_ptr, quant_ptr,
|
|
||||||
quant_shift_ptr, qcoeff_ptr, dqcoeff_ptr, dequant_ptr, eob_ptr,
|
|
||||||
scan_order->scan, scan_order->iscan));
|
|
||||||
for (int j = 0; j < sz; ++j) {
|
|
||||||
err_count += (ref_qcoeff_ptr[j] != qcoeff_ptr[j]) |
|
|
||||||
(ref_dqcoeff_ptr[j] != dqcoeff_ptr[j]);
|
|
||||||
}
|
|
||||||
err_count += (*ref_eob_ptr != *eob_ptr);
|
|
||||||
if (err_count && !err_count_total) {
|
|
||||||
first_failure = i;
|
|
||||||
}
|
|
||||||
err_count_total += err_count;
|
|
||||||
}
|
|
||||||
EXPECT_EQ(0, err_count_total)
|
|
||||||
<< "Error: Quantization Test, C output doesn't match SSE2 output. "
|
|
||||||
<< "First failed at test case " << first_failure;
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_P(VP9Quantize32Test, OperationCheck) {
|
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff_ptr[1024]);
|
|
||||||
DECLARE_ALIGNED(16, int16_t, zbin_ptr[2]);
|
|
||||||
DECLARE_ALIGNED(16, int16_t, round_ptr[2]);
|
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_ptr[2]);
|
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_shift_ptr[2]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, qcoeff_ptr[1024]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, dqcoeff_ptr[1024]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_qcoeff_ptr[1024]);
|
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_dqcoeff_ptr[1024]);
|
|
||||||
DECLARE_ALIGNED(16, int16_t, dequant_ptr[2]);
|
|
||||||
DECLARE_ALIGNED(16, uint16_t, eob_ptr[1]);
|
|
||||||
DECLARE_ALIGNED(16, uint16_t, ref_eob_ptr[1]);
|
|
||||||
int err_count_total = 0;
|
|
||||||
int first_failure = -1;
|
|
||||||
for (int i = 0; i < number_of_iterations; ++i) {
|
for (int i = 0; i < number_of_iterations; ++i) {
|
||||||
const int skip_block = i == 0;
|
// Test skip block for the first three iterations to catch all the different
|
||||||
const TX_SIZE sz = TX_32X32;
|
// sizes.
|
||||||
const TX_TYPE tx_type = (TX_TYPE)(i % 4);
|
const int skip_block = 0;
|
||||||
|
TX_SIZE sz;
|
||||||
|
if (max_size_ == 16) {
|
||||||
|
sz = static_cast<TX_SIZE>(i % 3); // TX_4X4, TX_8X8 TX_16X16
|
||||||
|
} else {
|
||||||
|
sz = TX_32X32;
|
||||||
|
}
|
||||||
|
const TX_TYPE tx_type = static_cast<TX_TYPE>((i >> 2) % 3);
|
||||||
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
||||||
const int count = (4 << sz) * (4 << sz); // 1024
|
const int count = (4 << sz) * (4 << sz);
|
||||||
int err_count = 0;
|
coeff.Set(&rnd, -max_value_, max_value_);
|
||||||
*eob_ptr = rnd.Rand16();
|
GenerateHelperArrays(&rnd, zbin_ptr_, round_ptr_, quant_ptr_,
|
||||||
*ref_eob_ptr = *eob_ptr;
|
quant_shift_ptr_, dequant_ptr_, round_fp_ptr_,
|
||||||
for (int j = 0; j < count; j++) {
|
quant_fp_ptr_);
|
||||||
coeff_ptr[j] = rnd.Rand16() & mask_;
|
int16_t *r_ptr = (is_fp_) ? round_fp_ptr_ : round_ptr_;
|
||||||
}
|
int16_t *q_ptr = (is_fp_) ? quant_fp_ptr_ : quant_ptr_;
|
||||||
for (int j = 0; j < 2; j++) {
|
ref_quantize_op_(coeff.TopLeftPixel(), count, skip_block, zbin_ptr_, r_ptr,
|
||||||
zbin_ptr[j] = rnd.Rand16() & mask_;
|
q_ptr, quant_shift_ptr_, ref_qcoeff.TopLeftPixel(),
|
||||||
round_ptr[j] = rnd.Rand16();
|
ref_dqcoeff.TopLeftPixel(), dequant_ptr_, &ref_eob,
|
||||||
quant_ptr[j] = rnd.Rand16();
|
|
||||||
quant_shift_ptr[j] = rnd.Rand16();
|
|
||||||
dequant_ptr[j] = rnd.Rand16();
|
|
||||||
}
|
|
||||||
ref_quantize_op_(coeff_ptr, count, skip_block, zbin_ptr, round_ptr,
|
|
||||||
quant_ptr, quant_shift_ptr, ref_qcoeff_ptr,
|
|
||||||
ref_dqcoeff_ptr, dequant_ptr, ref_eob_ptr,
|
|
||||||
scan_order->scan, scan_order->iscan);
|
scan_order->scan, scan_order->iscan);
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(quantize_op_(
|
ASM_REGISTER_STATE_CHECK(quantize_op_(
|
||||||
coeff_ptr, count, skip_block, zbin_ptr, round_ptr, quant_ptr,
|
coeff.TopLeftPixel(), count, skip_block, zbin_ptr_, r_ptr, q_ptr,
|
||||||
quant_shift_ptr, qcoeff_ptr, dqcoeff_ptr, dequant_ptr, eob_ptr,
|
quant_shift_ptr_, qcoeff.TopLeftPixel(), dqcoeff.TopLeftPixel(),
|
||||||
scan_order->scan, scan_order->iscan));
|
dequant_ptr_, &eob, scan_order->scan, scan_order->iscan));
|
||||||
for (int j = 0; j < sz; ++j) {
|
|
||||||
err_count += (ref_qcoeff_ptr[j] != qcoeff_ptr[j]) |
|
EXPECT_TRUE(qcoeff.CheckValues(ref_qcoeff));
|
||||||
(ref_dqcoeff_ptr[j] != dqcoeff_ptr[j]);
|
EXPECT_TRUE(dqcoeff.CheckValues(ref_dqcoeff));
|
||||||
|
|
||||||
|
EXPECT_EQ(eob, ref_eob);
|
||||||
|
|
||||||
|
if (HasFailure()) {
|
||||||
|
printf("Failure on iteration %d.\n", i);
|
||||||
|
qcoeff.PrintDifference(ref_qcoeff);
|
||||||
|
dqcoeff.PrintDifference(ref_dqcoeff);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
err_count += (*ref_eob_ptr != *eob_ptr);
|
|
||||||
if (err_count && !err_count_total) {
|
|
||||||
first_failure = i;
|
|
||||||
}
|
}
|
||||||
err_count_total += err_count;
|
|
||||||
}
|
|
||||||
EXPECT_EQ(0, err_count_total)
|
|
||||||
<< "Error: Quantization Test, C output doesn't match SSE2 output. "
|
|
||||||
<< "First failed at test case " << first_failure;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_P(VP9QuantizeTest, EOBCheck) {
|
TEST_P(VP9QuantizeTest, EOBCheck) {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff_ptr[256]);
|
Buffer<tran_low_t> coeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 16);
|
||||||
DECLARE_ALIGNED(16, int16_t, zbin_ptr[2]);
|
ASSERT_TRUE(coeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, round_ptr[2]);
|
Buffer<tran_low_t> qcoeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_ptr[2]);
|
ASSERT_TRUE(qcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_shift_ptr[2]);
|
Buffer<tran_low_t> dqcoeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, qcoeff_ptr[256]);
|
ASSERT_TRUE(dqcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, dqcoeff_ptr[256]);
|
Buffer<tran_low_t> ref_qcoeff =
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_qcoeff_ptr[256]);
|
Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_dqcoeff_ptr[256]);
|
ASSERT_TRUE(ref_qcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, dequant_ptr[2]);
|
Buffer<tran_low_t> ref_dqcoeff =
|
||||||
DECLARE_ALIGNED(16, uint16_t, eob_ptr[1]);
|
Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, uint16_t, ref_eob_ptr[1]);
|
ASSERT_TRUE(ref_dqcoeff.Init());
|
||||||
int err_count_total = 0;
|
uint16_t eob, ref_eob;
|
||||||
int first_failure = -1;
|
|
||||||
for (int i = 0; i < number_of_iterations; ++i) {
|
for (int i = 0; i < number_of_iterations; ++i) {
|
||||||
int skip_block = i == 0;
|
const int skip_block = 0;
|
||||||
TX_SIZE sz = (TX_SIZE)(i % 3); // TX_4X4, TX_8X8 TX_16X16
|
TX_SIZE sz;
|
||||||
TX_TYPE tx_type = (TX_TYPE)((i >> 2) % 3);
|
if (max_size_ == 16) {
|
||||||
|
sz = static_cast<TX_SIZE>(i % 3); // TX_4X4, TX_8X8 TX_16X16
|
||||||
|
} else {
|
||||||
|
sz = TX_32X32;
|
||||||
|
}
|
||||||
|
const TX_TYPE tx_type = static_cast<TX_TYPE>((i >> 2) % 3);
|
||||||
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
||||||
int count = (4 << sz) * (4 << sz); // 16, 64, 256
|
int count = (4 << sz) * (4 << sz);
|
||||||
int err_count = 0;
|
|
||||||
*eob_ptr = rnd.Rand16();
|
|
||||||
*ref_eob_ptr = *eob_ptr;
|
|
||||||
// Two random entries
|
// Two random entries
|
||||||
for (int j = 0; j < count; j++) {
|
coeff.Set(0);
|
||||||
coeff_ptr[j] = 0;
|
coeff.TopLeftPixel()[rnd(count)] =
|
||||||
}
|
static_cast<int>(rnd.RandRange(max_value_ * 2)) - max_value_;
|
||||||
coeff_ptr[rnd(count)] = rnd.Rand16() & mask_;
|
coeff.TopLeftPixel()[rnd(count)] =
|
||||||
coeff_ptr[rnd(count)] = rnd.Rand16() & mask_;
|
static_cast<int>(rnd.RandRange(max_value_ * 2)) - max_value_;
|
||||||
for (int j = 0; j < 2; j++) {
|
GenerateHelperArrays(&rnd, zbin_ptr_, round_ptr_, quant_ptr_,
|
||||||
zbin_ptr[j] = rnd.Rand16() & mask_;
|
quant_shift_ptr_, dequant_ptr_, round_fp_ptr_,
|
||||||
round_ptr[j] = rnd.Rand16();
|
quant_fp_ptr_);
|
||||||
quant_ptr[j] = rnd.Rand16();
|
int16_t *r_ptr = (is_fp_) ? round_fp_ptr_ : round_ptr_;
|
||||||
quant_shift_ptr[j] = rnd.Rand16();
|
int16_t *q_ptr = (is_fp_) ? quant_fp_ptr_ : quant_ptr_;
|
||||||
dequant_ptr[j] = rnd.Rand16();
|
ref_quantize_op_(coeff.TopLeftPixel(), count, skip_block, zbin_ptr_, r_ptr,
|
||||||
}
|
q_ptr, quant_shift_ptr_, ref_qcoeff.TopLeftPixel(),
|
||||||
|
ref_dqcoeff.TopLeftPixel(), dequant_ptr_, &ref_eob,
|
||||||
ref_quantize_op_(coeff_ptr, count, skip_block, zbin_ptr, round_ptr,
|
|
||||||
quant_ptr, quant_shift_ptr, ref_qcoeff_ptr,
|
|
||||||
ref_dqcoeff_ptr, dequant_ptr, ref_eob_ptr,
|
|
||||||
scan_order->scan, scan_order->iscan);
|
scan_order->scan, scan_order->iscan);
|
||||||
|
|
||||||
ASM_REGISTER_STATE_CHECK(quantize_op_(
|
ASM_REGISTER_STATE_CHECK(quantize_op_(
|
||||||
coeff_ptr, count, skip_block, zbin_ptr, round_ptr, quant_ptr,
|
coeff.TopLeftPixel(), count, skip_block, zbin_ptr_, r_ptr, q_ptr,
|
||||||
quant_shift_ptr, qcoeff_ptr, dqcoeff_ptr, dequant_ptr, eob_ptr,
|
quant_shift_ptr_, qcoeff.TopLeftPixel(), dqcoeff.TopLeftPixel(),
|
||||||
scan_order->scan, scan_order->iscan));
|
dequant_ptr_, &eob, scan_order->scan, scan_order->iscan));
|
||||||
|
|
||||||
for (int j = 0; j < sz; ++j) {
|
EXPECT_TRUE(qcoeff.CheckValues(ref_qcoeff));
|
||||||
err_count += (ref_qcoeff_ptr[j] != qcoeff_ptr[j]) |
|
EXPECT_TRUE(dqcoeff.CheckValues(ref_dqcoeff));
|
||||||
(ref_dqcoeff_ptr[j] != dqcoeff_ptr[j]);
|
|
||||||
|
EXPECT_EQ(eob, ref_eob);
|
||||||
|
|
||||||
|
if (HasFailure()) {
|
||||||
|
printf("Failure on iteration %d.\n", i);
|
||||||
|
qcoeff.PrintDifference(ref_qcoeff);
|
||||||
|
dqcoeff.PrintDifference(ref_dqcoeff);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
err_count += (*ref_eob_ptr != *eob_ptr);
|
|
||||||
if (err_count && !err_count_total) {
|
|
||||||
first_failure = i;
|
|
||||||
}
|
}
|
||||||
err_count_total += err_count;
|
|
||||||
}
|
|
||||||
EXPECT_EQ(0, err_count_total)
|
|
||||||
<< "Error: Quantization Test, C output doesn't match SSE2 output. "
|
|
||||||
<< "First failed at test case " << first_failure;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_P(VP9Quantize32Test, EOBCheck) {
|
TEST_P(VP9QuantizeTest, DISABLED_Speed) {
|
||||||
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
ACMRandom rnd(ACMRandom::DeterministicSeed());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, coeff_ptr[1024]);
|
Buffer<tran_low_t> coeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 16);
|
||||||
DECLARE_ALIGNED(16, int16_t, zbin_ptr[2]);
|
ASSERT_TRUE(coeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, round_ptr[2]);
|
Buffer<tran_low_t> qcoeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_ptr[2]);
|
ASSERT_TRUE(qcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, int16_t, quant_shift_ptr[2]);
|
Buffer<tran_low_t> dqcoeff = Buffer<tran_low_t>(max_size_, max_size_, 0, 32);
|
||||||
DECLARE_ALIGNED(16, tran_low_t, qcoeff_ptr[1024]);
|
ASSERT_TRUE(dqcoeff.Init());
|
||||||
DECLARE_ALIGNED(16, tran_low_t, dqcoeff_ptr[1024]);
|
uint16_t eob;
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_qcoeff_ptr[1024]);
|
TX_SIZE starting_sz, ending_sz;
|
||||||
DECLARE_ALIGNED(16, tran_low_t, ref_dqcoeff_ptr[1024]);
|
|
||||||
DECLARE_ALIGNED(16, int16_t, dequant_ptr[2]);
|
if (max_size_ == 16) {
|
||||||
DECLARE_ALIGNED(16, uint16_t, eob_ptr[1]);
|
starting_sz = TX_4X4;
|
||||||
DECLARE_ALIGNED(16, uint16_t, ref_eob_ptr[1]);
|
ending_sz = TX_16X16;
|
||||||
int err_count_total = 0;
|
} else {
|
||||||
int first_failure = -1;
|
starting_sz = TX_32X32;
|
||||||
for (int i = 0; i < number_of_iterations; ++i) {
|
ending_sz = TX_32X32;
|
||||||
int skip_block = i == 0;
|
}
|
||||||
TX_SIZE sz = TX_32X32;
|
|
||||||
TX_TYPE tx_type = (TX_TYPE)(i % 4);
|
for (TX_SIZE sz = starting_sz; sz <= ending_sz; ++sz) {
|
||||||
|
// zbin > coeff, zbin < coeff.
|
||||||
|
for (int i = 0; i < 2; ++i) {
|
||||||
|
const int skip_block = 0;
|
||||||
|
// TX_TYPE defines the scan order. That is not relevant to the speed test.
|
||||||
|
// Pick the first one.
|
||||||
|
const TX_TYPE tx_type = DCT_DCT;
|
||||||
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
const scan_order *scan_order = &vp9_scan_orders[sz][tx_type];
|
||||||
int count = (4 << sz) * (4 << sz); // 1024
|
const int count = (4 << sz) * (4 << sz);
|
||||||
int err_count = 0;
|
|
||||||
*eob_ptr = rnd.Rand16();
|
GenerateHelperArrays(&rnd, zbin_ptr_, round_ptr_, quant_ptr_,
|
||||||
*ref_eob_ptr = *eob_ptr;
|
quant_shift_ptr_, dequant_ptr_, round_fp_ptr_,
|
||||||
for (int j = 0; j < count; j++) {
|
quant_fp_ptr_);
|
||||||
coeff_ptr[j] = 0;
|
int16_t *r_ptr = (is_fp_) ? round_fp_ptr_ : round_ptr_;
|
||||||
|
int16_t *q_ptr = (is_fp_) ? quant_fp_ptr_ : quant_ptr_;
|
||||||
|
|
||||||
|
if (i == 0) {
|
||||||
|
// When |coeff values| are less than zbin the results are 0.
|
||||||
|
int threshold = 100;
|
||||||
|
if (max_size_ == 32) {
|
||||||
|
// For 32x32, the threshold is halved. Double it to keep the values
|
||||||
|
// from clearing it.
|
||||||
|
threshold = 200;
|
||||||
}
|
}
|
||||||
// Two random entries
|
for (int j = 0; j < 8; ++j) zbin_ptr_[j] = threshold;
|
||||||
coeff_ptr[rnd(count)] = rnd.Rand16() & mask_;
|
coeff.Set(&rnd, -99, 99);
|
||||||
coeff_ptr[rnd(count)] = rnd.Rand16() & mask_;
|
} else if (i == 1) {
|
||||||
for (int j = 0; j < 2; j++) {
|
for (int j = 0; j < 8; ++j) zbin_ptr_[j] = 50;
|
||||||
zbin_ptr[j] = rnd.Rand16() & mask_;
|
coeff.Set(&rnd, -500, 500);
|
||||||
round_ptr[j] = rnd.Rand16();
|
|
||||||
quant_ptr[j] = rnd.Rand16();
|
|
||||||
quant_shift_ptr[j] = rnd.Rand16();
|
|
||||||
dequant_ptr[j] = rnd.Rand16();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ref_quantize_op_(coeff_ptr, count, skip_block, zbin_ptr, round_ptr,
|
vpx_usec_timer timer;
|
||||||
quant_ptr, quant_shift_ptr, ref_qcoeff_ptr,
|
vpx_usec_timer_start(&timer);
|
||||||
ref_dqcoeff_ptr, dequant_ptr, ref_eob_ptr,
|
for (int j = 0; j < 100000000 / count; ++j) {
|
||||||
|
quantize_op_(coeff.TopLeftPixel(), count, skip_block, zbin_ptr_, r_ptr,
|
||||||
|
q_ptr, quant_shift_ptr_, qcoeff.TopLeftPixel(),
|
||||||
|
dqcoeff.TopLeftPixel(), dequant_ptr_, &eob,
|
||||||
scan_order->scan, scan_order->iscan);
|
scan_order->scan, scan_order->iscan);
|
||||||
ASM_REGISTER_STATE_CHECK(quantize_op_(
|
}
|
||||||
coeff_ptr, count, skip_block, zbin_ptr, round_ptr, quant_ptr,
|
vpx_usec_timer_mark(&timer);
|
||||||
quant_shift_ptr, qcoeff_ptr, dqcoeff_ptr, dequant_ptr, eob_ptr,
|
const int elapsed_time = static_cast<int>(vpx_usec_timer_elapsed(&timer));
|
||||||
scan_order->scan, scan_order->iscan));
|
if (i == 0) printf("Bypass calculations.\n");
|
||||||
|
if (i == 1) printf("Full calculations.\n");
|
||||||
|
printf("Quantize %dx%d time: %5d ms\n", 4 << sz, 4 << sz,
|
||||||
|
elapsed_time / 1000);
|
||||||
|
}
|
||||||
|
printf("\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
for (int j = 0; j < sz; ++j) {
|
using ::testing::make_tuple;
|
||||||
err_count += (ref_qcoeff_ptr[j] != qcoeff_ptr[j]) |
|
|
||||||
(ref_dqcoeff_ptr[j] != dqcoeff_ptr[j]);
|
|
||||||
}
|
|
||||||
err_count += (*ref_eob_ptr != *eob_ptr);
|
|
||||||
if (err_count && !err_count_total) {
|
|
||||||
first_failure = i;
|
|
||||||
}
|
|
||||||
err_count_total += err_count;
|
|
||||||
}
|
|
||||||
EXPECT_EQ(0, err_count_total)
|
|
||||||
<< "Error: Quantization Test, C output doesn't match SSE2 output. "
|
|
||||||
<< "First failed at test case " << first_failure;
|
|
||||||
}
|
|
||||||
using std::tr1::make_tuple;
|
|
||||||
|
|
||||||
#if HAVE_SSE2
|
#if HAVE_SSE2
|
||||||
|
#if CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
// TODO(johannkoenig): Fix vpx_quantize_b_sse2 in highbitdepth builds.
|
||||||
|
// make_tuple(&vpx_quantize_b_sse2, &vpx_highbd_quantize_b_c, VPX_BITS_8),
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2, VP9QuantizeTest,
|
SSE2, VP9QuantizeTest,
|
||||||
::testing::Values(make_tuple(&vpx_highbd_quantize_b_sse2,
|
::testing::Values(
|
||||||
&vpx_highbd_quantize_b_c, VPX_BITS_8),
|
make_tuple(&vpx_highbd_quantize_b_sse2, &vpx_highbd_quantize_b_c,
|
||||||
make_tuple(&vpx_highbd_quantize_b_sse2,
|
VPX_BITS_8, 16, false),
|
||||||
&vpx_highbd_quantize_b_c, VPX_BITS_10),
|
make_tuple(&vpx_highbd_quantize_b_sse2, &vpx_highbd_quantize_b_c,
|
||||||
make_tuple(&vpx_highbd_quantize_b_sse2,
|
VPX_BITS_10, 16, false),
|
||||||
&vpx_highbd_quantize_b_c, VPX_BITS_12)));
|
make_tuple(&vpx_highbd_quantize_b_sse2, &vpx_highbd_quantize_b_c,
|
||||||
|
VPX_BITS_12, 16, false),
|
||||||
|
make_tuple(&vpx_highbd_quantize_b_32x32_sse2,
|
||||||
|
&vpx_highbd_quantize_b_32x32_c, VPX_BITS_8, 32, false),
|
||||||
|
make_tuple(&vpx_highbd_quantize_b_32x32_sse2,
|
||||||
|
&vpx_highbd_quantize_b_32x32_c, VPX_BITS_10, 32, false),
|
||||||
|
make_tuple(&vpx_highbd_quantize_b_32x32_sse2,
|
||||||
|
&vpx_highbd_quantize_b_32x32_c, VPX_BITS_12, 32, false)));
|
||||||
|
|
||||||
|
#else
|
||||||
INSTANTIATE_TEST_CASE_P(
|
INSTANTIATE_TEST_CASE_P(
|
||||||
SSE2, VP9Quantize32Test,
|
SSE2, VP9QuantizeTest,
|
||||||
::testing::Values(make_tuple(&vpx_highbd_quantize_b_32x32_sse2,
|
::testing::Values(make_tuple(&vpx_quantize_b_sse2, &vpx_quantize_b_c,
|
||||||
&vpx_highbd_quantize_b_32x32_c, VPX_BITS_8),
|
VPX_BITS_8, 16, false),
|
||||||
make_tuple(&vpx_highbd_quantize_b_32x32_sse2,
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_sse2>,
|
||||||
&vpx_highbd_quantize_b_32x32_c, VPX_BITS_10),
|
&QuantFPWrapper<quantize_fp_nz_c>, VPX_BITS_8,
|
||||||
make_tuple(&vpx_highbd_quantize_b_32x32_sse2,
|
16, true)));
|
||||||
&vpx_highbd_quantize_b_32x32_c, VPX_BITS_12)));
|
|
||||||
#endif // HAVE_SSE2
|
|
||||||
#endif // CONFIG_VP9_HIGHBITDEPTH
|
#endif // CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#endif // HAVE_SSE2
|
||||||
|
|
||||||
|
#if HAVE_SSSE3 && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
#if ARCH_X86_64
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
SSSE3, VP9QuantizeTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_quantize_b_ssse3, &vpx_quantize_b_c,
|
||||||
|
VPX_BITS_8, 16, false),
|
||||||
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_ssse3>,
|
||||||
|
&QuantFPWrapper<quantize_fp_nz_c>, VPX_BITS_8,
|
||||||
|
16, true),
|
||||||
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_32x32_ssse3>,
|
||||||
|
&QuantFPWrapper<quantize_fp_32x32_nz_c>,
|
||||||
|
VPX_BITS_8, 32, true)));
|
||||||
|
#else
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSSE3, VP9QuantizeTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_quantize_b_ssse3,
|
||||||
|
&vpx_quantize_b_c,
|
||||||
|
VPX_BITS_8, 16, false)));
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if ARCH_X86_64
|
||||||
|
// TODO(johannkoenig): SSSE3 optimizations do not yet pass this test.
|
||||||
|
INSTANTIATE_TEST_CASE_P(DISABLED_SSSE3, VP9QuantizeTest,
|
||||||
|
::testing::Values(make_tuple(
|
||||||
|
&vpx_quantize_b_32x32_ssse3,
|
||||||
|
&vpx_quantize_b_32x32_c, VPX_BITS_8, 32, false)));
|
||||||
|
#endif // ARCH_X86_64
|
||||||
|
#endif // HAVE_SSSE3 && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
// TODO(johannkoenig): AVX optimizations do not yet pass the 32x32 test or
|
||||||
|
// highbitdepth configurations.
|
||||||
|
#if HAVE_AVX && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
AVX, VP9QuantizeTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_quantize_b_avx, &vpx_quantize_b_c,
|
||||||
|
VPX_BITS_8, 16, false),
|
||||||
|
// Even though SSSE3 and AVX do not match the reference
|
||||||
|
// code, we can keep them in sync with each other.
|
||||||
|
make_tuple(&vpx_quantize_b_32x32_avx,
|
||||||
|
&vpx_quantize_b_32x32_ssse3, VPX_BITS_8, 32,
|
||||||
|
false)));
|
||||||
|
#endif // HAVE_AVX && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
#if ARCH_X86_64 && HAVE_AVX2
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
AVX2, VP9QuantizeTest,
|
||||||
|
::testing::Values(make_tuple(&QuantFPWrapper<vp9_quantize_fp_avx2>,
|
||||||
|
&QuantFPWrapper<quantize_fp_nz_c>, VPX_BITS_8,
|
||||||
|
16, true)));
|
||||||
|
#endif // HAVE_AVX2 && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
// TODO(webm:1448): dqcoeff is not handled correctly in HBD builds.
|
||||||
|
#if HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
NEON, VP9QuantizeTest,
|
||||||
|
::testing::Values(make_tuple(&vpx_quantize_b_neon, &vpx_quantize_b_c,
|
||||||
|
VPX_BITS_8, 16, false),
|
||||||
|
make_tuple(&vpx_quantize_b_32x32_neon,
|
||||||
|
&vpx_quantize_b_32x32_c, VPX_BITS_8, 32,
|
||||||
|
false),
|
||||||
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_neon>,
|
||||||
|
&QuantFPWrapper<vp9_quantize_fp_c>, VPX_BITS_8,
|
||||||
|
16, true),
|
||||||
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_32x32_neon>,
|
||||||
|
&QuantFPWrapper<vp9_quantize_fp_32x32_c>,
|
||||||
|
VPX_BITS_8, 32, true)));
|
||||||
|
#endif // HAVE_NEON && !CONFIG_VP9_HIGHBITDEPTH
|
||||||
|
|
||||||
|
// Only useful to compare "Speed" test results.
|
||||||
|
INSTANTIATE_TEST_CASE_P(
|
||||||
|
DISABLED_C, VP9QuantizeTest,
|
||||||
|
::testing::Values(
|
||||||
|
make_tuple(&vpx_quantize_b_c, &vpx_quantize_b_c, VPX_BITS_8, 16, false),
|
||||||
|
make_tuple(&vpx_quantize_b_32x32_c, &vpx_quantize_b_32x32_c, VPX_BITS_8,
|
||||||
|
32, false),
|
||||||
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_c>,
|
||||||
|
&QuantFPWrapper<vp9_quantize_fp_c>, VPX_BITS_8, 16, true),
|
||||||
|
make_tuple(&QuantFPWrapper<quantize_fp_nz_c>,
|
||||||
|
&QuantFPWrapper<quantize_fp_nz_c>, VPX_BITS_8, 16, true),
|
||||||
|
make_tuple(&QuantFPWrapper<quantize_fp_32x32_nz_c>,
|
||||||
|
&QuantFPWrapper<quantize_fp_32x32_nz_c>, VPX_BITS_8, 32,
|
||||||
|
true),
|
||||||
|
make_tuple(&QuantFPWrapper<vp9_quantize_fp_32x32_c>,
|
||||||
|
&QuantFPWrapper<vp9_quantize_fp_32x32_c>, VPX_BITS_8, 32,
|
||||||
|
true)));
|
||||||
} // namespace
|
} // namespace
|
||||||
|
215
test/vp9_scale_test.cc
Normal file
215
test/vp9_scale_test.cc
Normal file
@ -0,0 +1,215 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2017 The WebM project authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Use of this source code is governed by a BSD-style license
|
||||||
|
* that can be found in the LICENSE file in the root of the source
|
||||||
|
* tree. An additional intellectual property rights grant can be found
|
||||||
|
* in the file PATENTS. All contributing project authors may
|
||||||
|
* be found in the AUTHORS file in the root of the source tree.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <assert.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "third_party/googletest/src/include/gtest/gtest.h"
|
||||||
|
|
||||||
|
#include "./vp9_rtcd.h"
|
||||||
|
#include "./vpx_config.h"
|
||||||
|
#include "./vpx_scale_rtcd.h"
|
||||||
|
#include "test/clear_system_state.h"
|
||||||
|
#include "test/register_state_check.h"
|
||||||
|
#include "test/vpx_scale_test.h"
|
||||||
|
#include "vpx_mem/vpx_mem.h"
|
||||||
|
#include "vpx_ports/vpx_timer.h"
|
||||||
|
#include "vpx_scale/yv12config.h"
|
||||||
|
|
||||||
|
namespace libvpx_test {
|
||||||
|
|
||||||
|
typedef void (*ScaleFrameFunc)(const YV12_BUFFER_CONFIG *src,
|
||||||
|
YV12_BUFFER_CONFIG *dst,
|
||||||
|
INTERP_FILTER filter_type, int phase_scaler);
|
||||||
|
|
||||||
|
class ScaleTest : public VpxScaleBase,
|
||||||
|
public ::testing::TestWithParam<ScaleFrameFunc> {
|
||||||
|
public:
|
||||||
|
virtual ~ScaleTest() {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual void SetUp() { scale_fn_ = GetParam(); }
|
||||||
|
|
||||||
|
void ReferenceScaleFrame(INTERP_FILTER filter_type, int phase_scaler) {
|
||||||
|
vp9_scale_and_extend_frame_c(&img_, &ref_img_, filter_type, phase_scaler);
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScaleFrame(INTERP_FILTER filter_type, int phase_scaler) {
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
scale_fn_(&img_, &dst_img_, filter_type, phase_scaler));
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunTest(INTERP_FILTER filter_type) {
|
||||||
|
static const int kNumSizesToTest = 20;
|
||||||
|
static const int kNumScaleFactorsToTest = 4;
|
||||||
|
static const int kSizesToTest[] = {
|
||||||
|
2, 4, 6, 8, 10, 12, 14, 16, 18, 20,
|
||||||
|
22, 24, 26, 28, 30, 32, 34, 68, 128, 134
|
||||||
|
};
|
||||||
|
static const int kScaleFactors[] = { 1, 2, 3, 4 };
|
||||||
|
for (int phase_scaler = 0; phase_scaler < 16; ++phase_scaler) {
|
||||||
|
for (int h = 0; h < kNumSizesToTest; ++h) {
|
||||||
|
const int src_height = kSizesToTest[h];
|
||||||
|
for (int w = 0; w < kNumSizesToTest; ++w) {
|
||||||
|
const int src_width = kSizesToTest[w];
|
||||||
|
for (int sf_up_idx = 0; sf_up_idx < kNumScaleFactorsToTest;
|
||||||
|
++sf_up_idx) {
|
||||||
|
const int sf_up = kScaleFactors[sf_up_idx];
|
||||||
|
for (int sf_down_idx = 0; sf_down_idx < kNumScaleFactorsToTest;
|
||||||
|
++sf_down_idx) {
|
||||||
|
const int sf_down = kScaleFactors[sf_down_idx];
|
||||||
|
const int dst_width = src_width * sf_up / sf_down;
|
||||||
|
const int dst_height = src_height * sf_up / sf_down;
|
||||||
|
if (sf_up == sf_down && sf_up != 1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
// I420 frame width and height must be even.
|
||||||
|
if (!dst_width || !dst_height || dst_width & 1 ||
|
||||||
|
dst_height & 1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
// vpx_convolve8_c() has restriction on the step which cannot
|
||||||
|
// exceed 64 (ratio 1 to 4).
|
||||||
|
if (src_width > 4 * dst_width || src_height > 4 * dst_height) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
ASSERT_NO_FATAL_FAILURE(ResetScaleImages(src_width, src_height,
|
||||||
|
dst_width, dst_height));
|
||||||
|
ReferenceScaleFrame(filter_type, phase_scaler);
|
||||||
|
ScaleFrame(filter_type, phase_scaler);
|
||||||
|
if (memcmp(dst_img_.buffer_alloc, ref_img_.buffer_alloc,
|
||||||
|
ref_img_.frame_size)) {
|
||||||
|
printf(
|
||||||
|
"filter_type = %d, phase_scaler = %d, src_width = %4d, "
|
||||||
|
"src_height = %4d, dst_width = %4d, dst_height = %4d, "
|
||||||
|
"scale factor = %d:%d\n",
|
||||||
|
filter_type, phase_scaler, src_width, src_height, dst_width,
|
||||||
|
dst_height, sf_down, sf_up);
|
||||||
|
PrintDiff();
|
||||||
|
}
|
||||||
|
CompareImages(dst_img_);
|
||||||
|
DeallocScaleImages();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PrintDiffComponent(const uint8_t *const ref, const uint8_t *const opt,
|
||||||
|
const int stride, const int width, const int height,
|
||||||
|
const int plane_idx) const {
|
||||||
|
for (int y = 0; y < height; y++) {
|
||||||
|
for (int x = 0; x < width; x++) {
|
||||||
|
if (ref[y * stride + x] != opt[y * stride + x]) {
|
||||||
|
printf("Plane %d pixel[%d][%d] diff:%6d (ref),%6d (opt)\n", plane_idx,
|
||||||
|
y, x, ref[y * stride + x], opt[y * stride + x]);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PrintDiff() const {
|
||||||
|
assert(ref_img_.y_stride == dst_img_.y_stride);
|
||||||
|
assert(ref_img_.y_width == dst_img_.y_width);
|
||||||
|
assert(ref_img_.y_height == dst_img_.y_height);
|
||||||
|
assert(ref_img_.uv_stride == dst_img_.uv_stride);
|
||||||
|
assert(ref_img_.uv_width == dst_img_.uv_width);
|
||||||
|
assert(ref_img_.uv_height == dst_img_.uv_height);
|
||||||
|
|
||||||
|
if (memcmp(dst_img_.buffer_alloc, ref_img_.buffer_alloc,
|
||||||
|
ref_img_.frame_size)) {
|
||||||
|
PrintDiffComponent(ref_img_.y_buffer, dst_img_.y_buffer,
|
||||||
|
ref_img_.y_stride, ref_img_.y_width, ref_img_.y_height,
|
||||||
|
0);
|
||||||
|
PrintDiffComponent(ref_img_.u_buffer, dst_img_.u_buffer,
|
||||||
|
ref_img_.uv_stride, ref_img_.uv_width,
|
||||||
|
ref_img_.uv_height, 1);
|
||||||
|
PrintDiffComponent(ref_img_.v_buffer, dst_img_.v_buffer,
|
||||||
|
ref_img_.uv_stride, ref_img_.uv_width,
|
||||||
|
ref_img_.uv_height, 2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ScaleFrameFunc scale_fn_;
|
||||||
|
};
|
||||||
|
|
||||||
|
TEST_P(ScaleTest, ScaleFrame_EightTap) { RunTest(EIGHTTAP); }
|
||||||
|
TEST_P(ScaleTest, ScaleFrame_EightTapSmooth) { RunTest(EIGHTTAP_SMOOTH); }
|
||||||
|
TEST_P(ScaleTest, ScaleFrame_EightTapSharp) { RunTest(EIGHTTAP_SHARP); }
|
||||||
|
TEST_P(ScaleTest, ScaleFrame_Bilinear) { RunTest(BILINEAR); }
|
||||||
|
|
||||||
|
TEST_P(ScaleTest, DISABLED_Speed) {
|
||||||
|
static const int kCountSpeedTestBlock = 100;
|
||||||
|
static const int kNumScaleFactorsToTest = 4;
|
||||||
|
static const int kScaleFactors[] = { 1, 2, 3, 4 };
|
||||||
|
const int src_width = 1280;
|
||||||
|
const int src_height = 720;
|
||||||
|
for (INTERP_FILTER filter_type = 2; filter_type < 4; ++filter_type) {
|
||||||
|
for (int phase_scaler = 0; phase_scaler < 2; ++phase_scaler) {
|
||||||
|
for (int sf_up_idx = 0; sf_up_idx < kNumScaleFactorsToTest; ++sf_up_idx) {
|
||||||
|
const int sf_up = kScaleFactors[sf_up_idx];
|
||||||
|
for (int sf_down_idx = 0; sf_down_idx < kNumScaleFactorsToTest;
|
||||||
|
++sf_down_idx) {
|
||||||
|
const int sf_down = kScaleFactors[sf_down_idx];
|
||||||
|
const int dst_width = src_width * sf_up / sf_down;
|
||||||
|
const int dst_height = src_height * sf_up / sf_down;
|
||||||
|
if (sf_up == sf_down && sf_up != 1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
// I420 frame width and height must be even.
|
||||||
|
if (dst_width & 1 || dst_height & 1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
ASSERT_NO_FATAL_FAILURE(
|
||||||
|
ResetScaleImages(src_width, src_height, dst_width, dst_height));
|
||||||
|
ASM_REGISTER_STATE_CHECK(
|
||||||
|
ReferenceScaleFrame(filter_type, phase_scaler));
|
||||||
|
|
||||||
|
vpx_usec_timer timer;
|
||||||
|
vpx_usec_timer_start(&timer);
|
||||||
|
for (int i = 0; i < kCountSpeedTestBlock; ++i) {
|
||||||
|
ScaleFrame(filter_type, phase_scaler);
|
||||||
|
}
|
||||||
|
libvpx_test::ClearSystemState();
|
||||||
|
vpx_usec_timer_mark(&timer);
|
||||||
|
const int elapsed_time =
|
||||||
|
static_cast<int>(vpx_usec_timer_elapsed(&timer) / 1000);
|
||||||
|
CompareImages(dst_img_);
|
||||||
|
DeallocScaleImages();
|
||||||
|
|
||||||
|
printf(
|
||||||
|
"filter_type = %d, phase_scaler = %d, src_width = %4d, "
|
||||||
|
"src_height = %4d, dst_width = %4d, dst_height = %4d, "
|
||||||
|
"scale factor = %d:%d, scale time: %5d ms\n",
|
||||||
|
filter_type, phase_scaler, src_width, src_height, dst_width,
|
||||||
|
dst_height, sf_down, sf_up, elapsed_time);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
INSTANTIATE_TEST_CASE_P(C, ScaleTest,
|
||||||
|
::testing::Values(vp9_scale_and_extend_frame_c));
|
||||||
|
|
||||||
|
#if HAVE_SSSE3
|
||||||
|
INSTANTIATE_TEST_CASE_P(SSSE3, ScaleTest,
|
||||||
|
::testing::Values(vp9_scale_and_extend_frame_ssse3));
|
||||||
|
#endif // HAVE_SSSE3
|
||||||
|
|
||||||
|
#if HAVE_NEON
|
||||||
|
INSTANTIATE_TEST_CASE_P(NEON, ScaleTest,
|
||||||
|
::testing::Values(vp9_scale_and_extend_frame_neon));
|
||||||
|
#endif // HAVE_NEON
|
||||||
|
|
||||||
|
} // namespace libvpx_test
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user