首页
学习
活动
专区
圈层
工具
发布

aplib解压
EN

Stack Overflow用户
提问于 2013-02-23 12:16:04
回答 1查看 2.3K关注 0票数 1
代码语言:javascript
复制
aP_depack_asm:
    ; aP_depack_asm(const void *source, void *destination)

    _ret$  equ 7*4
    _src$  equ 8*4 + 4
    _dst$  equ 8*4 + 8

    pushad

    mov    esi, [esp + _src$] ; C calling convention
    mov    edi, [esp + _dst$]

    cld
    mov    dl, 80h
    xor    ebx,ebx

literal:
    movsb
    mov    bl, 2
nexttag:
    call   getbit
    jnc    literal-------jump if no carry

    xor    ecx, ecx
    call   getbit
    jnc    codepair

    xor    eax, eax
    call   getbit
    jnc    shortmatch

    mov    bl, 2
    inc    ecx
    mov    al, 10h

.getmorebits:
    call   getbit
    adc    al, al
    jnc    .getmorebits

    jnz    domatch

    stosb
    jmp    nexttag

codepair:
    call   getgamma_no_ecx
    sub    ecx, ebx
    jnz    normalcodepair

    call   getgamma
    jmp    domatch_lastpos


shortmatch:
    lodsb
    shr    eax, 1
    jz     donedepacking

    adc    ecx, ecx
    jmp    domatch_with_2inc

normalcodepair:
    xchg   eax, ecx
    dec    eax
    shl    eax, 8
    lodsb
    call   getgamma

    cmp    eax, 32000
    jae    domatch_with_2inc
    cmp    ah, 5
    jae    domatch_with_inc

    cmp    eax, 7fh
    ja     domatch_new_lastpos

domatch_with_2inc:
    inc    ecx

domatch_with_inc:
    inc    ecx

domatch_new_lastpos:
    xchg   eax, ebp
domatch_lastpos:
    mov    eax, ebp

    mov    bl, 1

domatch:
    push   esi
    mov    esi, edi
    sub    esi, eax
    rep    movsb
    pop    esi
    jmp    nexttag

getbit:
    add    dl, dl
    jnz    .stillbitsleft
    mov    dl, [esi]
    inc    esi
    adc    dl, dl
  .stillbitsleft:
    ret

getgamma:
    xor    ecx, ecx

getgamma_no_ecx:
    inc    ecx
  .getgammaloop:
    call   getbit
    adc    ecx, ecx
    call   getbit
    jc     .getgammaloop

    ret

donedepacking:
    sub    edi, [esp + _dst$]
    mov    [esp + _ret$], edi ; return unpacked length in eax

    popad

    ret

上面是aplib解压。已经提到,它是lz78的派生。我想知道getbit的含义,它是如何以及在algorithm中用来从字典中读取代码的。

EN

回答 1

Stack Overflow用户

发布于 2019-08-20 22:18:35

函数getbit负责从输入数据流中读取一位(“混合”,即包含纯字节和打包成字节的8个单独位的组)。

代码语言:javascript
复制
getbit:
    add    dl, dl
    jnz    .stillbitsleft
    mov    dl, [esi]
    inc    esi
    adc    dl, dl
.stillbitsleft:
    ret

ApLib中使用的实际算法是原创的,但它构建在与LZ78非常不同的基础上,并且与LZ77有更多的关系。基本上,在解压缩器循环的每次迭代中,一个人从输入流读取一位,如果它是0,则将一个字节从输入流复制到输出中。另一方面,如果此位为1,则解压缩器知道必须从已经解压缩的数据中复制匹配。信号位的概念来自于LZSS。匹配的细节也在压缩数据流中指定。该格式的一个不太常见的功能包括使用rep-offsets的可能性,即允许重用偏移量的命令。这个想法很可能是从LZX中借鉴过来的,这个特性使得ApLib在压缩方面比许多其他固定格式的LZ77/LZSS压缩器要好得多。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/15036993

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档