⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 calmanfp.asm

📁 frasr200的win 版本源码(18.21),使用make文件,使用的vc版本较低,在我的环境下编译有问题! 很不错的分形程序代码!
💻 ASM
📖 第 1 页 / 共 3 页
字号:
	fninit

	mov     color,ax

	cmp     orbit_ptr,0             ; any orbits to clear?
	je      calcmandfpasm_ret_387   ; nope.
	call    far ptr scrub_orbit     ; clear out any old orbits
	mov     ax,color                ; restore color
					; speed not critical here in orbit land

calcmandfpasm_ret_387:
	UNFRAME <si,di>                 ; pop stack frame
	fwait				; just to make sure
	ret

	
over_bailout_387:                       ; x^2 y^2 xy Cx Cy b
; outside
	mov     ax,cx
	sub     ax,10                   ; 10 more next time before checking
	jns     no_fix_underflow_387
; if the number of iterations was within 10 of maxit, then subtracting
; 10 would underflow and cause periodicity checking to start right
; away.  Catching a period doesn't occur as often in the pixels at
; the edge of the set anyway.
	sub     ax,ax                   ; don't check next time
no_fix_underflow_387:
	mov     oldcolor,ax             ; check when past this - 10 next time
	mov     ax,maxit
	sub     ax,cx                   ; leave 'times through loop' in ax

; zero color fix
	jnz     zero_color_fix_387
	inc     ax                      ; if (ax == 0 ) ax = 1
zero_color_fix_387:
	mov     realcolor,ax            ; save unadjusted realcolor
	sub     kbdcount,ax             ; adjust the keyboard count

	cmp     outside,-1              ; iter ? (most common case)
	je      pop_stack_387
	cmp     outside,-2		; outside <= -2 ?
	jle     special_outside_387     ; yes, go do special outside options
	mov     ax,outside              ; use outside color
	jmp     short pop_stack_387
special_outside_387:
	call    near ptr special_outside
	jmp     short pop_stack_387

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; _287 version (closely resembles original code)
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
.286
.287
start_287:      ; 287
	cmp     fractype,JULIAFP        ; julia or mandelbrot set?
	je      short dojulia_287       ; julia set - go there

; Mandelbrot _287 initialization of stack
	dec     cx                      ; always requires at least 1 iteration

					; the fpu stack is shown below
					; st(0) ... st(7)
					; b (already on stack)
	fld     inity                   ; Cy b
	fld     initx                   ; Cx Cy b
	fld     st(1)                   ; Cy Cx Cy b
	fadd    parmy                   ; Py+Cy Cx Cy b
	fld1                            ; 1 Py+Cy Cx Cy b
	fld     st(1)                   ; Py+Cy 1 Py+Cy Cx Cy b
	fmul    st,st                   ; (Py+Cy)^2 1 Py+Cy Cx Cy b
	fld     st(3)                   ; Cx (Py+Cy)^2 1 Py+Cy Cx Cy b
	fadd    parmx                   ; Px+Cx (Py+Cy)^2 1 Py+Cy Cx Cy b
	fmul    st(3),st                ; Px+Cx (Py+Cy)^2 1 (Py+Cy)(Px+Cx) Cx Cy b
	fmul    st,st                   ; (Px+Cx)^2 (Py+Cy)^2 1 (Py+Cy)(Px+Cx) Cx Cy b
	; which is the next                x^2 y^2 1 xy Cx Cy b
	jmp     short top_of_cx_loop_287 ; branch around the julia switch

dojulia_287:
					; Julia 287 initialization of stack
					; note that init and parm are "reversed"
					; b (already on stack)
	fld     parmy                   ; Cy b
	fld     parmx                   ; Cx Cy b
	fld     inity                   ; y Cx Cy b
	fld1                            ; 1 y Cx Cy b
	fld     st(1)                   ; y 1 y Cx Cy b
	fmul    st,st                   ; y^2 1 y Cx Cy b
	fld     initx                   ; x y^2 1 y Cx Cy b
	fmul    st(3),st                ; x y^2 1 xy Cx Cy b
	fmul    st,st                   ; x^2 y^2 1 xy Cx Cy b

