/* Downsample all but the last DCT block of components. */ for (i = 0; i < width_in_blocks - 1; i++) {
uint8x16_t components = vld1q_u8(inptr + i * 2 * DCTSIZE); /* Add adjacent component values, widen to 16-bit, and add bias. */
uint16x8_t samples_u16 = vpadalq_u8(bias, components); /* Divide total by 2 and narrow to 8-bit. */
uint8x8_t samples_u8 = vshrn_n_u16(samples_u16, 1); /* Store samples to memory. */
vst1_u8(outptr + i * DCTSIZE, samples_u8);
}
/* Load components in last DCT block into a table. */
uint8x16_t components =
vld1q_u8(inptr + (width_in_blocks - 1) * 2 * DCTSIZE); #ifdefined(__aarch64__) || defined(_M_ARM64) || defined(_M_ARM64EC) /* Pad the empty elements with the value of the last component. */
components = vqtbl1q_u8(components, expand_mask); #else
uint8x8x2_t table =
{ { vget_low_u8(components), vget_high_u8(components) } };
components = vcombine_u8(vtbl2_u8(table, vget_low_u8(expand_mask)),
vtbl2_u8(table, vget_high_u8(expand_mask))); #endif /* Add adjacent component values, widen to 16-bit, and add bias. */
uint16x8_t samples_u16 = vpadalq_u8(bias, components); /* Divide total by 2, narrow to 8-bit, and store. */
uint8x8_t samples_u8 = vshrn_n_u16(samples_u16, 1);
vst1_u8(outptr + (width_in_blocks - 1) * DCTSIZE, samples_u8);
}
}
/* Downsample component values from a single plane. *Thisversionhandlesthestandardcaseof2:1horizontaland2:1vertical, *withoutsmoothing.
*/
void jsimd_h2v2_downsample_neon(JDIMENSION image_width, int max_v_samp_factor,
JDIMENSION v_samp_factor,
JDIMENSION width_in_blocks,
JSAMPARRAY input_data, JSAMPARRAY output_data)
{
JSAMPROW inptr0, inptr1, outptr; /* Load expansion mask to pad remaining elements of last DCT block. */ constint mask_offset = 16 * ((width_in_blocks * 2 * DCTSIZE) - image_width); const uint8x16_t expand_mask =
vld1q_u8(&jsimd_h2_downsample_consts[mask_offset]); /* Load bias pattern (alternating every component.) */ /* { 1, 2, 1, 2, 1, 2, 1, 2 } */ const uint16x8_t bias = vreinterpretq_u16_u32(vdupq_n_u32(0x00020001)); unsigned i, outrow;
/* Downsample all but the last DCT block of components. */ for (i = 0; i < width_in_blocks - 1; i++) {
uint8x16_t components_r0 = vld1q_u8(inptr0 + i * 2 * DCTSIZE);
uint8x16_t components_r1 = vld1q_u8(inptr1 + i * 2 * DCTSIZE); /* Add adjacent component values in row 0, widen to 16-bit, and add *bias.
*/
uint16x8_t samples_u16 = vpadalq_u8(bias, components_r0); /* Add adjacent component values in row 1, widen to 16-bit, and *accumulate.
*/
samples_u16 = vpadalq_u8(samples_u16, components_r1); /* Divide total by 4 and narrow to 8-bit. */
uint8x8_t samples_u8 = vshrn_n_u16(samples_u16, 2); /* Store samples to memory and increment pointers. */
vst1_u8(outptr + i * DCTSIZE, samples_u8);
}
/* Load components in last DCT block into a table. */
uint8x16_t components_r0 =
vld1q_u8(inptr0 + (width_in_blocks - 1) * 2 * DCTSIZE);
uint8x16_t components_r1 =
vld1q_u8(inptr1 + (width_in_blocks - 1) * 2 * DCTSIZE); #ifdefined(__aarch64__) || defined(_M_ARM64) || defined(_M_ARM64EC) /* Pad the empty elements with the value of the last component. */
components_r0 = vqtbl1q_u8(components_r0, expand_mask);
components_r1 = vqtbl1q_u8(components_r1, expand_mask); #else
uint8x8x2_t table_r0 =
{ { vget_low_u8(components_r0), vget_high_u8(components_r0) } };
uint8x8x2_t table_r1 =
{ { vget_low_u8(components_r1), vget_high_u8(components_r1) } };
components_r0 = vcombine_u8(vtbl2_u8(table_r0, vget_low_u8(expand_mask)),
vtbl2_u8(table_r0, vget_high_u8(expand_mask)));
components_r1 = vcombine_u8(vtbl2_u8(table_r1, vget_low_u8(expand_mask)),
vtbl2_u8(table_r1, vget_high_u8(expand_mask))); #endif /* Add adjacent component values in row 0, widen to 16-bit, and add bias.
*/
uint16x8_t samples_u16 = vpadalq_u8(bias, components_r0); /* Add adjacent component values in row 1, widen to 16-bit, and *accumulate.
*/
samples_u16 = vpadalq_u8(samples_u16, components_r1); /* Divide total by 4, narrow to 8-bit, and store. */
uint8x8_t samples_u8 = vshrn_n_u16(samples_u16, 2);
vst1_u8(outptr + (width_in_blocks - 1) * DCTSIZE, samples_u8);
}
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.