home *** CD-ROM | disk | FTP | other *** search
/ Il CD di internet / CD.iso / SOURCE / D / SVGALIB / SVGALIB1.TAR / svgalib / gl / mem.S < prev    next >
Encoding:
Text File  |  1994-08-23  |  7.9 KB  |  482 lines

  1.     .file "mem.S"
  2.  
  3.  # This file contains unrolled memcpy functions.
  4.  
  5.  
  6.  # Prototype: memcpy4to3( void *dest, void *src, int n )
  7.  # Copies pixels from 4-byte-per-pixel screen to 3-byte-per-pixel screen,
  8.  # discarding the last byte of each pixel.
  9.  # Only uses 32-bit aligned word accesses.
  10.  # Instructions have been shuffled a bit for possible avoidance of
  11.  # pipeline hazards.
  12.  
  13. .text
  14.     .align 4
  15.  
  16. .globl _memcpy4to3
  17. _memcpy4to3:
  18.     pushl %ebp
  19.     movl %esp,%ebp
  20.     pushl %edi
  21.     pushl %esi
  22.     pushl %ebx
  23.     pushl %ecx
  24.     movl 8(%ebp),%edi    # destination address
  25.     movl 12(%ebp),%esi    # source address
  26.     movl 16(%ebp),%ecx    # number of pixels
  27.  
  28.     # Handle chunks of 8 pixels.
  29. 1:    cmpl $8,%ecx
  30.     jl 2f
  31.  
  32.     movl (%esi),%eax    # pixel 0
  33.     movl 4(%esi),%ebx    # pixel 1
  34.     shll $8,%eax        # BGR0 in 8-31
  35.     shrd $8,%ebx,%eax    # BGR0 in 0-23, B1 in 24-31
  36.     movl %eax,(%edi)    # write word
  37.     shll $8,%ebx        # GR1 in 16-31
  38.     movl 8(%esi),%eax    # pixel 2
  39.     shrd $16,%eax,%ebx    # GR1 in 0-15, BG2 in 16-31
  40.     movl %ebx,4(%edi)    # write word
  41.     shll $8,%eax        # move R2 into 24-31
  42.     movl 12(%esi),%ebx    # pixel 3
  43.     shrd $24,%ebx,%eax    # R2 in 0-7, BGR3 in 8-31
  44.     movl %eax,8(%edi)    # write word
  45.  
  46.     movl 16(%esi),%eax    # pixel 4
  47.     shll $8,%eax        # BGR4 in 8-31
  48.     movl 20(%esi),%ebx    # pixel 5
  49.     shrd $8,%ebx,%eax    # BGR4 in 0-23, B5 in 24-31
  50.     movl %eax,12(%edi)    # write word
  51.     shll $8,%ebx        # GR5 in 16-31
  52.     movl 24(%esi),%eax    # pixel 6
  53.     shrd $16,%eax,%ebx    # GR5 in 0-15, BG6 in 16-31
  54.     movl %ebx,16(%edi)    # write word
  55.     subl $8,%ecx        # blended end-of-loop instruction
  56.     shll $8,%eax        # move R6 into 24-31
  57.     movl 28(%esi),%ebx    # pixel 7
  58.     shrd $24,%ebx,%eax    # R6 in 0-7, BGR7 in 8-31
  59.     addl $32,%esi        # blended end-of-loop instruction
  60.     movl %eax,20(%edi)    # write word
  61.  
  62.     addl $24,%edi
  63.     jmp 1b
  64.  
  65. 2:    # Do the remaining pixels.
  66.  
  67.     andl %ecx,%ecx
  68.     jz 4f            # none left
  69.  
  70. 3:    movl (%esi),%eax
  71.     movw %eax,(%edi)
  72.     shrl $16,%eax
  73.     movb %al,2(%edi)
  74.     addl $4,%esi
  75.     addl $3,%edi
  76.     decl %ecx
  77.     jnz 3b
  78.  
  79. 4:
  80.     popl %ecx
  81.     popl %ebx
  82.     popl %esi
  83.     popl %edi
  84.     popl %ebp
  85.     ret
  86.  
  87.  # Prototype: memcpy32shift8( void *dest, void *src, int n )
  88.  # Copies pixels from 4-byte-per-pixel screen organized as BGR0 to
  89.  # 0BGR 4-byte-per-pixel screen.
  90.  # Used by copyscreen for ATI mach32 32-bit truecolor modes.
  91.  
  92. .text
  93.     .align 4
  94.  
  95. .globl _memcpy32shift8
  96. _memcpy32shift8:
  97.     pushl %ebp
  98.     movl %esp,%ebp
  99.     pushl %edi
  100.     pushl %esi
  101.     pushl %ecx
  102.     popl %ebx
  103.     movl 8(%ebp),%edi    # destination address
  104.     movl 12(%ebp),%esi    # source address
  105.     movl 16(%ebp),%ecx    # number of pixels
  106.  
  107.     # Handle chunks of 8 pixels.
  108. 1:    cmpl $8,%ecx
  109.     jl 2f
  110.  
  111.     movl (%esi),%eax
  112.     shll $8,%eax
  113.     movl %eax,(%edi)
  114.     movl 4(%esi),%edx
  115.     shll $8,%edx
  116.     movl %edx,4(%edi)
  117.     movl 8(%esi),%eax
  118.     shll $8,%eax
  119.     movl %eax,8(%edi)
  120.     movl 12(%esi),%edx
  121.     shll $8,%edx
  122.     movl %edx,12(%edi)
  123.     movl 16(%esi),%eax
  124.     shll $8,%eax
  125.     movl %eax,16(%edi)
  126.     movl 20(%esi),%edx
  127.     shll $8,%edx
  128.     movl %edx,20(%edi)
  129.     movl 24(%esi),%eax
  130.     subl $8,%ecx
  131.     shll $8,%eax
  132.     movl %eax,24(%edi)
  133.     movl 28(%esi),%edx
  134.     addl $32,%esi
  135.     shll $8,%edx
  136.     movl %edx,28(%edi)
  137.     addl $32,%edi
  138.     jmp 1b
  139.  
  140. 2:    andl %ecx,%ecx
  141.     jz 4f
  142.  
  143. 3:    movl (%esi),%eax
  144.     shll $8,%eax
  145.     movl %eax,(%edi)
  146.     addl $4,%esi
  147.     addl $4,%edi
  148.     decl %ecx
  149.     jnz 3b
  150.  
  151. 4:    
  152.     popl %ebx
  153.     popl %ecx
  154.     popl %esi
  155.     popl %edi
  156.     popl %ebp
  157.     ret
  158.  
  159.  
  160. # Optimized memcpy.
  161. # Performance on par with inlined 32-bit aligned rep movsl on slow
  162. # motherboard.
  163. # Hypothesized to be fast on motherboards that handle writes efficiently
  164. # and suffer with slow rep movsl microcode in 486/Pentium.
  165. # (esp. Cyrix 486DX WB, Headland HTK 486 chipset, Pentium).
  166.  
  167. # Arguments passed in registers:
  168. # destination address in %ebx (original %ebx has been saved)
  169. # source address in %edx
  170. # count in %ecx
  171.  
  172. #define MOVEBYTE(n) movb n(%edx),%al; movb %al,n(%ebx)
  173.  
  174. #define MOVESHORT(n) movw n(%edx),%ax; movw %ax,n(%ebx)
  175.  
  176. #define MOVEWORD(n) movl n(%edx),%eax; movl %eax,n(%ebx)
  177.  
  178.     .align 4
  179. .globl __memcpy_jumptable
  180. __memcpy_jumptable:
  181.     .long copy0
  182.     .long copy1, copy2, copy3, copy4
  183.     .long copy5, copy6, copy7, copy8
  184.     .long copy9, copy10, copy11, copy12
  185.     .long copy13, copy14, copy15, copy16
  186.     .long copy17, copy18, copy19, copy20
  187.     .long copy21, copy22, copy23, copy24
  188.     .long copy25, copy26, copy27, copy28
  189.     .long copy29, copy30, copy31, copy32
  190.  
  191. jumptable2:
  192.     .long align0, align1, align2, align3
  193.  
  194.     .align 4
  195. .globl __memcpyasm_regargs
  196. __memcpyasm_regargs:
  197.  
  198.     # This is only valid if nu_bytes >= 3.
  199.  
  200.     # Align destination to 32-bit boundary
  201.     movl %ebx,%eax
  202.     andl $3,%eax
  203.     jmp *jumptable2(,%eax,4)
  204.  
  205. align1:    MOVESHORT(0)
  206.     MOVEBYTE(2)
  207.     addl $3,%edx
  208.     addl $3,%ebx
  209.     subl $3,%ecx
  210.     jmp copyaligned
  211.  
  212. align3:    MOVEBYTE(0)
  213.     incl %edx
  214.     incl %ebx
  215.     decl %ecx
  216.     jmp copyaligned
  217.  
  218. align2:    MOVESHORT(0)
  219.     addl $2,%edx
  220.     addl $2,%ebx
  221.     subl $2,%ecx
  222. align0:
  223.  
  224. copyaligned:
  225.     cmpl $32,%ecx
  226.     ja copyunrolled
  227.     # <= 32 bytes.
  228.     # Copy remaining bytes (0-32).
  229.     jmp *__memcpy_jumptable(,%ecx,4)
  230.     .align 4,0x90
  231.  
  232. # memcpyasm_regargs_aligned is only called if nu_bytes > 32.
  233. .globl __memcpyasm_regargs_aligned
  234. __memcpyasm_regargs_aligned:
  235.  
  236. copyunrolled:    
  237.     # Copy chunks of 32 bytes.
  238.     # End-of-loop increment instructions blended in.
  239.     addl $32,%ebx            #P ok
  240.     movl (%edx),%eax
  241.     movl %eax,(0-32)(%ebx)        #P ok
  242.     movl 4(%edx),%eax
  243.     movl %eax,(4-32)(%ebx)        #P ok
  244.     movl 8(%edx),%eax
  245.     movl %eax,(8-32)(%ebx)        #P ok
  246.     movl 12(%edx),%eax
  247.     movl %eax,(12-32)(%ebx)        #P ok
  248.     movl 16(%edx),%eax
  249.     addl $32,%edx            #P ok
  250.     movl %eax,(16-32)(%ebx)
  251.     subl $32,%ecx            #P ok
  252.     movl (20-32)(%edx),%eax
  253.     movl %eax,(20-32)(%ebx)        #P ok
  254.     movl (24-32)(%edx),%eax
  255.     movl %eax,(24-32)(%ebx)        #P ok
  256.     movl (28-32)(%edx),%eax
  257.     movl %eax,(28-32)(%ebx)        #P ok
  258.     cmpl $32,%ecx
  259.     jge copyunrolled        #P fail
  260.     # Copy remaining bytes (less than 32).
  261.     jmp *__memcpy_jumptable(,%ecx,4)
  262.  
  263. #define END ret
  264.  
  265. copy0:    END
  266.  
  267. copy1:    MOVEBYTE(0)
  268.     END
  269.  
  270. copy2:    MOVESHORT(0)
  271.     END
  272.  
  273. copy3:    MOVESHORT(0)
  274.     MOVEBYTE(2)
  275.     END
  276.  
  277. copy4:    MOVEWORD(0)
  278.     END
  279.  
  280. copy5:    MOVEWORD(0)
  281.     MOVEBYTE(4)
  282.     END
  283.  
  284. copy6:    MOVEWORD(0)
  285.     MOVESHORT(4)
  286.     END
  287.  
  288. copy7:    MOVEWORD(0)
  289.     MOVESHORT(4)
  290.     MOVEBYTE(6)
  291.     END
  292.  
  293. copy8:    MOVEWORD(0)
  294.     MOVEWORD(4)
  295.     END
  296.  
  297. copy9:    MOVEWORD(0)
  298.     MOVEWORD(4)
  299.     MOVEBYTE(8)
  300.     END
  301.  
  302. copy10:    MOVEWORD(0)
  303.     MOVEWORD(4)
  304.     MOVESHORT(8)
  305.     END
  306.  
  307. copy11:    MOVEWORD(0)
  308.     MOVEWORD(4)
  309.     MOVESHORT(8)
  310.     MOVEBYTE(10)
  311.     END
  312.  
  313. copy12:    MOVEWORD(0)
  314.     MOVEWORD(4)
  315.     MOVEWORD(8)
  316.     END
  317.  
  318. copy13:    MOVEWORD(0)
  319.     MOVEWORD(4)
  320.     MOVEWORD(8)
  321.     MOVEBYTE(12)
  322.     END
  323.  
  324. copy14:    MOVEWORD(0)
  325.     MOVEWORD(4)
  326.     MOVEWORD(8)
  327.     MOVESHORT(12)
  328.     END
  329.  
  330. copy15:    MOVEWORD(0)
  331.     MOVEWORD(4)
  332.     MOVEWORD(8)
  333.     MOVESHORT(12)
  334.     MOVEBYTE(14)
  335.     END
  336.  
  337. copy16:    MOVEWORD(0)
  338.     MOVEWORD(4)
  339.     MOVEWORD(8)
  340.     MOVEWORD(12)
  341.     END
  342.  
  343. copy17:    MOVEWORD(0)
  344.     MOVEWORD(4)
  345.     MOVEWORD(8)
  346.     MOVEWORD(12)
  347.     MOVEBYTE(16)
  348.     END
  349.  
  350. copy18:    MOVEWORD(0)
  351.     MOVEWORD(4)
  352.     MOVEWORD(8)
  353.     MOVEWORD(12)
  354.     MOVESHORT(16)
  355.     END
  356.  
  357. copy19:    MOVEWORD(0)
  358.     MOVEWORD(4)
  359.     MOVEWORD(8)
  360.     MOVEWORD(12)
  361.     MOVESHORT(16)
  362.     MOVEBYTE(18)
  363.     END
  364.  
  365. copy20:    MOVEWORD(0)
  366.     MOVEWORD(4)
  367.     MOVEWORD(8)
  368.     MOVEWORD(12)
  369.     MOVEWORD(16)
  370.     END
  371.  
  372. copy21:    MOVEWORD(0)
  373.     MOVEWORD(4)
  374.     MOVEWORD(8)
  375.     MOVEWORD(12)
  376.     MOVEWORD(16)
  377.     MOVEBYTE(20)
  378.     END
  379.  
  380. copy22:    MOVEWORD(0)
  381.     MOVEWORD(4)
  382.     MOVEWORD(8)
  383.     MOVEWORD(12)
  384.     MOVEWORD(16)
  385.     MOVESHORT(20)
  386.     END
  387.  
  388. copy23:    MOVEWORD(0)
  389.     MOVEWORD(4)
  390.     MOVEWORD(8)
  391.     MOVEWORD(12)
  392.     MOVEWORD(16)
  393.     MOVESHORT(20)
  394.     MOVEBYTE(22)
  395.     END
  396.  
  397. copy24:    MOVEWORD(0)
  398.     MOVEWORD(4)
  399.     MOVEWORD(8)
  400.     MOVEWORD(12)
  401.     MOVEWORD(16)
  402.     MOVEWORD(20)
  403.     END
  404.  
  405. copy25:    MOVEWORD(0)
  406.     MOVEWORD(4)
  407.     MOVEWORD(8)
  408.     MOVEWORD(12)
  409.     MOVEWORD(16)
  410.     MOVEWORD(20)
  411.     MOVEBYTE(24)
  412.     END
  413.  
  414. copy26:    MOVEWORD(0)
  415.     MOVEWORD(4)
  416.     MOVEWORD(8)
  417.     MOVEWORD(12)
  418.     MOVEWORD(16)
  419.     MOVEWORD(20)
  420.     MOVESHORT(24)
  421.     END
  422.  
  423. copy27:    MOVEWORD(0)
  424.     MOVEWORD(4)
  425.     MOVEWORD(8)
  426.     MOVEWORD(12)
  427.     MOVEWORD(16)
  428.     MOVEWORD(20)
  429.     MOVESHORT(24)
  430.     MOVEBYTE(26)
  431.     END
  432.  
  433. copy28:    MOVEWORD(0)
  434.     MOVEWORD(4)
  435.     MOVEWORD(8)
  436.     MOVEWORD(12)
  437.     MOVEWORD(16)
  438.     MOVEWORD(20)
  439.     MOVEWORD(24)
  440.     END
  441.  
  442. copy29:    MOVEWORD(0)
  443.     MOVEWORD(4)
  444.     MOVEWORD(8)
  445.     MOVEWORD(12)
  446.     MOVEWORD(16)
  447.     MOVEWORD(20)
  448.     MOVEWORD(24)
  449.     MOVEBYTE(28)
  450.     END
  451.  
  452. copy30:    MOVEWORD(0)
  453.     MOVEWORD(4)
  454.     MOVEWORD(8)
  455.     MOVEWORD(12)
  456.     MOVEWORD(16)
  457.     MOVEWORD(20)
  458.     MOVEWORD(24)
  459.     MOVESHORT(28)
  460.     END
  461.  
  462. copy31:    MOVEWORD(0)
  463.     MOVEWORD(4)
  464.     MOVEWORD(8)
  465.     MOVEWORD(12)
  466.     MOVEWORD(16)
  467.     MOVEWORD(20)
  468.     MOVEWORD(24)
  469.     MOVESHORT(28)
  470.     MOVEBYTE(30)
  471.     END
  472.  
  473. copy32:    MOVEWORD(0)
  474.     MOVEWORD(4)
  475.     MOVEWORD(8)
  476.     MOVEWORD(12)
  477.     MOVEWORD(16)
  478.     MOVEWORD(20)
  479.     MOVEWORD(24)
  480.     MOVEWORD(28)
  481.     END
  482.