Subversion Repositories Kolibri OS

Rev

Rev 7277 | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 7277 Rev 7754
1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
; A firework demo
2
; A firework demo
3
; Programmed by Yaniv LEVIATHAN
3
; Programmed by Yaniv LEVIATHAN
4
; http://yaniv.leviathanonline.com
4
; http://yaniv.leviathanonline.com
5
; Converted to DexOS, By Dex
5
; Converted to DexOS, By Dex
6
; Converted to KolibriOS, By Asper
6
; Converted to KolibriOS, By Asper
7
; Optimized for KolibriOS, By Diamond
7
; Optimized for KolibriOS, By Diamond
8
; Assemble with
8
; Assemble with
9
; c:fasm firework.asm firework.kex
9
; c:fasm firework.asm firework.kex
10
; NOTE: Needs MMX & SSE,
10
; NOTE: Needs MMX & SSE,
11
; optionally AVX, AVX2, AVX512
11
; optionally AVX, AVX2, AVX512
12
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
12
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
13
use32
13
use32
14
        org     0x0
14
        org     0x0
15
 
15
 
16
        db      'MENUET01'      ; 8 byte id
16
        db      'MENUET01'      ; 8 byte id
17
        dd      0x01            ; version
17
        dd      0x01            ; version
18
        dd      STARTAPP        ; program start
18
        dd      STARTAPP        ; program start
19
        dd      I_END           ; program image size
19
        dd      I_END           ; program image size
20
        dd      E_END           ; required amount of memory
20
        dd      E_END           ; required amount of memory
21
        dd      stacktop        ; reserved=no extended header
21
        dd      stacktop        ; reserved=no extended header
22
        dd      0, 0
22
        dd      0, 0
23
 
23
 
24
include '../../../macros.inc'
24
include '../../../macros.inc'
25
SCREEN_WIDTH   = 320
25
SCREEN_WIDTH   = 320
26
SCREEN_HEIGHT  = 200
26
SCREEN_HEIGHT  = 200
27
SIMD equ SSE
27
SIMD equ SSE
28
SIMD_BYTES = 8
28
SIMD_BYTES = 8
29
; SSE    8
29
; SSE    8
30
; AVX    16
30
; AVX    16
31
; AVX2   32
31
; AVX2   32
32
; AVX512 64
32
; AVX512 64
33
assert SCREEN_WIDTH mod SIMD_BYTES = 0
33
assert SCREEN_WIDTH mod SIMD_BYTES = 0
34
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
34
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
35
; Global defines
35
; Global defines
36
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
36
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
37
 
37
 
38
NUM_PARTS      = 150
38
NUM_PARTS      = 150
39
X_OFFSET       = 0
39
X_OFFSET       = 0
40
Y_OFFSET       = 4
40
Y_OFFSET       = 4
41
X_SPEED_OFFSET = 8
41
X_SPEED_OFFSET = 8
42
Y_SPEED_OFFSET = 12
42
Y_SPEED_OFFSET = 12
43
COLOR_OFFSET   = 16
43
COLOR_OFFSET   = 16
44
PART_SIZE      = 20
44
PART_SIZE      = 20
45
 
45
 
