Annotation of ntddk/src/video/displays/vga/i386/cpybits.asm, revision 1.1

1.1     ! root        1: ;!!! This is all temp crap to be replaced when the blinker is written
        !             2: 
        !             3: ;---------------------------Module-Header------------------------------;
        !             4: ; Module Name: cpybits.asm
        !             5: ;
        !             6: ; Copyright (c) 1992 Microsoft Corporation
        !             7: ;-----------------------------------------------------------------------;
        !             8:         page    ,132
        !             9:         title   DrvCopyBits Support
        !            10:         .386
        !            11: 
        !            12: ifndef  DOS_PLATFORM
        !            13:         .model  small,c
        !            14: else
        !            15: ifdef   STD_CALL
        !            16:         .model  small,c
        !            17: else
        !            18:         .model  small,pascal
        !            19: endif;  STD_CALL
        !            20: endif;  DOS_PLATFORM
        !            21: 
        !            22:         assume cs:FLAT,ds:FLAT,es:FLAT,ss:FLAT
        !            23:         assume fs:nothing,gs:nothing
        !            24: 
        !            25:         .xlist
        !            26:         include stdcall.inc             ;calling convention cmacros
        !            27:         include i386\egavga.inc         ;VGA register definitions
        !            28:         include i386\strucs.inc
        !            29:         .list
        !            30: 
        !            31: 
        !            32:         .data
        !            33: 
        !            34: ; Reuse the work area from the dib conversion code.
        !            35: 
        !            36: ; BUGBUG this should be allocated memory accessed via the DEVSURF, not static
        !            37: 
        !            38:         extrn   ajConvertBuffer:byte    ;Buffer for converting to/from display
        !            39: 
        !            40: ; BUGBUG this should be dynamically calculated
        !            41: 
        !            42: CJ_WORK_PLANE   equ     cj_max_scan+1   ;Width of each plane in ajConvertBuffer
        !            43: 
        !            44:         .code
        !            45: 
        !            46: ; ausLo16 is used to convert the low nibble of a byte into 4bpp packed pel
        !            47: 
        !            48: ausLo16 equ this word
        !            49: 
        !            50:         dw          0000h                   ;0000
        !            51:         dw          0100h                   ;0001
        !            52:         dw          1000h                   ;0010
        !            53:         dw          1100h                   ;0011
        !            54:         dw          0001h                   ;0100
        !            55:         dw          0101h                   ;0101
        !            56:         dw          1001h                   ;0110
        !            57:         dw          1101h                   ;0111
        !            58:         dw          0010h                   ;1000
        !            59:         dw          0110h                   ;1001
        !            60:         dw          1010h                   ;1010
        !            61:         dw          1110h                   ;1011
        !            62:         dw          0011h                   ;1100
        !            63:         dw          0111h                   ;1101
        !            64:         dw          1011h                   ;1110
        !            65:         dw          1111h                   ;1111
        !            66: 
        !            67: ; aulHi16 is used to convert the hi nibble of a byte into 4bpp packed pel
        !            68: 
        !            69: aulHi16 equ this dword
        !            70: 
        !            71:         dd          00000000h               ;0000
        !            72:         dd          01000000h               ;0001
        !            73:         dd          10000000h               ;0010
        !            74:         dd          11000000h               ;0011
        !            75:         dd          00010000h               ;0100
        !            76:         dd          01010000h               ;0101
        !            77:         dd          10010000h               ;0110
        !            78:         dd          11010000h               ;0111
        !            79:         dd          00100000h               ;1000
        !            80:         dd          01100000h               ;1001
        !            81:         dd          10100000h               ;1010
        !            82:         dd          11100000h               ;1011
        !            83:         dd          00110000h               ;1100
        !            84:         dd          01110000h               ;1101
        !            85:         dd          10110000h               ;1110
        !            86:         dd          11110000h               ;1111
        !            87: 
        !            88: ; ajRightMasks turns an exclusive bit position (0-7) into a mask of bits
        !            89: ; to alter for the right hand side of the blt
        !            90: 
        !            91: ajRightMasks equ this byte
        !            92: 
        !            93:         db          11111111b               ;0 should never be used
        !            94:         db          01111111b               ;1
        !            95:         db          00111111b               ;2
        !            96:         db          00011111b               ;3
        !            97:         db          00001111b               ;4
        !            98:         db          00000111b               ;5
        !            99:         db          00000011b               ;6
        !           100:         db          00000001b               ;7
        !           101: 
        !           102: ; ajLeftMasks turns a bit position (0-7) into a mask of bits to alter for
        !           103: ; the left hand side of the blt
        !           104: 
        !           105: ajLeftMasks equ this byte
        !           106: 
        !           107:         db          11111111b               ;0 should never be used
        !           108:         db          10000000b               ;1
        !           109:         db          11000000b               ;2
        !           110:         db          11100000b               ;3
        !           111:         db          11110000b               ;4
        !           112:         db          11111000b               ;5
        !           113:         db          11111100b               ;6
        !           114:         db          11111110b               ;7
        !           115: 
        !           116: 
        !           117: CB_4BPP_SCAN    equ (CX_SCREEN_MAX / 2)     ;# bytes for a 4bpp screen scan
        !           118: 
        !           119: ;-----------------------------Public-Routine----------------------------;
        !           120: ; vConvertVGAScan
        !           121: ;
        !           122: ; Converts a VGA scan into a 4bpp format with a given phase alignment,
        !           123: ; and returns a pointer to the converted buffer.
        !           124: ;
        !           125: ; pdsurfsrc - pointer to source surface (must be VGA display memory)
        !           126: ; xSrc      - X origin of the source
        !           127: ; ySrc      - Y origin of the source
        !           128: ; pjDstBase - Base address of the destination
        !           129: ; xDst      - X origin of the destination
        !           130: ; yDst      - Y origin of the destination
        !           131: ; cxPels    - Number of pels in X
        !           132: ; cyTotalScans - Number of scans in overall operation
        !           133: ; lDelta    - Width in bytes of a destination scan
        !           134: ; iFormat   - Format of destination
        !           135: ; pulXlate  - Color translation vector
        !           136: ;-----------------------------------------------------------------------;
        !           137: 
        !           138: ProcName    xxxvConvertVGA2DIB,vConvertVGA2DIB,44
        !           139: 
        !           140: xxxvConvertVGA2DIB proc uses esi edi ebx,\
        !           141:         pdsurfsrc       :ptr DEVSURF,   \
        !           142:         xSrc            :dword,         \
        !           143:         ySrc            :dword,         \
        !           144:         pjDstBase       :dword,         \
        !           145:         xDst            :dword,         \
        !           146:         yDst            :dword,         \
        !           147:         cxPels          :dword,         \
        !           148:         cyTotalScans    :dword,         \
        !           149:         lDelta          :dword,         \
        !           150:         iFormat         :dword,         \
        !           151:         pulXlate        :dword
        !           152: 
        !           153: ;-----------------------------------------------------------------------;
        !           154: ; Local variables and their meaning
        !           155: ;
        !           156: ; cjScreenCopy      This is the number of bytes to copy from each scan
        !           157: ;                   into ajConvertBuffer.
        !           158: ; jLeftMask         This is the left-hand side (lhs) mask used when copying
        !           159: ;                   the converted data to the destination
        !           160: ; jRightMask        This is the right-hand side (lhs) mask used when copying
        !           161: ;                   the converted data to the destination
        !           162: ; cRightShift       This is the number of bits that the converted data needs
        !           163: ;                   to be shifted right to align with the destination.
        !           164: ; cjRightShift      This is the number of bytes which must be shifted right
        !           165: ;                   by cRightShift
        !           166: ; cCopy             This is the number of full (e.g. not masked) bytes which
        !           167: ;                   must be copied to the destination
        !           168: ; pjWork            Pointer to the work area where
        !           169: ;                       a)  color converted data is written into
        !           170: ;                       b)  bits are phase-aligned if needed
        !           171: ;                       c)  data is read from for the final copy to the DIB
        !           172: ; pjSrc             Address of scan 0 in memory
        !           173: ; pjDst             Address of scan 0 in memory
        !           174: ; cyScans           Number of scans to do in current bank
        !           175: ; ulScanWidth       Offset from start of one scan to start of next
        !           176: ; ulBottomSrcScan   Bottom scan line of source rectangle (non-inclusive)
        !           177: ;-----------------------------------------------------------------------;
        !           178: 
        !           179:         local   cjScreenCopy    :dword
        !           180:         local   jLeftMask       :byte
        !           181:         local   jRightMask      :byte
        !           182:         local   cRightShift     :byte
        !           183:         local   cjRightShift    :dword
        !           184:         local   cCopy           :dword
        !           185:         local   pfnXlate        :ptr
        !           186:         local   pjWork          :ptr
        !           187:         local   cjSkip          :dword
        !           188:         local   pjSrc           :dword
        !           189:         local   pjDst           :dword
        !           190:         local   cyScans         :dword
        !           191:         local   ulScanWidth     :dword
        !           192:         local   ulBottomSrcScan :dword
        !           193: 
        !           194:         local   ajColorConv[16]:byte
        !           195:         local   ajWork[CB_4BPP_SCAN+4]:byte
        !           196:         local   aj8bpp[CX_SCREEN_MAX+8]:byte
        !           197: 
        !           198: 
        !           199: ;----------------------------------------------------------------------;
        !           200: ; Loop through source banks, copying & converting one bank at a time.
        !           201: 
        !           202: ; Calculate the bottom scan line of the source rectangle (non-inclusive).
        !           203: 
        !           204:         mov     eax,ySrc
        !           205:         add     eax,cyTotalScans
        !           206:         mov     ulBottomSrcScan,eax
        !           207: 
        !           208:         mov     ecx,pdsurfsrc           ;point to source surface
        !           209:         mov     eax,[ecx].dsurf_lNextScan
        !           210:         mov     ulScanWidth,eax         ;local copy of scan line width
        !           211: 
        !           212: ; Map in the bank containing the top scan to fill, if it's not mapped in
        !           213: ; already.
        !           214: 
        !           215:         mov     eax,ySrc                ;top scan line of source
        !           216: 
        !           217:         cmp     eax,[ecx].dsurf_rcl1WindowClip.yTop ;is fill top less than
        !           218:                                                     ; current bank?
        !           219:         jl      short map_init_bank             ;yes, map in proper bank
        !           220:         cmp     eax,[ecx].dsurf_rcl1WindowClip.yBottom ;fill top greater than
        !           221:                                                        ; current bank?
        !           222:         jl      short init_bank_mapped          ;no, proper bank already mapped
        !           223: map_init_bank:
        !           224: 
        !           225: ; Map in the bank containing the top scan line of the fill.
        !           226: 
        !           227:         ptrCall <dword ptr [ecx].dsurf_pfnBankControl>,<ecx,eax,JustifyTop>
        !           228: 
        !           229: init_bank_mapped:
        !           230: 
        !           231: bank_loop:
        !           232: 
        !           233: ; Set the start address of the source bitmap.
        !           234: ; Note that the start of the bitmap will change each time through the
        !           235: ; bank loop, because the start of the bitmap is varied to map the
        !           236: ; desired scan line to the banking window.
        !           237: 
        !           238:         mov     eax,pdsurfsrc           ;point to source surface
        !           239:         mov     ebx,[eax].dsurf_pvBitmapStart ;start of scan 0 in bitmap
        !           240:         mov     pjSrc,ebx
        !           241: 
        !           242: ; Set the start address of the destination bitmap.
        !           243: 
        !           244:         mov     ebx,pjDstBase
        !           245:         mov     pjDst,ebx
        !           246: 
        !           247: ; Figure out how many scan lines we'll fill in the current bank.
        !           248: 
        !           249:         mov     ebx,ulBottomSrcScan     ;bottom of destination rectangle
        !           250:         cmp     ebx,[eax].dsurf_rcl1WindowClip.yBottom
        !           251:                                         ;which comes first, the bottom of the
        !           252:                                         ; dest rect or the bottom of the
        !           253:                                         ; current bank?
        !           254:         jl      short BottomScanSet     ;fill bottom comes first, so draw to
        !           255:                                         ; that; this is the last bank in fill
        !           256:         mov     ebx,[eax].dsurf_rcl1WindowClip.yBottom
        !           257:                                         ;bank bottom comes first; draw to
        !           258:                                         ; bottom of bank
        !           259: BottomScanSet:
        !           260:         sub     ebx,ySrc        ;# of scans to fill in bank
        !           261:         mov     cyScans,ebx
        !           262:         push    ebx             ;remember # of scans in bank
        !           263: 
        !           264:         call    DoOneBank       ;copy and convert within the current bank
        !           265: 
        !           266:         pop     ebx             ;restore # of scans in bank
        !           267: 
        !           268:         sub     cyTotalScans,ebx        ;count off this bank's scans from total
        !           269:         jz      short banks_done        ;no more scans; done
        !           270:         add     yDst,ebx                ;advance to the next destination scan
        !           271:                                         ; to copy to
        !           272:         mov     edi,pdsurfsrc
        !           273:         mov     eax,[edi].dsurf_rcl1WindowClip.yBottom
        !           274:         mov     ySrc,eax                ;remember where the top of the bank
        !           275:                                         ; we're about to map in is (same as
        !           276:                                         ; bottom of bank we just did)
        !           277: 
        !           278:         ptrCall <dword ptr [edi].dsurf_pfnBankControl>,<edi,eax,JustifyTop>
        !           279:                                         ;map in the bank
        !           280: 
        !           281:         jmp     bank_loop               ;fill the next bank
        !           282: 
        !           283: 
        !           284: ; Done.
        !           285: 
        !           286:         align   4
        !           287: banks_done:
        !           288: 
        !           289:         cRet    vConvertVGA2DIB
        !           290: 
        !           291: ;----------------------------------------------------------------------;
        !           292: ; Copies and converts bits within a single bank.
        !           293: 
        !           294:         align   4
        !           295: DoOneBank:
        !           296: 
        !           297:         cld
        !           298: 
        !           299: ; Compute the number of bytes to copy from the screen, and the starting
        !           300: ; address of the source
        !           301: 
        !           302:         mov     eax,ySrc                ;Compute addr of first source scan
        !           303:         mov     ebx,xSrc
        !           304:         imul    eax,ulScanWidth
        !           305:         mov     ecx,ebx
        !           306:         shr     ebx,3
        !           307:         add     eax,ebx
        !           308:         add     pjSrc,eax
        !           309: 
        !           310: ; Compute the number of bytes to actually transfer from the screen
        !           311: 
        !           312:         mov     eax,cxPels              ;Compute rhs
        !           313:         add     eax,ecx
        !           314:         dec     eax                     ;Make rhs inclusive
        !           315:         shr     ecx,3                   ;Compute byte of lhs
        !           316:         shr     eax,3                   ;Compute byte of rhs
        !           317:         sub     eax,ecx                 ;Compute number of bytes for copy
        !           318:         inc     eax                     ;(because rhs inclusive, always inc)
        !           319:         mov     cjScreenCopy,eax
        !           320: 
        !           321: ; Compute the address of the starting destination scan.
        !           322: 
        !           323:         mov     eax,yDst
        !           324:         imul    lDelta
        !           325:         add     pjDst,eax
        !           326: 
        !           327: ; Set up for the preprocess loops and invoke the correct one.  First make
        !           328: ; some assumptions about defaults
        !           329: 
        !           330:         xor     eax,eax
        !           331:         mov     cRightShift,al          ;No shifting needed
        !           332:         mov     jLeftMask,al            ;No left masking needed
        !           333:         mov     jRightMask,al           ;No right masking needed
        !           334:         lea     eax,ajWork              ;Intermediate work area
        !           335:         mov     pjWork,eax
        !           336: 
        !           337:         mov     esi,cxPels
        !           338:         mov     ebx,xSrc
        !           339:         mov     edx,xDst
        !           340: 
        !           341:         mov     eax,iFormat
        !           342:         dec     eax
        !           343:         jz      preproc_1bpp
        !           344:         dec     eax
        !           345:         jz      preproc_4bpp
        !           346:         .errnz  BMF_1BPP-1
        !           347:         .errnz  BMF_4BPP-2
        !           348:         .errnz  BMF_8BPP-3
        !           349: 
        !           350: ; Destination is 8bpp.  Copy will be phased aligned from the conversion buffer
        !           351: ; to the destination.
        !           352: 
        !           353: preproc_8bpp:
        !           354:         add     pjDst,edx               ;Offset to first pel in DIB
        !           355:         and     ebx,7                   ;Offset to first pel for final copy
        !           356:         mov     cjSkip,ebx
        !           357:         mov     cCopy,esi               ;Number of bytes for final copy
        !           358:         lea     eax,aj8bpp              ;Intermediate work area
        !           359:         mov     pjWork,eax
        !           360:         mov     pfnXlate,offset FLAT:cvt_to_8bpp
        !           361:         jmp     preproc_done
        !           362: 
        !           363: 
        !           364: ; Destination is 4bpp.  Copy will either be phase aligned or be off by 4 in
        !           365: ; which case we will phase align the entire buffer before copying.
        !           366: 
        !           367: preproc_4bpp:
        !           368:         lea     eax,[esi][edx]          ;Compute rhs for later
        !           369:         test    dl,1                    ;Odd if left mask needed
        !           370:         jz      @F
        !           371:         mov     jLeftMask,11110000b
        !           372:         dec     esi                     ;One less pel in inner loop
        !           373: @@:
        !           374:         test    al,1                    ;Odd if right mask needed
        !           375:         jz      @F
        !           376:         mov     jRightMask,00001111b
        !           377:         dec     esi                     ;One less pel in inner loop
        !           378: @@:
        !           379: 
        !           380:         and     ebx,7                   ;Offset for final copy is xSrc mod 8
        !           381: 
        !           382: ; If the source and destination have different alignments, we'll have to
        !           383: ; compute phase alignment stuff.
        !           384: 
        !           385:         mov     eax,ebx
        !           386:         xor     eax,edx
        !           387:         shr     eax,1
        !           388:         jnc     @F
        !           389:         mov     eax,cjScreenCopy        ;* 4 for size of data in buffer
        !           390:         shl     eax,2
        !           391:         inc     eax                     ;+ 1 to shift into last byte!
        !           392:         mov     cjRightShift,eax
        !           393:         mov     cRightShift,4           ;Shift entire buffer right 4 pels
        !           394:         inc     ebx                     ;First pel just moved right
        !           395: @@:
        !           396: 
        !           397: ; Finish calculating the other parameters
        !           398: 
        !           399:         shr     edx,1                   ;Offset to first pel in DIB
        !           400:         add     pjDst,edx
        !           401:         shr     ebx,1
        !           402:         mov     cjSkip,ebx
        !           403:         shr     esi,1
        !           404:         mov     cCopy,esi               ;# of inner bytes for final copy
        !           405: 
        !           406:         mov     eax,offset FLAT:copy_to_dest;Assume no color translation needed
        !           407:         cmp     pulXlate,0
        !           408:         je      @F
        !           409:         mov     eax,offset FLAT:cvt_to_4bpp ;Addreess of color xlate routine
        !           410: @@:
        !           411:         mov     pfnXlate,eax
        !           412:         jmp     preproc_done
        !           413: 
        !           414: 
        !           415: ; Destination is 1bpp.  Copy most likely will require masking and phase
        !           416: ; alignment.
        !           417: 
        !           418: preproc_1bpp:
        !           419:         mov     edi,00000007h           ;A handy mask used a lot
        !           420:         xor     ecx,ecx                 ;CL = lhs mask, CH = rhs mask
        !           421:         lea     eax,[esi][edx]          ;Compute rhs for later
        !           422:         test    edx,edi                 ;See if partial byte
        !           423:         jz      preproc_1bpp_done_lhs   ;No partial lhs byte
        !           424:         mov     ecx,edx
        !           425:         neg     ecx
        !           426:         and     ecx,edi                 ;CL = # bits in lhs, CH = 0
        !           427:         sub     esi,ecx                 ;Compute # remaining bytes
        !           428:         mov     cl,ajLeftMasks[ecx]     ;Get lhs mask
        !           429:         jnc     preproc_1bpp_done_lhs   ;Didn't combine into one byte
        !           430:         and     eax,edi                 ;Combine rhs mask with lhs mask
        !           431:         and     cl,ajRightMasks[eax]
        !           432:         xor     esi,esi                 ;No more bytes
        !           433:         xor     eax,eax                 ;To show no rhs
        !           434:         jmp     short preproc_1bpp_have_masks
        !           435: 
        !           436: preproc_1bpp_done_lhs:
        !           437:         and     eax,edi                 ;See if partial rhs byte
        !           438:         jz      preproc_1bpp_have_masks ;No partial rhs byte
        !           439:         mov     ch,ajRightMasks[eax]
        !           440:         sub     esi,eax                 ;Compute # remaining bytes
        !           441: 
        !           442: preproc_1bpp_have_masks:
        !           443:         mov     jLeftMask,cl            ;Set left and right masks
        !           444:         mov     jRightMask,ch
        !           445:         shr     esi,3                   ;# of inner bytes for final copy
        !           446:         mov     cCopy,esi
        !           447: 
        !           448: ; Compute offset to first byte in destination DIB
        !           449: 
        !           450:         mov     eax,edx
        !           451:         shr     eax,3
        !           452:         add     pjDst,eax
        !           453: 
        !           454: ; Compute phase alignment parameters
        !           455: 
        !           456:         xor     ecx,ecx                 ;Assume cjSkip is 0
        !           457:         and     edx,edi
        !           458:         and     ebx,edi
        !           459:         sub     edx,ebx                 ;Determine phase alignment
        !           460:         jz      preproc_finish_1bpp     ;No phase alignment needed
        !           461: 
        !           462: ; We're really shifting left, so we'll set it up to shift right a lot, and
        !           463: ; get the first byte of the final move from byte 1 of the work area.
        !           464: 
        !           465:         adc     ecx,ecx                 ;Set cjSkip = 0 or 1
        !           466:         and     edx,edi                 ;3 LSBs is shift count
        !           467:         mov     cRightShift,dl          ;Phase for the shift
        !           468:         mov     eax,cjScreenCopy        ;Size of data in buffer
        !           469:         inc     eax                     ;+ 1 to shift into last byte!
        !           470:         mov     cjRightShift,eax
        !           471: preproc_finish_1bpp:
        !           472:         mov     cjSkip,ecx              ;No skipping needed
        !           473:         mov     esi,pulXlate            ;Copy color translation table to the
        !           474:         lea     edi,ajColorConv         ;  frame because we are out of regs.
        !           475:         mov     ecx,16
        !           476: @@:
        !           477:         lodsd
        !           478:         stosb
        !           479:         dec     ecx
        !           480:         jnz     @B
        !           481: 
        !           482:         mov     pfnXlate,offset FLAT:cvt_to_1bpp
        !           483: 
        !           484: preproc_done:
        !           485: 
        !           486: process_next_scan:
        !           487: 
        !           488:         mov     edi,offset FLAT:ajConvertBuffer
        !           489:         mov     edx,EGA_BASE + GRAF_ADDR
        !           490:         mov     eax,GRAF_READ_MAP
        !           491: copy_next_plane:
        !           492:         mov     esi,pjSrc               ;ESI --> first Source byte
        !           493:         out     dx,ax                   ;Set read plane
        !           494:         mov     ecx,cjScreenCopy        ;Set number of bytes to read
        !           495:         mov     ebx,edi
        !           496:         rep     movsb
        !           497:         lea     edi,[ebx][CJ_WORK_PLANE];EDI --> next scan in convert buf
        !           498:         inc     ah                      ;Set next read plane
        !           499:         cmp     ah,4
        !           500:         jb      copy_next_plane
        !           501: 
        !           502: ; The scan has been read in from the VGA.  Convert it into 4bpp format which
        !           503: ; will be needed for doing the color conversion.
        !           504: 
        !           505:         lea     edi,ajWork              ;Convert dwords into here
        !           506:         mov     esi,offset FLAT:ajConvertBuffer
        !           507:         mov     ecx,cjScreenCopy        ;# of source bytes to convert
        !           508: 
        !           509: cvt_next_src_byte:
        !           510:         xor     eax,eax
        !           511:         mov     al,[esi][CJ_WORK_PLANE*3]   ;Get data for plane C3
        !           512:         mov     ebx,eax
        !           513:         and     ebx,00001111b
        !           514:         shr     eax,4
        !           515:         mov     edx,aulHi16[ebx*4]
        !           516:         or      dx,ausLo16[eax*2]
        !           517:         shl     edx,1
        !           518:         mov     al,[esi][CJ_WORK_PLANE*2]   ;Get data for plane C2
        !           519:         mov     ebx,eax
        !           520:         and     ebx,00001111b
        !           521:         shr     eax,4
        !           522:         or      edx,aulHi16[ebx*4]
        !           523:         or      dx,ausLo16[eax*2]
        !           524:         shl     edx,1
        !           525:         mov     al,[esi][CJ_WORK_PLANE*1]   ;Get data for plane C1
        !           526:         mov     ebx,eax
        !           527:         and     ebx,00001111b
        !           528:         shr     eax,4
        !           529:         or      edx,aulHi16[ebx*4]
        !           530:         or      dx,ausLo16[eax*2]
        !           531:         shl     edx,1
        !           532:         lodsb                               ;Get data for plane C0
        !           533:         mov     ebx,eax
        !           534:         and     ebx,00001111b
        !           535:         shr     eax,4
        !           536:         or      edx,aulHi16[ebx*4]
        !           537:         or      dx,ausLo16[eax*2]
        !           538:         mov     eax,edx
        !           539:         stosd                               ;8 pels down!
        !           540:         dec     ecx
        !           541:         jnz     cvt_next_src_byte
        !           542: 
        !           543: 
        !           544: ; Perform the format conversion
        !           545:         mov     ecx,cjScreenCopy        ;Set lopp count
        !           546:         lea     esi,ajWork              ;Set source pointer
        !           547:         mov     edi,pjWork              ;Set destination pointer
        !           548:         mov     ebx,pulXlate            ;Set color translate vector
        !           549:         xor     eax,eax                 ;Init D31:D8 to 0
        !           550:         jmp     pfnXlate                ;Invoke correct conversion routine
        !           551: 
        !           552: ; Convert from 4bpp to 8bpp with color translation
        !           553: 
        !           554: cvt_to_8bpp:
        !           555:         lodsb                           ;Get two nibbles worth
        !           556:         mov     edx,eax
        !           557:         shr     eax,4
        !           558:         and     edx,00001111b
        !           559:         mov     al,[ebx][eax*4]
        !           560:         stosb
        !           561:         mov     al,[ebx][edx*4]
        !           562:         stosb
        !           563:         lodsb                           ;Get two nibbles worth
        !           564:         mov     edx,eax
        !           565:         shr     eax,4
        !           566:         and     edx,00001111b
        !           567:         mov     al,[ebx][eax*4]
        !           568:         stosb
        !           569:         mov     al,[ebx][edx*4]
        !           570:         stosb
        !           571:         lodsb                           ;Get two nibbles worth
        !           572:         mov     edx,eax
        !           573:         shr     eax,4
        !           574:         and     edx,00001111b
        !           575:         mov     al,[ebx][eax*4]
        !           576:         stosb
        !           577:         mov     al,[ebx][edx*4]
        !           578:         stosb
        !           579:         lodsb                           ;Get two nibbles worth
        !           580:         mov     edx,eax
        !           581:         shr     eax,4
        !           582:         and     edx,00001111b
        !           583:         mov     al,[ebx][eax*4]
        !           584:         stosb
        !           585:         mov     al,[ebx][edx*4]
        !           586:         stosb
        !           587:         dec     ecx
        !           588:         jnz     cvt_to_8bpp
        !           589:         jmp     copy_to_dest
        !           590: 
        !           591: ; Convert from 4bpp to 4bpp with color translation.
        !           592: 
        !           593: cvt_to_4bpp:
        !           594:         lodsb                           ;Get two nibbles worth
        !           595:         mov     edx,eax
        !           596:         shr     eax,4
        !           597:         and     edx,00001111b
        !           598:         mov     al,[ebx][eax*4]
        !           599:         shl     al,4
        !           600:         or      al,[ebx][edx*4]
        !           601:         stosb
        !           602:         lodsb                           ;Get two nibbles worth
        !           603:         mov     edx,eax
        !           604:         shr     eax,4
        !           605:         and     edx,00001111b
        !           606:         mov     al,[ebx][eax*4]
        !           607:         shl     al,4
        !           608:         or      al,[ebx][edx*4]
        !           609:         stosb
        !           610:         lodsb                           ;Get two nibbles worth
        !           611:         mov     edx,eax
        !           612:         shr     eax,4
        !           613:         and     edx,00001111b
        !           614:         mov     al,[ebx][eax*4]
        !           615:         shl     al,4
        !           616:         or      al,[ebx][edx*4]
        !           617:         stosb
        !           618:         lodsb                           ;Get two nibbles worth
        !           619:         mov     edx,eax
        !           620:         shr     eax,4
        !           621:         and     edx,00001111b
        !           622:         mov     al,[ebx][eax*4]
        !           623:         shl     al,4
        !           624:         or      al,[ebx][edx*4]
        !           625:         stosb
        !           626:         dec     ecx
        !           627:         jnz     cvt_to_4bpp
        !           628:         jmp     copy_to_dest
        !           629: 
        !           630: 
        !           631: ; Convert from 4bpp to 1bpp with color translation.
        !           632: 
        !           633: 
        !           634: cvt_to_1bpp:
        !           635:         lodsb                           ;Get two nibbles worth
        !           636:         mov     edx,eax
        !           637:         shr     eax,4
        !           638:         and     edx,00001111b
        !           639:         mov     bl,ajColorConv[eax]
        !           640:         shl     bl,1
        !           641:         or      bl,ajColorConv[edx]
        !           642:         lodsb
        !           643:         mov     edx,eax
        !           644:         shr     eax,4
        !           645:         and     edx,00001111b
        !           646:         shl     bl,1
        !           647:         or      bl,ajColorConv[eax]
        !           648:         shl     bl,1
        !           649:         or      bl,ajColorConv[edx]
        !           650:         lodsb                           ;Get two nibbles worth
        !           651:         mov     edx,eax
        !           652:         shr     eax,4
        !           653:         and     edx,00001111b
        !           654:         shl     bl,1
        !           655:         or      bl,ajColorConv[eax]
        !           656:         shl     bl,1
        !           657:         or      bl,ajColorConv[edx]
        !           658:         lodsb                           ;Get two nibbles worth
        !           659:         mov     edx,eax
        !           660:         shr     eax,4
        !           661:         and     edx,00001111b
        !           662:         shl     bl,1
        !           663:         or      bl,ajColorConv[eax]
        !           664:         shl     bl,1
        !           665:         or      bl,ajColorConv[edx]
        !           666:         mov     al,bl
        !           667:         stosb
        !           668:         dec     ecx
        !           669:         jnz     cvt_to_1bpp
        !           670: 
        !           671: 
        !           672: ; Copy to the destination.  This unfortunately may involve phase alignment
        !           673: 
        !           674: copy_to_dest:
        !           675:         movzx   ecx,cRightShift
        !           676:         jecxz   copy_aligned_to_dest
        !           677:         mov     edi,pjWork
        !           678:         mov     ebx,cjRightShift
        !           679: phase_align_it:
        !           680:         mov     ah,dl                   ;Get previous unused bits
        !           681:         mov     al,byte ptr [edi]
        !           682:         mov     dl,al
        !           683:         shr     eax,cl
        !           684:         stosb
        !           685:         dec     ebx
        !           686:         jnz     phase_align_it
        !           687: 
        !           688: copy_aligned_to_dest:
        !           689:         mov     esi,pjWork
        !           690:         add     esi,cjSkip
        !           691:         mov     edi,pjDst
        !           692: 
        !           693:         mov     dl,jLeftMask
        !           694:         or      dl,dl
        !           695:         jz      @F
        !           696:         lodsb
        !           697:         mov     ah,byte ptr [edi]
        !           698:         xor     ah,al
        !           699:         and     ah,dl
        !           700:         xor     al,ah
        !           701:         stosb
        !           702: @@:
        !           703:         mov     ecx,cCopy
        !           704:         rep     movsb
        !           705: 
        !           706:         mov     dl,jRightMask
        !           707:         or      dl,dl
        !           708:         jz      @F
        !           709:         lodsb
        !           710:         mov     ah,byte ptr [edi]
        !           711:         xor     ah,al
        !           712:         and     ah,dl
        !           713:         xor     al,ah
        !           714:         stosb
        !           715: @@:
        !           716: 
        !           717:         mov     eax,ulScanWidth
        !           718:         add     pjSrc,eax
        !           719:         mov     eax,lDelta
        !           720:         add     pjDst,eax
        !           721:         dec     cyScans
        !           722:         jnz     process_next_scan
        !           723: 
        !           724:         PLAIN_RET       ;we're done with this bank
        !           725: 
        !           726: xxxvConvertVGA2DIB endp
        !           727: 
        !           728:         end
        !           729: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.