Friday, December 02, 2011

Песочный ноутбук


Купил HP ноутбук с i5. На третий день вдруг обнаружил в отладчике опцию показывать ymm регистры. “Да ну, не может быть. Наверное, MS в студии свою готовность демонстрирует” - подумал я. Показалось, что слишком мало времени прошло. Но первый же результат google-поиска i5 2410M подтвердил - Sandy Bridge. Надо проверять. Следующий код
  int cpu[4];
  __cpuid(cpu,1);
  printf("CPU: %sSSE2,%sSSE3,%sSSSE3,%sSSE4,%sSSE42,"
     "%sSSE4a,%sAVX,%sAVXFMA\n",
     cpu[3]&0x04000000?"+":"-",
     cpu[2]&0x00000001?"+":"-",
     cpu[2]&0x00000200?"+":"-",
     cpu[2]&0x00080000?"+":"-",
     cpu[2]&0x00100000?"+":"-",
     cpu[2]&0x00000040?"+":"-", /// :)
     (cpu[2]&0x18000000)==0x18000000?"+":"-",
     (cpu[2]&0x18001000)==0x18001000?"+":"-");
подтвердил, имею AVX
CPU: +SSE2,+SSE3,+SSSE3,+SSE4,+SSE42,-SSE4a,+AVX,-AVXFMA
Супер! 
В действительности этой проверки недостаточно, надо проверять xgetbv, чтобы узнать, поддерживает ли OS AVX, смотри Intel документ 319433-011. Проверил доступность AVX в Ubuntu (которую установил на ноутбуке, как вторую OS) простым “cat /proc/cpuinfo”, - доступны.
Пишем что-нибудь проверить производительность, например axpy Y=Y+a*X. Для начала в 32 битном режиме. Сравниваем производительность AVX кода
@@by8:
  vmulps ymm0, ymm1, REAL4 PTR [esi+ecx*4-32]
  vaddps ymm2, ymm0, REAL4 PTR [eax+ecx*4-32]
  vmovaps REAL4 PTR [eax+ecx*4-32], ymm2
  sub ecx, 8
  jg @@by8
с кодом SSE2, который почти такой же, но двух-местный. Константу размножаем вместо pshufd новой инструкцией vbroadcastss и данные выравниваем не на 16, а на 32 байта. Ускорение есть, хоть и скромное. 
Правильность результата тоже проверена. 
Будем использовать, там, где ускорения можно ждать. Хорош ноутбук!

No comments:

Post a Comment