top_of_cx_loop_287:                     ; x^2 y^2 1 xy Cx Cy b
	fsubr                           ; x^2-y^2 1 xy Cx Cy b
	fadd    st,st(3)                ; x^2-y^2+Cx 1 xy Cx Cy b
	fxch    st(2)                   ; xy 1 x^2-y^2+Cx Cx Cy b
; FSCALE is faster than FADD for 287
	fscale                          ; 2xy 1 x^2-y^2+Cx Cx Cy b
	fadd    st,st(4)                ; 2xy+Cy 1 x^2-y^2+Cx Cx Cy b
					; now same as the new
					; y 1 x Cx Cy b

	cmp     outside,-2              ; real, imag, mult, or sum ?
	jg      no_save_new_xy_287      ; if not, then skip this
	fld     st(2)                   ; x y 1 x Cx Cy b
	fstp    newx                    ; y 1 x Cx Cy b
	fst     newy                    ; y 1 x Cx Cy b
no_save_new_xy_287:

	cmp     inside,-100                     ; epsilon cross ?
	jne     end_epsilon_cross_287
	call    near ptr epsilon_cross          ; y 1 x Cx Cy b
	jcxz    pop_stack_287                   ; if cx=0, pop stack
end_epsilon_cross_287:

	cmp     cx,oldcolor                     ; if cx >= oldcolor
	jae     end_periodicity_check_287       ; don't check periodicity
	call    near ptr periodicity_check_287_387 ; y 1 x Cx Cy b
	jcxz    pop_stack_287                   ; if cx=0, pop stack
end_periodicity_check_287:

	cmp     show_orbit,0            ; is show_orbit clear
	je      no_show_orbit_287       ; if so then skip
	call    near ptr show_orbit_xy  ; y 1 x Cx Cy b
no_show_orbit_287:
					; y 1 x Cx Cy b
	fld     st(2)                   ; x y 1 x Cx Cy b
	fld     st(1)                   ; y x y 1 x Cx Cy b
	fmul    st(4),st                ; y x y 1 xy Cx Cy b
	fmulp   st(2),st                ; x y^2 1 xy Cx Cy b
	fmul    st,st                   ; x^2 y^2 1 xy Cx Cy b
	fld     st                      ; x^2 x^2 y^2 1 xy Cx Cy b
	fadd    st,st(2)                ; x^2+y^2 x^2 y^2 1 xy Cx Cy b

	cmp     potflag,0		; check for potential
	je      no_potflag_287
	fst     magnitude		; if so, save magnitude
no_potflag_287:

	fcomp   st(7)                   ; x^2 y^2 1 xy Cx Cy b
	fstsw   ax
	sahf
	ja      over_bailout_287

;less than or equal to bailout
	loop    top_of_cx_loop_287      ; x^2 y^2 1 xy Cx Cy b

; reached maxit, inside
	mov     oldcolor,0FFFFh         ; check periodicity immediately next time
	mov     ax,maxit
	sub     kbdcount,ax             ; adjust the keyboard count
	mov     realcolor,ax            ; save unadjusted realcolor
	mov     ax,inside_color

	cmp     inside,-59              ; zmag ?
	jne     no_zmag_287
	fadd    st,st(1)                ; x^2+y^2 y^2 1 xy Cx Cy b
	fimul   maxit                   ; maxit*|z^2| x^2 y^2 1 xy Cx Cy b

; When type casting floating point variables to integers in C, the decimal
; is truncated.  When using FIST in asm, the value is rounded.  The following
; line cause the positive value to be truncated.
	fsub    round_down_half

	fist    tmp_word                ; tmp_word = |z^2|*maxit
	fwait
	mov     ax,tmp_word
	shr     ax,1                    ; |z^2|*maxit/2
	inc     ax                      ; |z^2|*maxit/2+1

no_zmag_287:

pop_stack_287:
	fninit

	mov     color,ax

	cmp     orbit_ptr,0             ; any orbits to clear?
	je      calcmandfpasm_ret_287   ; nope.
	call    far ptr scrub_orbit     ; clear out any old orbits
	mov     ax,color                ; restore color
					; speed not critical here in orbit land

calcmandfpasm_ret_287:
	UNFRAME <si,di>                 ; pop stack frame
	fwait                           ; just to make sure
	ret

