Часовой пояс: UTC + 3 часа




Начать новую тему Новая тема / Ответить на тему Ответить  Сообщений: 71 • Страница 2 из 4<  1  2  3  4  >
  Пред. тема | След. тема 
В случае проблем с отображением форума, отключите блокировщик рекламы
Автор Сообщение
 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
Глава 1. Немного теории из какого-то Intel Optimization Guide...
Вот посмотрите.
Время исполнения некоторых инструкций.
0F3n - (0F34 - это Пресскот, у меня типа),
0F2n - это видимо Нортвуд (потому что немного быстрее)
069n - это Pentium M (вообше странно - как у него могут быть такие огромные скорости, помоему мобильные скоростью не блещут, или я как всегда не прав?)
Инструкция 0F3n / 0F2n / 069n
Если написано только два числа - значит там нет ничего про 069n (не особо он нам нужен).
Что означает запись типа 18+17 я не знаю.
Деление с SSE (с каким SSE не посмотрел - ленивый)
Single(32 бита)
DIVPS xmm,xmm 40 / 39 / 18+17
DIVSS xmm,xmm 32 / 23
(Тут выходит что 4 операции деления выполняются всего за 40 тактов, что в принципе очень даже быстро)
Double(64 бита)
DIVPD xmm,xmm 70 / 69 / 32+31
DIVSD xmm,xmm 39 / 38 / 32

Умножение с SSE (аналогично)
Double
MULPD xmm, xmm 7 / 6
MULSD xmm, xmm 7 / 6
(А тут выходит 4 умножения(деления) со скоростью света)
Single
MULPS xmm, xmm 7 / 6 / 4+1
MULSS xmm, xmm 7 / 6

И всё остальное с любимым FPU
FADD 6 / 5 и FSUB 6 / 5 - это просто так.
FMUL 8 / 7
FDIV Single Precision (я понимаю тут 32бита) 30 / 23
FDIV Double Precision (а тут аж 64) 40 / 38
FDIV Extended Precision (и наконец все положенные 80) 44 / 43
(А тут одно деление, но скока тактов отнимает)
И обычным ALU
IMUL r32 10 / 14 / 4
IMUL imm32 "почему-то ничего не написано" / 14 / 4
IMUL "почему-то ничего не написано" / 15-18 / 4
IDIV 66-80 / 56-70

MUL 10 / 14-18
DIV 66-80 / 56-70

"почему-то ничего не написано" - почему-то не написали но числа по идее поменьше чем у норта, т.к. в скоте чёта с MUL'ями подкрутили(это я типа похвалил свой любимый пресскот, а то как не гляну в профиль сплошные атлоны). :oops:

Глава 2. Тепер "Нафига он это все напечатал?".
Данная таблица (почти таблица) показывает что лучше умножать нежели делить, причем во всех случаях начинаяя с FPU и заканчиваяя SSE. Возникает вопрос "А каким ... умножить, если надо разделить?!".
Отвечаю: Например как поделить на два. Деление на два можно заменить умножением на 0.5, аналогично деление на 4 заменяем умножением на 0.25. Вот даже формулу изобрел:
с=a/b менеяем на с=a*(1/b). Конечно в коде такое не надо писать, надо просто заменить все /b , на заранее посчитанные *1/b. Ну вы в общем меня поняли. В любом случае умножение на FPU быстрее деления на ALU!!! Вся эта петиция писалась относительно Пентиумов4 (но на Атлонах с их быстрющими FPU тоже наверное будет работать). Кстати про замену деления умножением я где-то прочитал (в нэте), а где не помню. Потом вспомнил - этому же в школе учили (кто не помнит (я недавно из школы улетел) это переворачивание дроби при делении дроби на дробь(переворачиваем делитель и меняем деление на умножение))!!!
Так что если много деления - можно получить солидный SpeedUp, а главное - никакого ассемблера, тока С или Паскаль.
И ВОТ САМОЕ ГЛАВНОЕ умножение и деление в SSE выполняются на РАЗНЫХ блоках, значит можно сразу множить и делить через умножение(или умножать)!!!
_serj А насчет NOP'ов ты прав, частично, но все равно пустоту для выравнивания надо чем-то забить. А может можно там NOP'ов натыкать и JMP перед ними (правда толку с этого), но все равно перед таким циклом это мелочи. И вот ещё: Интел в коде тоже пишет xor eax,eax ;clear eax - вот так вот...(наверное есть на то причина):):):)



Партнер
 

Advanced member
Статус: Не в сети
Регистрация: 10.04.2003
Откуда: Москва
Toad, почитай оптимизацию от AMD - там очень подробно и просто 'все это' расписано.
Только не используй REP для пустого выравнивания, на Intel Р4 комбинация "REP+NOP" что-то жуткое! Номер документа 22007


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
serj_ На что ты намекаешь?? И линк на доки кинь плиз.
Я потом тесты провел насчет деления и умножения и просто ужаснулся. Нифига не делаешь ~120 тактов, множить или делить через SSE ~2000 тактов(8 делений), через FPU ~25000 (1 деление)!!! Не могу в этот прикол въехать.


 

Member
Статус: Не в сети
Регистрация: 30.01.2003
Откуда: Москва
Toad Ошибка при подсчете времени? Не может быть, чтобы одно SSe или FPU деление занимало тысячи тактов.


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
Ща ещё хуже стало, два RDTSC занимают 25-30 тысяч тактов. Раньше получалось что миллион делений как раз за 40 тактов в среднем проскакивали с умножением какой то ужас - миллион умножений ~2 800 000 000 тактов!!!! Одно деление/умножение - дофига тактов, а если много то все по плану не считая некоторых глюков...


 

Advanced member
Статус: Не в сети
Регистрация: 10.04.2003
Откуда: Москва
Точно не помню, RDTSC для K7 порядка 27 тактов, для Р4 порядка 80.
Toad, зайди на сайт AMD и запусти поиск по номеру.


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
serj_ У меня меньше 96 за 2 RDTSC, ни разу не было (обычно ~110), еще зависит чем компилируешь + настроение компа!!! А для более менее стабильных результатов надо чтоб в начале что-то выполнилось (типа NasmW+MinGW=Стабильные результаты, FASM=Скачка от 96 до нескольких тысяч тактов). Кстати слил один с амд - очень классно там все написано. Короче с RDTSC мерить можно только большой кусок кода, а скока одна инструкция отнимает тактов - помоему бесполезно!


 

Advanced member
Статус: Не в сети
Регистрация: 30.08.2003
Откуда: Санкт-Петербург
Toad
Цитата:
короче с RDTSC мерить можно только большой кусок кода, а скока одна инструкция отнимает тактов - помоему бесполезно

конечно :) она же еще и спарится с чем-нибудь, и в microop превратится (а про перестановку microop'ов/операций процом помним?), так что фиг посчитаешь...
PS: понятно, что время исполнения операции - от 0 тактов до некой максимальной величины.. (если, конечно, не брать во внимание работу с памятью/кэшем)

_________________
{:€ дед в законе :-) нородный окодемег
почетный пользователь OpenSuSE 11.3
Ремонт и модернизация ноутбуков IBM (Lenovo) ThinkPad


 

Member
Статус: Не в сети
Регистрация: 14.03.2004
Откуда: Москва
господа... лучше компилятора все равно ни кто не оптимизирует. ФАКТ

_________________
ФИЗТЕХ- рулез, ФАКИ - сила, Кванты тоже хорошо


 

Member
Статус: Не в сети
Регистрация: 14.01.2004
Откуда: Киев, Украина
nickyoz компилятор, не оптимизирует под конкретную архитектуру процессора. Тем более знаем мы оптимизацию Сишного компилятора, лучше ее не включать.

_________________
Ку ку


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
Ну насчет перестановки, есть опреации сериализации (не знаю что это такое но они вперед себа RDTSC не пускают - это SFENCE MFENCE LFENCE и CPUID, их рекомендуюют ставить перед вторым RDTSC), но это в принципе ничего не меняет. Вот так вот VTune в зубы и мануалы и гиды читать. И все равно новый проц и все оптимизации улетучиваются (читали про XviD на ixbt.com) так что что-то сильно точить опасно :).


 

Member
Статус: Не в сети
Регистрация: 14.03.2004
Откуда: Москва
Daemon Да???????? приплыли господа. А -mcpu=arc что такое???

_________________
ФИЗТЕХ- рулез, ФАКИ - сила, Кванты тоже хорошо


 

Member
Статус: Не в сети
Регистрация: 14.01.2004
Откуда: Киев, Украина
nickyoz
Цитата:
Daemon Да???????? приплыли господа. А -mcpu=arc что такое???
Compile code for ARC variant, cpu. Which variants are supported depend on the configuration.