46
macro shade
46
macro shade
47
{
47
{
48
local .lop
48
local .lop
49
if SIMD eq SSE
49
if SIMD eq SSE
50
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
50
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
51
        mov     edi, buffer
51
        mov     edi, buffer
52
        movq    mm1, qword [sub_mask]
52
        movq    mm1, qword [sub_mask]
53
  .lop:
53
  .lop:
54
        movq    mm0, [edi]
54
        movq    mm0, [edi]
55
        psubusb mm0, mm1
55
        psubusb mm0, mm1
56
        movq    [edi], mm0
56
        movq    [edi], mm0
57
        add     edi, SIMD_BYTES
57
        add     edi, SIMD_BYTES
58
        loop    .lop
58
        loop    .lop
59
else if SIMD eq AVX
59
else if SIMD eq AVX
60
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
60
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
61
        mov     edi, buffer
61
        mov     edi, buffer
62
        vmovdqa xmm1, xword [sub_mask]
62
        vmovdqa xmm1, xword [sub_mask]
63
  .lop:
63
  .lop:
64
        vmovdqa xmm0, [edi]
64
        vmovdqa xmm0, [edi]
65
        vpsubusb xmm0, xmm0, xmm1
65
        vpsubusb xmm0, xmm0, xmm1
66
        vmovdqa [edi], xmm0
66
        vmovdqa [edi], xmm0
67
        add     edi, SIMD_BYTES
67
        add     edi, SIMD_BYTES
68
        loop    .lop
68
        loop    .lop
69
else if SIMD eq AVX2
69
else if SIMD eq AVX2
70
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
70
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
71
        mov     edi, buffer
71
        mov     edi, buffer
72
        vmovdqa ymm1, yword [sub_mask]
72
        vmovdqa ymm1, yword [sub_mask]
73
  .lop:
73
  .lop:
74
        vmovdqa ymm0, [edi]
74
        vmovdqa ymm0, [edi]
75
        vpsubusb ymm0, ymm0, ymm1
75
        vpsubusb ymm0, ymm0, ymm1
76
        vmovdqa [edi], ymm0
76
        vmovdqa [edi], ymm0
77
        add     edi, SIMD_BYTES
77
        add     edi, SIMD_BYTES
78
        loop    .lop
78
        loop    .lop
79
else if SIMD eq AVX512
79
else if SIMD eq AVX512
80
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
80
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / SIMD_BYTES
81
        mov     edi, buffer
81
        mov     edi, buffer
82
        vmovdqa64 zmm1, zword [sub_mask]
82
        vmovdqa64 zmm1, zword [sub_mask]
83
  .lop:
83
  .lop:
84
        vmovdqa64 zmm0, [edi]
84
        vmovdqa64 zmm0, [edi]
85
        vpsubusb zmm0, zmm0, zmm1
85
        vpsubusb zmm0, zmm0, zmm1
86
        vmovdqa64 [edi], zmm0
86
        vmovdqa64 [edi], zmm0
87
        add     edi, SIMD_BYTES
87
        add     edi, SIMD_BYTES
88
        loop    .lop
88
        loop    .lop
89
end if
89
end if
90
}
90
}
91
 
91
 
92
macro blur_prepare
92
macro blur_prepare
93
{
93
{
94
        mov     ecx, (SCREEN_WIDTH * SCREEN_HEIGHT - SCREEN_WIDTH * 2 - SIMD_BYTES*2) / SIMD_BYTES
94
        mov     ecx, (SCREEN_WIDTH * SCREEN_HEIGHT - SCREEN_WIDTH * 2 - SIMD_BYTES*2) / SIMD_BYTES
95
        mov     edi, buffer + SCREEN_WIDTH + SIMD_BYTES
95
        mov     edi, buffer + SCREEN_WIDTH + SIMD_BYTES
96
}
96
}
97
 
97
 
98
macro blur
98
macro blur
99
{
99
{
100
local .lop
100
local .lop
101
if SIMD eq SSE
101
if SIMD eq SSE
102
.lop:
102
.lop:
103
        movq    mm0, [edi]
103
        movq    mm0, [edi]
104
        movq    mm1, [edi + 1]
104
        movq    mm1, [edi + 1]
105
        movq    mm2, [edi - 1]
105
        movq    mm2, [edi - 1]
106
        movq    mm3, mm0
106
        movq    mm3, mm0
107
        movq    mm4, [edi - SCREEN_WIDTH]
107
        movq    mm4, [edi - SCREEN_WIDTH]
108
        movq    mm5, [edi + SCREEN_WIDTH]
108
        movq    mm5, [edi + SCREEN_WIDTH]
109
 
109
 
110
        pavgb   mm0, mm1 ; mm0 = avg(cur,cur+1)
110
        pavgb   mm0, mm1 ; mm0 = avg(cur,cur+1)
111
        pavgb   mm3, mm2 ; mm3 = avg(cur,cur-1)
111
        pavgb   mm3, mm2 ; mm3 = avg(cur,cur-1)
112
        pavgb   mm4, mm5 ; mm4 = avg(cur+width,cur-width)
112
        pavgb   mm4, mm5 ; mm4 = avg(cur+width,cur-width)
113
        pavgb   mm3, mm4 ; mm3 = avg(avg(cur,cur-1),avg(cur+width,cur-width))
113
        pavgb   mm3, mm4 ; mm3 = avg(avg(cur,cur-1),avg(cur+width,cur-width))
114
        pavgb   mm0, mm3 ; mm0 = avg(avg(cur,cur+1),
114
        pavgb   mm0, mm3 ; mm0 = avg(avg(cur,cur+1),
115
 
115
 
116
        movq    [edi], mm0
116
        movq    [edi], mm0
117
        add     edi, SIMD_BYTES
117
        add     edi, SIMD_BYTES
118
        loop    .lop
118
        loop    .lop
119
else if SIMD eq AVX
119
else if SIMD eq AVX
120
.lop:
120
.lop:
121
        vmovdqa xmm0, [edi]
121
        vmovdqa xmm0, [edi]
122
        vmovdqa xmm1, xmm0
122
        vmovdqa xmm1, xmm0
123
        vmovdqa xmm2, [edi - SCREEN_WIDTH]
123
        vmovdqa xmm2, [edi - SCREEN_WIDTH]
124
 
124
 
125
        vpavgb  xmm0, xmm0, [edi + 1]
125
        vpavgb  xmm0, xmm0, [edi + 1]
126
        vpavgb  xmm1, xmm1, [edi - 1]
126
        vpavgb  xmm1, xmm1, [edi - 1]
127
        vpavgb  xmm2, xmm2, [edi + SCREEN_WIDTH]
127
        vpavgb  xmm2, xmm2, [edi + SCREEN_WIDTH]
128
        vpavgb  xmm1, xmm1, xmm2
128
        vpavgb  xmm1, xmm1, xmm2
129
        vpavgb  xmm0, xmm0, xmm1
129
        vpavgb  xmm0, xmm0, xmm1
130
 
130
 
131
        vmovdqa [edi], xmm0
131
        vmovdqa [edi], xmm0
132
        add     edi, SIMD_BYTES
132
        add     edi, SIMD_BYTES
133
        loop    .lop
133
        loop    .lop
134
else if SIMD eq AVX2
134
else if SIMD eq AVX2
135
.lop:
135
.lop:
136
        vmovdqa ymm0, [edi]
136
        vmovdqa ymm0, [edi]
137
        vmovdqa ymm1, ymm0
137
        vmovdqa ymm1, ymm0
138
        vmovdqa ymm2, [edi - SCREEN_WIDTH]
138
        vmovdqa ymm2, [edi - SCREEN_WIDTH]
139
 
139
 
140
        vpavgb  ymm0, ymm0, [edi + 1]
140
        vpavgb  ymm0, ymm0, [edi + 1]
141
        vpavgb  ymm1, ymm1, [edi - 1]
141
        vpavgb  ymm1, ymm1, [edi - 1]
142
        vpavgb  ymm2, ymm2, [edi + SCREEN_WIDTH]
142
        vpavgb  ymm2, ymm2, [edi + SCREEN_WIDTH]
143
        vpavgb  ymm1, ymm1, ymm2
143
        vpavgb  ymm1, ymm1, ymm2
144
        vpavgb  ymm0, ymm0, ymm1
144
        vpavgb  ymm0, ymm0, ymm1
145
 
145
 
146
        vmovdqa [edi], ymm0
146
        vmovdqa [edi], ymm0
147
        add     edi, SIMD_BYTES
147
        add     edi, SIMD_BYTES
148
        loop    .lop
148
        loop    .lop
149
else if SIMD eq AVX512
149
else if SIMD eq AVX512
150
.lop:
150
.lop:
151
        vmovdqa64 zmm0, [edi]
151
        vmovdqa64 zmm0, [edi]
152
        vmovdqa64 zmm1, zmm0
152
        vmovdqa64 zmm1, zmm0
153
        vmovdqa64 zmm2, [edi - SCREEN_WIDTH]
153
        vmovdqa64 zmm2, [edi - SCREEN_WIDTH]
154
 
154
 
155
        vpavgb  zmm0, zmm0, [edi + 1]
155
        vpavgb  zmm0, zmm0, [edi + 1]
156
        vpavgb  zmm1, zmm1, [edi - 1]
156
        vpavgb  zmm1, zmm1, [edi - 1]
157
        vpavgb  zmm2, zmm2, [edi + SCREEN_WIDTH]
157
        vpavgb  zmm2, zmm2, [edi + SCREEN_WIDTH]
158
        vpavgb  zmm1, zmm1, zmm2
158
        vpavgb  zmm1, zmm1, zmm2
159
        vpavgb  zmm0, zmm0, zmm1
159
        vpavgb  zmm0, zmm0, zmm1
160
 
160
 
161
        vmovdqa64 [edi], zmm0
161
        vmovdqa64 [edi], zmm0
162
        add     edi, SIMD_BYTES
162
        add     edi, SIMD_BYTES
163
        loop    .lop
163
        loop    .lop
164
end if
164
end if
165
}
165
}
166
 
166
 
167
macro blur_right
167
macro blur_right
168
{
168
{
169
local .lop
169
local .lop
170
if SIMD eq SSE
170
if SIMD eq SSE
171
  .lop:
171
  .lop:
172
        movq    mm0, [edi]
172
        movq    mm0, [edi]
173
        movq    mm1, [edi + 1]
173
        movq    mm1, [edi + 1]
174
        movq    mm2, [edi + SCREEN_WIDTH]
174
        movq    mm2, [edi + SCREEN_WIDTH]
175
        movq    mm3, [edi + SCREEN_WIDTH + 1]
175
        movq    mm3, [edi + SCREEN_WIDTH + 1]
176
        pavgb   mm0, mm1
176
        pavgb   mm0, mm1
177
        pavgb   mm3, mm2
177
        pavgb   mm3, mm2
178
        pavgb   mm0, mm3
178
        pavgb   mm0, mm3
179
        movq    [edi], mm0
179
        movq    [edi], mm0
180
        add     edi, SIMD_BYTES
180
        add     edi, SIMD_BYTES
181
        loop    .lop
181
        loop    .lop
182
else if SIMD eq AVX
182
else if SIMD eq AVX
183
  .lop:
183
  .lop:
184
        vmovdqa xmm0, [edi]
184
        vmovdqa xmm0, [edi]
185
        vmovdqu xmm1, [edi + SCREEN_WIDTH + 1]
185
        vmovdqu xmm1, [edi + SCREEN_WIDTH + 1]
186
        vpavgb  xmm2, xmm0, [edi + 1]
186
        vpavgb  xmm2, xmm0, [edi + 1]
187
        vpavgb  xmm3, xmm1, [edi + SCREEN_WIDTH]
187
        vpavgb  xmm3, xmm1, [edi + SCREEN_WIDTH]
188
        vpavgb  xmm4, xmm2, xmm3
188
        vpavgb  xmm4, xmm2, xmm3
189
        vmovdqa [edi], xmm4
189
        vmovdqa [edi], xmm4
190
        add     edi, SIMD_BYTES
190
        add     edi, SIMD_BYTES
191
        loop    .lop
191
        loop    .lop
192
else if SIMD eq AVX2
192
else if SIMD eq AVX2
193
  .lop:
193
  .lop:
194
        vmovdqa ymm0, [edi]
194
        vmovdqa ymm0, [edi]
195
        vmovdqu ymm1, [edi + SCREEN_WIDTH + 1]
195
        vmovdqu ymm1, [edi + SCREEN_WIDTH + 1]
196
        vpavgb  ymm2, ymm0, [edi + 1]
196
        vpavgb  ymm2, ymm0, [edi + 1]
197
        vpavgb  ymm3, ymm1, [edi + SCREEN_WIDTH]
197
        vpavgb  ymm3, ymm1, [edi + SCREEN_WIDTH]
198
        vpavgb  ymm4, ymm2, ymm3
198
        vpavgb  ymm4, ymm2, ymm3
199
        vmovdqa [edi], ymm4
199
        vmovdqa [edi], ymm4
200
        add     edi, SIMD_BYTES
200
        add     edi, SIMD_BYTES
201
        loop    .lop
201
        loop    .lop
202
else if SIMD eq AVX512
202
else if SIMD eq AVX512
203
  .lop:
203
  .lop:
204
        vmovdqa64 zmm0, [edi]
204
        vmovdqa64 zmm0, [edi]
205
        vmovdqu64 zmm1, [edi + SCREEN_WIDTH + 1]
205
        vmovdqu64 zmm1, [edi + SCREEN_WIDTH + 1]
206
        vpavgb  zmm2, zmm0, [edi + 1]
206
        vpavgb  zmm2, zmm0, [edi + 1]
207
        vpavgb  zmm3, zmm1, [edi + SCREEN_WIDTH]
207
        vpavgb  zmm3, zmm1, [edi + SCREEN_WIDTH]
208
        vpavgb  zmm4, zmm2, zmm3
208
        vpavgb  zmm4, zmm2, zmm3
209
        vmovdqa64 [edi], zmm4
209
        vmovdqa64 [edi], zmm4
210
        add     edi, SIMD_BYTES
210
        add     edi, SIMD_BYTES
211
        loop    .lop
211
        loop    .lop
212
end if 
212
end if 
213
}
213
}
214
 
214
 
215
STARTAPP:
215
STARTAPP:
216
 
216
 
217
init_palette:
217
init_palette:
218
        mov     edi, pal
218
        mov     edi, pal
219
        xor     eax, eax
219
        xor     eax, eax
220
red_loop:
220
red_loop:
221
        stosd
221
        stosd
222
        stosd
222
        stosd
223
        add     eax, 0x040000
223
        add     eax, 0x040000
224
        and     eax, 0xFFFFFF
224
        and     eax, 0xFFFFFF
225
        jnz     red_loop
225
        jnz     red_loop
226
 
226
 
227
        mov     eax, 63*4 SHL 16
227
        mov     eax, 63*4 SHL 16
228
@@:
228
@@:
229
        stosd
229
        stosd
230
        stosd
230
        stosd
231
        add     ax, 0x0404
231
        add     ax, 0x0404
232
        jnc     @b
232
        jnc     @b
233
 
233
 
234
;zero_buffer:
234
;zero_buffer:
235
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / 4
235
        mov     ecx, SCREEN_WIDTH * SCREEN_HEIGHT / 4
236
;       mov     edi, buffer
236
;       mov     edi, buffer
237
        xor     eax, eax
237
        xor     eax, eax
238
        rep     stosd
238
        rep     stosd
239
 
239
 
240
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
240
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
241
; Main Functions
241
; Main Functions
242
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
242
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
243
virtual at esp
243
virtual at esp
244
        global_x        dd ?
244
        global_x        dd ?
245
        global_y        dd ?
245
        global_y        dd ?
246
        seed            dd ?
246
        seed            dd ?
247
end virtual
247
end virtual
248
 
248
 
249
        rdtsc
249
        rdtsc
250
        push    eax      ; seed
250
        push    eax      ; seed
251
        push    100 * 64 ; global_y
251
        push    100 * 64 ; global_y
252
        push    160 * 64 ; global_x
252
        push    160 * 64 ; global_x
253
 
253
 
254
   jmp MAIN
254
   jmp MAIN
255
 
255
 
256
 
256
 
257
red:
257
red:
258
        mcall   9, proc_info, -1
258
        mcall   9, proc_info, -1
259
x = 100
259
x = 100
260
y = 70
260
y = 70
261
xsize = SCREEN_WIDTH+9
261
xsize = SCREEN_WIDTH+9
262
ysize = SCREEN_HEIGHT+4
262
ysize = SCREEN_HEIGHT+4
263
areacolor = 0x54224466
263
areacolor = 0x54224466
264
        mov     eax, 12                 ; function 12:tell os about windowdraw
264
        mov     eax, 12                 ; function 12:tell os about windowdraw
265
        mov     ebx, 1                  ; 1, start of draw
265
        mov     ebx, 1                  ; 1, start of draw
266
        int     0x40
266
        int     0x40
267
        mov     eax, 48
267
        mov     eax, 48
268
        mov     ebx, 4
268
        mov     ebx, 4
269
        int     0x40
269
        int     0x40
270
        lea     ecx, [(y SHL 16) + ysize + eax]
270
        lea     ecx, [(y SHL 16) + ysize + eax]
271
        xor     eax, eax                ; function 0 : define and draw window
271
        xor     eax, eax                ; function 0 : define and draw window
272
        mov     ebx, (x SHL 16) + xsize ; [x start] *65536 + [x size]
272
        mov     ebx, (x SHL 16) + xsize ; [x start] *65536 + [x size]
273
        mov     edx, areacolor          ; color of work area RRGGBB
273
        mov     edx, areacolor          ; color of work area RRGGBB
274
        mov     edi, window_title
274
        mov     edi, window_title
275
        int     0x40
275
        int     0x40
276
        mov     eax, 12                 ; end of redraw
276
        mov     eax, 12                 ; end of redraw
277
        mov     ebx, 2
277
        mov     ebx, 2
278
        int     0x40
278
        int     0x40
279
 
279
 
280
MAIN:
280
MAIN:
281
        test    [proc_info.wnd_state], 0x04
281
        test    [proc_info.wnd_state], 0x04
282
        jnz     still
282
        jnz     still
283
        mov     ecx, NUM_PARTS
283
        mov     ecx, NUM_PARTS
284
        mov     ebp, particles
284
        mov     ebp, particles
285
  .advance_particles:
285
  .advance_particles:
286
        mov     eax, [ebp + X_OFFSET]
286
        mov     eax, [ebp + X_OFFSET]
287
        mov     ebx, [ebp + Y_OFFSET]
287
        mov     ebx, [ebp + Y_OFFSET]
288
 
288
 
289
        sar     eax, 6
289
        sar     eax, 6
290
        sar     ebx, 6
290
        sar     ebx, 6
291
 
291
 
292
        cmp     eax, 5
292
        cmp     eax, 5
293
        jb      .new_particle
293
        jb      .new_particle
294
        cmp     eax, SCREEN_WIDTH - 5
294
        cmp     eax, SCREEN_WIDTH - 5
295
        jge     .new_particle
295
        jge     .new_particle
296
        cmp     ebx, 5
296
        cmp     ebx, 5
297
        jb      .new_particle
297
        jb      .new_particle
298
        cmp     ebx, SCREEN_HEIGHT - 5
298
        cmp     ebx, SCREEN_HEIGHT - 5
299
        jl      .part_ok
299
        jl      .part_ok
300
 
300
 
301
  .new_particle:
301
  .new_particle:
302
        call    init_particle
302
        call    init_particle
303
        jmp     .advance_particles
303
        jmp     .advance_particles
304
 
304
 
305
  .part_ok:
305
  .part_ok:
306
        imul    edi, ebx, SCREEN_WIDTH
306
        imul    edi, ebx, SCREEN_WIDTH
307
        mov     dl, [ebp+COLOR_OFFSET]
307
        mov     dl, [ebp+COLOR_OFFSET]
308
        mov     [buffer+eax+edi], dl
308
        mov     [buffer+eax+edi], dl
309
 
309
 
310
        mov     eax, [ebp+X_SPEED_OFFSET]
310
        mov     eax, [ebp+X_SPEED_OFFSET]
311
        add     [ebp+X_OFFSET], eax
311
        add     [ebp+X_OFFSET], eax
312
        mov     eax, [ebp+Y_SPEED_OFFSET]
312
        mov     eax, [ebp+Y_SPEED_OFFSET]
313
        add     [ebp+Y_OFFSET], eax
313
        add     [ebp+Y_OFFSET], eax
314
 
314
 
315
        rdtsc
315
        rdtsc
316
        and     al, 0x7F
316
        and     al, 0x7F
317
        jnz     .dont_inc_y_speed
317
        jnz     .dont_inc_y_speed
318
        inc     dword [ebp+Y_SPEED_OFFSET]
318
        inc     dword [ebp+Y_SPEED_OFFSET]
319
    .dont_inc_y_speed:
319
    .dont_inc_y_speed:
320
 
320
 
321
        add     ebp, PART_SIZE
321
        add     ebp, PART_SIZE
322
        loop    .advance_particles
322
        loop    .advance_particles
323
 
323
 
324
        shade
324
        shade
325
;       jmp     .copy_buffer_to_video
325
;       jmp     .copy_buffer_to_video
326
        blur_prepare
326
        blur_prepare
327
        test    dword [blur_right_flag] , 0x800000
327
        test    dword [blur_right_flag] , 0x800000
328
        jnz     .do_blur_right
328
        jnz     .do_blur_right
329
        blur
329
        blur
330
        rdtsc
330
        rdtsc
331
        and     al, 1
331
        and     al, 1
332
        jz      .blur_ok
332
        jz      .blur_ok
333
        jmp     .dont_blur
333
        jmp     .dont_blur
334
    .do_blur_right:
334
    .do_blur_right:
335
        blur_right
335
        blur_right
336
    .blur_ok:
336
    .blur_ok:
337
        add     dword [blur_right_flag], 0x1000
337
        add     dword [blur_right_flag], 0x1000
338
    .dont_blur:
338
    .dont_blur:
339
 
339
 
340
    .copy_buffer_to_video:
340
    .copy_buffer_to_video:
341
 
341
 
342
        mcall   48, 4
342
        mcall   48, 4
343
        lea     edx, [(5 SHL 16) + eax]
343
        lea     edx, [(5 SHL 16) + eax]
344
 
344
 
345
        mov     eax, 65
345
        mov     eax, 65
346
        mov     ebx, buffer
346
        mov     ebx, buffer
347
        mov     ecx, (SCREEN_WIDTH SHL 16) + SCREEN_HEIGHT
347
        mov     ecx, (SCREEN_WIDTH SHL 16) + SCREEN_HEIGHT
348
        push    8
348
        push    8
349
        pop     esi
349
        pop     esi
350
        mov     edi, pal
350
        mov     edi, pal
351
        xor     ebp, ebp
351
        xor     ebp, ebp
352
        int     0x40
352
        int     0x40
353
 
353
 
354
 
354
 
355
still:
355
still:
356
        mov     eax, 11             ; Test if there is an event in the queue.
356
        mov     eax, 11             ; Test if there is an event in the queue.
357
        int     0x40
357
        int     0x40
358
 
358
 
359
        dec     eax                   ; redraw request ?
359
        dec     eax                   ; redraw request ?
360
        jz      red
360
        jz      red
361
        dec     eax                   ; key in buffer ?
361
        dec     eax                   ; key in buffer ?
362
        jz      key
362
        jz      key
363
        dec     eax                   ; button in buffer ?
363
        dec     eax                   ; button in buffer ?
364
        jz      button
364
        jz      button
365
 
365
 
366
        jmp     MAIN
366
        jmp     MAIN
367
 
367
 
368
 
368
 
369
key:
369
key:
370
        mov     eax, 2
370
        mov     eax, 2
371
        int     0x40
371
        int     0x40
372
;       cmp     ah, 1               ; Test Esc in Scan
372
;       cmp     ah, 1               ; Test Esc in Scan
373
;       je      close_app
373
;       je      close_app
374
        cmp     ah, 27              ; Test Esc in ASCII
374
        cmp     ah, 27              ; Test Esc in ASCII
375
        je      close_app
375
        je      close_app
376
        jmp     MAIN
376
        jmp     MAIN
377
 
377
 
378
button:
378
button:
379
; we have only one button, close
379
; we have only one button, close
380
close_app:
380
close_app:
381
        mov     eax, -1         ; close this program
381
        mov     eax, -1         ; close this program
382
        int     0x40
382
        int     0x40
383
 
383
 
384
init_particle:
384
init_particle:
385
        rdtsc
385
        rdtsc
386
        and     al, 0x1F
386
        and     al, 0x1F
387
        jnz     .dont_re_init_globals
387
        jnz     .dont_re_init_globals
388
        ; init x
388
        ; init x
389
        call    rand
389
        call    rand
390
        cdq
390
        cdq
391
        ;xor dx, dx
391
        ;xor dx, dx
392
        mov     ebx, SCREEN_WIDTH
392
        mov     ebx, SCREEN_WIDTH
393
        div     ebx
393
        div     ebx
394
        shl     edx, 6
394
        shl     edx, 6
395
        mov     [4 + global_x], edx
395
        mov     [4 + global_x], edx
396
        ; init y
396
        ; init y
397
        call    rand
397
        call    rand
398
        cdq
398
        cdq
399
        ;xor    dx, dx
399
        ;xor    dx, dx
400
        mov     ebx, SCREEN_HEIGHT
400
        mov     ebx, SCREEN_HEIGHT
401
        div     ebx
401
        div     ebx
402
        shl     edx, 6
402
        shl     edx, 6
403
        mov     [4 + global_y], edx
403
        mov     [4 + global_y], edx
404
  .dont_re_init_globals:
404
  .dont_re_init_globals:
405
        ; init x
405
        ; init x
406
        mov     eax, [4 + global_x]
406
        mov     eax, [4 + global_x]
407
        mov     [ebp + X_OFFSET], eax
407
        mov     [ebp + X_OFFSET], eax
408
        ; init y
408
        ; init y
409
        mov     eax, [4 + global_y]
409
        mov     eax, [4 + global_y]
410
        mov     [ebp + Y_OFFSET], eax
410
        mov     [ebp + Y_OFFSET], eax
411
        ; init x speed
411
        ; init x speed
412
        call    rand
412
        call    rand
413
        and     eax, 31
413
        and     eax, 31
414
        sub     eax, 15
414
        sub     eax, 15
415
        ;shl    ax, 6
415
        ;shl    ax, 6
416
        mov     [ebp + X_SPEED_OFFSET], eax
416
        mov     [ebp + X_SPEED_OFFSET], eax
417
        ; init y speed
417
        ; init y speed
418
        call    rand
418
        call    rand
419
        and     eax, 31
419
        and     eax, 31
420
        sub     eax, 15
420
        sub     eax, 15
421
        ;shl    ax, 6
421
        ;shl    ax, 6
422
        mov     [ebp + Y_SPEED_OFFSET], eax
422
        mov     [ebp + Y_SPEED_OFFSET], eax
423
        ; init color
423
        ; init color
424
        mov     [ebp + COLOR_OFFSET], dword 255
424
        mov     [ebp + COLOR_OFFSET], dword 255
425
        ret
425
        ret
426
 
426
 
427
rand:
427
rand:
428
        mov     eax, [8 + seed]
428
        mov     eax, [8 + seed]
429
        imul    eax, 214013
429
        imul    eax, 214013
430
        add     eax, 2531011
430
        add     eax, 2531011
431
        mov     [8 + seed], eax
431
        mov     [8 + seed], eax
432
        shr     eax, 16
432
        shr     eax, 16
433
        ret
433
        ret
434
 
434
 
435
; DATA AREA
435
; DATA AREA
436
window_title    db 'Firework demo',0
436
window_title    db 'Firework',0
437
align SIMD_BYTES
437
align SIMD_BYTES
438
sub_mask        db SIMD_BYTES dup 0x01
438
sub_mask        db SIMD_BYTES dup 0x01
439
;                             x, y, x_speed, y_speed, color
439
;                             x, y, x_speed, y_speed, color
440
particles: times NUM_PARTS dd 0, 0, 0,       0,       0
440
particles: times NUM_PARTS dd 0, 0, 0,       0,       0
441
blur_right_flag dd 0
441
blur_right_flag dd 0
442
I_END:
442
I_END:
443
proc_info       process_information
443
proc_info       process_information
444
align 16
444
align 16
445
pal             rb 256 * 4
445
pal             rb 256 * 4
446
align SIMD_BYTES
446
align SIMD_BYTES
447
buffer          rb SCREEN_WIDTH * SCREEN_HEIGHT
447
buffer          rb SCREEN_WIDTH * SCREEN_HEIGHT
448
E_END:
448
E_END:
449
rd 0x200
449
rd 0x200
450
stacktop:
450
stacktop: