summaryrefslogtreecommitdiff
path: root/apps/plugins/sdl/progs/quake/d_copy.S
diff options
context:
space:
mode:
Diffstat (limited to 'apps/plugins/sdl/progs/quake/d_copy.S')
-rw-r--r--apps/plugins/sdl/progs/quake/d_copy.S149
1 files changed, 149 insertions, 0 deletions
diff --git a/apps/plugins/sdl/progs/quake/d_copy.S b/apps/plugins/sdl/progs/quake/d_copy.S
new file mode 100644
index 0000000000..92e414a1bf
--- /dev/null
+++ b/apps/plugins/sdl/progs/quake/d_copy.S
@@ -0,0 +1,149 @@
1//
2// d_copy.s
3// x86 assembly-language screen copying code.
4//
5
6#include "asm_i386.h"
7#include "quakeasm.h"
8#include "asm_draw.h"
9
10 .data
11
12LCopyWidth: .long 0
13LBlockSrcStep: .long 0
14LBlockDestStep: .long 0
15LSrcDelta: .long 0
16LDestDelta: .long 0
17
18#define bufptr 4+16
19
20// copies 16 rows per plane at a pop; idea is that 16*512 = 8k, and since
21// no Mode X mode is wider than 360, all the data should fit in the cache for
22// the passes for the next 3 planes
23
24 .text
25
26.globl C(VGA_UpdatePlanarScreen)
27C(VGA_UpdatePlanarScreen):
28 pushl %ebp // preserve caller's stack frame
29 pushl %edi
30 pushl %esi // preserve register variables
31 pushl %ebx
32
33 movl C(VGA_bufferrowbytes),%eax
34 shll $1,%eax
35 movl %eax,LBlockSrcStep
36 movl C(VGA_rowbytes),%eax
37 shll $1,%eax
38 movl %eax,LBlockDestStep
39
40 movl $0x3C4,%edx
41 movb $2,%al
42 outb %al,%dx // point the SC to the Map Mask
43 incl %edx
44
45 movl bufptr(%esp),%esi
46 movl C(VGA_pagebase),%edi
47 movl C(VGA_height),%ebp
48 shrl $1,%ebp
49
50 movl C(VGA_width),%ecx
51 movl C(VGA_bufferrowbytes),%eax
52 subl %ecx,%eax
53 movl %eax,LSrcDelta
54 movl C(VGA_rowbytes),%eax
55 shll $2,%eax
56 subl %ecx,%eax
57 movl %eax,LDestDelta
58 shrl $4,%ecx
59 movl %ecx,LCopyWidth
60
61LRowLoop:
62 movb $1,%al
63
64LPlaneLoop:
65 outb %al,%dx
66 movb $2,%ah
67
68 pushl %esi
69 pushl %edi
70LRowSetLoop:
71 movl LCopyWidth,%ecx
72LColumnLoop:
73 movb 12(%esi),%bh
74 movb 8(%esi),%bl
75 shll $16,%ebx
76 movb 4(%esi),%bh
77 movb (%esi),%bl
78 movl %ebx,(%edi)
79 addl $16,%esi
80 addl $4,%edi
81 decl %ecx
82 jnz LColumnLoop
83
84 addl LDestDelta,%edi
85 addl LSrcDelta,%esi
86 decb %ah
87 jnz LRowSetLoop
88
89 popl %edi
90 popl %esi
91 incl %esi
92
93 shlb $1,%al
94 cmpb $16,%al
95 jnz LPlaneLoop
96
97 subl $4,%esi
98 addl LBlockSrcStep,%esi
99 addl LBlockDestStep,%edi
100 decl %ebp
101 jnz LRowLoop
102
103 popl %ebx // restore register variables
104 popl %esi
105 popl %edi
106 popl %ebp // restore the caller's stack frame
107
108 ret
109
110
111#define srcptr 4+16
112#define destptr 8+16
113#define width 12+16
114#define height 16+16
115#define srcrowbytes 20+16
116#define destrowbytes 24+16
117
118.globl C(VGA_UpdateLinearScreen)
119C(VGA_UpdateLinearScreen):
120 pushl %ebp // preserve caller's stack frame
121 pushl %edi
122 pushl %esi // preserve register variables
123 pushl %ebx
124
125 cld
126 movl srcptr(%esp),%esi
127 movl destptr(%esp),%edi
128 movl width(%esp),%ebx
129 movl srcrowbytes(%esp),%eax
130 subl %ebx,%eax
131 movl destrowbytes(%esp),%edx
132 subl %ebx,%edx
133 shrl $2,%ebx
134 movl height(%esp),%ebp
135LLRowLoop:
136 movl %ebx,%ecx
137 rep/movsl (%esi),(%edi)
138 addl %eax,%esi
139 addl %edx,%edi
140 decl %ebp
141 jnz LLRowLoop
142
143 popl %ebx // restore register variables
144 popl %esi
145 popl %edi
146 popl %ebp // restore the caller's stack frame
147
148 ret
149