You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

65C816汇编内存调色板加载异常,求添加secondary colors方案

65C816汇编调色板加载:主色+次色连续实现方案

问题背景

使用65C816汇编实现内存调色板加载时,主色加载正常,但取消注释次色表后,添加次色存储代码出现数据偏移。需求是让次色紧跟主色存储(如内存地址$E19E20处为00 00 B0 00 D9 0A...格式),但当前代码存在寄存器冲突,无法正确读取下一个次色值。

颜色表定义

;
; --- Tables for setting SCB and color tables for color --------
;
    ENTRY logocolor
logocolor   DC.W $00B0
            DC.W $0AD9
            DC.W $0FF0
            DC.W $0FFB
            DC.W $0F60
            DC.W $0FA7
            DC.W $0E10
            DC.W $0E99
            DC.W $0F0A
            DC.W $0E7C
            DC.W $000D
            DC.W $0AAE

    ENTRY scanbyte
scanbyte    DC.B 1
            DC.B 1
            DC.B 1
            DC.B 2
            DC.B 3
            DC.B 4
            DC.B 5
            DC.B 6

现有加载代码片段

ldx #6 ;I think this is keeping track of each line of the logo
    ldy #22 ;this used to be 10, but we have 6 more colors

lop202  phx Save.
    phy Save.
    ;each time we loop back y is decreased by 2, x by 1
    lda logocolor,y ; Load defined color value in the table, using y as index into a
    ldy #ColorTable+2 ; Load value of ColorTable + 2
    sta [<data],y ; Store read defined color
    ;
    ;--- here we need some operation to get the next color in the table -----
    ;
    ldy #ColorTable+4 ; then load value of ColorTable + 4
    sta [<data],y ; Store read defined color from our imagary operation
    ldy <screenmode
    beq ok202
    
    ;640 mode??? Yes, most certainly is for 640 mode. Need to add the second color here as well.
    ldy #ColorTable+10
    sta [<data],y
    ldy #ColorTable+18
    sta [<data],y
    ldy #ColorTable+26
    sta [<data],y

ok202   phx Table number.
    jsr pushColorTable
    _SetColorTable

    ply Restore.
    plx Restore.
    dey
    dey
    dex
    bne lop202

    brl pop0bytes   no error

    ENDP

解决方案

核心问题分析

现有代码中,读取主色后用ldy #ColorTable+2覆盖了logocolor的索引Y,导致无法直接获取下一个次色的位置。需要先保存索引Y,再恢复并调整索引读取次色,同时修正循环的索引步长。

修改后的代码实现

ldx #6 ; 处理6组主色+次色
    ldy #20 ; 初始指向最后一个主色的索引(对应$000D),次色在y+2

lop202  phx ; 保存X寄存器
    phy ; 保存当前logocolor的主色索引Y
    ; --- 存储主色 ---
    lda logocolor,y ; 读取主色
    ldy #ColorTable+2 ; 主色存储位置
    sta [<data],y ; 写入主色
    ; --- 存储次色 ---
    ply ; 恢复主色索引Y
    iny ; 偏移到次色索引(主色索引+2)
    iny
    lda logocolor,y ; 读取次色
    phx ; 临时保存X
    ldy #ColorTable+4 ; 次色存储位置(紧跟主色)
    sta [<data],y ; 写入次色
    phy ; 保存次色索引,用于后续循环调整
    ; --- 640模式下的额外存储(补充次色写入) ---
    ldy <screenmode
    beq ok202
    
    ; 先写入主色到额外位置
    ply ; 恢复次色索引
    dey
    dey
    lda logocolor,y ; 重新读取主色
    ldy #ColorTable+10
    sta [<data],y
    ldy #ColorTable+18
    sta [<data],y
    ldy #ColorTable+26
    sta [<data],y
    ; 再写入次色到对应额外位置
    iny
    iny
    lda logocolor,y
    ldy #ColorTable+12
    sta [<data],y
    ldy #ColorTable+20
    sta [<data],y
    ldy #ColorTable+28
    sta [<data],y
    phy ; 重新保存次色索引

ok202   phx ; 传入表号给pushColorTable
    jsr pushColorTable
    _SetColorTable

    ply ; 恢复次色索引
    plx ; 恢复X
    dey ; 调整索引到上一组的主色(次色索引-4)
    dey
    dey
    dey
    dex
    bne lop202

    brl pop0bytes   no error

    ENDP

代码重构建议

为提升效率和可读性,推荐使用零页变量存储临时索引,减少栈操作开销:

; 定义零页临时变量,用于存储logocolor的当前索引
temp_idx    DC.W 0

InitPalette
    ldx #6 ; 6组颜色
    ldy #20 ; 初始主色索引
    sty temp_idx ; 保存初始索引到零页

lop202  phx
    ; --- 存储主色 ---
    ldy temp_idx
    lda logocolor,y
    ldy #ColorTable+2
    sta [<data],y
    ; --- 存储次色 ---
    ldy temp_idx
    iny
    iny
    lda logocolor,y
    ldy #ColorTable+4
    sta [<data],y
    ; --- 640模式处理 ---
    ldy <screenmode
    beq skip_640
    ; 主色写入额外位置
    ldy temp_idx
    lda logocolor,y
    ldy #ColorTable+10
    sta [&lt;data],y
    ldy #ColorTable+18
    sta [&lt;data],y
    ldy #ColorTable+26
    sta [&lt;data],y
    ; 次色写入额外位置
    ldy temp_idx
    iny
    iny
    lda logocolor,y
    ldy #ColorTable+12
    sta [&lt;data],y
    ldy #ColorTable+20
    sta [&lt;data],y
    ldy #ColorTable+28
    sta [&lt;data],y
skip_640
    phx
    jsr pushColorTable
    _SetColorTable
    plx
    ; 更新索引:下一组主色 = 当前主色索引 -4
    lda temp_idx
    sec
    sbc #4
    sta temp_idx
    lda temp_idx+1
    sbc #0
    sta temp_idx+1
    dex
    bne lop202
    brl pop0bytes
ENDP

重构后的代码优势:

  • 用零页变量替代栈操作,减少CPU周期开销
  • 逻辑更清晰,避免寄存器冲突
  • 减少重复代码,便于维护

内容的提问来源于stack exchange,提问作者cjp

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 08:38:49