over_bailout_287:                       ; x^2 y^2 1 xy Cx Cy b
; outside
	mov     ax,cx
	sub     ax,10                   ; 10 more next time before checking
	jns     no_fix_underflow_287
; if the number of iterations was within 10 of maxit, then subtracting
; 10 would underflow and cause periodicity checking to start right
; away.  Catching a period doesn't occur as often in the pixels at
; the edge of the set anyway.
	sub     ax,ax                   ; don't check next time
no_fix_underflow_287:
	mov     oldcolor,ax             ; check when past this - 10 next time
	mov     ax,maxit
	sub     ax,cx                   ; leave 'times through loop' in ax

; zero color fix
	jnz     zero_color_fix_287
	inc     ax                      ; if (ax == 0 ) ax = 1
zero_color_fix_287:
	mov     realcolor,ax            ; save unadjusted realcolor
	sub     kbdcount,ax             ; adjust the keyboard count

	cmp     outside,-1              ; iter ? (most common case)
	je      pop_stack_287
	cmp     outside,-2		; outside <= -2 ?
	jle     special_outside_287     ; yes, go do special outside options
	mov     ax,outside              ; use outside color
	jmp     short pop_stack_287
special_outside_287:
	call    near ptr special_outside
	jmp     short pop_stack_287


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; _87 code is just like 287 code except that it must use
;       fstsw   tmp_word
;       fwait
;       mov     ax,tmp_word
; instead of
;       fstsw   ax
;
.8086
.8087
start_87:
; let emulation fall through to the 87 code here
; as it seems not emulate correctly on an 8088/86 otherwise
	cmp     fractype,JULIAFP        ; julia or mandelbrot set?
	je      short dojulia_87        ; julia set - go there

; Mandelbrot _87 initialization of stack
	dec     cx                      ; always requires at least 1 iteration

					; the fpu stack is shown below
					; st(0) ... st(7)
					; b (already on stack)
	fld     inity                   ; Cy b
	fld     initx                   ; Cx Cy b
	fld     st(1)                   ; Cy Cx Cy b
	fadd    parmy                   ; Py+Cy Cx Cy b
	fld1                            ; 1 Py+Cy Cx Cy b
	fld     st(1)                   ; Py+Cy 1 Py+Cy Cx Cy b
	fmul    st,st                   ; (Py+Cy)^2 1 Py+Cy Cx Cy b
	fld     st(3)                   ; Cx (Py+Cy)^2 1 Py+Cy Cx Cy b
	fadd    parmx                   ; Px+Cx (Py+Cy)^2 1 Py+Cy Cx Cy b
	fmul    st(3),st                ; Px+Cx (Py+Cy)^2 1 (Py+Cy)(Px+Cx) Cx Cy b
	fmul    st,st                   ; (Px+Cx)^2 (Py+Cy)^2 1 (Py+Cy)(Px+Cx) Cx Cy b
	; which is the next               x^2 y^2 1 xy Cx Cy b
	jmp     short top_of_cx_loop_87 ; branch around the julia switch

dojulia_87:
					; Julia 87 initialization of stack
					; note that init and parm are "reversed"
					; b (already on stack)
	fld     parmy                   ; Cy b
	fld     parmx                   ; Cx Cy b
	fld     inity                   ; y Cx Cy b
	fld1                            ; 1 y Cx Cy b
	fld     st(1)                   ; y 1 y Cx Cy b
	fmul    st,st                   ; y^2 1 y Cx Cy b
	fld     initx                   ; x y^2 1 y Cx Cy b
	fmul    st(3),st                ; x y^2 1 xy Cx Cy b
	fmul    st,st                   ; x^2 y^2 1 xy Cx Cy b

top_of_cx_loop_87:                      ; x^2 y^2 1 xy Cx Cy b
	fsubr                           ; x^2-y^2 1 xy Cx Cy b
	fadd    st,st(3)                ; x^2-y^2+Cx 1 xy Cx Cy b
	fxch    st(2)                   ; xy 1 x^2-y^2+Cx Cx Cy b
