CPC Rulez
https://cpcrulez.fr/forum/

Nouvelle optimisation de code
https://cpcrulez.fr/forum/viewtopic.php?f=4&t=4272
Page 1 sur 1

Auteur :  Demoniak [ 22 Juil 2010, 08:00 ]
Sujet du message :  Nouvelle optimisation de code

Bon, je vous en propose un autre :

Code :
int Depack( UBYTE * InBuf, UBYTE * OutBuf )
{
    UBYTE a, DepackBits = 0;
    int Bit, InBytes = 0, Longueur, Delta, OutBytes = 0;

    for ( ;; )
        {
        Bit = DepackBits & 1;
        DepackBits >>= 1;
        if ( ! DepackBits )
            {
            DepackBits = InBuf[ InBytes++ ];
            Bit = DepackBits & 1;
            DepackBits >>= 1;
            DepackBits |= 0x80;
            }
        if ( ! Bit )
            OutBuf[ OutBytes++ ] = InBuf[ InBytes++ ];
        else
            {
            if ( ! InBuf[ InBytes ] )
                break; /* EOF */

            a = InBuf[ InBytes ];
            if ( a & 0x80 )
                {
                Longueur = 3 + ( ( InBuf[ InBytes ] >> 4 ) & 7 );
                Delta = ( InBuf[ InBytes++ ] & 15 ) << 8;
                Delta |= InBuf[ InBytes++ ];
                Delta++;
                }
            else
                if ( a & 0x40 )
                    {
                    Longueur = 2;
                    Delta = InBuf[ InBytes++ ] & 0x3f;
                    Delta++;
                    }
                else
                    if ( a & 0x20 )
                        {
                        Longueur = 2 + ( InBuf[ InBytes++ ] & 31 );
                        Delta = InBuf[ InBytes++ ];
                        Delta++;
                        }
                    else
                        if ( a & 0x10 )
                            {
                            Delta = ( InBuf[ InBytes++ ] & 15 ) << 8;
                            Delta |= InBuf[ InBytes++ ];
                            Longueur = InBuf[ InBytes++ ] + 1;
                            Delta++;
                            }
                        else
                            {
                            if ( InBuf[ InBytes ] == 15 )
                                {
                                Longueur = Delta = InBuf[ InBytes+1 ] + 1;
                                InBytes += 2;
                                }
                            else
                                {
                                if ( InBuf[ InBytes ] > 1 )
                                    Longueur = Delta = InBuf[ InBytes ];
                                else
                                    Longueur = Delta = 256;

                                InBytes++;
                                }
                            }
            for ( ; Longueur--; )
                {
                OutBuf[ OutBytes ] = OutBuf[ OutBytes - Delta ];
                OutBytes++;
                }
            }
        }
    return( OutBytes );
}

Que je traduis en Z80 de la façon suivante :
Code :
;
; Entrée :
; - HL = Buffer (fichier compacté)
; - DE = Destination
; Sortie :
; - AF, BC, DE, HL modifiés
;
DepkLzw:
        XOR     A
        LD      (BclLzw+1),A            ; DepackBits = 0
;
TstBitLzw:
        LD      A,(HL)                  ; DepackBits = InBuf[ InBytes++ ]
        INC     HL
        RRA                             ; Rotation rapide calcul seulement flag C
        SET     7,A                     ; Positionne bit 7 en gardant flag C
        LD      (BclLzw+1),A
        JR      C,TstCodeLzw
CopByteLzw:
        LDI                             ; OutBuf[ OutBytes++ ] = InBuf[ InBytes++ ]
;
BclLzw:
        LD      A,0
        RR      A                       ; Rotation avec calcul Flags C et Z
        LD      (BclLzw+1),A
        JR      NC,CopByteLzw
        JR      Z,TstBitLzw

TstCodeLzw:
;
;       a = InBuf[ InBytes ];
;
        LD      A,(HL)
        AND     A
;
; Plus d'octets à traiter
; = fini
;
        RET     Z

        INC     HL
        LD      B,A                     ; B = InBuf[ InBytes ]
        RLCA                            ; A & 0x80 ?
        JR      NC,TstLzw40
;
;       Longueur = 3 + ( ( InBuf[ InBytes ] >> 4 ) & 7 );
;       Delta = ( InBuf[ InBytes++ ] & 15 ) << 8;
;       Delta |= InBuf[ InBytes++ ];
;       Delta++;
;
        LD      C,(HL)                  ; C = poids faible Delta
        RLCA
        RLCA
        RLCA
        AND     7
        ADD     A,3
        PUSH    HL
        LD      H,A                     ; H = Longueur
        LD      A,B                     ; B = InBuf[InBytes]
        AND     #0F
        LD      B,A                     ; B = poids fort Delta
        LD      A,H                     ; A = Length
        LD      H,D
        LD      L,E
        SCF                             ; Repositionner flag C
        SBC     HL,BC                   ; HL=HL-(BC-1)
        LD      B,0
        LD      C,A
        LDIR
        POP     HL
        INC     HL
        JR      BclLzw
