Важная информация

User Tag List

Страница 8 из 9 ПерваяПервая ... 456789 ПоследняяПоследняя
Показано с 71 по 80 из 82

Тема: Хочу писать программы для ретрокомпьютеров

  1. #71
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,611
    Спасибо Благодарностей отдано 
    2,187
    Спасибо Благодарностей получено 
    140
    Поблагодарили
    106 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    В том случае это не просто было сворачивание константных подвыражений. Это было сворачивание параметра функции до константы, раз он передавался только константой. Согласитесь, это несколько другое.

  2. #72
    Master Аватар для Sandro
    Регистрация
    20.01.2010
    Адрес
    г. Зеленоград
    Сообщений
    590
    Спасибо Благодарностей отдано 
    27
    Спасибо Благодарностей получено 
    211
    Поблагодарили
    115 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    В том случае это не просто было сворачивание константных подвыражений. Это было сворачивание параметра функции до константы, раз он передавался только константой. Согласитесь, это несколько другое.
    Категорически не соглашусь. Аргумент функции в C -- ровно такое же выражение, как и любое другое. С точки зрения компилятора, между этими двумя вызовами функции нет никакой разницы:

    Код:
    int a = 5 + 8;
    func(a)
    ...
    func(5+8)
    Точнее, разница только в том, что значение переменной a может потребоваться сохранить.

    - - - Добавлено - - -

    Или речь о том, что он сворачивает вызов чистых функций с константными аргументами в предвычисленную константу? Так это тоже оптимизация константных подвыражений. Чистые функции по определению всегда возвращают одно и то же при тех же аргументах.

  3. #73
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,611
    Спасибо Благодарностей отдано 
    2,187
    Спасибо Благодарностей получено 
    140
    Поблагодарили
    106 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Имеется в виду вот что:

    Код:
    void func (int a, int b, int с) {
      ... a ; // вот здесь компилятор прямо вставляет константу вместо a,
        // ибо он проверил, что все вызовы func идут с этой константой
    }
    Насколько говорит мой опыт, компиляторы Си (особенно набортные или для ретро-таргетов) эту оптимизацию не делают.

  4. #74
    Master Аватар для Sandro
    Регистрация
    20.01.2010
    Адрес
    г. Зеленоград
    Сообщений
    590
    Спасибо Благодарностей отдано 
    27
    Спасибо Благодарностей получено 
    211
    Поблагодарили
    115 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    А, понял. На самом деле, такая частичная параметризация возможна не всегда. Если мы экспортируем функцию, то компилятор не имеет права так делать, поскольку мало ли кто её с какими параметрами будет вызывать.

    Что же касается GCC, то, видимо, это косвенный эффект оптимизации шаблонов с константными параметрами, типа MyTemplate<a, 5>. В STL и Boost это просто необходимо, там такого -- вагон и маленькая тележка. Страшный язык этот современный C++, вот что я скажу.
    А вот в C компиляторах я действительно никогда такого не видел.

    Думаю, если эту фекцию экспортировать, то ничего подобного не будет, скорее всего компилятор даже не попытается порождать специализированную версию. Лень проверять

  5. #75
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,611
    Спасибо Благодарностей отдано 
    2,187
    Спасибо Благодарностей получено 
    140
    Поблагодарили
    106 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Видимо, да. Функция не экспортирована, помечена static, потому и возможна эта оптимизация. Но GCC реально удивляет качеством кода и помимо этого случая.

  6. #76
    Veteran
    Регистрация
    22.11.2009
    Адрес
    Москва
    Сообщений
    1,588
    Спасибо Благодарностей отдано 
    68
    Спасибо Благодарностей получено 
    157
    Поблагодарили
    103 сообщений
    Mentioned
    12 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    жаль, что godbolt не умеет в pdp11

    любопытно посмотреть, во что развернется такой код

    Код:
    void update(unsigned char *mem, int *bitmap, int x, int y) {
        for (int m = x; m < x+y; m++) {
            unsigned char bits = *mem++;
            for (int i = 0; i < 8; i++) {
                *bitmap++ = (bits >> i) & 1;
            }
        }
    }

  7. #76
    С любовью к вам, Yandex.Direct
    Размещение рекламы на форуме способствует его дальнейшему развитию

  8. #77
    Veteran Аватар для Oleg N. Cher
    Регистрация
    24.08.2007
    Адрес
    Днепропетровская обл.
    Сообщений
    1,611
    Спасибо Благодарностей отдано 
    2,187
    Спасибо Благодарностей получено 
    140
    Поблагодарили
    106 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    GCC даёт такой код:

    Код:
    ; ---------------------------------------------------------------------------
                    mov     R2, -(SP)
                    mov     R3, -(SP)
                    mov     R4, -(SP)
                    mov     R5, -(SP)
                    add     #-12, SP
                    mov     30(SP), R3
                    clr     R2
                    mov     32(SP), R0
                    add     R3, R0
                    mov     32(SP), R1
                    inc     R1
                    cmp     R3, R0
                    bgt     loc_1062
                    cmp     R0, #-100000
                    bne     loc_1066
    
    loc_1062:                               ; CODE XREF: RAM:001052↑j
                    mov     #1, R1
    
    loc_1066:                               ; CODE XREF: RAM:001060↑j
                                            ; RAM:001242↓j
                    mov     #4, R0
                    mov     R2, R3
    
    loc_1074:                               ; CODE XREF: RAM:001100↓j
                    asl     R3
                    dec     R0
                    bne     loc_1074
                    add     26(SP), R3
                    mov     R3, 10(SP)
                    dec     R1
                    beq     loc_1122
                    jmp     loc_1140
    ; ---------------------------------------------------------------------------
    
    loc_1122:                               ; CODE XREF: RAM:001114↑j
                    add     #12, SP
                    mov     (SP)+, R5
                    mov     (SP)+, R4
                    mov     (SP)+, R3
                    mov     (SP)+, R2
                    return
    ; ---------------------------------------------------------------------------
    
    loc_1140:                               ; CODE XREF: RAM:001116↑J
                    mov     24(SP), R0
                    add     R2, R0
                    movb    @R0, 7(SP)
                    clr     R0
                    mov     #10, R3
    
    loc_1160:                               ; CODE XREF: RAM:001236↓j
                    mov     R0, R4
                    asl     R4
                    add     10(SP), R4
                    mov     R4, 2(SP)
                    clr     R4
                    bisb    7(SP), R4
                    mov     R4, @SP
                    mov     R0, R5
                    ble     loc_1220
    
    loc_1210:                               ; CODE XREF: RAM:001214↓j
                    asr     R4
                    dec     R5
                    bne     loc_1210
                    mov     R4, @SP
    
    loc_1220:                               ; CODE XREF: RAM:001206↑j
                    mov     @SP, R4
                    bic     #-2, R4
                    mov     2(SP), R5
                    mov     R4, @R5
                    inc     R0
                    sob     R3, loc_1160
                    inc     R2
                    br      loc_1066
    ; ---------------------------------------------------------------------------

  9. #78
    Master Аватар для Sandro
    Регистрация
    20.01.2010
    Адрес
    г. Зеленоград
    Сообщений
    590
    Спасибо Благодарностей отдано 
    27
    Спасибо Благодарностей получено 
    211
    Поблагодарили
    115 сообщений
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Oleg N. Cher Посмотреть сообщение
    GCC даёт такой код:
    Печально. Оптимизатор не осилил.

    Вот, например:

    Код:
    loc_1066:                               ; CODE XREF: RAM:001060↑j
                                            ; RAM:001242↓j
                    mov     #4, R0
                    mov     R2, R3
    
    loc_1074:                               ; CODE XREF: RAM:001100↓j
                    asl     R3
                    dec     R0
                    bne     loc_1074
    Очевидные ошибки:
    1) Проигнорировано существование команды SOB. Компилятор прибит гвоздями к самым младшим моделям PDP-11? Не верится, дальше-то SOB есть.
    2) Правильно этот код пишется так:

    Код:
                    mov     R2, R3
                    asl     R3
                    asl     R3
                    asl     R3
                    asl     R3
    На слово короче, не использует дополнительный регистр и как минимум в 3 раза быстрее.

    3) Чудовищным образом закодирован цикл со счётом вниз до нуля. Ну это же типовая идиома, кодогенератор должен её узнавать и вставлять шаблон.

    А самое главное -- это не совсем от этой функции код :P

    Вот сходу в уме декомпилировал начало функции:

    Код:
    func(int a, int b, int c, int d) {
                    int v3 = c;
                    int v2 = c + d;
                    int v1 = d +1
                    // ЧТО ЭТО ???
                    if (v3 > v0 || v0 == 0100000) {
                                    v3 = v2* 16;
                    }
    
                    while (--v1 > 0) {
                                    ...
                    }  
    }
    - - - Добавлено - - -

    Цитата Сообщение от shattered Посмотреть сообщение
    жаль, что godbolt не умеет в pdp11
    любопытно посмотреть, во что развернется такой код

    Код:
    void update(unsigned char *mem, int *bitmap, int x, int y) {
        for (int m = x; m < x+y; m++) {
            unsigned char bits = *mem++;
            for (int i = 0; i < 8; i++) {
                *bitmap++ = (bits >> i) & 1;
            }
        }
    }
    А в этом коде ничего, случаем, не пропало? Что там происходит с x? Зачем он нужен?

    - - - Добавлено - - -

    Переписал вручную на ассемблере. Если x всё-таки имеет значение, то в инициализации цикла добавляется ещё несколько команд.
    Аргументы в регистрах r1..r4

    Код:
    ;void update(unsigned char *mem, int *bitmap, int x, int y) {
    ;    for (int m = x; m < x+y; m++) {
    ;        unsigned char bits = *mem++;
    ;        for (int i = 0; i < 8; i++) {
    ;            *bitmap++ = (bits >> i) & 1;
    ;        }
    ;    }
    ;}
    
    update: mov r5, -(sp)
    	mov r4, -(sp)
    	mov r3, -(sp)
    	mov r2, -(sp)
    	mov r1, -(sp)
    	cmp #0, r4
    	bge 0$
    1$:	movb (r1)+, r0
    	mov #10, r5
    2$:	clr r3
    	asr r0
    	adc r3
    	mov r3, (r2)+
    	sob r5, 2$
    	sob r4, 1$
    0$:	mov (sp)+, r1
    	mov (sp)+, r2
    	mov (sp)+, r3
    	mov (sp)+, r4
    	mov (sp)+, r5
    	ret
    - - - Добавлено - - -

    Таки залез на gobolt.org, и проверил, что тамошняя коллекция компялиторов думает.

    Несколько родственный MSP-430
    Код:
    update:
            PUSHM.W #1, R10
            SUB.W   #14, R1
            MOV.W   R12, 6(R1)
            MOV.W   R13, 4(R1)
            MOV.W   R14, 2(R1)
            MOV.W   R15, @R1
            MOV.W   2(R1), 12(R1)
            BR      #.L2
    .L5:
            MOV.W   6(R1), R12
            MOV.W   R12, R13
            ADD.W   #1, R13
            MOV.W   R13, 6(R1)
            MOV.B   @R12, 9(R1)
            MOV.W   #0, 10(R1)
            BR      #.L3
    .L4:
            MOV.W   4(R1), R10
            MOV.W   R10, R12
            ADD.W   #2, R12
            MOV.W   R12, 4(R1)
            MOV.B   9(R1), R12
            MOV.W   10(R1), R13
            CALL    #__mspabi_srai
            AND.B   #1, R12
            MOV.W   R12, @R10
            ADD.W   #1, 10(R1)
    .L3:
            MOV.B   #7, R12
            CMP.W   10(R1), R12 { JGE     .L4
            ADD.W   #1, 12(R1)
    .L2:
            MOV.W   2(R1), R12
            ADD.W   @R1, R12
            CMP.W   R12, 12(R1) { JL      .L5
            NOP
            ADD.W   #14, R1
            POPM.W  #1, r10
            RET
    Ужас какой! Плохо у GCC с 16-битками...

    Богомерзкий RISC-V:
    Код:
    update(unsigned char*, int*, int, int):
            add     a5,a2,a3
            add     a7,a0,a3
            li      a6,8
            ble     a5,a2,.L1
    .L5:
            lbu     a2,0(a0)
            mv      a3,a1
            addi    a0,a0,1
            li      a5,0
    .L3:
            sra     a4,a2,a5
            addi    a3,a3,4
            andi    a4,a4,1
            sw      a4,-4(a3)
            addi    a5,a5,1
            bne     a5,a6,.L3
            addi    a1,a1,32
            bne     a7,a0,.L5
    .L1:
            ret
    А вот это примерно то же самое, что и я написал.

  10. #79
    Guru Аватар для andrews
    Регистрация
    20.04.2006
    Адрес
    Санкт-Петербург
    Сообщений
    2,688
    Спасибо Благодарностей отдано 
    423
    Спасибо Благодарностей получено 
    196
    Поблагодарили
    174 сообщений
    Mentioned
    4 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    Цитата Сообщение от Sandro Посмотреть сообщение
    Богомерзкий RISC-V
    где бы этот скачать c-компилер?

  11. #80
    Veteran
    Регистрация
    22.11.2009
    Адрес
    Москва
    Сообщений
    1,588
    Спасибо Благодарностей отдано 
    68
    Спасибо Благодарностей получено 
    157
    Поблагодарили
    103 сообщений
    Mentioned
    12 Post(s)
    Tagged
    0 Thread(s)

    По умолчанию

    изначально этот код выглядел примерно так:

    https://github.com/mamedev/mame/blob...an240.cpp#L424

    Код:
    u32 okean240_state::screen_update_okean240(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
    {
    	for (u16 y = 0; y < 256; y++)
    	{
    		u8 const ma = y + m_scroll; // ma must be 8-bit
    		u16 *p = &bitmap.pix(y);
    
    		for (u16 x = 0; x < 0x4000; x+=0x200)
    		{
    			u8 const gfx = m_p_videoram[x|ma] | m_p_videoram[x|ma|0x100];
    
    			/* Display a scanline of a character */
    			*p++ = BIT(gfx, 0);
    			*p++ = BIT(gfx, 1);
    			*p++ = BIT(gfx, 2);
    			*p++ = BIT(gfx, 3);
    			*p++ = BIT(gfx, 4);
    			*p++ = BIT(gfx, 5);
    			*p++ = BIT(gfx, 6);
    			*p++ = BIT(gfx, 7);
    		}
    	}
    	return 0;
    }

Страница 8 из 9 ПерваяПервая ... 456789 ПоследняяПоследняя

Информация о теме

Пользователи, просматривающие эту тему

Эту тему просматривают: 1 (пользователей: 0 , гостей: 1)

Похожие темы

  1. Ответов: 105
    Последнее: 10.02.2020, 18:51
  2. Программы для Apple II
    от sergey2b в разделе Apple
    Ответов: 3
    Последнее: 17.03.2019, 14:51
  3. Для спектрума можно писать на FASM
    от ZX_NOVOSIB в разделе Программирование
    Ответов: 5
    Последнее: 23.07.2017, 21:22
  4. Программы для модемов
    от p@lex в разделе Софт
    Ответов: 21
    Последнее: 11.02.2006, 21:36

Ваши права

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