; FSCALE is faster than FADD for 87
	fscale                          ; 2xy 1 x^2-y^2+Cx Cx Cy b
	fadd    st,st(4)                ; 2xy+Cy 1 x^2-y^2+Cx Cx Cy b
					; now same as the new
					; y 1 x Cx Cy b

	cmp     outside,-2              ; real, imag, mult, or sum ?
	jg      no_save_new_xy_87       ; if not, then skip this
	fld     st(2)                   ; x y 1 x Cx Cy b
	fstp    newx                    ; y 1 x Cx Cy b
	fst     newy                    ; y 1 x Cx Cy b
no_save_new_xy_87:

	cmp     inside,-100                     ; epsilon cross ?
	jne     end_epsilon_cross_87
	call    near ptr epsilon_cross          ; y 1 x Cx Cy b
	test    cx,cx                           ; if cx=0, pop stack
	jnz     end_epsilon_cross_87            ; replaces jcxz
	jmp     pop_stack_6_87                  ; with a long jump
end_epsilon_cross_87:

	cmp     cx,oldcolor                     ; if cx >= oldcolor
	jae     no_periodicity_check_87         ; don't check periodicity
	call    near ptr periodicity_check_87   ; y 1 x Cx Cy b
	jcxz    pop_stack_6_87                  ; if cx=0, pop stack
no_periodicity_check_87:

	cmp     show_orbit,0            ; is show_orbit clear
	je      no_show_orbit_87        ; if so then skip
	call    near ptr show_orbit_xy  ; y 1 x Cx Cy b
no_show_orbit_87:

					; y 1 x Cx Cy b
	fld     st(2)                   ; x y 1 x Cx Cy b
	fld     st(1)                   ; y x y 1 x Cx Cy b
	fmul    st(4),st                ; y x y 1 xy Cx Cy b
	fmulp   st(2),st                ; x y^2 1 xy Cx Cy b
	fmul    st,st                   ; x^2 y^2 1 xy Cx Cy b
	fld     st                      ; x^2 x^2 y^2 1 xy Cx Cy b
	fadd    st,st(2)                ; x^2+y^2 x^2 y^2 1 xy Cx Cy b

	cmp     potflag,0               ; check for potential
	je      no_potflag_87
	fst     magnitude               ; if so, save magnitude
no_potflag_87:

	fcomp   st(7)                   ; x^2 y^2 1 xy Cx Cy b
	fstsw   tmp_word
	fwait
	mov     ax,tmp_word
	sahf
	ja      over_bailout_87

;less than or equal to bailout
	loop    top_of_cx_loop_87       ; x^2 y^2 1 xy Cx Cy b

; reached maxit
	mov     oldcolor,0FFFFh         ; check periodicity immediately next time
	mov     ax,maxit
	sub     kbdcount,ax             ; adjust the keyboard count
	mov     realcolor,ax            ; save unadjusted realcolor
	mov     ax,inside_color

	cmp     inside,-59              ; zmag ?
	jne     no_zmag_87
	fadd    st,st(1)                ; x^2+y^2 y^2 1 xy Cx Cy b
	fimul   maxit                   ; maxit*|z^2| x^2 y^2 1 xy Cx Cy b

; When type casting floating point variables to integers in C, the decimal
; is truncated.  When using FIST in asm, the value is rounded.  The following
; line cause the positive value to be truncated.
	fsub    round_down_half

	fist    tmp_word                ; tmp_word = |z^2|*maxit
	fwait
	mov     ax,tmp_word
	shr     ax,1                    ; |z^2|*maxit/2
	inc     ax                      ; |z^2|*maxit/2+1

no_zmag_87:

pop_stack_7_87:
; The idea here is just to clear the floating point stack.  There was a
; problem using FNINIT with the emulation library.  It didn't seem to
; properly clear the emulated stack, resulting in "stack overflow"
; messages.  Therefore, if emulation is being used, then FSTP's are used
; instead.

	cmp     fpu,0                   ; are we using emulation?
	jne     no_emulation            ; if not, then jump
	fstp    st
; you could just jump over this next check, but its faster to just check again
pop_stack_6_87:
	cmp     fpu,0                   ; are we using emulation?
	jne     no_emulation            ; if not, then jump
	fstp    st
	fstp    st
	fstp    st
	fstp    st
	fstp    st
	fstp    st

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -