uglobal align 4 ReadGIF.globalColor dd ? ReadGIF.cur_info dd ? ; image table pointer ReadGIF.codesize dd ? ReadGIF.compsize dd ? ReadGIF.bit_count dd ? ReadGIF.CC dd ? ReadGIF.EOI dd ? ReadGIF.Palette dd ? ReadGIF.block_ofs dd ? ReadGIF.gif_workarea rb 16*1024 endg ; unpacks GIF image ReadGIF: ; in: ; esi - pointer to GIF file in memory ; edi - pointer to output image list ; out: ; eax=0 -> ok, eax=1 -> invalid signature ; eax>=8 -> unsupported image attributes push esi edi mov [.cur_info],edi xor eax,eax mov [.globalColor],eax inc eax cmp dword[esi],'GIF8' jne .ex ; signature mov ecx,[esi+0xa] add esi,0xd mov edi,esi test cl,cl jns .nextblock mov [.globalColor],esi call .Gif_skipmap .nextblock: cmp byte[edi],0x21 jne .noextblock inc edi inc edi .block_skip: movzx eax,byte[edi] lea edi,[edi+eax+1] test eax,eax jnz .block_skip jmp .nextblock .noextblock: mov al,8 cmp byte[edi],0x2c ; image beginning jne .ex inc edi mov esi,[.cur_info] xchg esi,edi movzx eax,word[esi+4] stosd movzx eax,word[esi+6] stosd add esi,8 push edi mov ecx,[esi] inc esi test cl,cl js .uselocal push [.globalColor] mov edi,esi jmp .setPal .uselocal: call .Gif_skipmap push esi .setPal: movzx ecx,byte[edi] inc ecx mov [.codesize],ecx dec ecx pop [.Palette] lea esi,[edi+1] mov edi,.gif_workarea xor eax,eax lodsb ; eax - block_count add eax,esi mov [.block_ofs],eax mov [.bit_count],8 mov eax,1 shl eax,cl mov [.CC],eax mov ecx,eax inc eax mov [.EOI],eax mov eax, 1000h shl 16 .filltable: stosd inc eax loop .filltable pop edi .reinit: mov edx,[.EOI] inc edx push [.codesize] pop [.compsize] call .Gif_get_sym cmp eax,[.CC] je .reinit call .Gif_output .cycle: movzx ebx,ax call .Gif_get_sym cmp eax,edx jae .notintable cmp eax,[.CC] je .reinit cmp eax,[.EOI] je .end call .Gif_output .add: mov dword [.gif_workarea+edx*4],ebx cmp edx,0xFFF jae .cycle inc edx bsr ebx,edx cmp ebx,[.compsize] jne .noinc inc [.compsize] .noinc: jmp .cycle .notintable: push eax mov eax,ebx call .Gif_output push ebx movzx eax,bx call .Gif_output pop ebx eax jmp .add .end: xor eax,eax .ex: pop edi esi ret .Gif_skipmap: ; in: ecx - image descriptor, esi - pointer to colormap ; out: edi - pointer to area after colormap and ecx,111b inc ecx ; color map size mov ebx,1 shl ebx,cl lea ebx,[ebx*2+ebx] lea edi,[esi+ebx] ret .Gif_get_sym: mov ecx,[.compsize] push ecx xor eax,eax .shift: ror byte[esi],1 rcr eax,1 dec [.bit_count] jnz .loop1 inc esi cmp esi,[.block_ofs] jb .noblock push eax xor eax,eax lodsb test eax,eax jnz .nextbl mov eax,[.EOI] sub esi,2 add esp,8 jmp .exx .nextbl: add eax,esi mov [.block_ofs],eax pop eax .noblock: mov [.bit_count],8 .loop1: loop .shift pop ecx rol eax,cl .exx: xor ecx,ecx ret .Gif_output: push esi eax edx mov edx,.gif_workarea .next: push word[edx+eax*4] mov ax,word[edx+eax*4+2] inc ecx cmp ax,1000h jnz .next shl ebx,16 mov bx,[esp] .loop2: pop ax lea esi,[eax+eax*2] add esi,[.Palette] mov esi,[esi] bswap esi shr esi,8 mov [edi],esi add edi,3 loop .loop2 pop edx eax esi ret