;
TstLzw40:
        RLCA                            ; A & 0x40 ?
        JR      NC,TstLzw20
;
;       Longueur = 2;
;       Delta = InBuf[ InBytes++ ] & 0x3f;
;       Delta++;
;
        LD      C,B
        RES     6,C
        LD      B,0                     ; BC = Delta -1, pas de +1 car flag C = 1
        PUSH    HL
        LD      H,D
        LD      L,E
        SBC     HL,BC
        LDI
        LDI
        POP     HL
        JR      BclLzw
;
TstLzw20:
        RLCA                            ; A & 0x20 ?
        JR      NC,TstLzw10
;
;       Longueur = 2 + ( InBuf[ InBytes++ ] & 31 );
;       Delta = InBuf[ InBytes++ ];
;       Delta++;
;
        PUSH    HL
        LD      A,B
        RES     5,A
        LD      C,(HL)                  ; C = Delta
        LD      B,0
        LD      H,D
        LD      L,E
        SBC     HL,BC
        ADD     A,2
        LD      C,A                     ; C = Longueur
        LDIR
        POP     HL
        INC     HL
        JR      BclLzw

;
TstLzw10:
        RLCA                            ; A & 0x10 ?
        JR      NC,CodeLzw0F
;
;       Delta = ( InBuf[ InBytes++ ] & 15 ) << 8;
;       Delta |= InBuf[ InBytes++ ];
;       Longueur = InBuf[ InBytes++ ] + 1;
;       Delta++;
;
        RES     4,B                     ; B = Delta(high)
        LD      C,(HL)                  ; C = Delta(low)
        INC     HL
        LD      A,(HL)                  ; A = Longueur - 1
        PUSH    HL
        LD      H,D
        LD      L,E
        SBC     HL,BC                   ; Flag C=1 -> hl=hl-(bc+1)
        LD      B,0
        LD      C,A
        INC     BC                      ; BC = Longueur
        LDIR
        POP     HL
        INC     HL
        JR      BclLzw
;
CodeLzw0F:
        LD      C,(HL)
        PUSH    HL
        LD      H,D
        LD      L,E
        LD      A,B
        CP      #0F
        JR      NZ,CodeLzw02
;
;       Longueur = Delta = InBuf[ InBytes + 1 ] + 1;
;       InBytes += 2;
;
        XOR     A
        LD      B,A
        INC     BC
        SBC     HL,BC
        LDIR
        POP     HL
        INC     HL
        JP      BclLzw
;
CodeLzw02:
        CP      2
        JR      C,CodeLzw01
;
;       Longueur = Delta = InBuf[ InBytes ];
;
        LD      C,A
        XOR     A
        LD      B,A
        SBC     HL,BC
        LDIR
        POP     HL
        JP      BclLzw
;
;       Longueur = Delta = 256;
;
CodeLzw01:                              ; Ici, A = B = 1
        XOR     A
        LD      C,A
        DEC     H
        LDIR
        POP     HL
        JP      BclLzw

J'attends vous idées d'optimisations :sweatingbullets:
(Optimisation en vitesse biensur ;-) )

Auteur :  Demoniak [ 23 Juil 2010, 12:27 ]
Sujet du message :  Re: Nouvelle optimisation de code

ça n'inspire personne ? Peut-être un peu compliqué celui-là... J'en ai plein d'autres en réserve :)

Auteur :  hERMOL [ 23 Juil 2010, 13:05 ]
Sujet du message :  Re: Nouvelle optimisation de code

c'est du costo.. niveau licence en Z80... :D

Auteur :  fano [ 23 Juil 2010, 20:18 ]
Sujet du message :  Re: Nouvelle optimisation de code

Un décompresseur LZW ? faut avouer qu'aussi long ça rebute un peu :D

Auteur :  Megachur [ 24 Juil 2010, 07:31 ]
Sujet du message :  Re: Nouvelle optimisation de code

si quelqu'un à le temps d'analyser qu'elle est la boucle qui prend le plus de temps machine -> je veux bien regarder ça !

:eng:

Nota: là je suis sur trop de truc en même temps pour m'y pencher en détail ! :winner:

Auteur :  exolon [ 22 Août 2010, 16:03 ]
Sujet du message :  Re: Nouvelle optimisation de code

Pour ma part c'est surtout la gueule du code C que j'aurais optimisé , avec des while / do while , et des switch/case . Mais bon...
On dirait que tu es parti du source Z80 pour fournir un truc en C comme ça ;)

Page 1 sur 1 Le fuseau horaire est UTC+1 heure
Powered by phpBB® Forum Software © phpBB Group
https://www.phpbb.com/