IS new text system complete
This commit is contained in:
245
ep_ai_main.asm
Normal file
245
ep_ai_main.asm
Normal file
@@ -0,0 +1,245 @@
|
||||
; ===== ОСНОВНАЯ ФУНКЦИЯ ПЕЧАТИ =====
|
||||
.org 0x80090000
|
||||
ExternalPrint:
|
||||
lhu v0,0x0(a0) ; Читаем 2 байта текста
|
||||
nop
|
||||
srl v1,v0,0xD ; Проверяем 13-й бит (система 1-байтовых символов)
|
||||
bne v1,zero,MyPrintLineRoutine ; Если установлен - используем кастомную систему
|
||||
clear v1
|
||||
j PrintBigDMAText ; Иначе - оригинальная система печати
|
||||
nop
|
||||
|
||||
; ===== КАСТОМНАЯ СИСТЕМА ПЕЧАТИ =====
|
||||
MyPrintLineRoutine:
|
||||
addiu sp,sp,-0x50 ; Сохраняем контекст
|
||||
sw s4,0x38(sp)
|
||||
move s4,r4 ; s4 = адрес текста для чтения
|
||||
sw s0,0x28(sp)
|
||||
move s0,r5 ; s0 = параметр X
|
||||
sw s1,0x2c(sp)
|
||||
move s1,r6 ; s1 = параметр Y
|
||||
sw s3,0x34(sp)
|
||||
|
||||
; ===== ИНИЦИАЛИЗАЦИЯ ПАРАМЕТРОВ ТЕКСТА =====
|
||||
andi v0,v0,0xff
|
||||
addiu s4,s4,0x2 ; Сдвигаем указатель текста на +2 байта
|
||||
|
||||
lui s3,MyAddr
|
||||
sw v0,-0x10(s3) ; Сохраняем счётчик байтов @ 8008fff0
|
||||
sh zero,-0xE(s3) ; Очищаем счётчик символов @ 8008fff2
|
||||
|
||||
; ===== ИНИЦИАЛИЗАЦИЯ DMA ЦЕПОЧЕК =====
|
||||
lui s3,0x1f80
|
||||
ori s3,s3,0x3d0 ; s3 = 1f8003d0 - команда копирования спрайта в scratch
|
||||
|
||||
lui t0,0xff
|
||||
ori t0,t0,0xffff ; t0 = 00FFFFFF (маска)
|
||||
|
||||
andi r4,r7,0xff ; Режим текста (цвет и тень)
|
||||
lui r7, 0x8008 ; r7 = 80080000
|
||||
lui r6, 0xff00 ; r6 = FF000000 (маска)
|
||||
|
||||
; ЗАГРУЗКА ЦЕПОЧКИ ФОРМИРОВАНИЯ СИМВОЛОВ
|
||||
addiu t1,r7,-0x31a8 ; t1 = адрес цепочки формирования (8007ce58)
|
||||
lw v1, -0x31a8(r7) ; v1 = текущая свободная цепочка формирования
|
||||
lbu r5,0x60(sp) ; Флаг тени из стека
|
||||
|
||||
and r6,v1,r6 ; r6 = старшие байты цепочки (FFxxxxxx)
|
||||
andi r5,r5,0xff ; Очищаем режим текста
|
||||
and v1,v1,t0 ; v1 = младшие байты цепочки (00xxxxxx)
|
||||
or s5,v1,v0 ; s5 = адрес текущей цепочки формирования (80xxxxxx)
|
||||
|
||||
; ОБНОВЛЕНИЕ СЧЁТЧИКА И ЦЕПОЧКИ
|
||||
lw v0,0x4(t1) ; Счётчик команд DMA
|
||||
lw v1,0x0(s5) ; Следующая свободная цепочка
|
||||
addiu v0,v0,-0x1 ; Уменьшаем счётчик
|
||||
and v1,v1,t0 ; Обрезаем старший байт
|
||||
or r6,r6,v1 ; Объединяем с старшими байтами
|
||||
sw v0,0x4(t1) ; Сохраняем счётчик
|
||||
jal storeColor
|
||||
sw r6,-0x31a8(r7) ; Сохраняем обновлённую цепочку
|
||||
|
||||
; ===== ИНИЦИАЛИЗАЦИЯ ЦЕПОЧКИ КОПИРОВАНИЯ =====
|
||||
move r4,s5 ; Адрес текущей цепочки
|
||||
sll r5,s0,0x10 ; Координата X
|
||||
sra r5,r5,0x10
|
||||
sll r6,s1,0x10 ; Координата Y
|
||||
jal initCopyCharChain ; Инициализация цепочки копирования
|
||||
sra r6,r6,0x10
|
||||
|
||||
; ===== НАСТРОЙКА SCRATCH PAD ДЛЯ DMA =====
|
||||
lui r6,0x1f80
|
||||
ori r6,r6,0x348 ; r6 = 1f800348 - начало данных символа в scratch
|
||||
|
||||
; ... (паттерны 4-bit и инициализация пропущены для краткости)
|
||||
|
||||
; ===== ОСНОВНОЙ ЦИКЛ ОБРАБОТКИ СИМВОЛОВ =====
|
||||
NextChar:
|
||||
addiu r4,r4,-0x20 ; Сдвигаем непечатаемые символы
|
||||
|
||||
; ОБРАБОТКА ПРОБЕЛОВ
|
||||
bne r4,zero,SpaceCheckBranch
|
||||
nop
|
||||
|
||||
lui t2,MyAddr
|
||||
lh v0,-0xE(t2) ; Текущий счётчик символов
|
||||
nop
|
||||
lh t3,-0x10(t2) ; Общий счётчик символов
|
||||
addiu v0,v0,1
|
||||
beq v0,t3,SpaceCheckBranch ; Если последний символ - не обрабатываем пробел
|
||||
nop
|
||||
|
||||
; ПРОБЕЛ - только сдвигаем позицию
|
||||
sh v0,-0xE(t2) ; Обновляем счётчик
|
||||
nop
|
||||
lbu r4,0x0(s4) ; Следующий символ
|
||||
|
||||
; СДВИГ ПОЗИЦИИ X
|
||||
lhu v0,0xa8(gp) ; Начальный X
|
||||
lhu v1,0x8(s3) ; Текущий X в scratch
|
||||
addiu v0,v0,0x6 ; Сдвиг на 6 пикселей
|
||||
addu v1,v1,v0 ; Новый X
|
||||
sh v1,0x8(s3) ; Обновляем в scratch DMA
|
||||
|
||||
j NextChar
|
||||
addiu s4,s4,0x1 ; Следующий байт текста
|
||||
|
||||
; ===== ОБРАБОТКА НЕ-ПРОБЕЛЬНЫХ СИМВОЛОВ =====
|
||||
SpaceCheckBranch:
|
||||
jal makeCharPixelsCustom ; СОЗДАЁМ ПИКСЕЛИ СИМВОЛА В SCRATCH
|
||||
clear s2
|
||||
|
||||
; ===== ФОРМИРОВАНИЕ КОМАНДЫ КОПИРОВАНИЯ SPRITE =====
|
||||
PageLoop:
|
||||
; ЗАГРУЗКА ЦЕПОЧКИ КОПИРОВАНИЯ SPRITE
|
||||
lw v0,-0x3198(s6) ; Адрес свободной цепочки копирования (8007ce68)
|
||||
nop
|
||||
and r4,v0,t2 ; Старшие байты
|
||||
and v0,v0,s0 ; Младшие байты
|
||||
or r5,v0,s1 ; r5 = полный адрес цепочки (80xxxxxx)
|
||||
|
||||
; ОБНОВЛЕНИЕ СЧЁТЧИКА КОПИРОВАНИЯ
|
||||
lw v0,0x4(s7) ; Счётчик команд копирования
|
||||
lw v1,0x0(r5) ; Следующая свободная цепочка
|
||||
addiu v0,v0,-0x1 ; Уменьшаем счётчик
|
||||
and v1,v1,s0 ; Обрезаем старший байт
|
||||
or r4,r4,v1 ; Объединяем
|
||||
sw v0,0x4(s7) ; Сохраняем счётчик
|
||||
sw r4,-0x3198(s6) ; Сохраняем обновлённую цепочку
|
||||
|
||||
; ===== КОПИРОВАНИЕ ИЗ SCRATCH В ЦЕПОЧКУ =====
|
||||
CopyCmdFromScratch:
|
||||
; Копируем команду DMA из scratch в цепочку
|
||||
lw t9,0x0(s3) ; Количество команд (04000000)
|
||||
lw t7,0x4(s3) ; Команда копирования спрайта (64808080)
|
||||
lw t8,0x8(s3) ; Координаты XY на экране
|
||||
lw t5,0xc(s3) ; CLUT и координаты текстуры
|
||||
|
||||
; СОХРАНЯЕМ В ЦЕПОЧКУ КОПИРОВАНИЯ
|
||||
sw t9,0x0(r5) ;
|
||||
sw t7,0x4(r5)
|
||||
sw t8,0x8(r5)
|
||||
sw t5,0xc(r5)
|
||||
lw t9,0x10(s3) ; Размер спрайта после копирования
|
||||
nop
|
||||
sw t9,0x10(r5) ; Последняя команда
|
||||
|
||||
; ===== СВЯЗЫВАНИЕ ЦЕПОЧЕК =====
|
||||
; СВЯЗЬ: ЦЕПОЧКА ФОРМИРОВАНИЯ → ЦЕПОЧКА КОПИРОВАНИЯ
|
||||
lw v1,0x18(t1) ; Текущая цепочка формирования
|
||||
lw v0,0x0(r5) ; Текущая команда копирования
|
||||
lw v1,0x0(v1) ; Следующая цепочка формирования
|
||||
and v0,v0,t2 ; Маска старших байтов
|
||||
and v1,v1,s0 ; Маска младших байтов
|
||||
or v0,v0,v1 ; Объединяем
|
||||
sw v0,0x0(r5) ; Обновляем команду
|
||||
|
||||
; ОБНОВЛЯЕМ ССЫЛКУ В ЦЕПОЧКЕ ФОРМИРОВАНИЯ
|
||||
lw r4,0x18(t1) ; Адрес цепочки формирования
|
||||
nop
|
||||
lw v0,0x0(r4) ; Текущая команда формирования
|
||||
and v1,r5,s0 ; Адрес цепочки копирования
|
||||
and v0,v0,t2 ; Маска старших байтов
|
||||
or v0,v0,v1 ; Объединяем
|
||||
sw v0,0x0(r4) ; Сохраняем обновлённую ссылку
|
||||
|
||||
sw r5,0x18(t1) ; Сохраняем текущую цепочку копирования
|
||||
|
||||
; ===== ПРОВЕРКА ПЕРВОГО СИМВОЛА =====
|
||||
lhu v0,0x4(t6) ; Счётчик символов
|
||||
nop
|
||||
bne v0,zero,NotFirstChar ; Если не первый символ - пропускаем
|
||||
nop
|
||||
|
||||
; ИНИЦИАЛИЗАЦИЯ ДЛЯ ПЕРВОГО СИМВОЛА
|
||||
sw r5,0x28(t1) ; Устанавливаем первую цепочку символа
|
||||
sw t8,0xc(t6) ; Сохраняем координаты в параметрах
|
||||
|
||||
NotFirstChar:
|
||||
|
||||
; ===== КОПИРОВАНИЕ ДАННЫХ СИМВОЛА ИЗ SCRATCH =====
|
||||
lui r5,0x1f80
|
||||
ori r5,r5,0x348 ; r5 = данные символа в scratch
|
||||
|
||||
lw v0,-0x31a8(t3) ; Следующая свободная цепочка формирования
|
||||
and r4,v0,t2 ; Старшие байты
|
||||
and v0,v0,s0 ; Младшие байты
|
||||
or r7,v0,s1 ; r7 = адрес цепочки (80xxxxxx)
|
||||
move r6,r7 ; r6 = адрес назначения
|
||||
|
||||
; ... (копирование данных пропущено для краткости)
|
||||
|
||||
; ===== СВЯЗЫВАНИЕ: ДАННЫЕ СИМВОЛА → КОМАНДА КОПИРОВАНИЯ =====
|
||||
lw v1,0x18(t1) ; Текущая команда копирования
|
||||
lw v0,0x0(r7) ; Текущие данные символа
|
||||
lw v1,0x0(v1) ; Следующая команда копирования
|
||||
and v0,v0,t2 ; Маска старших байтов
|
||||
and v1,v1,s0 ; Маска младших байтов
|
||||
or v0,v0,v1 ; Объединяем
|
||||
sw v0,0x0(r7) ; Обновляем данные символа
|
||||
|
||||
; ОБНОВЛЯЕМ ССЫЛКУ В КОМАНДЕ КОПИРОВАНИЯ
|
||||
lw r4,0x18(t1) ; Адрес команды копирования
|
||||
nop
|
||||
lw v0,0x0(r4) ; Текущая команда
|
||||
and v1,r7,s0 ; Адрес данных символа
|
||||
and v0,v0,t2 ; Маска старших байтов
|
||||
or v0,v0,v1 ; Объединяем
|
||||
sw v0,0x0(r4) ; Сохраняем обновлённую ссылку
|
||||
|
||||
sw r7,0x18(t1) ; Сохраняем текущие данные символа
|
||||
|
||||
; ===== СДВИГ ПОЗИЦИИ ДЛЯ СЛЕДУЮЩЕГО СИМВОЛА =====
|
||||
lhu v0,0xa8(gp) ; Начальный X
|
||||
lhu v1,0x8(s3) ; Текущий X
|
||||
addiu v0,v0,0x6 ; Сдвиг на 6 пикселей
|
||||
addu v1,v1,v0 ; Новый X
|
||||
sh v1,0x8(s3) ; Обновляем
|
||||
|
||||
; ===== ПРОВЕРКА ЗАВЕРШЕНИЯ ТЕКСТА =====
|
||||
lhu v0,0x4(s5) ; Счётчик символов DMA
|
||||
lui t9,MyAddr
|
||||
addiu v0,v0,0x1
|
||||
sh v0,0x4(s5) ; Сохраняем
|
||||
|
||||
; ПРОВЕРКА ПЕРЕПОЛНЕНИЯ DMA
|
||||
lw v0,0x4(s7) ; Текущий счётчик
|
||||
move v1,5 ; Минимальный лимит
|
||||
sltu v0,v0,v1 ; Проверяем переполнение
|
||||
bne v0,zero,TextEnd ; Если переполнение - завершаем
|
||||
|
||||
; ПРОВЕРКА КОНЦА СТРОКИ
|
||||
lui t3,MyAddr
|
||||
lhu v0,-0xE(t3) ; Текущий символ
|
||||
lhu v1,-0x10(t3) ; Общее количество символов
|
||||
addiu v0,v0,0x1
|
||||
lbu r4,0x0(s4) ; Следующий символ
|
||||
sh v0,-0xE(t3) ; Сохраняем счётчик
|
||||
addiu s4,s4,0x1 ; Сдвигаем указатель
|
||||
|
||||
bne v0,v1,NextChar ; Если не конец - продолжаем
|
||||
nop
|
||||
|
||||
; ===== ЗАВЕРШЕНИЕ ОБРАБОТКИ ТЕКСТА =====
|
||||
TextEnd:
|
||||
; ... (восстановление контекста и завершение)
|
||||
Reference in New Issue
Block a user