Цитата(jcxz @ Jul 16 2018, 09:50)

Я так понимаю - Вы сами пытались оптимизировать функцию Diff() asm-вставками? И в её начале - закомментаренное си-тело?
Если так, то действие:
Код
int c1v = (c1 & Vmask) - (c2 & Vmask);
if (Absolute(c1v) > trV)
совсем не аналогично варианту на асме ниже.
Подумайте, что будет если к примеру c1==0x81, c2==0 в первом и во втором случае.
Если конечно в реализации изначально не заложено какое-то ограничение по количеству цветов (диапазону значений байтов).
Но в любом случае: взятие модуля от числа - не аналогично операции x=-x.
Да и вычитать
SSUB8 c1,c2 чтобы потом находить NEG от каждого байта - это как-то бессмысленно. Почему бы тогда сразу не сделать
SSUB8 c2,c1 ?
PS: Так что похоже у Вас ещё и реализация кривая....

Это не реализация!!! Это драфт, не претендующий на конечный вариант.
За ошибку спасибо!
Нашёл с того форума(про фильтр на NEON) реализацию Диффа. Но я не силён в GCC-asm и его синтаксис ставит меня немного в ступор:
Код
static inline int Diff(u32 yuv1, u32 yuv2)
{
register u32 tmp1, tmp2;
asm(
"usub8 %[tmp1], %[value1], %[value2] \n\t" // tmp1 = value1 - value2 // tmp1 = yuv1 - yuv2
"usub8 %[value2], %[value2], %[value1] \n\t" // value2 = value2 - value1 // value2 = yuv2 - yuv1
"mov %[tmp2], #0 \n\t" // tmp2 = 0
"movw %[value1], #0x0706 \n\t"
"movt %[value1], #0x30 \n\t" // value1 = 0x300706
"sel %[tmp1], %[value2], %[tmp1] \n\t" // tmp1 = (value2 >= 0)?value2:tmp1 // tmp1 = abs(yuv1 - yuv2)
"usub8 %[value2], %[value1], %[tmp1] \n\t" // value2 = value1 - tmp1 // value2 = 0x300706 - abs(yuv1 - yuv2)
"sel %[value1], %[tmp2], %[value1] " // value1 = (value2 >= 0)?tmp2:value1 // value1 = (0x300706 >= abs(yuv1 - yuv2))?0:0x300706
: [value1] "+r" (yuv1), [value2] "+r" (yuv2), [tmp1] "=r" (tmp1), [tmp2] "=r" (tmp2)
:
: "cc"
);
return yuv1;
Начал переделывать под Keil Asm (или ARM Asm):
Код
static inline int Diff(u32 yuv1, u32 yuv2)
{
register u32 tmp1,tmp2;
register u32 value1=yuv1,value2=yuv2;
__asm
{
usub8 tmp1,value1,value2 // tmp1 = value1 - value2 // tmp1 = yuv1 - yuv2
usub8 value2,value2,value1 // value2 = value2 - value1 // value2 = yuv2 - yuv1
mov tmp2,#0 // tmp2 = 0
movw value1,#0x0706
movt value1,#0x30 // value1 = 0x300706
sel tmp1,value2,tmp1 // tmp1 = (value2 >= 0)?value2:tmp1 // tmp1 = abs(yuv1 - yuv2)
usub8 value2,value1,tmp1 // value2 = value1 - tmp1 // value2 = 0x300706 - abs(yuv1 - yuv2)
sel value1,tmp2,value1 // value1 = (value2 >= 0)?tmp2:value1 // value1 = (0x300706 >= abs(yuv1 - yuv2))?0:0x300706
}
return yuv1; // ???
}
Знающие GCC ASM, подскажите пожалуйста, по переделке на ARM ASM, что загоняется в value1, value 2? И куда возвращаемый результат кладётся?
И что означает в конце:
Код
: [value1] "+r" (yuv1), [value2] "+r" (yuv2), [tmp1] "=r" (tmp1), [tmp2] "=r" (tmp2)
:
: "cc"
?