EMU618社区

 找回密码
 立即注册
搜索
查看: 116|回复: 0

[原创] [FC][Mapper19][IRQ学习源码]

[复制链接]

签到天数: 39 天

[LV.5]常住居民I

发表于 2023-7-16 20:16:44 | 显示全部楼层 |阅读模式
  1. ;[FC][Mapper19 IRQ]
    1 h4 f2 S; f3 m* r7 t' q
  2. ;FlameCyclone 20230710
    8 u0 y5 m# w$ y
  3. " V+ ^, k! r" b2 `* X% a
  4. ;文件头$ L5 N( P: e; x2 j
  5. ;======================================================================5 |& G/ E2 k# _  r( M9 `3 C$ z
  6. .INESPRG 4                                              ;16KB PRG 数量6 E# B8 j' R+ N) B6 @
  7. .INESCHR 1                                               ;8KB CHR 数量
    4 W( v5 j& R* w* T$ Q: n+ _
  8. .INESMAP 19                                                 ;mapper 19
    9 p% ~& j# E. P" \7 G6 y; o7 p
  9. .INESMIR 1                                   ;命名表镜像 0水平 1垂直, W: W9 V6 W; c' H
  10. ; {& l4 |3 p7 n( E& h5 M
  11. ;必要条件* b" [, c) W+ L- F
  12. ;1.持有CHR ROM+ i( e+ Y; ~" I1 [7 I! Y# @9 U
  13. ;2.背景Tile和精灵Tile必须使用不同的图案表, 如背景图案$0000, 精灵图案$1000% a  B/ d0 z3 ]  t  [# j
  14. ;3.精灵内存(OAM)不为空& f, y, \7 L/ k! j, @0 Q/ R& t
  15. 3 T6 {5 t/ v( u, s, r) ~1 \" O
  16. ;==================================================+ ^0 Q6 z9 Z; h
  17. ;NES端口常量
    - M5 Y! Y- q1 m( r6 O
  18. PPU_CTRL                =   $2000   ;PPU控制寄存器
    - J) t, t8 T  g5 k8 I2 I  n' E
  19. PPU_MASK                =   $2001   ;PPU掩码寄存器: ^0 g9 K. ~8 x; |: ]" u
  20. PPU_STATUS              =   $2002   ;PPU状态寄存器:读取后PPU_SCROLL和PPU_ADDRESS被复位,下一个写到PPU_SCROLL的数据是水平的,写到PPU_ADDRESS的数据是高位
    / c2 |' h% x8 ?0 D
  21. PPU_OAM_ADDR            =   $2003   ;精灵RAM地址:用来设置通过PPU_OAM_DATA访问的256字节精灵RAM地址。每次访问PPU_OAM_DATA后该地址增加1. e+ T% @, s- Q
  22. PPU_OAM_DATA            =   $2004   ;精灵RAM数据:用来读/写精灵内存。地址通过PPU_OAM_ADDR来设置,每次访问后地址增加1
    3 N5 U- \# `; H9 o5 o
  23. PPU_SCROLL              =   $2005   ;屏幕滚动偏移:第一个写的值会进入垂直滚动寄存器(若>239,被忽略)。第二个值出现在水平滚动寄存器 & y7 [+ a* T; g5 B6 M1 W4 [. @4 u
  24. PPU_ADDRESS             =   $2006   ;VRAM地址:设置PPU_DATA访问的VRAM地址。第一个写地址的高6位。第二个写低8位。每次访问PPU_DATA后地址增加
    1 I7 v% D3 o2 p3 g
  25. PPU_DATA                =   $2007   ;VRAM数据:用来访问VRAM数据,通过PPU_ADDRESS设置的地址在每次访问之后会增加1或32
    + ?0 f0 t! m( r3 X6 D; {. `
  26. OAM_DMA                 =   $4014   ;DMA访问精灵RAM:通过写一个值xx到这个端口,引起CPU内存地址为$xx00-$xxFF的区域传送到精灵内存/ b) m! A. N% T( \2 L# T2 O
  27. APU_STATUS              =   $4015   ;声音通道切换
    / g4 R- M# t' d2 Q, \
  28. JOY1_FRAME              =   $4016   ;手柄1 + 选通) t0 [* p# F5 q3 w
  29. JOY2_FRAME              =   $4017   ;手柄2 + 选通
    8 S6 R8 m2 M$ h) M! [  ^, ?& o3 q
  30.   M3 W. I+ h* u' C0 x0 A( A- |
  31. ;==================================================' N) g# E  y* t% G/ f9 A
  32. ;MAPPER 19端口常量% _9 M( P- L9 C0 h% r7 V
  33. M19_CHR_0000    =   $8000; m4 B) V% K, V0 n7 m; d
  34. M19_CHR_0400    =   $8800
    0 k1 s! F2 }" h3 Y! w# v
  35. M19_CHR_0800    =   $9000! z% h& ^8 Y8 J1 Z0 F- d) ^$ F! U
  36. M19_CHR_0C00    =   $9800, ~9 C, @  o/ V- }
  37. M19_CHR_1000    =   $A0007 \& \9 ]1 t; R2 k
  38. M19_CHR_1400    =   $A8005 U- I2 y9 V2 \7 G4 A$ h+ h1 ^* k
  39. M19_CHR_1800    =   $B000
    3 ~& F3 u+ `" T: ^& e7 V
  40. M19_CHR_1C00    =   $B800
    7 d3 i4 c' {1 E) j* @
  41. M19_NT_2000     =   $C000
    9 N0 n3 r: P8 k2 X
  42. M19_NT_2400     =   $C800
    5 }! G# S! Y/ l5 |
  43. M19_NT_2800     =   $D000
    $ x) i2 L: t  g. A  T$ y
  44. M19_NT_2C00     =   $D800
    # p3 {& J9 B6 J! \- ]  c
  45. M19_PRG_8000    =   $E000
    4 W( a+ n' t" Q& Q
  46. M19_PRG_A000    =   $E800
    8 q+ _6 T& W2 L$ W; j0 s
  47. M19_PRG_C000    =   $F000
    3 b8 Z) ?  Z$ S# {1 C
  48. M19_IRQ_COUNT_L =   $5000
      G; }) S* x3 Q( O" c- ~( N1 E
  49. M19_IRQ_COUNT_H =   $5800$ a: p' M3 x4 J- b# r

  50. - f, o; x0 p- J2 Z) p
  51. ;==================================================% I# d( W$ G2 G+ y$ N
  52. ;程序块配置% c8 X+ ?9 {, ]* s+ b
  53. BANK_DATA_MASK          = $07
    ; S7 n6 _" e4 B8 f* V
  54. ;--------------------------------------------------4 ^6 b/ N8 K& W6 W
  55. RESET_BANK              = $077 R. P* N3 G  o  p+ `8 u6 U
  56. RESET_ADDR              = $FC00" }8 A) R7 C, o/ n, h! e$ B8 ^" j3 P
  57. . }8 X; B8 Z% {3 Q+ r3 p% p+ \
  58. ;==================================================
    ( y4 p& `5 T: f# r  t; d5 D3 v# H6 e8 f
  59. ;图像块配置5 {- [- ?) \! B7 v2 t$ M; V
  60. CHR_DATA_BANK           = $08
    - z' X" b; I& u# g

  61. ( \2 m+ f- y& Y/ \7 }$ Y7 h
  62. ;==================================================
    ) @* l3 b! n/ K: b" n, ^1 g+ ^4 T
  63. ;零页内存地址配置
    1 T, X' z( Y" O+ i& j
  64. Use_Ram_Addr            = $80
    8 w: K1 E+ C9 F0 y3 a% z" n# D4 ^- O
  65. PPU_Ctrl_Buf            = Use_Ram_Addr' `2 G* @3 `$ @5 t! h5 t; v
  66. PPU_Msak_Buf            = PPU_Ctrl_Buf + $017 f% S( L9 P1 ^5 Z
  67. PPU_Scroll_H            = PPU_Msak_Buf + $01
    2 u- ~( M; G& l1 J1 u2 n. o
  68. PPU_Scroll_V            = PPU_Scroll_H + $01$ J( Y+ {8 |$ W6 G0 s0 m3 O- }
  69. FC_Data_L               = PPU_Scroll_V + $01
    0 h0 g! \- _. m1 [
  70. FC_Data_H               = FC_Data_L + $01& z/ K+ P/ i) t0 n2 n3 P
  71. FC_Data_Buf             = FC_Data_H + $012 b9 ]$ g9 I7 p: I
  72. ;==================================================& X9 w: Y: |  D  X  D; Y. N9 U0 h9 T1 Y. f

  73. * g5 p; m+ V, z3 W; u$ i
  74. GAMEPAD_MERGE_FLAG = $04
    8 l6 ~$ K, {8 N$ S
  75. - S# B5 K' }/ _
  76. Gamepad_Keep            =       FC_Data_Buf + 1
    % w! g0 \/ {6 q9 J: Q" V
  77. Gamepad_Once            =       Gamepad_Keep + 2+ _$ k! F) q9 g- ~# [, M- u
  78. Gamepad_Temp            =       Gamepad_Once + 2
    5 F) g& H) }, k: y/ Z
  79.                                 $ J! X4 P3 P9 H
  80. Gamepad_0_State         =       Gamepad_Temp + 2
    , U3 a  A& B1 e" t4 F
  81. Gamepad_1_State         =       Gamepad_0_State + 10 I" l6 v% S8 B/ B0 v5 g$ z, O
  82. Gamepad_0_Value         =       Gamepad_1_State + 1
    7 S5 l, M: F* S4 Z, M
  83. Gamepad_1_Value         =       Gamepad_0_Value + 1
    7 p: S0 Y! U, ]$ D
  84. Gamepad_Port_Value      =       Gamepad_1_Value + 1! L2 ]+ R9 p+ D" _$ i1 j
  85. Gamepad_Merge           =       Gamepad_Port_Value + 1; I) s7 i% u3 e2 A' K: G) m
  86. : W( j0 \/ {+ L) h6 E1 J9 P
  87. ;==================================================
    , u& w( B1 Y4 r4 K- m. t
  88. IRQ_Index               =       Gamepad_Merge + $01
    / o" c2 ]/ I' k" r) k/ D
  89. ;==================================================
    - k: m" h+ F; C, A

  90. 8 N1 Q  q* a# `6 {: n
  91. ;CHR图形数据* u. b) b' e4 C
  92. ;==================================================
    1 G. |6 X- q% z2 S/ R. B
  93. .BANK CHR_DATA_BANK
    + Z9 A. i2 c) \- e
  94. .INCBIN "chr_bank/chr_data.chr"$ C" b4 s' x5 ?! C; I+ n" I' Q( J

  95. : I  V4 }8 s$ ]! V
  96. .BANK RESET_BANK & BANK_DATA_MASK/ t9 q2 }7 U) s& [
  97. .ORG RESET_ADDR% ^' T3 W; Z5 \: h, U: B
  98. % b; I7 Z) |  }6 q1 Q* [8 Y
  99. ;--------------------------------------------------
    * a8 ], N7 G# G" ]  U
  100. Attributes_Data
    * v  Y- [2 q0 U
  101. ;命名表属性
    ' J6 Q* R5 S8 s% X$ a/ j8 V; L/ A5 Q2 G
  102. .DB $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$006 J9 W' `; O9 i1 X: f* o. ]
  103. .DB $50,$50,$50,$50,$50,$50,$50,$50,$FF,$FF,$FF,$FF,$BB,$AA,$AA,$AA
      P$ y9 O9 T9 f+ t% e
  104. .DB $0F,$0F,$0F,$0F,$0B,$0A,$0A,$0A,$AA,$AA,$AA,$AA,$AA,$AA,$AA,$AA
    . \; ^+ e3 j- P0 D# w
  105. .DB $AA,$AA,$AA,$AA,$AA,$AA,$AA,$55,$55,$55,$55,$55,$55,$55,$55,$55
    . m) b* u- P, @  d% m$ D2 H6 R
  106. ;--------------------------------------------------8 z2 t- k1 @5 g% I
  107. ;调色板数据
    ( Z2 H+ j5 k# n+ j' P1 _. D! U3 Y
  108. Palette_Data
    ; Q% D" x! q  [+ S& v5 F) W
  109. .DB $0F,$27,$20,$0F,$0F,$24,$20,$0F,$0F,$21,$20,$0F,$0F,$25,$20,$0F
    ) h& K  a. p( Z& [0 C7 T
  110. .DB $0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F6 s; I: p: T" N7 A( J# _
  111. / o& i3 K5 i  {- y2 e. {
  112. ;==================================================+ ^/ G. ]1 P- x2 ^
  113. ;命名表初始化
    8 T* I" y8 F. g/ }! ]5 j- ?
  114. Init_Name_Table* e3 k& i  u8 d+ l, |
  115. LDA #$20
    ! Z9 r: B. I0 Z1 r8 I
  116. STA PPU_ADDRESS
    : J9 g, c: r' a$ Q% S
  117. LDA #$00
    3 S* h( H" C  k. J7 J4 A
  118. STA PPU_ADDRESS
    * ^/ j3 A2 t. f- m- m
  119. LDA #$00
    8 l; S' K9 \3 Z8 ]& r  s- b% @
  120. LDY #$00" B& q1 T* r8 ^: R
  121. LDX #$10' ]% J, _* ]$ p0 n
  122. Init_Name_Table_Write
    , x4 O6 k8 Y0 ^, D
  123. STA PPU_DATA1 `8 S$ Y  a: d3 j7 X2 Z. j
  124. INY
    + p. n$ s$ T- l4 L0 h
  125. BNE Init_Name_Table_Write
    + w, u1 b1 r, ~# e
  126. DEX8 W! ~- V+ ^% {( t( V7 ~
  127. BNE Init_Name_Table_Write
    6 z- q6 @. q4 [
  128. RTS
      y" ~$ i4 x  z1 g- E

  129.   B9 [; S( E2 c$ ^1 ~5 `
  130. ;==================================================4 M7 J2 D" z1 i
  131. ;调色板初始化- F8 T/ t- I. Q5 l6 B% N
  132. Init_Palette
    : c! }+ G1 k# w! `
  133. BIT PPU_STATUS" T! ]% @7 P7 Q5 J
  134. LDA #$3F
    0 M; m6 \2 F* h! R6 [
  135. STA PPU_ADDRESS
    * R5 D" N) N5 T- p0 t* c
  136. LDA #$00$ `0 k/ c, Z5 ?
  137. STA PPU_ADDRESS- r$ T2 X9 g+ Y
  138. LDX #$00- p4 G$ b6 T( y8 t" R
  139. Init_Palette_Write
    $ k: |0 t* S' W$ E
  140. LDA Palette_Data,X- F& B9 h( L, c" Z, H
  141. STA PPU_DATA
    - R% l2 a2 N0 y$ Q  y- w
  142. INX
    1 V1 p8 e6 Y% G
  143. CPX #$20
    ; Q, @; B% m  Z8 h7 P
  144. BCC Init_Palette_Write( \& T$ |6 T  E
  145. RTS
    8 J# h$ q5 r5 Q% e; l

  146. 9 g9 H7 }" a  P' O4 x* g
  147. ;==================================================- i) N$ P( p- S* |
  148. ;设置命名表属性
    . y4 `; s2 k9 _8 V) N
  149. Init_NameTable_Attributes
    8 `# C( _: k9 z( F* Y
  150. BIT PPU_STATUS
    " Q' q1 A' i4 V5 u" j, J" g3 E
  151. LDA #$23
    / S3 J; b" m5 |5 N- {
  152. STA PPU_ADDRESS
    - {8 D8 [2 P# S" O/ q
  153. LDA #$C0, c6 L2 x1 r) X4 @
  154. STA PPU_ADDRESS
    ( g1 p5 a# [# j3 c  o' \; B9 S
  155. LDX #$00
    3 [3 s* ]3 n4 U$ y* o' M# Y
  156. Init_NameTable_Attributes_Write
    0 R" ?  Z( v; W, ]
  157. LDA Attributes_Data,X" H  U# H1 j9 l' N/ m3 I6 W$ u. R7 }
  158. STA PPU_DATA
    ! O% H* m& N# B) l$ X+ U: }0 g
  159. INX
    + z; V0 _5 R6 C5 v0 x" U
  160. CPX #$40* m* B0 [: w3 C7 D$ E
  161. BCC Init_NameTable_Attributes_Write
    ; z4 I. R/ g3 m" X
  162. RTS
    ! A8 l6 r  o0 i; G/ n* }

  163. 7 s! S# x, ^9 |2 ?1 ?8 W5 \: a
  164. ;==================================================6 p9 t$ l3 c* H5 g
  165. ;初始化命名表文本6 ?! ~2 M  ~0 d% J
  166. Init_Name_Table_Text7 L4 y' ~8 y$ \* l6 v, E( _
  167. BIT PPU_STATUS* Z% j' O& Z# m7 Y& T; {
  168. LDA #$20
    2 R9 q0 p7 B1 J4 q- N4 U
  169. STA PPU_ADDRESS
    # ~/ ]4 K0 z7 q- m& }/ h7 f$ M5 i
  170. LDA #$001 x; R/ p. U/ a+ l0 T
  171. STA PPU_ADDRESS: w; M* A9 j; {- s7 \6 W  |  r" B- v
  172. LDA #$00
    / K! y( Z; f/ I; o3 u
  173. STA FC_Data_Buf
    ' M0 q3 p) g) N& \" d) ?$ ]; Q7 ?
  174. LDY #30( W0 M) ?' X" a( K, _+ L2 W- R
  175. Init_Name_Table_Text_Write
    ) n/ i4 J  ~' _# z4 Z8 S7 N9 D
  176. LDX #32$ o; k" w" G. e/ w% _& o
  177. Init_Name_Table_Text_Write_Char& S) o$ y) l0 O0 W) V) O
  178. LDA #'0'
    7 x! C. q/ {. s# M7 T3 c
  179. CLC0 M! D9 t6 }1 F
  180. ADC FC_Data_Buf6 s2 \; q# d/ O; Y  M- E
  181. STA PPU_DATA
    ! X4 I5 X& s/ f" m
  182. DEX1 Y! R) @$ ^% k' w2 v
  183. LDA #$14
    2 p0 }8 ^) S0 c& V
  184. STA PPU_DATA
    - W* Q" N+ o) g5 j6 t
  185. DEX. T( E7 V* [% F# U* A* e- Y
  186. BNE Init_Name_Table_Text_Write_Char
    % e+ i1 f* H1 b$ e: S$ H3 C
  187. INC FC_Data_Buf- @; |8 N( c+ Z" P. j
  188. DEY
    % q* J" F9 }* r1 }$ m8 U& a
  189. BNE Init_Name_Table_Text_Write
    9 V$ t' Y; R/ e
  190. RTS
      a9 \# v# c& n! `8 O6 \
  191. ; r3 r+ B1 _; {* X% K
  192. ;==============================" ^% A/ N: L0 E, F% F
  193. Init_OAM_Ram;初始化精灵内存
    * w8 |4 r. i8 W
  194. LDX #$00
    # i2 y( m. e/ E7 Q' H
  195. LDA #$004 Y& L5 _! X) U* \7 L( V
  196. STA PPU_OAM_ADDR# r3 p/ p7 L8 C3 e
  197. LDA #$F8
    9 A6 J( g5 X- |9 n
  198. Init_OAM_Ram_Write
    % V- j1 Z, D9 k% ?* t9 U
  199. STA PPU_OAM_DATA( g  B9 g. c2 ]8 ~9 P5 r
  200. INX
    3 F" P! ~8 d% B; f& X5 v
  201. BNE Init_OAM_Ram_Write
    ( H" [  G0 X1 z4 x6 P% R, L% w3 i0 R( x0 l
  202. RTS
      w) }. d+ R0 c& w0 l
  203. $ b2 _: z/ C! x# N
  204. GamepadProcess;手柄处理
    + V* M/ E/ ^" G0 {+ c
  205. JSR GamepadDatacan, f3 Y1 c) ?) [
  206. LDA <Gamepad_0_Value$ F$ b7 i+ \- w! Z
  207. STA <Gamepad_0_State, r0 k! f6 Z+ C5 h2 E2 G0 E' J* }
  208. LDA <Gamepad_1_Value7 v6 d2 K1 \& j* K' m% Z" t/ t) i6 {
  209. STA <Gamepad_1_State: ]; l3 d  o0 e7 z7 l' Y; `
  210. JSR GamepadDatacan
    . z( S8 A2 C6 K7 M, w
  211. LDX #$01
    4 z. G6 s, v4 k. e
  212. GamepadMergeCheck;合并手柄输入检查
    6 v, }& ]; q- ~/ _
  213. LDA <Gamepad_0_Value,X
    ( a" Y. B! v. }
  214. CMP <Gamepad_0_State,X
    5 M" E& S4 Y9 O! T) U; S3 Y' `
  215. BEQ GamepadMergeInput. _4 E& y5 o. W3 b
  216. LDA <Gamepad_Temp,X( ~/ ]' D4 ?  ~, l' G
  217. STA <Gamepad_0_Value,X
    # J% V8 _& K( e; g! |' a
  218. GamepadMergeInput;合并手柄输入
    # V. e" ]  M- P" s( ~! ]
  219. DEX; ^3 I9 \7 j0 A& S+ Y; p7 S6 ?
  220. BPL GamepadMergeCheck& _) ~( ]4 V' {  \
  221. LDA <Gamepad_Merge
    0 o" v( l! A7 q/ b" d3 R6 x) x& v
  222. AND #GAMEPAD_MERGE_FLAG$ Z. [5 |' c. u4 D
  223. BNE GamepadStateProcess, W  Q% F' S7 x$ a! M
  224. LDA <Gamepad_0_Value' J& C+ I' U  L7 v* d" j: `. T8 {  ?
  225. ORA <Gamepad_1_Value
    5 U+ ^1 G1 v: b2 y" Q
  226. STA <Gamepad_0_Value% w2 g3 F( N& M7 }  h: Y) i
  227. GamepadStateProcess;手柄状态处理
    ( \1 n( {- ]1 ~- B# \3 e: r  y
  228. LDX #$01/ D* S1 g! ]$ E% \" A
  229. GamepadStateSave;手柄状态保存7 r' W7 R( `( S3 R. G# Q$ B
  230. LDA <Gamepad_0_Value,X' W& `9 p* r. h; a6 `9 m
  231. TAY1 d# q+ b+ q1 r2 L! c/ g3 K
  232. EOR <Gamepad_Temp,X
    6 [$ \) L! K  Z( a0 e1 m- {
  233. AND <Gamepad_0_Value,X
    ' f4 f/ V% g* m9 b, _
  234. STA <Gamepad_Once,X
    5 N5 ?9 q; _2 T% ^4 O
  235. STY <Gamepad_Keep,X
    , u( c1 i& D, Q6 E9 D; F
  236. STY <Gamepad_Temp,X6 g- j; @1 F. Z5 q
  237. DEX
    2 x, X! u" s8 H  e
  238. BPL GamepadStateSave. c9 X; A- D: z1 G( E% e
  239. RTS
    0 H0 M7 U3 e; r, L. A6 x5 l

  240. 1 r7 V. T8 I) E  O# m
  241. GamepadDatacan;手柄数据扫描
    ; S$ c/ J( V" L6 c( O( K* z
  242. LDX #$014 e& S) t5 T, e3 U
  243. STX $4016
    : j/ K: j2 m! k  m
  244. DEX% L' C  t( `. V7 m
  245. STX $4016: d/ ?: h. [4 X' B. v, e* |
  246. LDY #$08$ w% y# F( P% z' p. q$ |
  247. GamepadPortScan;手柄端口扫描0 y/ T! w& O" ^; B+ b0 X
  248. LDA $4016
    * A7 j/ X2 i2 i5 D
  249. STA <Gamepad_Port_Value
    1 H% V2 A7 s, ?) z5 T6 T5 V8 \
  250. LSR A1 M  ?$ G. S. j3 k9 \# q
  251. ORA <Gamepad_Port_Value
    * ?+ b, w1 v1 ], o
  252. LSR A4 Q, W+ t, F& a1 q. O+ o* `) S! g* e3 P
  253. ROL <Gamepad_0_Value, }  ]* ]# Q" Q  H
  254. LDA $4017  c6 e+ Q3 Y3 D3 N, j
  255. STA <Gamepad_Port_Value2 S8 o6 ^2 _5 x
  256. LSR A
    ' ^$ T* ?% g. Y4 }
  257. ORA <Gamepad_Port_Value- F& w8 b0 k2 w4 Y  B* l. E
  258. LSR A
    " w- |7 F7 }: z/ {- d
  259. ROL <Gamepad_1_Value9 J3 B) n. L2 V
  260. DEY$ u% g% I' r  V' A' M
  261. BNE GamepadPortScan
    ! I( e: s3 g7 [
  262. RTS
    ' X- m; a! z/ M& H2 O" u

  263. % m$ d  ~& r* {+ |" V, j) p
  264. ;==================================================
      K4 Z9 n' J' p# T7 J0 K! Z9 v3 n
  265. ;PPU处理
    4 l' ]8 x6 i1 @( u/ T' F  n8 |6 L' _, k
  266. PPU_Process7 W. c/ k* u8 f% g( ?! S
  267. LDA #$00
    ! [+ o$ x" ^/ _
  268. STA PPU_MASK& t7 M- k7 I( h9 V

  269. ( o9 d: e( M: D, Z8 q" u! n
  270. BIT PPU_STATUS5 |8 L' c! g3 i* o) z+ B
  271. LDA #$20$ s$ Q0 {9 k6 N
  272. STA PPU_ADDRESS& F5 M1 Z+ o+ n8 D- Z
  273. LDA #$00
    & `% B! q1 w: K) n/ @* B
  274. STA PPU_ADDRESS
    : E" k% ?' L' Z7 R* E( b+ _( [/ ]3 J

  275. + z# F- S8 `) s8 g
  276. STA PPU_SCROLL8 X6 j. Q: X1 o4 Q/ Q9 j1 ^
  277. STA PPU_SCROLL
    3 b7 e6 p& R5 e. U6 [$ h" G

  278. 2 Z& m$ a2 r! M# x
  279. LDA PPU_Msak_Buf# J5 `/ ~% Z+ {5 [
  280. STA PPU_MASK* M. Y7 d8 [6 ^, I7 X5 h
  281. 2 P! v( Q4 t$ F6 Q0 |+ ^  \+ W
  282. RTS
    " E) ^* u4 f& Z

  283. , Q1 j$ f* K& Q+ Y$ U0 y
  284. ;==============================) P% s$ y, _$ O' D  l0 u7 w0 C
  285. Time_For_Vblank;延时等待  ]" l# L5 e$ C" u2 D6 p
  286. LDA PPU_STATUS
    4 F1 {4 U8 p9 t0 G3 A- K
  287. BPL Time_For_Vblank
    , W. S' ]/ N. a! g( v0 U- M
  288. RTS
    / r: b: S6 I' a, T5 b

  289. ) q8 C! v) M3 w9 n
  290. ;==============================
    , Z3 {& m( T* s/ K
  291. ;初始化MAPPER19
    7 Q% W0 ]% h1 e& n
  292. Init_Mapper19
    , Z  K, n6 p+ n1 G& J1 o% L
  293. LDA #$00
    9 F8 P7 u& y( e+ E2 U
  294. STA M19_CHR_0000
    ' {2 E' \# [" ]: ?7 a: q! @- }1 K
  295. LDA #$01
    * ?& H6 Q4 U% }
  296. STA M19_CHR_0400
    ; q  Y0 G/ V# x9 i& W
  297. LDA #$02$ X( t/ y. W. l% r
  298. STA M19_CHR_0800
    6 J  m; j  p0 A" E( g" X
  299. LDA #$03, v, ?1 [: `% @  P& I! d
  300. STA M19_CHR_0C00& Q% h' y/ f- @" j
  301. LDA #$04) x' y/ \: g- k7 c- C. w1 P
  302. STA M19_CHR_1000: s9 g5 [, v7 ?* i; ^
  303. LDA #$05: |+ n/ z! h, j: ~
  304. STA M19_CHR_1400
    ) ~8 W" d- ~, T7 a) }/ v: x
  305. LDA #$06
    " P9 }( {( n- R& F9 ~( ?
  306. STA M19_CHR_1800
    1 p! K" J+ {/ N$ w; b' H9 N& l
  307. LDA #$07
    0 ?' }: t+ U( {* {5 ^+ y( S" {
  308. STA M19_CHR_1C00
    : w8 W% A4 B7 \" i4 e" }5 M6 m, n

  309. 0 d4 S7 [& e: h1 U" A" q# O% C
  310. ;禁用IRQ+ W7 e% _9 D# M! w) Q9 \4 m" S
  311. LDA M19_IRQ_COUNT_H/ k: R' _/ @  F7 G# J4 I
  312. AND #$7F
    2 J( [) w6 m* e. f+ r/ J; E( I
  313. STA M19_IRQ_COUNT_H
    7 T9 Q8 |/ n: O/ w
  314. , N- N+ @0 {5 i3 j
  315. ;命名表
    7 Z' D0 z% f& B6 b! n& V
  316. LDA #$E0! v1 S/ t0 h; q( \( l/ o1 X0 q3 x
  317. STA M19_NT_20003 F6 z$ m( B. r* Z7 _& l
  318. STA M19_NT_24007 l3 K3 P2 Q" D+ a: q
  319. * o3 S) W- }" C: ]+ e
  320. ;命名表; _% Y% x0 G7 i+ q# V
  321. LDA #$E1
    ) V) v- B. Z* I; v. Y
  322. STA M19_NT_2800
    ; B" P2 ?4 ^- N) H$ C. I
  323. STA M19_NT_2C00
    " V( F$ q. C$ r4 A

  324. 0 N! j. d* q- k$ W% v  p+ S. P/ i
  325. RTS
    8 [2 ~% e  j+ @& a( o2 |9 I4 d$ G' n, E
  326. * f6 }5 g" v( O# G) U" c
  327. ;==================================================
    2 [$ {7 n5 ?! V8 S
  328. ;重置中断处理5 l$ _: n6 [1 f7 {( u4 T7 b
  329. ResetProgram* o( w' i  m# u% h% {
  330. SEI
    2 T( u% _" u1 B
  331. CLD) L2 J( m8 r/ J. }! U2 L& \
  332. LDA #$007 v; x2 g6 ~' ]$ E7 j2 L: Y
  333. STA PPU_CTRL( F$ b5 c2 t. B
  334. STA PPU_MASK
    0 l# F9 Q& i& @! J2 ?
  335. STA PPU_STATUS  D- P3 [# C! A
  336. STA JOY2_FRAME% S- t0 O8 L& g$ S) p* s
  337. STA APU_STATUS
    - J" i6 \- Z% @0 W- H

  338. / }$ b  v1 y9 _+ s; Y& ?" c! ]9 r) a
  339. LDA #$C0
    * u# I  \+ Y4 }' m
  340. STA JOY2_FRAME7 a6 Q8 V' q/ l  K) U: |. e; T8 U

  341. * c; @" k- P2 Y! X% [- W
  342. ;等待vblank/ R3 w/ i4 v2 S, G2 ^3 B2 E9 t+ P3 r
  343. LDX #$02; |1 l8 E; t$ m' f2 j& q- P4 i
  344. Vblank_Wait_1
    ( a2 z  v; i/ o; }
  345. BIT PPU_STATUS/ r0 X, J8 c! \5 P
  346. BPL Vblank_Wait_1  h9 q. B% \; T3 w6 D) K+ @+ S
  347. Vblank_Wait_2
    - Y4 C2 z2 n) O* Y$ e7 G
  348. BIT PPU_STATUS- ^! A" H$ w: C
  349. BMI Vblank_Wait_2: a  U+ `; v" o
  350. DEX/ \3 R8 P: A6 k$ j6 [+ H
  351. BNE Vblank_Wait_1
    & O( W' H( [6 \5 X

  352. 9 ]% H" M! f* T! Y: _" T
  353. LDX #$FF. v  X5 K8 y* K+ \+ Z
  354. TXS9 b2 \" U0 s5 N. n3 d: T; J
  355. - X5 ?" c" N2 A" d/ ?4 ?5 b
  356. ;初始化MAPPER19
    . n$ d. k2 M+ P$ V4 z% a" m
  357. JSR Init_Mapper19
    ; g( i" f  V# W& s  n
  358. 8 H) I( Q. Z$ S( ?5 V" J; c
  359. ;==============================
    2 y1 @1 q7 V3 L! o
  360. ;RAM初始化
    9 p* b+ d, o% u2 K* x* [
  361. Nes_Ram_Init' w% f+ F  Y8 z' d
  362. LDY #$00
    6 ?$ ^/ u, Z# [4 ^2 w6 a
  363. LDX #$08' O, J2 ~, Y# u) E8 e! X
  364. LDA #$00
    ) U( H, {( j- _* ]# Z- I
  365. STA <$00+ q  g! S- S, Q& W7 \
  366. STA <$01+ G3 b  N1 z8 o
  367. Nes_Ram_Init_Write$ ?  _& U2 J) t# \" F3 _
  368. STA [$00],Y" f& B: t- G& G/ j3 r" `2 U: |
  369. INY) O' Q. g5 J0 s
  370. BNE Nes_Ram_Init_Write
    # q+ O* ^2 I9 J. a0 e- h
  371. INC <$01
    * y7 r- h; \: z( L6 P& Y
  372. DEX  K0 R. b- B5 w* L
  373. BNE Nes_Ram_Init_Write$ A4 ?4 w: {2 K8 W4 S; a( s, j
  374. ) u' P- [; `3 j( [" m
  375. ;初始化命名表2 B7 P+ O# Y% M' M4 e
  376. JSR Init_Name_Table
    ( l2 I9 H7 c+ }/ h8 P& D. f

  377. 7 l. ~$ ]9 j" c% I! R# N0 j
  378. ;初始化调色板* i- p5 p- E; z  U5 r9 ?% d
  379. JSR Init_Palette; y; S) G& s0 d) z, Y1 f

  380. 3 D# [$ t; k0 ?4 U" @
  381. ;初始化命名表属性+ J  M6 ?2 U+ e' ?$ x1 p  q
  382. JSR Init_NameTable_Attributes
    . f0 x7 h1 c, f: y

  383. 6 |# v# ]! u+ Q" B& \( P
  384. ;初始化精灵内存) ]3 c6 B3 I& g+ ~, X4 f8 Y
  385. JSR Init_OAM_Ram
    + [! U1 O$ d& C1 C
  386. & g! C( \9 [( c7 m6 ]" n
  387. ;在屏幕上写点东西
    ' Q8 X% f; H- o8 s* A; y
  388. JSR Init_Name_Table_Text, b8 J' [- L( e0 E. ^
  389. 5 w+ K3 }4 `0 F% |8 p$ ?9 ^
  390. JSR Time_For_Vblank
    3 S8 Y1 p% M% l% ^6 S! o
  391. ;开启PPU控制
    3 G6 \+ e: E$ N2 v
  392. LDA #$A8/ ?4 i/ w: x* L6 ^
  393. STA PPU_Ctrl_Buf% k5 |2 f; m5 [' l4 q: Q
  394. STA PPU_CTRL
    / P. ^! q5 O* W1 K  w5 R$ Z3 q
  395.   H: |; A! Z; k. k
  396. ;开启PPU显示& y! A+ u3 T2 ?
  397. LDA #$1E
    8 Q& ]. }' l- S* w7 p. V- u( Z
  398. STA PPU_Msak_Buf# |6 ~# ?' ~% u7 Z9 o2 l

  399. : C/ J; U+ q" \; G
  400. CLI2 K0 S" Z2 g# b% u
  401. JMP Loop
    ) S( X5 k- H% P# i! S

  402. : W, ]2 v4 ^' n' T0 t
  403. ;==============================& t6 i2 ~( p% z; T2 e3 E* V
  404. ;死循环, 等待NMI中断5 D0 e0 E! G  c
  405. Loop
    , A7 `3 P$ O8 J% x) r
  406. JMP Loop& Z5 W, ?# v2 {: w, k
  407. 8 s' u0 T1 `2 a, I( W: d
  408. ;每行扫描线1789772.5Hz / (262 * 59.94) = 113.967! C! z. ?" f" [; {) i! g
  409. : B0 z4 @5 e* V5 d
  410. ;BEGIN_LINE_CYCLES_START = 32768 - ((260 - 240 + 16) * 113.967)# N7 r+ ?8 j& G- h* T* z1 _/ j- D- i
  411. BEGIN_LINE_CYCLES_START = 32768 - (4103)
    3 e! D% a( e( P2 O1 o
  412. ;==================================================
    3 }" Q  w2 h. [7 b, I- x  o+ A
  413. ;NMI中断处理
    * t) P! U* \: j8 {; b: L0 L
  414. NmiProgram
    8 `8 V& o% j5 [3 O* D; Q3 T
  415. PHA1 }$ I3 N$ q, L# z4 M4 @% H( [
  416. TXA& Q5 N7 h. [& H( H
  417. PHA: d( B' u% U! r) c: A
  418. TYA
    % M. g( X6 h. ^# n8 M) }" B
  419. PHA! O3 j' ?# O& u# W# q3 o3 C3 i! Y

  420. / X, t" v( V* \  |- `
  421. BIT PPU_STATUS
    5 {; m1 b7 A; [
  422. ' _4 C" t6 s  X3 _& N$ F3 R. A
  423. LDA #$007 ^# G3 }+ v" }, O4 H
  424. STA IRQ_Index
    ; V8 T- n! h8 n9 K: _

  425. ) T* o! u5 s  p" [& C7 h6 z) Z, D
  426. ;Mapper 19 的IRQ是基于CPU周期的, 为了IRQ稳定, 首先开启IRQ, 避免PPU处理周期不稳定导致IRQ抖动3 X. i7 ^* s3 @4 A$ b' l1 Y# H
  427. LDA #LOW(BEGIN_LINE_CYCLES_START)
    " N3 f% W. U- f: v9 U, u# O' q7 D( J
  428. STA M19_IRQ_COUNT_L
    + [1 n8 m5 Y5 e3 u7 @/ Y/ m  U
  429. LDA #HIGH(BEGIN_LINE_CYCLES_START)
    / l/ O7 k2 f: u- S7 ^3 x
  430. ORA #$80% T/ Z0 Z6 ~2 f6 v8 c% y
  431. STA M19_IRQ_COUNT_H
    - k# E0 T% [9 k/ e+ _3 B
  432. CLI
    " Q, _3 @6 o" ^

  433. : ?5 W5 P( ]9 E% d0 o* m
  434. ;关闭PPU控制
    3 e& ~- T; `" A: L/ p
  435. LDA #$006 B8 p" ~3 E& B; j$ d
  436. STA PPU_CTRL
    9 Q( V# c1 V! f0 g

  437. - W4 e2 x5 m* c; _) g
  438. ;处理PPU0 B9 m) ]9 Q6 ~- l* z* a  X; U
  439. JSR PPU_Process  h: ?( O- V5 I' ?! U6 R/ I

  440.   \" f! s4 l5 y/ o
  441. ;开启PPU控制
    ( d8 ?+ o1 A- V6 y  ~8 }5 L4 \
  442. LDA PPU_Ctrl_Buf, z2 N* ^7 K: h7 S/ u5 d4 V
  443. STA PPU_CTRL' {5 @3 {8 A" U& B- q, c" ?2 p

  444. . z% a/ E& _# N
  445. ;手柄处理7 a6 K' s' E+ H/ y/ r9 a
  446. JSR GamepadProcess
    1 X5 t' c0 A$ M, R! I
  447. # m; K3 g& Q9 V& i/ P2 i7 x
  448. LDA #$00
    9 z9 a8 O2 i' W! K( O
  449. STA IRQ_Index
    : E3 Y) t5 ~! J

  450. ) _5 R  l! o* S7 W. l- U
  451. PLA
    / G! ~9 _3 w' s4 h. Q
  452. TAY+ Y1 G/ C5 i4 E( j+ `0 _+ h8 L
  453. PLA
    4 ~' D* y0 R5 F" P! r. ^
  454. TAX6 Z. [! j- G$ m7 I- }1 N4 _
  455. PLA
    8 f& e) r+ ?6 r7 v- I
  456. RTI0 |) V7 {: w! i! Z" X6 D

  457. + x: Z: U# H- o9 Q
  458. ;每行扫描线113.67, y+ B; b. ]. S* `2 e5 e
  459. ;BEGIN_LINE_CYCLES = 32768 - (16 * 113.967)
    7 p! I4 m0 L1 T5 X5 `, l$ c
  460. BEGIN_LINE_CYCLES = 32768 - (1824) + 27 + 7
    ' c) v. g# O* p  A* v
  461. ;==================================================8 u: n/ R# f! J3 w8 R6 u+ L, Z" q
  462. ;IRQ中断处理1 R7 w- }' V8 b1 C) B
  463. IrqProgram
    # S" M  F* T- z# n; b
  464. PHA
    ( l; S: f& Q2 M: y
  465. TXA" L2 V/ E# f3 j2 g( g
  466. PHA# }" t; B' U: g. w+ y' H4 f' ^
  467. TYA
    8 T/ e' }, g# _4 f! t
  468. PHA) w$ Z* M- x' n5 f, m* H" t
  469. 7 ^7 m2 H+ y# R6 d6 ?5 H; T
  470. ;16条扫描线后触发IRQ
    ) N8 _; {, Y3 e) T  Z
  471. LDA #LOW(BEGIN_LINE_CYCLES)
    9 Q& {8 Q4 n1 G1 K; X3 L# v+ g
  472. STA M19_IRQ_COUNT_L
    # o% ~: s; v4 z
  473. LDA #HIGH(BEGIN_LINE_CYCLES)2 z, u# n) U5 R
  474. ORA #$80
    2 K) b! V, Y3 k) Q3 {1 C
  475. STA M19_IRQ_COUNT_H" ?4 s$ F& N3 l; |
  476. / s% e( H+ j# [' ^- x. j1 y5 C
  477. LDA <IRQ_Index5 t6 i6 d6 ]( c  @9 E; }6 L
  478. BNE * + 4
    3 v* M: F3 w3 q3 N0 \% E3 B
  479. INC <PPU_Scroll_H
    : u5 Z. h" f9 x6 d3 E2 `& E
  480. . o. }1 @, n8 M9 i, x6 y
  481. ;设置屏幕滚动# _  c: _' C3 `2 X: r& v( N
  482. LDA <IRQ_Index8 U: C6 k7 j% o7 ?& {4 W
  483. AND #$01
    1 r) \" {+ V  W( D# q0 }/ y
  484. BEQ Irq_Scroll_Right4 T# L3 B. }* M5 U
  485. & l8 O5 n% ]. @5 L" m( F' c
  486. Irq_Scroll_Left
    ! _# h! Z+ F( w; T
  487. BIT PPU_STATUS
    ; ^* m2 G0 m9 C
  488. LDA <PPU_Scroll_H" k1 ]) [/ }; ]
  489. STA PPU_SCROLL
    0 a6 `1 ?0 m7 e  M
  490. STA PPU_SCROLL
    : `5 h- E1 R8 l: J8 E% Y
  491. JMP Irq_Scroll_Over
    : L; z9 e- q3 z) l! @/ I
  492. 3 o3 m/ j5 s4 I4 B+ S/ U
  493. Irq_Scroll_Right
    ) H  j; r: G( m5 R+ e, f0 \: p
  494. SEC
    1 a8 v; @  Y0 o8 Z7 x: y/ g# I
  495. SBC <PPU_Scroll_H
    0 U. P( v, O7 O! G- k& ^' v
  496. STA PPU_SCROLL1 q$ a, g9 A( s8 i( p0 P
  497. STA PPU_SCROLL1 U9 T- U: |: f+ m/ ]
  498. Irq_Scroll_Over
    / i( Y" U+ z, q: Y# m' v3 `

  499. , I( U( t! Q$ A% H8 L# e
  500. INC <IRQ_Index7 H6 @( @+ G9 D9 e$ O2 K3 L* w
  501. % e: J) ~9 o  r
  502. LDA <IRQ_Index4 H7 e% R/ ]! L2 I8 R' g
  503. CMP #14
    % D9 v  t2 b( G2 C8 x/ n- ]$ g) f0 ?6 T, Y
  504. BCC * + 10' {; ]  N3 w9 X0 U
  505. LDA #$00: {6 H6 g2 |; f( P2 E5 F
  506. STA M19_IRQ_COUNT_L+ U6 g: P4 x3 ^# o" P, N
  507. STA M19_IRQ_COUNT_H( J# O9 S5 ]& g
  508.   d  q- t/ ], S( q4 M4 t# x- j3 E
  509. IrqProgramEnd6 n. s% H# N% N& N' X6 w- ^
  510. PLA! a' c( [$ B' L+ k6 t: r
  511. TAY& ~6 f% _  i1 c. _
  512. PLA
    3 D/ q, @3 b8 y
  513. TAX
    ' h4 T. A/ |! M8 ~4 g, h
  514. PLA+ h+ {7 `5 t3 b/ X, ~& r
  515. RTI; Q; b3 H& B6 e, `" ]
  516. # m! Y: N2 T  r; N" X6 V3 y
  517. ;==================================================
    8 b9 g' `4 N0 C) F7 b
  518. ;中断表
    * E" m7 N6 t4 E
  519. .ORG $FFFA
    " V! A  Y) g- F/ u, G+ h
  520. .WORD NmiProgram8 [; Q* _; t+ F+ B
  521. .WORD ResetProgram  R0 [4 t9 F2 x6 m) U
  522. .WORD IrqProgram
复制代码

+ t' Z# k/ I' h6 J) O' o6 ?& M

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

x
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|国治模拟精品屋 ( 沪ICP备15012945号-1 )

GMT+8, 2024-11-17 00:20 , Processed in 1.073242 second(s), 20 queries , Gzip On.

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表