filters/turn.cpp
| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | // Avisynth v2.5. Copyright 2002 Ben Rudiak-Gould et al. | ||
| 2 | // http://avisynth.nl | ||
| 3 | |||
| 4 | // This program is free software; you can redistribute it and/or modify | ||
| 5 | // it under the terms of the GNU General Public License as published by | ||
| 6 | // the Free Software Foundation; either version 2 of the License, or | ||
| 7 | // (at your option) any later version. | ||
| 8 | // | ||
| 9 | // This program is distributed in the hope that it will be useful, | ||
| 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 12 | // GNU General Public License for more details. | ||
| 13 | // | ||
| 14 | // You should have received a copy of the GNU General Public License | ||
| 15 | // along with this program; if not, write to the Free Software | ||
| 16 | // Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA, or visit | ||
| 17 | // http://www.gnu.org/copyleft/gpl.html . | ||
| 18 | // | ||
| 19 | // Linking Avisynth statically or dynamically with other modules is making a | ||
| 20 | // combined work based on Avisynth. Thus, the terms and conditions of the GNU | ||
| 21 | // General Public License cover the whole combination. | ||
| 22 | // | ||
| 23 | // As a special exception, the copyright holders of Avisynth give you | ||
| 24 | // permission to link Avisynth with independent modules that communicate with | ||
| 25 | // Avisynth solely through the interfaces defined in avisynth.h, regardless of the license | ||
| 26 | // terms of these independent modules, and to copy and distribute the | ||
| 27 | // resulting combined work under terms of your choice, provided that | ||
| 28 | // every copy of the combined work is accompanied by a complete copy of | ||
| 29 | // the source code of Avisynth (the version of Avisynth used to produce the | ||
| 30 | // combined work), being distributed under the terms of the GNU General | ||
| 31 | // Public License plus this exception. An independent module is a module | ||
| 32 | // which is not derived from or based on Avisynth, such as 3rd-party filters, | ||
| 33 | // import and export plugins, or graphical user interfaces. | ||
| 34 | |||
| 35 | /* | ||
| 36 | ** Turn. version 0.1 | ||
| 37 | ** (c) 2003 - Ernst Peché | ||
| 38 | ** | ||
| 39 | */ | ||
| 40 | |||
| 41 | #include "turn.h" | ||
| 42 | #ifdef INTEL_INTRINSICS | ||
| 43 | #include "intel/turn_sse.h" | ||
| 44 | #include "intel/turn_avx2.h" | ||
| 45 | #endif | ||
| 46 | #ifdef NEON_INTRINSICS | ||
| 47 | #include "aarch64/turn_neon.h" | ||
| 48 | #endif | ||
| 49 | #include "resample.h" | ||
| 50 | #include "planeswap.h" | ||
| 51 | #include "../core/internal.h" | ||
| 52 | #include <stdint.h> | ||
| 53 | #include "../convert/convert_helper.h" | ||
| 54 | |||
| 55 | |||
| 56 | extern const AVSFunction Turn_filters[] = { | ||
| 57 | { "TurnLeft", BUILTIN_FUNC_PREFIX, "c", Turn::create_turnleft }, | ||
| 58 | { "TurnRight", BUILTIN_FUNC_PREFIX, "c", Turn::create_turnright }, | ||
| 59 | { "Turn180", BUILTIN_FUNC_PREFIX, "c", Turn::create_turn180 }, | ||
| 60 | { 0 } | ||
| 61 | }; | ||
| 62 | |||
| 63 | enum TurnDirection | ||
| 64 | { | ||
| 65 | DIRECTION_LEFT = 0, | ||
| 66 | DIRECTION_RIGHT = 1, | ||
| 67 | DIRECTION_180 = 2 | ||
| 68 | }; | ||
| 69 | |||
| 70 | |||
| 71 | // TurnLeft() is FlipVertical().TurnRight().FlipVertical(). | ||
| 72 | // Therefore, we don't have to implement both TurnRight() and TurnLeft(). | ||
| 73 | |||
| 74 | template <typename T> | ||
| 75 | 160 | void turn_right_plane_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int height, int src_pitch, int dst_pitch) | |
| 76 | { | ||
| 77 | 160 | const BYTE* AVS_RESTRICT s0 = srcp + src_pitch * (height - 1); | |
| 78 | |||
| 79 |
12/12void turn_right_plane_c<Rgb24>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 42 times.
✓ Branch 7 → 8 taken 8 times.
void turn_right_plane_c<Rgb48>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 26 times.
✓ Branch 7 → 8 taken 6 times.
void turn_right_plane_c<unsigned char>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 406 times.
✓ Branch 7 → 8 taken 69 times.
void turn_right_plane_c<unsigned int>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 288 times.
✓ Branch 7 → 8 taken 32 times.
void turn_right_plane_c<unsigned long>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 96 times.
✓ Branch 7 → 8 taken 17 times.
void turn_right_plane_c<unsigned short>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 272 times.
✓ Branch 7 → 8 taken 28 times.
|
1290 | for (int y = 0; y < height; ++y) |
| 80 | { | ||
| 81 | 1130 | BYTE* AVS_RESTRICT d0 = dstp; | |
| 82 |
12/12void turn_right_plane_c<Rgb24>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 382 times.
✓ Branch 5 → 6 taken 42 times.
void turn_right_plane_c<Rgb48>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 170 times.
✓ Branch 5 → 6 taken 26 times.
void turn_right_plane_c<unsigned char>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 6542 times.
✓ Branch 5 → 6 taken 406 times.
void turn_right_plane_c<unsigned int>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 1888 times.
✓ Branch 5 → 6 taken 288 times.
void turn_right_plane_c<unsigned long>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 352 times.
✓ Branch 5 → 6 taken 96 times.
void turn_right_plane_c<unsigned short>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 3008 times.
✓ Branch 5 → 6 taken 272 times.
|
13472 | for (int x = 0; x < src_rowsize; x += sizeof(T)) |
| 83 | { | ||
| 84 | 12342 | *reinterpret_cast<T*>(d0) = *reinterpret_cast<const T*>(s0 + x); | |
| 85 | 12342 | d0 += dst_pitch; | |
| 86 | } | ||
| 87 | 1130 | s0 -= src_pitch; | |
| 88 | 1130 | dstp += sizeof(T); | |
| 89 | } | ||
| 90 | 160 | } | |
| 91 | |||
| 92 | |||
| 93 | // Explicit instantiation, can be used from other modules. | ||
| 94 | template void turn_right_plane_c<uint64_t>(const BYTE*, BYTE*, int, int, int, int); | ||
| 95 | |||
| 96 | |||
| 97 | 64 | void turn_right_plane_8_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 98 | { | ||
| 99 | 64 | turn_right_plane_c<BYTE>(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 100 | 64 | } | |
| 101 | |||
| 102 | |||
| 103 | 5 | void turn_left_plane_8_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 104 | { | ||
| 105 | 5 | turn_right_plane_c<BYTE>(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 106 | 5 | } | |
| 107 | |||
| 108 | |||
| 109 | 24 | void turn_right_plane_16_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 110 | { | ||
| 111 | 24 | turn_right_plane_c<uint16_t>(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 112 | 24 | } | |
| 113 | |||
| 114 | |||
| 115 | 4 | void turn_left_plane_16_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 116 | { | ||
| 117 | 4 | turn_right_plane_c<uint16_t>(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize / 2 - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 118 | 4 | } | |
| 119 | |||
| 120 | |||
| 121 | 24 | void turn_right_plane_32_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 122 | { | ||
| 123 | 24 | turn_right_plane_c<uint32_t>(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 124 | 24 | } | |
| 125 | |||
| 126 | |||
| 127 | 8 | void turn_left_plane_32_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 128 | { | ||
| 129 | 8 | turn_right_plane_c<uint32_t>(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize / 4 - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 130 | 8 | } | |
| 131 | |||
| 132 | |||
| 133 | // on RGB, TurnLeft and TurnRight are reversed. | ||
| 134 | 4 | void turn_left_rgb32_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 135 | { | ||
| 136 | 4 | turn_right_plane_32_c(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 137 | 4 | } | |
| 138 | |||
| 139 | |||
| 140 | 4 | void turn_right_rgb32_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 141 | { | ||
| 142 | 4 | turn_left_plane_32_c(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 143 | 4 | } | |
| 144 | |||
| 145 | |||
| 146 | struct Rgb24 { | ||
| 147 | BYTE b, g, r; | ||
| 148 | }; | ||
| 149 | |||
| 150 | |||
| 151 | 4 | void turn_left_rgb24(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 152 | { | ||
| 153 | 4 | turn_right_plane_c<Rgb24>(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 154 | 4 | } | |
| 155 | |||
| 156 | |||
| 157 | 4 | void turn_right_rgb24(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 158 | { | ||
| 159 | 4 | turn_right_plane_c<Rgb24>(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize / 3 - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 160 | 4 | } | |
| 161 | |||
| 162 | |||
| 163 | struct Rgb48 { | ||
| 164 | uint16_t b, g, r; | ||
| 165 | }; | ||
| 166 | |||
| 167 | |||
| 168 | 3 | void turn_left_rgb48_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 169 | { | ||
| 170 | 3 | turn_right_plane_c<Rgb48>(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 171 | 3 | } | |
| 172 | |||
| 173 | |||
| 174 | 3 | void turn_right_rgb48_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 175 | { | ||
| 176 | 3 | turn_right_plane_c<Rgb48>(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize / 6 - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 177 | 3 | } | |
| 178 | |||
| 179 | |||
| 180 | 4 | void turn_left_rgb64_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 181 | { | ||
| 182 | 4 | turn_right_plane_c<uint64_t>(srcp, dstp, src_rowsize, src_height, src_pitch, dst_pitch); | |
| 183 | 4 | } | |
| 184 | |||
| 185 | |||
| 186 | 4 | void turn_right_rgb64_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 187 | { | ||
| 188 | 4 | turn_right_plane_c<uint64_t>(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize / 8 - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 189 | 4 | } | |
| 190 | |||
| 191 | |||
| 192 | ✗ | static void turn_right_yuy2(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 193 | { | ||
| 194 | ✗ | dstp += (src_height - 2) * 2; | |
| 195 | |||
| 196 | ✗ | for (int y = 0; y < src_height; y += 2) | |
| 197 | { | ||
| 198 | ✗ | BYTE* d0 = dstp - y * 2; | |
| 199 | ✗ | for (int x = 0; x < src_rowsize; x += 4) | |
| 200 | { | ||
| 201 | ✗ | int u = (srcp[x + 1] + srcp[x + 1 + src_pitch] + 1) / 2; | |
| 202 | ✗ | int v = (srcp[x + 3] + srcp[x + 3 + src_pitch] + 1) / 2; | |
| 203 | |||
| 204 | ✗ | d0[0] = srcp[x + src_pitch]; | |
| 205 | ✗ | d0[1] = u; | |
| 206 | ✗ | d0[2] = srcp[x]; | |
| 207 | ✗ | d0[3] = v; | |
| 208 | ✗ | d0 += dst_pitch; | |
| 209 | |||
| 210 | ✗ | d0[0] = srcp[x + src_pitch + 2]; | |
| 211 | ✗ | d0[1] = u; | |
| 212 | ✗ | d0[2] = srcp[x + 2]; | |
| 213 | ✗ | d0[3] = v; | |
| 214 | ✗ | d0 += dst_pitch; | |
| 215 | } | ||
| 216 | ✗ | srcp += src_pitch * 2; | |
| 217 | } | ||
| 218 | ✗ | } | |
| 219 | |||
| 220 | |||
| 221 | ✗ | static void turn_left_yuy2(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 222 | { | ||
| 223 | ✗ | turn_right_yuy2(srcp + src_pitch * (src_height - 1), dstp + dst_pitch * (src_rowsize / 2 - 1), src_rowsize, src_height, -src_pitch, -dst_pitch); | |
| 224 | ✗ | } | |
| 225 | |||
| 226 | |||
| 227 | template <typename T> | ||
| 228 | 24 | void turn_180_plane_c(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 229 | { | ||
| 230 | 24 | dstp += dst_pitch * (src_height - 1) + src_rowsize - sizeof(T); | |
| 231 | 24 | src_rowsize /= sizeof(T); | |
| 232 | |||
| 233 |
8/12void turn_180_plane_c<Rgb24>(unsigned char const*, unsigned char*, int, int, int, int):
✗ Branch 7 → 3 not taken.
✗ Branch 7 → 8 not taken.
void turn_180_plane_c<Rgb48>(unsigned char const*, unsigned char*, int, int, int, int):
✗ Branch 7 → 3 not taken.
✗ Branch 7 → 8 not taken.
void turn_180_plane_c<unsigned char>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 63 times.
✓ Branch 7 → 8 taken 7 times.
void turn_180_plane_c<unsigned int>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 35 times.
✓ Branch 7 → 8 taken 5 times.
void turn_180_plane_c<unsigned long>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 35 times.
✓ Branch 7 → 8 taken 5 times.
void turn_180_plane_c<unsigned short>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 7 → 3 taken 49 times.
✓ Branch 7 → 8 taken 7 times.
|
206 | for (int y = 0; y < src_height; ++y) |
| 234 | { | ||
| 235 | 182 | const T* AVS_RESTRICT s0 = reinterpret_cast<const T*>(srcp); | |
| 236 | 182 | T* AVS_RESTRICT d0 = reinterpret_cast<T*>(dstp); | |
| 237 | |||
| 238 |
8/12void turn_180_plane_c<Rgb24>(unsigned char const*, unsigned char*, int, int, int, int):
✗ Branch 5 → 4 not taken.
✗ Branch 5 → 6 not taken.
void turn_180_plane_c<Rgb48>(unsigned char const*, unsigned char*, int, int, int, int):
✗ Branch 5 → 4 not taken.
✗ Branch 5 → 6 not taken.
void turn_180_plane_c<unsigned char>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 1503 times.
✓ Branch 5 → 6 taken 63 times.
void turn_180_plane_c<unsigned int>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 259 times.
✓ Branch 5 → 6 taken 35 times.
void turn_180_plane_c<unsigned long>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 147 times.
✓ Branch 5 → 6 taken 35 times.
void turn_180_plane_c<unsigned short>(unsigned char const*, unsigned char*, int, int, int, int):
✓ Branch 5 → 4 taken 609 times.
✓ Branch 5 → 6 taken 49 times.
|
2700 | for (int x = 0; x < src_rowsize; ++x) |
| 239 | { | ||
| 240 | 2518 | d0[-x] = s0[x]; | |
| 241 | } | ||
| 242 | 182 | srcp += src_pitch; | |
| 243 | 182 | dstp -= dst_pitch; | |
| 244 | } | ||
| 245 | 24 | } | |
| 246 | |||
| 247 | ✗ | static void turn_180_yuy2(const BYTE* srcp, BYTE* dstp, int src_rowsize, int src_height, int src_pitch, int dst_pitch) | |
| 248 | { | ||
| 249 | ✗ | dstp += dst_pitch * (src_height - 1) + src_rowsize - 4; | |
| 250 | |||
| 251 | ✗ | for (int y = 0; y < src_height; ++y) | |
| 252 | { | ||
| 253 | ✗ | for (int x = 0; x < src_rowsize; x += 4) | |
| 254 | { | ||
| 255 | ✗ | dstp[-x + 2] = srcp[x + 0]; | |
| 256 | ✗ | dstp[-x + 1] = srcp[x + 1]; | |
| 257 | ✗ | dstp[-x + 0] = srcp[x + 2]; | |
| 258 | ✗ | dstp[-x + 3] = srcp[x + 3]; | |
| 259 | } | ||
| 260 | ✗ | srcp += src_pitch; | |
| 261 | ✗ | dstp -= dst_pitch; | |
| 262 | } | ||
| 263 | ✗ | } | |
| 264 | |||
| 265 | |||
| 266 |
4/8✓ Branch 2 → 3 taken 17 times.
✗ Branch 2 → 60 not taken.
✓ Branch 3 → 4 taken 17 times.
✗ Branch 3 → 58 not taken.
✓ Branch 5 → 6 taken 17 times.
✗ Branch 5 → 65 not taken.
✓ Branch 6 → 7 taken 17 times.
✗ Branch 6 → 63 not taken.
|
17 | Turn::Turn(PClip c, int direction, IScriptEnvironment* env) : GenericVideoFilter(c), u_or_b_source(nullptr), v_or_r_source(nullptr) |
| 267 | { | ||
| 268 |
2/2✓ Branch 7 → 8 taken 4 times.
✓ Branch 7 → 9 taken 13 times.
|
17 | if (vi.pixel_type & VideoInfo::CS_INTERLEAVED) { |
| 269 | 4 | num_planes = 1; | |
| 270 |
7/10✓ Branch 9 → 10 taken 13 times.
✗ Branch 9 → 61 not taken.
✓ Branch 10 → 11 taken 13 times.
✗ Branch 10 → 13 not taken.
✓ Branch 11 → 12 taken 13 times.
✗ Branch 11 → 61 not taken.
✓ Branch 12 → 13 taken 3 times.
✓ Branch 12 → 14 taken 10 times.
✓ Branch 15 → 16 taken 3 times.
✓ Branch 15 → 17 taken 10 times.
|
13 | } else if (vi.IsPlanarRGBA() || vi.IsYUVA()) { |
| 271 | 3 | num_planes = 4; | |
| 272 | } else { | ||
| 273 | 10 | num_planes = 3; | |
| 274 | } | ||
| 275 | |||
| 276 |
3/4✓ Branch 18 → 19 taken 17 times.
✗ Branch 18 → 61 not taken.
✓ Branch 19 → 20 taken 4 times.
✓ Branch 19 → 21 taken 13 times.
|
17 | splanes[0] = vi.IsRGB() ? PLANAR_G : PLANAR_Y; |
| 277 |
3/4✓ Branch 22 → 23 taken 17 times.
✗ Branch 22 → 61 not taken.
✓ Branch 23 → 24 taken 4 times.
✓ Branch 23 → 25 taken 13 times.
|
17 | splanes[1] = vi.IsRGB() ? PLANAR_B : PLANAR_U; |
| 278 |
3/4✓ Branch 26 → 27 taken 17 times.
✗ Branch 26 → 61 not taken.
✓ Branch 27 → 28 taken 4 times.
✓ Branch 27 → 29 taken 13 times.
|
17 | splanes[2] = vi.IsRGB() ? PLANAR_R : PLANAR_V; |
| 279 | 17 | splanes[3] = PLANAR_A; | |
| 280 | |||
| 281 |
2/2✓ Branch 30 → 31 taken 14 times.
✓ Branch 30 → 56 taken 3 times.
|
17 | if (direction != DIRECTION_180) |
| 282 | { | ||
| 283 |
3/8✓ Branch 31 → 32 taken 14 times.
✗ Branch 31 → 61 not taken.
✗ Branch 32 → 33 not taken.
✓ Branch 32 → 35 taken 14 times.
✗ Branch 33 → 34 not taken.
✗ Branch 33 → 35 not taken.
✗ Branch 36 → 37 not taken.
✓ Branch 36 → 38 taken 14 times.
|
14 | if (vi.IsYUY2() && (vi.height & 1)) |
| 284 | { | ||
| 285 | ✗ | env->ThrowError("Turn: YUY2 data must have mod2 height."); | |
| 286 | } | ||
| 287 |
2/2✓ Branch 38 → 39 taken 10 times.
✓ Branch 38 → 55 taken 4 times.
|
14 | if (num_planes > 1) { |
| 288 |
3/6✓ Branch 39 → 40 taken 10 times.
✗ Branch 39 → 61 not taken.
✗ Branch 40 → 41 not taken.
✓ Branch 40 → 42 taken 10 times.
✓ Branch 42 → 43 taken 10 times.
✗ Branch 42 → 61 not taken.
|
10 | int mod_h = vi.IsRGB() ? 1 : (1 << vi.GetPlaneWidthSubsampling(PLANAR_U)); |
| 289 |
3/6✓ Branch 44 → 45 taken 10 times.
✗ Branch 44 → 61 not taken.
✗ Branch 45 → 46 not taken.
✓ Branch 45 → 47 taken 10 times.
✓ Branch 47 → 48 taken 10 times.
✗ Branch 47 → 61 not taken.
|
10 | int mod_v = vi.IsRGB() ? 1 : (1 << vi.GetPlaneHeightSubsampling(PLANAR_U)); |
| 290 |
2/2✓ Branch 49 → 50 taken 2 times.
✓ Branch 49 → 55 taken 8 times.
|
10 | if (mod_h != mod_v) |
| 291 | { | ||
| 292 |
1/2✗ Branch 50 → 51 not taken.
✓ Branch 50 → 52 taken 2 times.
|
2 | if (vi.width % mod_h) |
| 293 | { | ||
| 294 | ✗ | env->ThrowError("Turn: Planar data must have MOD %d height.", mod_h); | |
| 295 | } | ||
| 296 |
1/2✗ Branch 52 → 53 not taken.
✓ Branch 52 → 54 taken 2 times.
|
2 | if (vi.height % mod_v) |
| 297 | { | ||
| 298 | ✗ | env->ThrowError("Turn: Planar data must have MOD %d width.", mod_v); | |
| 299 | } | ||
| 300 |
1/2✓ Branch 54 → 55 taken 2 times.
✗ Branch 54 → 61 not taken.
|
2 | SetUVSource(mod_h, mod_v, env); |
| 301 | } | ||
| 302 | } | ||
| 303 | 14 | int t = vi.width; | |
| 304 | 14 | vi.width = vi.height; | |
| 305 | 14 | vi.height = t; | |
| 306 | } | ||
| 307 | |||
| 308 |
1/2✓ Branch 56 → 57 taken 17 times.
✗ Branch 56 → 61 not taken.
|
17 | SetTurnFunction(direction, env); |
| 309 | 17 | } | |
| 310 | |||
| 311 | |||
| 312 | 2 | void Turn::SetUVSource(int mod_h, int mod_v, IScriptEnvironment* env) | |
| 313 | { | ||
| 314 |
1/2✓ Branch 2 → 3 taken 2 times.
✗ Branch 2 → 86 not taken.
|
2 | MitchellNetravaliFilter filter(1.0 / 3, 1.0 / 3); |
| 315 |
4/12✓ Branch 3 → 4 taken 2 times.
✗ Branch 3 → 48 not taken.
✓ Branch 4 → 5 taken 2 times.
✗ Branch 4 → 48 not taken.
✓ Branch 5 → 6 taken 2 times.
✗ Branch 5 → 48 not taken.
✓ Branch 6 → 7 taken 2 times.
✗ Branch 6 → 48 not taken.
✗ Branch 48 → 49 not taken.
✗ Branch 48 → 52 not taken.
✗ Branch 50 → 51 not taken.
✗ Branch 50 → 52 not taken.
|
10 | AVSValue subs[4] = { 0.0, 0.0, 0.0, 0.0 }; |
| 316 | |||
| 317 |
1/2✓ Branch 7 → 8 taken 2 times.
✗ Branch 7 → 77 not taken.
|
2 | bool isRGB = vi.IsRGB(); // can be planar |
| 318 | |||
| 319 |
6/14✓ Branch 8 → 9 taken 2 times.
✗ Branch 8 → 77 not taken.
✗ Branch 9 → 10 not taken.
✓ Branch 9 → 11 taken 2 times.
✓ Branch 12 → 13 taken 2 times.
✗ Branch 12 → 55 not taken.
✓ Branch 13 → 14 taken 2 times.
✗ Branch 13 → 53 not taken.
✓ Branch 14 → 15 taken 2 times.
✗ Branch 14 → 53 not taken.
✗ Branch 16 → 17 not taken.
✓ Branch 16 → 18 taken 2 times.
✗ Branch 56 → 57 not taken.
✗ Branch 56 → 58 not taken.
|
2 | u_or_b_source = new SwapUVToY(child, isRGB ? SwapUVToY::BToY8 : SwapUVToY::UToY8, env); // Y16 and Y32 capable |
| 320 |
6/14✓ Branch 18 → 19 taken 2 times.
✗ Branch 18 → 77 not taken.
✗ Branch 19 → 20 not taken.
✓ Branch 19 → 21 taken 2 times.
✓ Branch 22 → 23 taken 2 times.
✗ Branch 22 → 61 not taken.
✓ Branch 23 → 24 taken 2 times.
✗ Branch 23 → 59 not taken.
✓ Branch 24 → 25 taken 2 times.
✗ Branch 24 → 59 not taken.
✗ Branch 26 → 27 not taken.
✓ Branch 26 → 28 taken 2 times.
✗ Branch 62 → 63 not taken.
✗ Branch 62 → 64 not taken.
|
2 | v_or_r_source = new SwapUVToY(child, isRGB ? SwapUVToY::RToY8 : SwapUVToY::VToY8, env); |
| 321 | |||
| 322 |
1/2✓ Branch 29 → 30 taken 2 times.
✗ Branch 29 → 77 not taken.
|
2 | const VideoInfo& vi_u = u_or_b_source->GetVideoInfo(); |
| 323 | |||
| 324 | 2 | const int uv_height = vi_u.height * mod_v / mod_h; | |
| 325 | 2 | const int uv_width = vi_u.width * mod_h / mod_v; | |
| 326 | |||
| 327 | 2 | const int force = 0; | |
| 328 | 2 | const bool preserve_center = true; | |
| 329 | 2 | const char* placement_name = ""; // n/a | |
| 330 | 2 | const int forced_chroma_placement = -1; // n/a | |
| 331 | // chroma planes are extracted, behave like Y when resized, no chroma is involved | ||
| 332 | |||
| 333 |
3/6✓ Branch 30 → 31 taken 2 times.
✗ Branch 30 → 69 not taken.
✓ Branch 31 → 32 taken 2 times.
✗ Branch 31 → 67 not taken.
✓ Branch 32 → 33 taken 2 times.
✗ Branch 32 → 65 not taken.
|
2 | u_or_b_source = FilteredResize::CreateResize(u_or_b_source, uv_width, uv_height, subs, force, &filter, preserve_center, placement_name, forced_chroma_placement, env); |
| 334 |
3/6✓ Branch 35 → 36 taken 2 times.
✗ Branch 35 → 75 not taken.
✓ Branch 36 → 37 taken 2 times.
✗ Branch 36 → 73 not taken.
✓ Branch 37 → 38 taken 2 times.
✗ Branch 37 → 71 not taken.
|
2 | v_or_r_source = FilteredResize::CreateResize(v_or_r_source, uv_width, uv_height, subs, force, &filter, preserve_center, placement_name, forced_chroma_placement, env); |
| 335 | |||
| 336 | 2 | splanes[1] = 0; | |
| 337 | 2 | splanes[2] = 0; | |
| 338 |
2/4✓ Branch 41 → 42 taken 8 times.
✓ Branch 41 → 45 taken 2 times.
✗ Branch 78 → 79 not taken.
✗ Branch 78 → 82 not taken.
|
12 | } |
| 339 | |||
| 340 | |||
| 341 | 17 | void Turn::SetTurnFunction(int direction, IScriptEnvironment* env) | |
| 342 | { | ||
| 343 | #ifdef INTEL_INTRINSICS | ||
| 344 |
1/2✓ Branch 2 → 3 taken 17 times.
✗ Branch 2 → 55 not taken.
|
17 | const int cpu = env->GetCPUFlags(); |
| 345 | 17 | const bool sse2 = cpu & CPUF_SSE2; | |
| 346 | 17 | const bool ssse3 = cpu & CPUF_SSSE3; | |
| 347 | 17 | const bool avx2 = cpu & CPUF_AVX2; | |
| 348 | #endif | ||
| 349 | |||
| 350 | #ifdef NEON_INTRINSICS | ||
| 351 | const bool neon = env->GetCPUFlags() & CPUF_ARM_NEON; | ||
| 352 | const bool dotprod = env->GetCPUFlags() & CPUF_ARM_DOTPROD; | ||
| 353 | #endif | ||
| 354 | |||
| 355 | TurnFuncPtr funcs[3]; | ||
| 356 | 17 | auto set_funcs = [&funcs](TurnFuncPtr tleft, TurnFuncPtr tright, TurnFuncPtr t180) { | |
| 357 | 17 | funcs[0] = tleft; | |
| 358 | 17 | funcs[1] = tright; | |
| 359 | 17 | funcs[2] = t180; | |
| 360 | 34 | }; | |
| 361 | |||
| 362 |
2/4✓ Branch 3 → 4 taken 17 times.
✗ Branch 3 → 55 not taken.
✗ Branch 4 → 5 not taken.
✓ Branch 4 → 10 taken 17 times.
|
17 | if (vi.IsRGB64()) |
| 363 | { | ||
| 364 | #ifdef INTEL_INTRINSICS | ||
| 365 | ✗ | if (avx2) | |
| 366 | ✗ | set_funcs(turn_left_rgb64_avx2, turn_right_rgb64_avx2, turn_180_plane_avx2<uint64_t>); | |
| 367 | ✗ | else if (sse2) | |
| 368 | ✗ | set_funcs(turn_left_rgb64_sse2, turn_right_rgb64_sse2, turn_180_plane_sse2<uint64_t>); | |
| 369 | else | ||
| 370 | #elif defined(NEON_INTRINSICS) | ||
| 371 | if (neon) | ||
| 372 | set_funcs(turn_left_rgb64_neon, turn_right_rgb64_neon, turn_180_plane_neon<uint64_t>); | ||
| 373 | else | ||
| 374 | #endif | ||
| 375 | { | ||
| 376 | ✗ | set_funcs(turn_left_rgb64_c, turn_right_rgb64_c, turn_180_plane_c<uint64_t>); | |
| 377 | } | ||
| 378 | |||
| 379 | } | ||
| 380 |
3/4✓ Branch 10 → 11 taken 17 times.
✗ Branch 10 → 55 not taken.
✓ Branch 11 → 12 taken 2 times.
✓ Branch 11 → 13 taken 15 times.
|
17 | else if (vi.IsRGB48()) |
| 381 | { | ||
| 382 | 2 | set_funcs(turn_left_rgb48_c, turn_right_rgb48_c, turn_180_plane_c<Rgb48>); | |
| 383 | } | ||
| 384 |
2/4✓ Branch 13 → 14 taken 15 times.
✗ Branch 13 → 55 not taken.
✗ Branch 14 → 15 not taken.
✓ Branch 14 → 20 taken 15 times.
|
15 | else if (vi.IsRGB32()) |
| 385 | { | ||
| 386 | #ifdef INTEL_INTRINSICS | ||
| 387 | ✗ | if (avx2) | |
| 388 | ✗ | set_funcs(turn_left_rgb32_avx2, turn_right_rgb32_avx2, turn_180_plane_avx2<uint32_t>); | |
| 389 | ✗ | else if (sse2) | |
| 390 | ✗ | set_funcs(turn_left_rgb32_sse2, turn_right_rgb32_sse2, turn_180_plane_sse2<uint32_t>); | |
| 391 | else | ||
| 392 | #elif defined(NEON_INTRINSICS) | ||
| 393 | if (neon) | ||
| 394 | set_funcs(turn_left_rgb32_neon, turn_right_rgb32_neon, turn_180_plane_neon<uint32_t>); | ||
| 395 | else | ||
| 396 | #endif | ||
| 397 | { | ||
| 398 | ✗ | set_funcs(turn_left_rgb32_c, turn_right_rgb32_c, turn_180_plane_c<uint32_t>); | |
| 399 | } | ||
| 400 | } | ||
| 401 |
3/4✓ Branch 20 → 21 taken 15 times.
✗ Branch 20 → 55 not taken.
✓ Branch 21 → 22 taken 2 times.
✓ Branch 21 → 23 taken 13 times.
|
15 | else if (vi.IsRGB24()) |
| 402 | { | ||
| 403 | 2 | set_funcs(turn_left_rgb24, turn_right_rgb24, turn_180_plane_c<Rgb24>); | |
| 404 | } | ||
| 405 |
2/4✓ Branch 23 → 24 taken 13 times.
✗ Branch 23 → 55 not taken.
✗ Branch 24 → 25 not taken.
✓ Branch 24 → 26 taken 13 times.
|
13 | else if (vi.IsYUY2()) |
| 406 | { | ||
| 407 | ✗ | set_funcs(turn_left_yuy2, turn_right_yuy2, turn_180_yuy2); | |
| 408 | } | ||
| 409 |
3/4✓ Branch 26 → 27 taken 13 times.
✗ Branch 26 → 55 not taken.
✓ Branch 27 → 28 taken 10 times.
✓ Branch 27 → 36 taken 3 times.
|
13 | else if (vi.ComponentSize() == 1) // 8 bit |
| 410 | { | ||
| 411 | #ifdef INTEL_INTRINSICS | ||
| 412 |
1/2✓ Branch 28 → 29 taken 10 times.
✗ Branch 28 → 30 not taken.
|
10 | if(avx2) |
| 413 | { | ||
| 414 | 10 | set_funcs(turn_left_plane_8_avx2, turn_right_plane_8_avx2, turn_180_plane_avx2<BYTE>); | |
| 415 | } | ||
| 416 | ✗ | else if (sse2) | |
| 417 | { | ||
| 418 | ✗ | set_funcs(turn_left_plane_8_sse2, turn_right_plane_8_sse2, | |
| 419 | ssse3 ? turn_180_plane_ssse3<BYTE> : turn_180_plane_sse2<BYTE>); | ||
| 420 | } | ||
| 421 | else | ||
| 422 | #elif defined(NEON_INTRINSICS) | ||
| 423 | if (neon) | ||
| 424 | { | ||
| 425 | set_funcs(turn_left_plane_8_neon, turn_right_plane_8_neon, turn_180_plane_neon<BYTE>); | ||
| 426 | } | ||
| 427 | else | ||
| 428 | #endif | ||
| 429 | { | ||
| 430 | ✗ | set_funcs(turn_left_plane_8_c, turn_right_plane_8_c, turn_180_plane_c<BYTE>); | |
| 431 | } | ||
| 432 | } | ||
| 433 |
2/4✓ Branch 36 → 37 taken 3 times.
✗ Branch 36 → 55 not taken.
✓ Branch 37 → 38 taken 3 times.
✗ Branch 37 → 46 not taken.
|
3 | else if (vi.ComponentSize() == 2) // 16 bit |
| 434 | { | ||
| 435 | #ifdef INTEL_INTRINSICS | ||
| 436 |
1/2✓ Branch 38 → 39 taken 3 times.
✗ Branch 38 → 40 not taken.
|
3 | if (avx2) |
| 437 | { | ||
| 438 | 3 | set_funcs(turn_left_plane_16_avx2, turn_right_plane_16_avx2, turn_180_plane_avx2<uint16_t>); | |
| 439 | } | ||
| 440 | ✗ | else if (sse2) | |
| 441 | { | ||
| 442 | ✗ | set_funcs(turn_left_plane_16_sse2, turn_right_plane_16_sse2, | |
| 443 | ssse3 ? turn_180_plane_ssse3<uint16_t> : turn_180_plane_sse2<uint16_t>); | ||
| 444 | } | ||
| 445 | else | ||
| 446 | #elif defined(NEON_INTRINSICS) | ||
| 447 | if (neon) | ||
| 448 | { | ||
| 449 | set_funcs(turn_left_plane_16_neon, turn_right_plane_16_neon, turn_180_plane_neon<uint16_t>); | ||
| 450 | } | ||
| 451 | else | ||
| 452 | #endif | ||
| 453 | { | ||
| 454 | ✗ | set_funcs(turn_left_plane_16_c, turn_right_plane_16_c, turn_180_plane_c<uint16_t>); | |
| 455 | } | ||
| 456 | } | ||
| 457 | ✗ | else if (vi.ComponentSize() == 4) // 32 bit | |
| 458 | { | ||
| 459 | #ifdef INTEL_INTRINSICS | ||
| 460 | ✗ | if(avx2) { | |
| 461 | ✗ | set_funcs(turn_left_plane_32_avx2, turn_right_plane_32_avx2, turn_180_plane_avx2<uint32_t>); | |
| 462 | } | ||
| 463 | ✗ | else if (sse2) { | |
| 464 | ✗ | set_funcs(turn_left_plane_32_sse2, turn_right_plane_32_sse2, turn_180_plane_sse2<uint32_t>); | |
| 465 | } | ||
| 466 | else | ||
| 467 | #elif defined(NEON_INTRINSICS) | ||
| 468 | if (neon) { | ||
| 469 | set_funcs(turn_left_plane_32_neon, turn_right_plane_32_neon, turn_180_plane_neon<uint32_t>); | ||
| 470 | } | ||
| 471 | else | ||
| 472 | #endif | ||
| 473 | { | ||
| 474 | ✗ | set_funcs(turn_left_plane_32_c, turn_right_plane_32_c, turn_180_plane_c<uint32_t>); | |
| 475 | } | ||
| 476 | } | ||
| 477 | ✗ | else env->ThrowError("Turn: Image format not supported!"); | |
| 478 | |||
| 479 | 17 | turn_function = funcs[direction]; | |
| 480 | 17 | } | |
| 481 | |||
| 482 | |||
| 483 | 4 | int __stdcall Turn::SetCacheHints(int cachehints, int frame_range) | |
| 484 | { | ||
| 485 | AVS_UNUSED(frame_range); | ||
| 486 |
1/2✓ Branch 2 → 3 taken 4 times.
✗ Branch 2 → 4 not taken.
|
4 | return cachehints == CACHE_GET_MTMODE ? MT_NICE_FILTER : 0; |
| 487 | } | ||
| 488 | |||
| 489 | |||
| 490 | 17 | PVideoFrame __stdcall Turn::GetFrame(int n, IScriptEnvironment* env) | |
| 491 | { | ||
| 492 | 17 | const int dplanes[] = { | |
| 493 | 0, | ||
| 494 |
3/4✓ Branch 2 → 3 taken 17 times.
✗ Branch 2 → 66 not taken.
✓ Branch 3 → 4 taken 4 times.
✓ Branch 3 → 5 taken 13 times.
|
17 | vi.IsRGB() ? PLANAR_B : PLANAR_U, |
| 495 |
2/2✓ Branch 7 → 8 taken 4 times.
✓ Branch 7 → 9 taken 13 times.
|
17 | vi.IsRGB() ? PLANAR_R : PLANAR_V, |
| 496 | PLANAR_A, | ||
| 497 |
1/2✓ Branch 6 → 7 taken 17 times.
✗ Branch 6 → 66 not taken.
|
17 | }; |
| 498 | |||
| 499 |
1/2✓ Branch 11 → 12 taken 17 times.
✗ Branch 11 → 66 not taken.
|
17 | auto src = child->GetFrame(n, env); |
| 500 |
1/2✓ Branch 12 → 13 taken 17 times.
✗ Branch 12 → 64 not taken.
|
17 | auto dst = env->NewVideoFrameP(vi, &src); |
| 501 | |||
| 502 | PVideoFrame srcs[4] = { | ||
| 503 | src, | ||
| 504 |
2/2✓ Branch 15 → 16 taken 2 times.
✓ Branch 15 → 18 taken 15 times.
|
17 | u_or_b_source ? u_or_b_source->GetFrame(n, env) : src, |
| 505 |
2/2✓ Branch 20 → 21 taken 2 times.
✓ Branch 20 → 23 taken 15 times.
|
17 | v_or_r_source ? v_or_r_source->GetFrame(n, env) : src, |
| 506 | src, | ||
| 507 |
6/16✓ Branch 13 → 14 taken 17 times.
✗ Branch 13 → 50 not taken.
✓ Branch 17 → 19 taken 2 times.
✗ Branch 17 → 50 not taken.
✓ Branch 18 → 19 taken 15 times.
✗ Branch 18 → 50 not taken.
✓ Branch 22 → 24 taken 2 times.
✗ Branch 22 → 50 not taken.
✓ Branch 23 → 24 taken 15 times.
✗ Branch 23 → 50 not taken.
✓ Branch 24 → 25 taken 17 times.
✗ Branch 24 → 50 not taken.
✗ Branch 50 → 51 not taken.
✗ Branch 50 → 54 not taken.
✗ Branch 52 → 53 not taken.
✗ Branch 52 → 54 not taken.
|
119 | }; |
| 508 | |||
| 509 |
2/2✓ Branch 40 → 26 taken 46 times.
✓ Branch 40 → 41 taken 17 times.
|
63 | for (int p = 0; p < num_planes; ++p) { |
| 510 | 46 | const int splane = splanes[p]; | |
| 511 | 46 | const int dplane = dplanes[p]; | |
| 512 |
7/14✓ Branch 27 → 28 taken 46 times.
✗ Branch 27 → 55 not taken.
✓ Branch 29 → 30 taken 46 times.
✗ Branch 29 → 55 not taken.
✓ Branch 31 → 32 taken 46 times.
✗ Branch 31 → 55 not taken.
✓ Branch 33 → 34 taken 46 times.
✗ Branch 33 → 55 not taken.
✓ Branch 35 → 36 taken 46 times.
✗ Branch 35 → 55 not taken.
✓ Branch 37 → 38 taken 46 times.
✗ Branch 37 → 55 not taken.
✓ Branch 38 → 39 taken 46 times.
✗ Branch 38 → 55 not taken.
|
46 | turn_function(srcs[p]->GetReadPtr(splane), dst->GetWritePtr(dplane), |
| 513 | srcs[p]->GetRowSize(splane), srcs[p]->GetHeight(splane), | ||
| 514 | srcs[p]->GetPitch(splane), dst->GetPitch(dplane)); | ||
| 515 | } | ||
| 516 | |||
| 517 | 34 | return dst; | |
| 518 |
2/4✓ Branch 42 → 43 taken 68 times.
✓ Branch 42 → 46 taken 17 times.
✗ Branch 56 → 57 not taken.
✗ Branch 56 → 60 not taken.
|
102 | } |
| 519 | |||
| 520 | |||
| 521 | ✗ | AVSValue __cdecl Turn::create_turnleft(AVSValue args, void* , IScriptEnvironment* env) | |
| 522 | { | ||
| 523 | ✗ | return new Turn(args[0].AsClip(), DIRECTION_LEFT, env); | |
| 524 | } | ||
| 525 | |||
| 526 | |||
| 527 | ✗ | AVSValue __cdecl Turn::create_turnright(AVSValue args, void* , IScriptEnvironment* env) | |
| 528 | { | ||
| 529 | ✗ | return new Turn(args[0].AsClip(), DIRECTION_RIGHT, env); | |
| 530 | } | ||
| 531 | |||
| 532 | |||
| 533 | ✗ | AVSValue __cdecl Turn::create_turn180(AVSValue args, void* , IScriptEnvironment* env) | |
| 534 | { | ||
| 535 | ✗ | return new Turn(args[0].AsClip(), DIRECTION_180, env); | |
| 536 | } | ||
| 537 |