- ОБНОВЛЕНИЕ - время корректного тестирования было значительно медленнее при использовании не ассемблерного кода, я буду искать другой метод
Я сравнил этот код сборки:
#define __arm_ssat(src, bits) asm("ssat %[srcr], %[satv], %[srcr]" :[srcr]"+r"(src):[satv]"I"(bits));
с этим:
#define MAX_SIGNED_NUM(bits) ((1 << (bits -1)) -1)
#define __arm_ssat(src, bits) {src = ((src > MAX_SIGNED_NUM(bits)) ? MAX_SIGNED_NUM(bits) : src);}
при выполнении этого - ОБНОВЛЕННОГО ТЕСТА - на 32-битном устройстве:
volatile void assert_ssat_asm(int* buf, size_t loops){
int64_t num = buf[0];
int64_t num_a = buf[1];
int64_t num_b = buf[2];
int sum = 0;
struct timeval tmv1; gettimeofday(&tmv1,NULL);
for (int i = 0; i < loops; ++i){
__arm_ssat(num, 8);
sum+=num;
assert( 127 == num);
num = buf[0];
__arm_ssat(num, 16);
sum+=num;
assert(32767 == num);
__arm_ssat(num_a, 8);
sum+=num;
assert( 127 == num_a);
num_a = buf[1];
__arm_ssat(num_a, 16);
sum+=num;
assert( 690 == num_a);
__arm_ssat(num_b, 8);
sum+=num;
assert( 127 == num_b);
num_b = buf[2];
__arm_ssat(num_b, 16);
sum+=num;
assert( 32767 == num_b);
}
struct timeval tmv2; gettimeofday(&tmv2,NULL);
int tdiff_usec = (tmv2.tv_sec*1000000 + tmv2.tv_usec) - (tmv1.tv_sec*1000000 + tmv1.tv_usec);
printf("%d\n", sum);
printf("ran %d times, total time: %d, average time asm: %.7f\n", loops, tdiff_usec, (double)tdiff_usec/loops);
}
int main ()
{
int buf[] = { 69000, 690, 64000 };
test_ssat(buf, 1000000);
}
Я получил такие результаты:
Выполнить 1000000 циклов, среднее время рег: 0,0210270
Выполнить 1000000 циклов, среднее время сборки: 0,0057960