Добавлено спустя 43 секунды:
Но
Цитата:
Тем более знаем мы оптимизацию Сишного компилятора, лучше ее не включать.

_________________
Ку ку


 

Member
Статус: Не в сети
Регистрация: 14.03.2004
Откуда: Москва
Daemon Да. Щас. Я что нибудь напишу.
Берем простейшую программу.
Код:
#include <stdlib.h>

int func(){
  int a=1;
  static int b=3;
  while(a==(b+=(func()-1)))
    ;
  return 0;
}

int main(){
  call();
  return 0;
}

выполняем оптимизаци под athlon
Код:
   .file   "opt.c"
   .text
   .p2align 4,,15
.globl main
   .type   main, @function
main:
   pushl   %ebp
   movl   %esp, %ebp
   subl   $8, %esp
   andl   $-16, %esp
   call   call
   xorl   %eax, %eax
   leave
   ret
   .size   main, .-main
   .data
   .align 4
   .type   b.0, @object
   .size   b.0, 4
b.0:
   .long   3
   .text
   .p2align 4,,15
.globl func
   .type   func, @function
func:
   pushl   %ebp
   movl   %esp, %ebp
   pushl   %ebx
   movl   $1, %ebx
   .p2align 4,,7
.L21:
   call   func
   addl   b.0, %eax
   decl   %eax
   cmpl   %eax, %ebx
   movl   %eax, b.0
   je   .L21
   popl   %ebx
   xorl   %eax, %eax
   leave
   ret
   .size   func, .-func
   .section   .note.GNU-stack,"",@progbits
   .ident   "GCC: (GNU) 3.3.5-20050130 (Gentoo Linux 3.3.5.20050130-r1, ssp-3.3.5.20050130-1, pie-8.7.7.1)"

выполняем оптимизаци под pentium
Код:
   .file   "opt.c"
   .text
   .p2align 4,,15
.globl main
   .type   main, @function
main:
   pushl   %ebp
   movl   %esp, %ebp
   pushl   %eax
   pushl   %eax
   andl   $-16, %esp
   call   call
   movl   %ebp, %esp
   xorl   %eax, %eax
   popl   %ebp
   ret
   .size   main, .-main
   .data
   .align 4
   .type   b.0, @object
   .size   b.0, 4
b.0:
   .long   3
   .text
   .p2align 4,,15
.globl func
   .type   func, @function
func:
   pushl   %ebp
   movl   %esp, %ebp
   pushl   %ebx
   movl   $1, %ebx
   .p2align 4,,7
.L21:
   call   func
   movl   b.0, %ecx
   addl   %ecx, %eax
   decl   %eax
   movl   %eax, b.0
   cmpl   %eax, %ebx
   je   .L21
   xorl   %eax, %eax
   popl   %ebx
   popl   %ebp
   ret
   .size   func, .-func
   .section   .note.GNU-stack,"",@progbits
   .ident   "GCC: (GNU) 3.3.5-20050130 (Gentoo Linux 3.3.5.20050130-r1, ssp-3.3.5.20050130-1, pie-8.7.7.1)"

без потимизации
Код:
   .file   "opt.c"
   .data
   .align 4
   .type   b.0, @object
   .size   b.0, 4
b.0:
   .long   3
   .text
.globl func
   .type   func, @function
func:
   pushl   %ebp
   movl   %esp, %ebp
   subl   $4, %esp
   movl   $1, -4(%ebp)
.L5:
   call   func
   addl   b.0, %eax
   decl   %eax
   movl   %eax, b.0
   movl   b.0, %eax
   cmpl   %eax, -4(%ebp)
   je   .L5
   movl   $0, %eax
   leave
   ret
   .size   func, .-func
.globl main
   .type   main, @function
main:
   pushl   %ebp
   movl   %esp, %ebp
   subl   $8, %esp
   andl   $-16, %esp
   movl   $0, %eax
   subl   %eax, %esp
   call   call
   movl   $0, %eax
   leave
   ret
   .size   main, .-main
   .section   .note.GNU-stack,"",@progbits
   .ident   "GCC: (GNU) 3.3.5-20050130 (Gentoo Linux 3.3.5.20050130-r1, ssp-3.3.5.20050130-1, pie-8.7.7.1)"

коментарии нужны?

Сорри... щас все верно

_________________
ФИЗТЕХ- рулез, ФАКИ - сила, Кванты тоже хорошо


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
Я компилил Gogo-no coda на MSVC6 и на ICL - результат ~2,6 раза, естессно в пользу ICL.


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
nickyoz А есть ли русская инструкция как пользоваться АСМом в GCC? А то в ихней ничего понять не могу, а хочеться на самому пописать.


 

Advanced member
Статус: Не в сети
Регистрация: 30.08.2003
Откуда: Санкт-Петербург
Toad
Цитата:
А есть ли русская инструкция как пользоваться АСМом в GCC

вряд ли. Зато есть книжка Зубкова "Ассемблер для DOS, Windows и Unix", а там синтаксис AT&T описан... Проблема в том, что в GCC асм - юниксовый и в нем немного по другому сделана система команд. Например,
1) каждая команда имеет суффикс в зависимости от размера операнда
b = byte
w = word
l = long = double word
q = quad word
s = single precision float (32-bit)
l = double precision (long) float (64-bit)
t = 80-bit float. В паскале вроде обзывался Extended..
Например:
movb $0, var - переместить байт 0 в переменную var размером 1 байт
movw $0, var - переместить слово 0 в переменную var размером 2 байта
и т.д.
2) регистры обознаются %. Например: %eax - регистр eax
3) immediate value, т.е. непосредственное значение ("константа") обозначаются $. Например: $2 - значение 2, $200h - 200h=512
4) порядок аргументов всегда обратный интеловскому. Т.е. сначала источник, затем место назначения:
movb %al, var - переместить из AL в байтовую переменную VAR
movb var, %al - переместить из байтовой переменной VAR в AL
и т.д.

Добавлено спустя 1 минуту, 28 секунд:
Для того чтобы в СИшный код вставить ассемблерную вставку можно сделать так:
Цитата:
void make_sound()
{
__asm__("\n\t",
"movb $0xB6,%al\n\t",
"outb %al,$0x43\n\t",
"movb $0xB0,%al\n\t",
"outb %al,$0x42\n\t",
"movb $0x11,%al\n\t",
"outb %al,$0x42\n\t",
"inb $0x61,%al\n\t",
"orb $3,%al\n\t",
"outb %al,$0x61\n\t"
);
}

это функция, которая "бибикает" спикером.

_________________
{:€ дед в законе :-) нородный окодемег
почетный пользователь OpenSuSE 11.3
Ремонт и модернизация ноутбуков IBM (Lenovo) ThinkPad


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
Root А там еще что-то через двоеточия пишеться, типа КОМАНДА : "=r" : r (это я от балды написал) - что эти иероглифы значат?


 

Advanced member
Статус: Не в сети
Регистрация: 30.08.2003
Откуда: Санкт-Петербург
Toad
а! Ну, это подстановка в код переменных так реализована ;)

Смотри:
Цитата:
extern inline void outb(unsigned char value, unsigned short port)
{
__asm__ __volatile__ ("out" "b" " %" "b" "0,%" "w" "1" : : "a" (value), "Nd" (port));
}

extern inline void outw(unsigned short value, unsigned short port)
{
__asm__ __volatile__ ("out" "w" " %" "w" "0,%" "w" "1" : : "a" (value), "Nd" (port));
}

это вывод в порт port значения value. 0 и 1 заменяется значением value и port
ввод из порта:
Цитата:
extern inline void insw(unsigned short port, void * addr, unsigned long count)
{
__asm__ __volatile__ ("cld ; rep ; ins" "w" : "=D" (addr), "=c" (count) : "d" (port),"0" (addr),"1" (count));
}

а здесь ситуация такая, что надо по адресу addr положить данные.
в общем, формат очень похож на printf:
сначала идет текст команды+модификаторы, а в конце то, что вместо них подставляется...

_________________
{:€ дед в законе :-) нородный окодемег
почетный пользователь OpenSuSE 11.3
Ремонт и модернизация ноутбуков IBM (Lenovo) ThinkPad


 

Member
Статус: Не в сети
Регистрация: 28.02.2005
Откуда: Брянск
Root Караул :shock:, лучше на чистом асме, чем на этом ужасе. Лана попробую разобраться, пасиба тебе о великий Root!


Показать сообщения за:  Поле сортировки  
Начать новую тему Новая тема / Ответить на тему Ответить  Сообщений: 71 • Страница 2 из 4<  1  2  3  4  >
-

Часовой пояс: UTC + 3 часа


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 3


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Перейти:  
cron
Создано на основе phpBB® Forum Software © phpBB Group
Русская поддержка phpBB | Kolobok smiles © Aiwan