From 5b02a99eb465467fd09705b00466698009bb547f Mon Sep 17 00:00:00 2001 From: Kevin Bracey <kbracey@gitlab.riscosopen.org> Date: Thu, 1 May 1997 08:09:35 +0000 Subject: [PATCH] RISC OS 3.71 version taken --- TestSrc/Begin | 124 ++++++++++++++-- TestSrc/Ioc | 11 +- TestSrc/Mem1IOMD | 20 ++- TestSrc/Mem2 | 62 ++++++-- TestSrc/Mem3 | 4 + Version | 6 +- s/AMBControl/memmap | 48 +++++- s/ARM600 | 352 +++++++++++++++++++++++++++++++++++++++----- s/ChangeDyn | 9 ++ s/Copro15ops | 172 +++++++++++++++++++++- s/GetAll | 40 ++++- s/KbdResPC | 14 +- s/Kernel | 7 + s/Middle | 27 ++-- s/NewReset | 93 +++++++++++- s/PMF/osinit | 14 +- s/vdu/vdudriver | 23 ++- 17 files changed, 894 insertions(+), 132 deletions(-) diff --git a/TestSrc/Begin b/TestSrc/Begin index 7c1dd7b6..1cc7ca4c 100644 --- a/TestSrc/Begin +++ b/TestSrc/Begin @@ -284,6 +284,20 @@ ts_ROM_bvectors SetMode SVC32_mode,$tmp MEND + [ StrongARM_POST +; ensure 26-bit mode for StrongARM or ARM 8 (since there is no 26 bit configuration) + MACRO + Ensure26bit_ARM8A $tmp + ARM_read_ID $tmp + AND $tmp, $tmp, #&F000 + CMP $tmp, #&A000 + CMPNE $tmp, #&8000 + mrs EQ, $tmp, CPSR_all + BICEQ $tmp, $tmp, #&10 + msr EQ, CPSR_all, $tmp + MEND + ] + ; ; Define an area of storage with the required set of data bus patterns ; These are used both for testing the complete width of the data bus @@ -481,8 +495,13 @@ ts_User_startup ROUT ADDS r1,r1,r1 ; then shift it into carry BCC ts_Self_test_end ; POR bit clear - do soft reset. -; it's a power-on reset, so assume we can't be in 32-bit mode +; it's a power-on reset, so assume we can't be in 32-bit mode for ARM 6/7 + [ StrongARM_POST + ; make sure we are in 26-bit mode (ARM 6/7 reset in 26-bit config) + ; note that MOV_fiq macro assumes 26-bit, so must sort this now + Ensure26bit_ARM8A r0 + ] MOV_fiq r12_fiq, #R_HARD B ts_Self_test_startup | @@ -501,6 +520,11 @@ ts_User_startup ROUT ts_Forced_startup ROUT + [ StrongARM_POST + ; make sure we are in 26-bit mode (ARM 6/7 reset in 26-bit config) + ; note that MOV_fiq macro assumes 26-bit, so must sort this now + Ensure26bit_ARM8A r0 + ] MOV_fiq r12_fiq, #R_TESTED B ts_Self_test_startup @@ -508,6 +532,11 @@ ts_Forced_startup ROUT ts_Dealer_startup ROUT + [ StrongARM_POST + ; make sure we are in 26-bit mode (ARM 6/7 reset in 26-bit config) + ; note that MOV_fiq macro assumes 26-bit, so must sort this now + Ensure26bit_ARM8A r4 + ] MOV_fiq r12_fiq, #R_EXTERN LDR r4,%FT02 ; make a pointer to signon string @@ -538,10 +567,17 @@ ts_Self_test_startup ROUT MOV r2, #IOMD_Base LDRB r0, [r2, #IOMD_ID0] - CMP r0, #&98 + CMP r0, #&E7 LDRB r0, [r2, #IOMD_ID1] - CMPEQ r0, #&5B - BNE %FT10 + CMPEQ r0, #&D4 + BEQ %FT10 + + [ RO371Timings + + MOV r0, #0 ;Calling from POST + BL TimeCPU ;just sets things according to assumed bus speeds for each IOMD id, in this case + + | ; else if not RO371Timings ; ; PSwindell wants all prescalers set to divide by 1 @@ -557,6 +593,7 @@ ts_Self_test_startup ROUT ; LDRB r1, [r2, #IOMD_ROMCR0] AND r1, r1, #&40 ; clear all but 16-bit mode bit + [ :LNOT: AutoSpeedROMS [ NormalSpeedROMS ;Normal code @@ -570,12 +607,16 @@ ts_Self_test_startup ROUT ! 0, "*** WARNING *** Slow ROM version ment for PSwindell" ] + STRB r1, [r2, #IOMD_ROMCR0] STRB r1, [r2, #IOMD_ROMCR1] ; and do the same for extension ROMs (just in case) | MOV r0, #0 ;Don't muck with the CPU coprocessor regs BL TimeCPU ;This times the memory bus & sets the ROM speed accordingly ] + + ] ;RO371Timings conditional + ; 10 ] @@ -609,15 +650,27 @@ ts_InitVIDC STRNE r0, [r1] BNE %BT10 - [ StrongARM - ;just too horrible to fix POST for StrongARM (Architecture 4) at the moment - ARM_read_ID r0 - AND r0,r0,#&F000 - CMP r0,#&A000 ;if we are a StrongARM... - LDREQ r0,=C_WARMSTART ;the colour that indicates no POST performed - STREQ r0,[r1] - BEQ ts_Hardstart ;RISC OS - right now! + [ :LNOT: StrongARM_POST + ;skip POST for StrongARM or ARM8 + ARM_read_ID r0 + AND r0,r0,#&F000 + CMP r0,#&A000 ;if we are a StrongARM... + CMPNE r0,#&8000 ;or an ARM8... + LDREQ r0,=C_WARMSTART ;the colour that indicates no POST performed + STREQ r0,[r1] + BEQ ts_Hardstart ;RISC OS - right now! + ] + + [ ARM810support :LAND: (:LNOT: ARM810_POST) + ;just too horrible to fix POST for ARM 8 at the moment + ARM_read_ID r0 + AND r0,r0,#&F000 + CMP r0,#&8000 ;if we are an ARM 8 + LDREQ r0,=C_WARMSTART ;the colour that indicates no POST performed + STREQ r0,[r1] + BEQ ts_Hardstart ;RISC OS - right now! ] + LDR r0,=C_ARMOK ; set initial screen colour STR r0, [r1] @@ -1162,6 +1215,27 @@ ts_CAMtest ; ts_restore_physical + + [ StrongARM_POST + ;make sure ARM810 cache or StrongARM data cache is cleaned/flushed, because we are going to remap + ARM_read_ID r5 + AND r5,r5,#&F000 + CMP r5,#&8000 + BNE %FT22 +;ARM810 +;;; ARM8_cleanflush_IDC r5 ;not implemented yet + B %FT24 +22 + CMP r5,#&A000 + BNE %FT24 +;StrongARM +;tricky...we'll read 16k of data in current ROM space, to act as clean and flush of current data + MOV r3,pc + BIC r3,r3,#31 ;32 byte aligned + ARMA_clean_DC r3,r5,r7 +24 + ] ;StrongARM_POST + MOV r5, pc ; obtain current address SUB r5, r5,#PhysSpace ; adjust to point to unmapped version MOV r5, r5, LSR #20 ; divide by 1MB @@ -1174,8 +1248,20 @@ ts_restore_physical ADD r3, r3, #DRAMOffset_L1PT STR r7, [r3, r5, LSL #2] ; store replacement entry in L1 (not U,C or B) + [ StrongARM_POST + ;flush cache if ARM 6/7 (ARM 8,StrongARM already sorted, above) + ;flush TLB(s) + ARM_read_ID r4 + AND r4,r4,#&F000 + CMP r4,#&8000 ;ARM 8? + CMPNE r4,#&A000 ;or StrongARM? + MCRNE ARM_config_cp,0,R0,ARM67_cacheflush_reg,C0,0 ;flush 6/7 cache + MCRNE ARM_config_cp,0,R0,ARM67_TLBflush_reg,C0,0 ;flush 6/7 TLB + MCREQ ARM_config_cp,0,R0,ARM8A_TLB_reg,C7,0 ;flush 8/StrongARM TLB(s) + | SetCop r7, CR_IDCFlush ; flush cache + TLB just in case SetCop r7, CR_TLBFlush ; (data written is irrelevant) + ] ; The ROM should now be mapped at the present address less PhysSpace, which is where it ; would be if the MMU were turned off. @@ -1184,9 +1270,15 @@ ts_restore_physical SUB pc,pc,r4 NOP ; this instruction is skipped - MOV r7, #MMUC_D ; Now turn the MMU off +; now turn the MMU off, also ensures 26 bit mode, if ARM 6/7 (since P bit zero) + MOV r7, #MMUC_D SetCop r7, CR_Control + [ StrongARM_POST + Ensure26bit_ARM8A r7 + MOV r7, #MMUC_D ;avoid corrupting r7, just in case + ] + B ts_VIDCtest ; @@ -1223,10 +1315,10 @@ ts_VIDCtest MOV r3, #IOMD_Base LDRB r0, [r3, #IOMD_ID0] - CMP r0, #&98 + CMP r0, #&E7 LDRB r0, [r3, #IOMD_ID1] - CMPEQ r0, #&5B ; skip Virq test on Morris - BEQ %FT10 + CMPEQ r0, #&D4 ; skip Virq test on Morris + BNE %FT10 ] BL ts_VIDC_period diff --git a/TestSrc/Ioc b/TestSrc/Ioc index 1c37914c..e5a9ac07 100644 --- a/TestSrc/Ioc +++ b/TestSrc/Ioc @@ -3,7 +3,7 @@ TTL RISC OS 2+ POST IO controller ; ; This initial IOC test simply reports the content of the IRQ and FIRQ -; registers, to show any unexpected pending IRQs. +; registers, to show any unexpected pending IRQs. ; Certain of these should really be cleared, and the effect of an ; interrupt tested. ; @@ -77,8 +77,9 @@ ts_IOCstat LDR r1,=ts_IOMD_ID CMPS r0,r1 ; check IOMD identity [ MorrisSupport - LDRNE r1,=ts_IOMD_IDmorris ; allow for Morris variant - CMPNES r0,r1 +;; LDRNE r1,=ts_IOMD_IDmorris ; allow for Morris variant +;; CMPNES r0,r1 + CMPNE r0,r0 ;insist on not failing (allow 7500,7500FE...) ] MOV r0,r0,LSL #16 LDRB r1,[r3,#IOMD_VERSION] @@ -98,5 +99,5 @@ ts_IOCstat MOV pc,r14 ] - END - + END + diff --git a/TestSrc/Mem1IOMD b/TestSrc/Mem1IOMD index d44b2a96..10230ab0 100644 --- a/TestSrc/Mem1IOMD +++ b/TestSrc/Mem1IOMD @@ -42,10 +42,10 @@ ts_LineTest MOV r12, #IOMD_Base LDRB r0, [r12, #IOMD_ID0] - CMP r0, #&98 + CMP r0, #&E7 LDRB r0, [r12, #IOMD_ID1] - CMPEQ r0, #&5B - BNE ts_LineTestIOMD ; NOT MORRIS assume Medusa hardware + CMPEQ r0, #&D4 + BEQ ts_LineTestIOMD ; Medusa hardware, else assume Morris ; ; ts_LineTest for Morris @@ -54,9 +54,14 @@ ts_LineTest MOV r14, #IOMD_Base STRB r11, [r14, #IOMD_DRAMWID] - MOV r0,#MMUC_D ; enable 32-bit addressing of data +; enable 32-bit addressing of data, also forces 26 bit mode, if ARM 6/7 (since P bit zero) + MOV r0,#MMUC_D SetCop r0,CR_Control + [ StrongARM_POST + Ensure26bit_ARM8A r0 + ] + MOV r0,#0 MOV_fiq r9,r0 ; r9-fiq records low DRAM address for use elsewhere @@ -344,9 +349,14 @@ ts_LineTestIOMD MOV r14, #IOMD_Base STRB r11, [r14, #IOMD_DRAMCR] - MOV r0,#MMUC_D ; enable 32-bit addressing of data +; enable 32-bit addressing of data, also forces 26 bit mode, if ARM 6/7 (since P bit zero) + MOV r0,#MMUC_D SetCop r0,CR_Control + [ StrongARM_POST + Ensure26bit_ARM8A r10 + ] + MOV r10, #0 ; indicate no RAM found yet MOV r9, #IOMD_DRAMCR_DRAM_Small ; bit to OR into DRAMCR MOV r12, #DRAM0PhysRam diff --git a/TestSrc/Mem2 b/TestSrc/Mem2 index 89f5bc2d..09e9b97a 100644 --- a/TestSrc/Mem2 +++ b/TestSrc/Mem2 @@ -1,13 +1,13 @@ ;> MEM2C -; +; ; RISC OS 2+ BOOT TEST SOFTWARE ; MEMORY TEST 2 VERSION A. ; BRIAN RICE 30-10-89 ; 06-Apr-90 ArtG 0.1 Test variable memory size ; ; This file will perform a simple test on all DRAM. -; The test code for this test was taken from thhe A680 Quick memory -; test software. The software was copied straight but the number of times +; The test code for this test was taken from thhe A680 Quick memory +; test software. The software was copied straight but the number of times ; the test looped arround was cut down to two loops, because of time ; constraints when testing the memory. @@ -50,8 +50,8 @@ test_mem_quit ANDS r2,r2,#1 ; calculate expected data ADREQ r12,%20 ; and load suitable message ADRNE r12,%21 - MOVS r0,r0 ; with zero flag set for PASS. -10 + MOVS r0,r0 ; with zero flag set for PASS. +10 LDR pc,[r13,#Test_wks_return1] ; Fail messages indicate incorrect data read after WRote 0 or Wrote 1 @@ -84,7 +84,7 @@ test_mem_code STR r14, [r13, #Test_wks_return2] ; ; Copy the ram test code into low ram, modifying MOV instructions -; to MVN in accordance with the test pattern. +; to MVN in accordance with the test pattern. ; ADR r1, test_mem_template ADD r2, r13, #Test_code_off @@ -149,7 +149,7 @@ test_mem_code ; The following code is copied (and modified) into RAM for execution ; -test_mem_template +test_mem_template ROUT STR r0, test_mem_stadd ; save initial RAM address STR r13, test_mem_base ; save test area base address @@ -188,7 +188,7 @@ test_mem_template CMPEQ r11, #0 ; Converted to cmneq if bit = 1 CMPEQ r12, #0 ; Converted to cmneq if bit = 1 CMPEQ r13, #0 ; Converted to cmneq if bit = 1 -test_mem_chk +test_mem_chk BNE %F5 ; go report fault data CMP r0, r14 BLO %B1 ; else loop for next batch @@ -201,7 +201,7 @@ test_mem_chk ; the first failing address and data. ; Note that the test instructions are copied to %8 to permit individual ; execution, and %7 is overwritten with an instruction used to copy -; the failing data into r1. Change this code very carefully ! +; the failing data into r1. Change this code very carefully ! 5 LDR r14,%2 ; Obtain first test in the set @@ -218,8 +218,8 @@ test_mem_chk ; r14 => failing instruction LDR r1,[r14,#4]! ;fetch next instruction - AND r1,r1,#&f0000 ;make an instruction - MOV r1,r1,LSR #16 ;to copy the next register + AND r1,r1,#&f0000 ;make an instruction + MOV r1,r1,LSR #16 ;to copy the next register ORR r1,r1,#&E1000000 ;down to r1 ORR r1,r1,#&00A00000 ;e.g. CMPEQ r10,#0 ORR r1,r1,#&00001000 @@ -243,6 +243,27 @@ test_mem_template_end ROUT ts_remap_ttab + + [ StrongARM_POST + ;make sure ARM810 cache or StrongARM data cache is cleaned/flushed, because we are going to remap + ARM_read_ID r3 + AND r3,r3,#&F000 + CMP r3,#&8000 + BNE %FT22 +;ARM810 +;;; ARM8_cleanflush_IDC r3 ;not implemented yet + B %FT24 +22 + CMP r3,#&A000 + BNE %FT24 +;StrongARM +;tricky...we'll read 16k of data in current ROM space, to act as clean and flush of current data + MOV r3,pc + BIC r3,r3,#31 ;32 byte aligned + ARMA_clean_DC r3,r4,r5 +24 + ] ;StrongARM_POST + MOV r2,#FixedAreasL2Size ADD r0,r0,r2 ; point to locations in PhysSpace ADD r0,r0,#PhysSpace @@ -255,7 +276,7 @@ ts_remap_ttab SUBS r2,r2,#(8*4) BNE %BT10 - SUB r9,r1,r0 ; r9 = offset from original to copy + SUB r9,r1,r0 ; r9 = offset from original to copy ADD r0, r0, #DRAMOffset_L1PT-DRAMOffset_L2PT ; r0 -> copy of L1Phys SUB r10, r0, #PhysSpace ; keep real address of L1PT for MMU ADD r2,r0,#((1 :SHL: (32-20))*4) ; size of L1PT - 1 word per meg of memory @@ -265,14 +286,27 @@ ts_remap_ttab SUBEQ r3,r3,r9 ; adjust the page table base address STREQ r3,[r0,#-4] CMPS r0,r2 ; repeat for all the level 1 table - BNE %BT11 + BNE %BT11 SetCop r10, CR_TTabBase ; set up MMU pointer to L1 + + [ StrongARM_POST + ;flush cache if ARM 6/7 (ARM 8,StrongARM already sorted, above) + ;flush TLB(s) + ARM_read_ID r4 + AND r4,r4,#&F000 + CMP r4,#&8000 ;ARM 8? + CMPNE r4,#&A000 ;or StrongARM? + MCRNE ARM_config_cp,0,R0,ARM67_cacheflush_reg,C0,0 ;flush 6/7 cache + MCRNE ARM_config_cp,0,R0,ARM67_TLBflush_reg,C0,0 ;flush 6/7 TLB + MCREQ ARM_config_cp,0,R0,ARM8A_TLB_reg,C7,0 ;flush 8/StrongARM TLB(s) + | SetCop r0, CR_IDCFlush ; flush cache + TLB just in case SetCop r0, CR_TLBFlush ; (data written is irrelevant) + ] MOV pc,r14 END - + diff --git a/TestSrc/Mem3 b/TestSrc/Mem3 index 1313275f..482c5fad 100644 --- a/TestSrc/Mem3 +++ b/TestSrc/Mem3 @@ -36,6 +36,10 @@ ts_CRCsize * (2 * 4) ts_ROM_checksum +;StrongARM_POST issue: +;ARM810 - this will probably go bang! because ARM810 aborts if the processor +; vectors (00 - 1C) are read in 26-bit mode + MOV r1, #&00 ; initialise accumulator LDR r0, =PhysROM ; initialise pointer LDR r2, [r0, #ts_ROMSIZE] ; initialise endstop diff --git a/Version b/Version index 13586c92..fc4ea6b7 100644 --- a/Version +++ b/Version @@ -4,8 +4,8 @@ GBLS VString GBLS Date -Version SETA 370 -VString SETS "3.70" -Date SETS "30 Jul 1996" +Version SETA 371 +VString SETS "3.71" +Date SETS "19 Feb 1997" END diff --git a/s/AMBControl/memmap b/s/AMBControl/memmap index 7a4067de..95c5ae3d 100644 --- a/s/AMBControl/memmap +++ b/s/AMBControl/memmap @@ -235,6 +235,33 @@ AMB_movepagesout_L2PT ROUT ARMA_drain_WB EQ ;because L2PT area for AppSpace will be bufferable Pull "r0-r8,pc" + [ ARM810support + ;Previously supported ARMs all tolerate cache (clean and) flush _after_ + ;remapping - ARMs 6,7 because there is no clean, StrongARM because the cache + ;writebacks use physical address. + ;ARM810 does not support clean of writeback cache after remapping, since + ;writebacks use virtual address. Rather than completely restructure code, + ;this routine is called before remapping where necessary, and cleans/flushes + ;if it finds we are running on ARM 810. + ; + ;corrupts r3 + ; +AMB_cachecleanflush_ifARM810 + ARM_read_ID r3 + AND r3,r3,#&F000 + CMP r3,#&8000 + MOVNE pc,lr ;not ARM8 + [ ARM810cleanflushbroken + Push "lr" + ARM8_cleanflush_IDC r3,lr + Pull "pc" + | + ARM8_cleanflush_IDC r3 + MOV pc,lr + ] + + ] ;ARM810support + ;************************************************************************** ; AMB_SetMemMapEntries: ; @@ -285,6 +312,9 @@ AMB_SetMemMapEntries ROUT ;could be an optimise here if source is FreePool and we know that FreePool ;has not been used - ie. no need to clean/flush cache(s) - not done yet (requires ;sorting of Wimp_ClaimFreeMemory) + [ ARM810support + BL AMB_cachecleanflush_ifARM810 + ] MOV r3,r5 BL AMB_movepagesout_L2PT BL AMB_movepagesin_L2PT @@ -293,6 +323,9 @@ AMB_SetMemMapEntries ROUT ;all pages sourced from same old logical page 'nowhere' AMB_smme_mapin + [ ARM810support + BL AMB_cachecleanflush_ifARM810 + ] MOV r3,r5 BL AMB_movepagesin_L2PT BL AMB_movepagesin_CAM @@ -303,14 +336,22 @@ AMB_smme_mapin ;all pages destined for same new logical page 'nowhere' AMB_smme_mapout + [ ARM810support + BL AMB_cachecleanflush_ifARM810 + ] LDR r3,=DuffEntry BL AMB_movepagesout_L2PT BL AMB_movepagesout_CAM -;(clean and) flush cache(s) appropriately +;(clean and) flush cache(s) appropriately, then flush TLB(s) AMB_smme_cachecleanflush ARM_read_ID r0 AND r0,r0,#&F000 + [ ARM810support + CMP r0,#&8000 ;cache clean/flush done before remapping if ARM810 + ARM8_flush_TLB EQ + Pull "r0-r4,r7-r11, pc",EQ + ] CMP r0,#&A000 ARM67_flush_cache NE ARM67_flush_TLB NE @@ -389,11 +430,16 @@ AMB_smme_StrongARM_flushrange Pull "r0-r4,r7-r11, pc" AMB_smme_TLBflush + [ ARM810support + ;there is a general macro, should have used this before anyway + ARM_flush_TLB r0 + | ARM_read_ID r0 AND r0,r0,#&F000 CMP r0,#&A000 ARM67_flush_TLB NE ARMA_flush_TLBs EQ + ] AMB_smme_exit Pull "r0-r4,r7-r11, pc" diff --git a/s/ARM600 b/s/ARM600 index a09307f0..8639cb3c 100644 --- a/s/ARM600 +++ b/s/ARM600 @@ -27,9 +27,9 @@ DebugAborts SETL {FALSE} ; Created by TMD 15-Jul-92 ; Comments updated by TMD 04-Aug-93 -;now effectively codes for ARM 6 onwards (6,7,8,A, where A = StrongARM) - MJS, 24-01-96 - -;but ARM8 not done yet! (29-01-96) +;24-01-96 MJS now effectively codes for ARM 6 onwards (6,7,8,A, where A = StrongARM) +; but ARM8 not properly supported (not needed for RO 3.70) +;07-10-96 MJS proper support for ARM810 added ; Workspace needed for ARM600 work is as follows: @@ -113,8 +113,13 @@ ARM_default_MMU_CR_table ;ARM 7 FRSB1DPWCAM DCD 2_0011001111101 ; + [ ARM810bpbroken ;branch prediction broken! +;ARM 8 Z0RSB111WCAM + DCD 2_0001001111101 + | ;ARM 8 Z0RSB111WCAM DCD 2_0101001111101 + ] ; ;ARM 9 ?? DCD 0 @@ -434,18 +439,44 @@ BangL2PT ; internal entry point used only | TST r11, #DynAreaFlags_DoublyMapped BNE BangL2PT_sledgehammer ;if doubly mapped, don't try to be clever + ] + [ ARM810support + ;if we are mapping out a cacheable page on an ARM810, must clean+flush cache _before_ + ;remapping, since ARM810 relies on virtual addresses for writebacks + ARM_read_ID r4 + AND r4,r4,#&F000 ;ARM ID nibble now in r4 + CMP r0,#0 ;EQ if map out + TSTEQ r11,#DynAreaFlags_NotCacheable ;EQ if also cacheable + CMPEQ r4,#&8000 ;EQ if also ARM 8 + BNE BangL2PT_noARM810flush + [ ARM810cleanflushbroken + ARM8_cleanflush_IDC r6,r4 + MOV r4,#&8000 + | + ARM8_cleanflush_IDC r6 + ] +BangL2PT_noARM810flush ] STR r0, [r1, r3, LSR #10] ;update L2PT + [ :LNOT: ARM810support ARM_read_ID r4 AND r4,r4,#&F000 ;ARM ID nibble in r4 + ] CMP r0,#0 BEQ BangL2PT_mapout ;the update is a map out => cache(s) may need clean/flush ;else update is a map in (and nothing should be there at the moment) => no cache worries CMP r4,#&A000 BEQ BangL2PT_mapin_StrongARM + [ ARM810support + CMP r4,#&8000 + ARM8_flush_TLBentry r3,EQ ;flush TLB entry for this page, ARM 8 + ARM67_flush_TLBentry r3,NE ;flush TLB entry for this page, ARM 6,7 + MOV pc,lr + | ;else assume ARM 6,7 ARM67_flush_TLBentry r3 ;flush TLB entry for this page MOV pc,lr + ] BangL2PT_mapin_StrongARM ARMA_drain_WB ;in case L2PT entry itself is in a bufferable area @@ -460,6 +491,11 @@ BangL2PT_mapin_StrongARM BangL2PT_mapout CMP r4,#&A000 BEQ BangL2PT_mapout_StrongARM + [ ARM810support + CMP r4,#&8000 + ARM8_flush_TLBentry r3,EQ ;flush TLB entry for this page, ARM 8 + MOVEQ pc,lr ;ARM8 cache already flushed, if necessary + ] ;else assume ARM 6,7 TST r11,#DynAreaFlags_NotCacheable ARM67_flush_cache EQ ;flush instruction/data cache if necessary @@ -516,6 +552,20 @@ BangL2PT_mapout_StrongARM MOV pc,lr BangL2PT_sledgehammer + [ ARM810support + ;if necessary, clean+flush _before_ reamapping, since ARM810 writebacks use virtual addresses + ARM_read_ID r4 + AND r4,r4,#&F000 + CMP r4,#&8000 + TSTEQ r11,#DynAreaFlags_NotCacheable + BNE BangL2PT_sledge_noARM810flush + [ ARM810cleanflushbroken + ARM8_cleanflush_IDC r4,r6 + | + ARM8_cleanflush_IDC r4 + ] +BangL2PT_sledge_noARM810flush + ] BICS r4, r3, #(3 :SHL: 10) ; ensure going to be on word boundary [ {FALSE} ; this breaks too many things at the moment BICEQ r0, r0, #&30 ; if logical page zero, then make 1st 1K no user access @@ -535,6 +585,11 @@ BangL2PT_sledgehammer AND r4,r4,#&F000 CMP r4,#&A000 BEQ BangL2PT_sledgehammer_StrongARM + [ ARM810support + CMP r4,#&8000 + ARM8_flush_TLB EQ + MOVEQ pc, lr ;ARM8 cache already flushed if necessary + ] ;else assume ARM 6,7 TST r11,#DynAreaFlags_NotCacheable ARM67_flush_cache EQ @@ -664,7 +719,7 @@ ClearPhysRAM ROUT [ :LNOT: RunningOnEmul ;StrongARM - We will make the logical representation of physical space for RAM temporarily bufferable -; (on any ARM). This is harmless for ARM 6,7 but a big speed benefit for StrongARM (which +; (on any ARM). This is small boost for ARM 6,7,8 but a big speed benefit for StrongARM (which ; won't burst write in non bufferable areas). LDR r0, =L1PT @@ -675,6 +730,9 @@ ClearPhysRAM ROUT SUB r11,r11,#&100000 ; 1 Mb will be done on first L1PT update ORR r10, r10, #PhysSpace ; point to logical representation of physical space ADD r1,r0,r10,LSR #(20-2) ; L1PT address for same +;MJS bug fix (since 3.70) for memory fragments not necessarily 1Mb aligned (eg 2 Mb Kryten) + BIC r1,r1,#3 +; 04 LDR r2,[r1] ORR r2,r2,#4 ; bufferable bit @@ -750,6 +808,9 @@ ClearPhysRAM ROUT SUB r11,r11,#&100000 ; 1 Mb will be done on first L1PT update ORR r10, r10, #PhysSpace ; point to logical representation of physical space ADD r1,r0,r10,LSR #(20-2) ; L1PT address for same +;MJS bug fix (since 3.70) for memory fragments not necessarily 1Mb aligned (eg 2 Mb Kryten) + BIC r1,r1,#3 +; 34 LDR r2,[r1] BIC r2,r2,#4 ; bufferable bit @@ -853,16 +914,37 @@ InitMEMC ROUT STRB r12, [r12, #IOMD_DMAREQ] ; writes to DMAREQ are ignored LDRB r0, [r12, #IOMD_ID0] - CMP r0, #&98 + CMP r0, #&E7 LDRB r0, [r12, #IOMD_ID1] - CMPEQ r0, #&5B + CMPEQ r0, #&D4 ;MOVEQ r3, #xxxx - BNE MedusaInit ; NOT MORRIS assume Medusa hardware + BEQ MedusaInit ; Medusa, else assume Morris ; ; MORRIS contains IOMD equivalant circuitry. Due to lack of VRAM, presence of 16/32 bit support ; and a different ROM speed register, we program it slightly differently. ; + [ RO371Timings + ;IOMD_ID1 still in r0 - check for 7500FE + CMP r0, #&aa ; EQ if 7500FE => assume 64 MHz bus, EDO RAM + ; NE assume 7500 => assume 32 MHz bus +;7500FE +;set memory to 32MHz for early boot (avoid probs with POST and with power-on key detection) + MOVEQ r0, #&12 ; 5-3 cycle ROM access, Half speed (ie. 10-6) + STREQB r0, [r12, #IOMD_ROMCR0] + STREQB r0, [r12, #IOMD_ROMCR1] + MOVEQ r0, #&70 ; EDO RAM selected, 32 bit wide, conservative RAS,CAS timing + STREQB r0, [r12, #IOMD_DRAMWID] ; DRAM control reg. (more than just width on FE) + MOVEQ r0, #&04 ; clock dividers: /1 for CPU, /2 for memory, /2 for I/O + STREQB r0, [r12, #IOMD_CLKCTL] +;7500 + MOVNE r0, #&32 ; 5-3 cycle ROM access + STRNEB r0, [r12, #IOMD_ROMCR0] + STRNEB r0, [r12, #IOMD_ROMCR1] + MOVNE r0, #&07 ; clock dividers: /1 for I/O, /1 for CPU, /1 for memory + STRNEB r0, [r12, #IOMD_CLKCTL] + + | ;else if not RO371Timings ; ; PSwindell wants all prescalers set to divide by 1 ; @@ -892,8 +974,12 @@ InitMEMC ROUT ! 0, "*** WARNING *** Slow ROM version ment for PSwindell" ] ] + STRB r0, [r12, #IOMD_ROMCR0] STRB r0, [r12, #IOMD_ROMCR1] ; and do the same for extension ROMs (just in case) + + ] ;RO371Timings conditional + ; ; MORRIS doesn't support VRAM. Kryten has same DRAM speed as Medusa ; @@ -916,6 +1002,11 @@ InitMEMC ROUT MedusaInit ] + + [ RO371Timings + MOV r0, #&12 ; 5-3 cycle ROM access + | + [ Simulator MOV r0, #IOMD_ROMCR_62 + IOMD_ROMCR_BurstOff ; make faster for simulation (no point in burst mode, it's ; no faster than the fastest initial speed) @@ -937,6 +1028,9 @@ MedusaInit MOV r0, #IOMD_ROMCR_156 + IOMD_ROMCR_BurstOff ; initialise ROM speed to 156.25ns (changed from 187ns 21-Jan-94) ] ] + + ] ;RO371Timings conditional + STRB r0, [r12, #IOMD_ROMCR0] STRB r0, [r12, #IOMD_ROMCR1] ; and do the same for extension ROMs (just in case) @@ -1122,15 +1216,19 @@ MemSize ROUT [ MorrisSupport ; LDRB r0, [r12, #IOMD_ID0] - CMP r0, #&98 + CMP r0, #&E7 LDRB r0, [r12, #IOMD_ID1] - CMPEQ r0, #&5B + CMPEQ r0, #&D4 ;MOVEQ r3, #xxxx - BNE MemSizeIOMD ; NOT MORRIS assume Medusa hardware + BEQ MemSizeIOMD ; IOMD (Medusa), else assume Morris ; ; MemSize for Morris ; + [ RO371Timings + MOV r11, #&70 ;all 4 banks assumed 32 bit - EDO and timing bits set in case 7500FE (don't care bits otherwise) + | MOV r11, #IOMD_DRAMWID_DRAM_32bit * &0F ;set all 4 banks to be 32bit initially + ] MOV r14, #IOMD_Base STRB r11, [r14, #IOMD_DRAMWID] [ 1 = 0 @@ -1414,8 +1512,23 @@ MemSizeIOMD ORR r2,r2,#&1000 ;I cache bit is bit 12 ARM_write_control r2 ARMA_fastcoreclock - + [ ARM810fastclock + B MemSizeIOMD_not810 + ] MemSizeIOMD_notSA + [ ARM810fastclock + ;fast clock for ARM 810 now + ARM_read_ID r2 + AND r2,r2,#&F000 + CMP r2,#&8000 + BNE MemSizeIOMD_not810 + [ ARM810usePLL + ARM8_pll_fclk r2 + | + ARM8_refclk_fclk r2 + ] +MemSizeIOMD_not810 + ] MOV r2, #IOMD_VREFCR_VRAM_256Kx64 :OR: IOMD_VREFCR_REF_16 ; assume 2 banks of VRAM by default STRB r2, [r12, #IOMD_VREFCR] @@ -1862,8 +1975,12 @@ MemSizeDone ARM_flush_cacheandTLB r7 ; flush cache + TLB just in case ARM_number r2 ;should be 6,7,8 or &A + [ ARM810support + ;ARM810 has already had fast clock selected (MemSizeIOMD) - so has StrongARM, therefore code below removed + | CMP r2,#&A ARMA_fastcoreclock EQ ;otherwise StrongARM is going to have a limp wrist + ] SUB r2,r2,#6 ; r2 := 0..4 for ARM 6,7,8,(9),&A ADRL r7,ARM_default_MMU_CR_table LDR r7,[r7,r2,LSL #2] ;get appropriate default value for MMU control reg @@ -2100,15 +2217,78 @@ Page8K * &4 Page4K * &0 ; +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -; In r0=0 -> Coming from the Test routine, just go back! +; In r0=0 -> Coming from the Test routine - no fancy business! ; r1-r6 trashable -; r9 = Current MEMC CR (true MEMC value, not fudged to look like 4K page size) +; [[[ r9 = Current MEMC CR (true MEMC value, not fudged to look like 4K page size) ]]] -; Out r9 MEMC value with slowest ROM speed, correct pagesize +; Out [[[ r9 MEMC value with slowest ROM speed, correct pagesize ]]] ; r7 processor speed in kHz, bit 16 => can do STM to I/O (ie MEMC1a, MEMC2), bit 17 => MEMC2 ; This routine must work in 32-bit mode, and should not use any memory!!!! + [ RO371Timings + +TimeCPU ROUT ;does not actually measure anything - assumes timings (and EDO for 7500FE) according to IOMD id + + MOV r2, #IOC ; Address of the IO controller (IOMD) + + LDRB r7, [r2, #IOMD_ID0] ; Is + CMP r7, #&E7 ; It + LDRB r7, [r2, #IOMD_ID1] ; A + CMPEQ r7, #&D4 ; Risc PC ? + BEQ timecpuriscpc + CMP r7, #&AA ; assume 7500 or 7500FE + BEQ timecpu7500FE +;7500 then + MOV r7, #&32 ; 5-3 cycle ROM access + STRB r7, [r2, #IOMD_ROMCR0] + STRB r7, [r2, #IOMD_ROMCR1] + MOV r7, #&07 ; clock dividers: /1 for I/O, /1 for CPU, /1 for memory + STRB r7, [r2, #IOMD_CLKCTL] + LDR r7, =(1 :SHL: 16) :OR: 16000 ; assumed 16MHz RAM (32 MHz bus) + MOV pc, lr + +timecpu7500FE +;set memory to 32MHz for early boot (avoid probs with POST and with power-on key detection) + MOV r7, #&12 ; 5-3 cycle ROM access, half speed (ie. 10-6) + STRB r7, [r2, #IOMD_ROMCR0] + STRB r7, [r2, #IOMD_ROMCR1] + MOV r7, #&70 ; EDO RAM, 32 bit wide, conservative RAS and CAS timing + STRB r7, [r2, #IOMD_DRAMWID] ; DRAM control reg. (more than just width on FE) + MOV r7, #&04 ; clock dividers: /1 for CPU, /2 for memory, /2 for I/O + STRB r7, [r2, #IOMD_CLKCTL] + LDR r7, =(1 :SHL: 16) :OR: 32000 ; assumed 32MHz RAM (64 MHz bus), even though /2 at the moment + MOV pc, lr + +timecpuriscpc + MOV r7, #&12 ; 5-3 cycle ROM access + STR r7, [r2, #IOMD_ROMCR0] + STR r7, [r2, #IOMD_ROMCR1] + LDR r7, =(1 :SHL: 16) :OR: 16000 ; assumed 16MHz RAM (32 MHz bus) + MOV pc, lr + +;used by NewReset, after main kernel boot +;sets full 64MHz memory if on 7500FE +;preserves registers _and_ flags +; +finalmemoryspeed ROUT + Push "r0,lr" + MOV lr, #IOC + LDRB r0, [lr, #IOMD_ID0] ; Is + CMP r0, #&E7 ; It + LDRB r0, [lr, #IOMD_ID1] ; A + CMPEQ r0, #&D4 ; Risc PC ? + BEQ fmspeed_done + CMP r0, #&AA ; EQ if 7500FE + MOVEQ r0, #&80 + STREQB r0, [lr, #&CC] ; ASTCR register: set i/o asynchronous timing for fast memory clock + MOVEQ r0, #&06 ; clock dividers: /1 for CPU, /1 for memory, /2 for I/O + STREQB r0, [lr, #IOMD_CLKCTL] +fmspeed_done + Pull "r0,pc",,^ + + | ; else if not RO371Timings + ncpuloops * 1024 ; don't go longer than 4ms without refresh ! nmulloops * 128 @@ -2119,14 +2299,18 @@ TimeCPU ROUT ;ONLY WORKS FOR IOMD(L) machines - this shouldn't be a p [ {TRUE} ;don't do timing for Risc PC - LDRB r0, [r3, #IOMD_ID0] ; Is - CMP r0, #&98 ; It - LDRB r0, [r3, #IOMD_ID1] ; A - CMPEQ r0, #&5B ; Morris? - MOVNE r7,#&3e00 ;for non-Morris force 16MHz timing, assumed Risc PC - ORRNE r7,r7,#&80 - ORRNE r7,r7,#&10000 ;and note we're on IOMD - MOVNE pc,lr +; +;MJS bug fix (since 3.70) - setup r3 properly, and don't corrupt r0 you fool +; + MOV r3, #IOC ; Address of the IO controller + LDRB r7, [r3, #IOMD_ID0] ; Is + CMP r7, #&E7 ; It + LDRB r7, [r3, #IOMD_ID1] ; A + CMPEQ r7, #&D4 ; Medusa? + MOVEQ r7,#&3e00 ;for non-Morris force 16MHz timing, assumed Risc PC + ORREQ r7,r7,#&80 + ORREQ r7,r7,#&10000 ;and note we're on IOMD + MOVEQ pc,lr ] ; Time CPU/Memory speed @@ -2197,12 +2381,12 @@ TimeCPU ROUT ;ONLY WORKS FOR IOMD(L) machines - this shouldn't be a p [ MorrisSupport LDRB r0, [r3, #IOMD_ID0] ; Is - CMP r0, #&98 ; It + CMP r0, #&E7 ; It LDRB r0, [r3, #IOMD_ID1] ; A - CMPEQ r0, #&5B ; Morris? - LDREQ r0, =(4*15*500*ncpuloops) ;Morris timing values [reordered to prevent miscalculation + CMPEQ r0, #&D4 ; Medusa? + LDRNE r0, =(4*15*500*ncpuloops) ;Morris timing values [reordered to prevent miscalculation ;due to Aasm integering mid-calculation] (30720000) - LDRNE r0, =(4*(8*500/1000)*ncpuloops*1000) ;RiscPC/IOMD timing values (16384000) + LDREQ r0, =(4*(8*500/1000)*ncpuloops*1000) ;RiscPC/IOMD timing values (16384000) DivRem r7, r0, r2, r1 ; r2 preserved, R7=memory speed in kHz (MEMCLK/2) | LDR r0, =(4*(8*500/1000)*ncpuloops*1000) ;RiscPC/IOMD timing values (16384000) @@ -2257,6 +2441,8 @@ TimeCPU ROUT ;ONLY WORKS FOR IOMD(L) machines - this shouldn't be a p timecpu_sodthefancytimingstuff MOV pc, lr + ] ;RO371Timings conditional + MemClkTable DCB 2_100101 ; 0 cycles (set to min which is 2) DCB 2_100101 ; 1 cycle (set to min. which is 2) @@ -2346,22 +2532,39 @@ MMUControl_ModifyControl ROUT MOV r3, #0 LDR lr, [r3, #MMUControlSoftCopy] CMP r5,#&A + [ ARM810support + CMPNE r5,#8 ; can read control reg on ARM 810 too + ] ARM_read_control lr,EQ MOVEQ lr,lr,LSL #19 MOVEQ lr,lr,LSR #19 ; if StrongARM then we can read control reg. - trust this more than soft copy AND r2, r2, lr EOR r2, r2, r1 MOV r1, lr + [ ARM810support + CMP r5,#8 + BNE %FT03 + TST r2,#4 + ORRNE r2,r2,#&800 ; if ARM810 then Z bit (branch prediction) mirrors C bit + BICEQ r2,r2,#&800 +03 + ] CMP r5,#&A BNE %FT05 TST r2,#&4 ; if StrongARM, then I bit mirrors C bit ORRNE r2,r2,#&1000 BICEQ r2,r2,#&1000 05 + [ SAWBbroken :LOR: ARM810bpbroken + MOV lr,r2 [ SAWBbroken CMP r5,#&A - BICEQ lr,r2,#&0008 ;sorry guys, we can't use write buffer (safe-ish - safer would zap data cache bit as well) - MOVNE lr,r2 + BICEQ lr,lr,#&0008 ;sorry guys, we can't use write buffer (safe-ish - safer would zap data cache bit as well) + ] + [ ARM810bpbroken + CMP r5, #8 + BICEQ lr,lr,#&0800 ;sorry guys (or sorry Guy!), we can't use branch predictor + ] STR lr, [r3, #MMUControlSoftCopy] | STR r2, [r3, #MMUControlSoftCopy] @@ -2371,6 +2574,25 @@ MMUControl_ModifyControl ROUT BEQ %FT10 ARM_flush_cache r3 10 + [ ARM810support + CMP r5,#8 + BNE %FT12 + BIC lr, r1, r2 ; lr = bits going from 1->0 + TST lr, #MMUC_C ; if cache turning off then clean/flush cache first + BEQ %FT12 + [ ARM810cleanflushbroken + Push "r0,r1" + ARM8_cleanflush_IDC r0,r1 + ARM8_branchpredict_off r0 ; and turn off branch predict cleanly (must go off with cache) + Pull "r0,r1" + | + Push "r0" + ARM8_cleanflush_IDC r0 + ARM8_branchpredict_off r0 ; and turn off branch predict cleanly (must go off with cache) + Pull "r0" + ] +12 + ] CMP r5,#&A BNE %FT15 BIC lr, r1, r2 ; lr = bits going from 1->0 @@ -2384,10 +2606,16 @@ MMUControl_ModifyControl ROUT ARMA_clean_DC r0,r1,r2 Pull "r0-r2" 15 + [ SAWBbroken :LOR: ARM810bpbroken + MOV lr,r2 [ SAWBbroken CMP r5,#&A - BICEQ lr,r2,#&0008 ;sorry guys, we can't use write buffer - MOVNE lr,r2 + BICEQ lr,lr,#&0008 ;sorry guys, we can't use write buffer + ] + [ ARM810bpbroken + CMP r5,#8 + BICEQ lr,lr,#&0800 ;sorry guys, we can't use branch predictor + ] ARM_write_control lr | ARM_write_control r2 @@ -2405,6 +2633,9 @@ MMUC_modcon_readonly MOV r3, #0 LDR lr, [r3, #MMUControlSoftCopy] CMP r5,#&A + [ ARM810support + CMPNE r5,#8 ; can read control reg on ARM 810 too + ] ARM_read_control lr,EQ MOVEQ lr,lr,LSL #19 MOVEQ lr,lr,LSR #19 ; if StrongARM then we can read control reg. - trust this more than soft copy @@ -2421,8 +2652,24 @@ MMUControl_Flush BEQ MMUC_flush_flushT ;flush cache CMP r4,#&A000 - ARM67_flush_cache NE ;if not StrongARM, assume 6,7 + [ ARM810support + CMPNE r4,#&8000 + ] + ARM67_flush_cache NE ;if not StrongARM or ARM810, assume 6,7 BNE MMUC_flush_flushT + [ ARM810support + CMP r4,#&A000 + BEQ MMUC_flush_SA +;ARM810 then + [ ARM810cleanflushbroken + ARM8_cleanflush_IDC r1,r4 + MOV r4,#&8000 + | + ARM8_cleanflush_IDC r1 + ] + B MMUC_flush_flushT +MMUC_flush_SA + ] ;StrongARM then MOV r2,#ARMA_Cleaner_flipflop LDR r1,[r2] @@ -2434,9 +2681,14 @@ MMUControl_Flush MMUC_flush_flushT TST r0,#&40000000 BEQ MMUC_flush_done + [ ARM810support + ;there is a general macro, should have used this before anyway + ARM_flush_TLB r1 + | CMP r4,#&A000 ARMA_flush_TLBs EQ ARM67_flush_TLB NE ;if not StrongARM, assume 6,7 + ] MMUC_flush_done Pull "r0-r4,pc" @@ -2544,7 +2796,13 @@ DAbPreVeneer ROUT BIC r1, r1, #&1F ; knock out current mode bits ANDS r3, r0, #&1F ; extract old mode bits (and test for USR26_mode (=0)) TEQNE r3, #USR32_mode ; if usr26 or usr32 then use ^ to store registers + [ SASTMhatbroken + STMEQIA r2!,{r8-r12} + STMEQIA r2 ,{r13,r14}^ + SUBEQ r2, r2, #5*4 + | STMEQIA r2, {r8-r14}^ + ] BEQ %FT05 ORR r3, r3, r1 ; and put in user's @@ -2561,7 +2819,15 @@ DAbPreVeneer ROUT Push "r0, lr_svc" ; save SPSR_abort and lr_svc SUB sp_svc, sp_svc, #8*4 ; make room for r8_usr to r14_usr and PC + [ SASTMhatbroken + STMIA sp_svc!,{r8-r12} + STMIA sp_svc, {r13,r14}^ + NOP + STR pc, [sp_svc,#2*4] + SUB sp_svc, sp_svc, #5*4 ; save USR bank in case STM ^, and also so we can corrupt them + | STMIA sp_svc, {r8-r15}^ ; save USR bank in case STM ^, and also so we can corrupt them + ] SUB r11, r2, #8*4 ; r11 -> register bank STR r4, [sp_svc, #7*4] ; store aborter's PC in user register bank @@ -2914,9 +3180,6 @@ DAbPreVeneer ROUT ADD r2, r11, #8*4 ; point r2 at 2nd half of main register bank LDMIA sp, {r8-r14}^ ; reload user bank registers NOP ; don't access banked registers after LDM^ - [ SAUBxferbroken - NOP ; 'fraid so - ] ADD sp, sp, #8*4 ; junk user bank stack frame Pull "r0, lr" ; r0 = (possibly updated) SPSR_abort, restore lr_svc @@ -2929,9 +3192,6 @@ DAbPreVeneer ROUT TEQNE r7, #USR32_mode ; test also for USR32 LDMEQIA r2, {r8-r14}^ ; if user mode then just use ^ to reload registers NOP - [ SAUBxferbroken - NOP ; 'fraid so - ] BEQ %FT80 ORR r6, r6, #I32_bit ; use aborter's flags and mode but set I @@ -3075,6 +3335,7 @@ ProcessTransfer ENTRY "r1-r7,r12" 20 ;ARM 8 and StrongARM will abort for vector reads (as well as writes) in 26bit mode, so we must ;handle vector reads properly as well now +;In fact, StrongARM does not abort (optional in architecture 4), but ARM 8 does - MJS 08-10-96 [ {FALSE} TST r0, #1 ; if load from memory BNE %FT60 ; then skip @@ -3502,12 +3763,18 @@ dtgps_SAloop1 ARMA_drain_WB ; squeeze out those last drops MOV pc,lr +;ARM810 equiv of dtgps_SAcleanflush must clean/flush whole cache (cannot clean/flush by virtual address) +;and is shared with code in meminfo_flushplease, below meminfo_flushplease ; used by MemInfo ARM_read_ID r0 AND r0,r0,#&F000 CMP r0,#&A000 BEQ mifp_SA + [ ARM810support + CMP r0,#&8000 + BEQ mifp_810 + ] ;assume ARM 6 or 7 - simple! ARM67_flush_cache MOV pc,lr @@ -3520,7 +3787,16 @@ mifp_SA ARMA_clean_DC r0,r1,r2 ;clean/flush data cache wrt non-interrupt stuff (trashes r0,r1,r2) ARMA_flush_IC ;do *not* flush DC - may be interrupt stuff MOV pc,lr - + [ ARM810support +mifp_810 +dtgps_810cleanflush ;entry point also used during pages_unsafe/safe in ChangeDyn + [ ARM810cleanflushbroken + ARM8_cleanflush_IDC r0,r1 + | + ARM8_cleanflush_IDC r0 + ] + MOV pc,lr + ] ; DCB "GROT" ;spare words marker diff --git a/s/ChangeDyn b/s/ChangeDyn index 12c7e22d..9efb8fa3 100644 --- a/s/ChangeDyn +++ b/s/ChangeDyn @@ -3283,6 +3283,15 @@ DoTheGrowPagesSpecified BLEQ dtgps_SAcleanflush ] + [ ARM810support + ; + ; ARM810 has writeback cache too + ; + ARM_number r0 + CMP r0,#8 + BLEQ dtgps_810cleanflush + ] + ; now move the pages LDR r2, TotalAmount ; amount moving diff --git a/s/Copro15ops b/s/Copro15ops index 3a3428dc..e76fce00 100644 --- a/s/Copro15ops +++ b/s/Copro15ops @@ -18,7 +18,8 @@ ;and cater for ARM 6,7,8,A (A=StrongARM). ;Routines detect which ARM directly by reading ARM ID register (avoids memory reads). -; Created by MJS, 24-01-96 +; 24-01-96 MJS Created +; 07-10-96 MJS Updated for proper ARM 810 support (not needed for RO 3.70) ARM_config_cp CP 15 ;coprocessor number for configuration control @@ -37,6 +38,8 @@ ARM8A_TLB_reg CN 8 ;TLB operations, ARMs 8 or StrongARM ARM8_cacheLD_reg CN 9 ;cache lock-down, ARM 8 ARM8_TLBLD_reg CN 10 ;TLB lock-down, ARM 8 +ARM8_CTC_reg CN 15 ;Clock and test configuration + ARMA_TCI_reg CN 15 ;Test,Clock and Idle control ;so that AASM will accept the general value for MCR CRm field @@ -165,9 +168,174 @@ C15 CN 15 MEND ; -; -------------- ARM 8 only ---------------------------------------------- +; -------------- ARM 810 only ---------------------------------------------- +; + + [ ARM810support + +;turn off branch prediction +; - the forced mispredicted branch ensures that the predictor is trapped in +; this code segment when turned off +; - corrupts $temp and status flags +; + MACRO + ARM8_branchpredict_off $temp +01 + ARM_read_control $temp + BIC $temp,$temp,#&800 ;z bit (branch prediction) + ARM_write_control $temp + SEC ;set carry flag + BCC %BT01 + MEND + +;turn on branch prediction + MACRO + ARM8_branchpredict_on $temp + ARM_read_control $temp + ORR $temp,$temp,#&800 ;z bit (branch prediction) + ARM_write_control $temp + MEND + +;flush branch prediction, which is sufficient for an IMB (instruction memory +;barrier) on ARM 810, BUT... +; - intended for in line use only, where efficiency matters, or SWI call is +; awkward +; - general code should use SWI OS_SynchroniseCodeAreas to implement +; an IMB (instruction memory barrier) in future proof, ARM independent way +; - kernel code may use this without regard to which ARM running - ie. assumed +; harmless on other ARMs +; + MACRO + ARM8_branchpredict_flush + SUB PC,PC,#4 ;flush, because PC is written by data op + MEND + +;clean cache entry +; - segment,index spec in $reg +; - bits 4..6 = segment (0..7) +; - bits 26..31 = index (0..63) +; - all other bits zero + MACRO + ARM8_clean_IDCentry $reg,$cond + MCR$cond ARM_config_cp,0,$reg,ARM8A_cache_reg,C11,1 + MEND + +;flush cache entry - segment,index spec in $reg, as for ARM8_clean_IDCentry + MACRO + ARM8_flush_IDCentry $reg,$cond + MCR$cond ARM_config_cp,0,$reg,ARM8A_cache_reg,C7,1 + MEND + +;clean and flush cache entry - segment,index spec in $reg, as for ARM8_clean_IDCentry +; +;if ARM810cleanflushbroken is TRUE, interrupts *must* be currently diabled (see below) +; + MACRO + ARM8_cleanflush_IDCentry $reg,$cond + [ ARM810cleanflushbroken + ARM8_clean_IDCentry $reg,$cond + ARM8_flush_IDCentry $reg,$cond + | + MCR$cond ARM_config_cp,0,$reg,ARM8A_cache_reg,C15,1 + ] + MEND + +;fully clean and flush cache (assumes no locked-down entries to preserve) +; +;if ARM810cleanflushbroken is TRUE, then we have to make sure interrupts are disabled during +;the sequence of 2 MCRs that make up ARM8_cleanflush_IDCentry, to avoid an interrupt hole. +;The hole occurs if an interrupt fills and dirties the particular cache entry after the clean +;but before the flush. We don't have this problem with StrongARM, because the entry is +;specified by virtual address, and RISC OS only cleans/flushes address space not currently +;involved in interrupts. ; + [ ARM810cleanflushbroken + + MACRO + ARM8_cleanflush_IDC $temp,$temp2 + ;for simplicity, disable interrupts during entire operation - 26-bit assumed + MOV $temp2,pc + AND $temp2,$temp2,#I_bit + EOR $temp2,$temp2,#I_bit ;temp := <current I> EOR <I set> + TEQP $temp2,pc ;disable I + MOV $temp,#0 ;initial segment and index +01 + ARM8_cleanflush_IDCentry $temp + ADD $temp,$temp,#1 :SHL: 26 ;next index + CMP $temp,#1 :SHL: 26 ;last index done if index field wrapped to 0 + BHS %BT01 + ADD $temp,$temp,#1 :SHL: 4 ;next segment + CMP $temp,#8 :SHL: 4 ;8 segments done? + BLO %BT01 + TEQP $temp2,pc ;restore I + MEND + + | + + MACRO + ARM8_cleanflush_IDC $temp + MOV $temp,#0 ;initial segment and index +01 + ARM8_cleanflush_IDCentry $temp + ADD $temp,$temp,#1 :SHL: 26 ;next index + CMP $temp,#1 :SHL: 26 ;last index done if index field wrapped to 0 + BHS %BT01 + ADD $temp,$temp,#1 :SHL: 4 ;next segment + CMP $temp,#8 :SHL: 4 ;8 segments done? + BLO %BT01 + MEND + + ] + +;flush whole TLB (actually, same as ARMA_flush_TLBs) + MACRO + ARM8_flush_TLB $cond + MCR$cond ARM_config_cp,0,R0,ARM8A_TLB_reg,C7,0 + MEND + +;flush TLB entry, virtual address in $reg + MACRO + ARM8_flush_TLBentry $reg,$cond + MCR$cond ARM_config_cp,0,$reg,ARM8A_TLB_reg,C7,1 + MEND + +;select external Refclk pin as fast clock (dynamic switching, asynchronous) + MACRO + ARM8_refclk_fclk $temp + MRC ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + BIC $temp, $temp,#&1 ;turn off dynamic bus switching (bit0) + MCR ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + BIC $temp,$temp,#&2 ;select asynchronous mode (default) (bit1) + ORR $temp,$temp,#&4 ;select REFCLK as the FCLK source (bits3:2) + BIC $temp,$temp,#&10 ;ensure L=0 when writing (PLL locked) (bit4) + MCR ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + NOP + NOP + NOP + NOP + ORR $temp,$temp,#&1 ;select dynamic clock switching (bit0) + MCR ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + MEND + +;select PLL output as fast clock (dynamic switching, asynchronous) + MACRO + ARM8_pll_fclk $temp + MRC ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + BIC $temp,$temp,#&1 ;turn off dynamic bus switching (bit0) + MCR ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + BIC $temp,$temp,#&2 ;select asynchronous mode (default) (bit1) + ORR $temp,$temp,#&C ;select PLLClkOut as the FCLK source (bits3:2) + BIC $temp,$temp,#&10 ;ensure L=0 when writing (PLL locked) (bit4) + MCR ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + NOP + NOP + NOP + NOP + ORR $temp,$temp,#&1 ;select dynamic clock switching (bit0) + MCR ARM_config_cp,0,$temp,ARM8_CTC_reg,C0,0 + MEND + ] ;ARM810support ; ; -------------- StrongARM only ------------------------------------------ diff --git a/s/GetAll b/s/GetAll index 2c8e73ba..cdd7464e 100644 --- a/s/GetAll +++ b/s/GetAll @@ -190,12 +190,22 @@ IncludeTestSrc SETL :LNOT: (MEMM_Type = "MEMC2") ; not on internal test vers IncludeTestSrc SETL {FALSE} ] +;RISC OS 3.71 onwards assumed bus timings - if true, then ROM speeds atc are assumed according to IOMD ID regs. as follows: +; if IOMD (Risc PC) ROM ticks 5-3 (assumed bus 32 MHz) +; if 7500 (A7000) ROM ticks 5-3 (assumed bus 32 MHz), all clocks divide-by-1 +; if 7500FE (A7000+) ROM ticks 5-3,half speed (asssumed bus 64 MHz), EDO memory, divide-by-2 I/O, divide-by-1 CPU and memory +; + GBLL RO371Timings +RO371Timings SETL {TRUE} + + + [ :LNOT: RO371Timings GBLL NormalSpeedROMS NormalSpeedROMS SETL {FALSE} ;use FALSE for slow EPROMS GBLL AutoSpeedROMS -AutoSpeedROMS SETL {TRUE} +AutoSpeedROMS SETL {TRUE} ;WARNING: may not be reliable if true GBLL RISCPCBurstMode RISCPCBurstMode SETL {FALSE} @@ -203,6 +213,8 @@ RISCPCBurstMode SETL {FALSE} ;>>>RISC PC (no reason why it shouldn't) all references to RISCPCBurstMode ;>>>could be replaced by NormalSpeedROMS + ] + GBLL Select16BitSound Select16BitSound SETL {TRUE} @@ -276,18 +288,38 @@ IgnoreVRAM SETL {FALSE} LateAborts SETL MEMM_Type = "ARM600" :LAND: {TRUE} - GBLL StrongARM GBLL SAWBbroken ;whether StrongARM Write Buffer is broken (pass 1 silicon only) GBLL SAcleanflushbroken ;whether StrongARM single MCR for DC clean+flush broken (is always for SA110) - GBLL SAUBxferbroken ;whether extra NOPs required for user bank STM/LDM (is so far) + GBLL SASTMhatbroken ;whether ROM must support SA110's with broken STM^ (revision 3 should fix this) + GBLL StrongARM_POST ;whether to run POST for StrongARM (and possibly ARM8) + + GBLL ARM810support ;StrongARM must also be true for this to be useful + GBLL ARM810bpbroken ;whether branch predict is broken + GBLL ARM810cleanflushbroken ;whether single MCR for IDC clean+flush broken (a la StrongARM!) + GBLL ARM810fastclock ;whether to attempt to use fast clock (false means bus clock) + GBLL ARM810usePLL ;whether to use PLL for fast clock (else RefClk pin) + GBLL ARM810_POST ;whether to run POST for ARM810 (StrongARM_POST must also be true) StrongARM SETL {TRUE} SAWBbroken SETL {FALSE} :LAND: StrongARM SAcleanflushbroken SETL {TRUE} :LAND: StrongARM -SAUBxferbroken SETL {TRUE} :LAND: StrongARM +SASTMhatbroken SETL {TRUE} :LAND: StrongARM +StrongARM_POST SETL {TRUE} :LAND: StrongARM + +ARM810support SETL {FALSE} :LAND: StrongARM +ARM810bpbroken SETL {TRUE} :LAND: ARM810support +ARM810cleanflushbroken SETL {TRUE} :LAND: ARM810support +ARM810fastclock SETL {FALSE} :LAND: ARM810support +ARM810usePLL SETL {TRUE} :LAND: ARM810fastclock +ARM810_POST SETL {FALSE} :LAND: ARM810support + + GBLL VCOstartfix ;code in early kernel to fix VCO start problem on A7000 (esp. 7500FE) +VCOstartfix SETL {TRUE} + GBLL MorrisIDString ;whether printed CPU string includes 7500/7500FE recognition +MorrisIDString SETL {TRUE} :LAND: StrongARM ;printed CPU type only implemented if StrongARM true GBLL CheckProtectionLink ; if true, disallow CMOS RAM changes if link in protected position CheckProtectionLink SETL (IO_Type = "IOMD") :LAND: {TRUE} ; NB affects Delete/Copy/R/T and 0-9/. diff --git a/s/KbdResPC b/s/KbdResPC index e3e56852..8bfc394c 100644 --- a/s/KbdResPC +++ b/s/KbdResPC @@ -74,11 +74,11 @@ SetUpKbd MOV r0, #IOBase [ MorrisSupport - LDRB R1, [R0, #IOMD_ID0] ;Are we running on Morris - CMP R1, #&98 + LDRB R1, [R0, #IOMD_ID0] ;Are we running on Medusa + CMP R1, #&E7 LDRB R1, [R0, #IOMD_ID1] - CMPEQ R1, #&5B - BNE %FT30 ;NE: no, assume IOMD, so only one PS2 port + CMPEQ R1, #&D4 + BEQ %FT30 ;EQ: yes, it is IOMD, so only one PS2 port [ 1 = 1 ; @@ -178,10 +178,10 @@ SetUpKbd [ MorrisSupport LDRB R1, [R0, #IOMD_ID0] ;Are we running on Morris - CMP R1, #&98 + CMP R1, #&E7 LDRB R1, [R0, #IOMD_ID1] - CMPEQ R1, #&5B - BNE %FT30 ;NE: no, assume IOMD, so only one PS2 port + CMPEQ R1, #&D4 + BEQ %FT30 ;EQ: yes, it is IOMD, so only one PS2 port MOV R1, #IOMD_MSECR_Enable ;yes, so initialise 2nd PS2 (mouse) port cos STRB R1, [R0, #IOMD_MSECR] ;keyboard may be connected there instead diff --git a/s/Kernel b/s/Kernel index 473515ff..153b7b65 100644 --- a/s/Kernel +++ b/s/Kernel @@ -812,7 +812,14 @@ Do_CallBack ; CallBack allowed: STR r14, [r12, #4*15] ; user PC MOV r14, r12 Pull "r10-r12" + [ SASTMhatbroken + STMIA r14!,{r0-r12} + STMIA r14,{r13,r14}^ ; user registers + NOP + SUB r14,r14,#13*4 + | STMIA r14, {r0-r14}^ ; user registers + ] MOV R12, #CallAd_ws LDMIA R12, {R12, PC} ; jump to CallBackHandler diff --git a/s/Middle b/s/Middle index 1a043b56..708489e8 100644 --- a/s/Middle +++ b/s/Middle @@ -247,15 +247,14 @@ SBRKPT ROUT MOV r0, r12 LDMFD sp, {r10-r12} - [ SAUBxferbroken - NOP - NOP - ] + [ SASTMhatbroken + STMIA r0!,{r1-r12} + STMIA r0, {r13_usr,r14_usr}^ ; user mode case done. + SUB r0, r0, #12*4 + | STMIA r0, {r1-r12, r13_usr, r14_usr}^ ; user mode case done. NOP - [ SAUBxferbroken - NOP - ] + ] 10 LDR stack, =SVCSTK MOV r12, #BrkAd_ws @@ -390,15 +389,8 @@ EVENTH MOV pc, lr NOCALL MOV r0, #0 ; default callback routine LDR r14, [r0, #CallBf] - [ SAUBxferbroken - NOP - NOP - ] LDMIA r14, {r0-r12, r13_usr, r14_usr}^ ; load user's regs NOP - [ SAUBxferbroken - NOP - ] LDR r14, [r14, #4*15] MOVS pc, r14 @@ -597,9 +589,12 @@ DumpyTheRegisters ROUT LDR R1, [R0, -R0] ; PC when exception happened STR R1, [R0, #(15-8)*4] ; In the right slot now ... TST R1, #SVC_mode + [ SASTMhatbroken + STMEQIA R0!,{R8-R12} + STMEQIA R0, {R13,R14}^ ; user mode case done. + SUBEQ R0, R0, #5*4 + | STMEQIA R0, {R8-R14}^ ; user mode case done. - [ SAUBxferbroken - NOP ] BEQ UNDEF1 diff --git a/s/NewReset b/s/NewReset index a70c9a03..d06f4042 100644 --- a/s/NewReset +++ b/s/NewReset @@ -290,7 +290,11 @@ VIDCTAB ; Program Control Register first, to clear power-down bit + [ VCOstartfix + & &E0000404 ; CR: FIFO load 16 words, 1 bpp, ck/2, vclk (allow for doubled VCO freq) + | & &E0000400 ; CR: FIFO load 16 words, 1 bpp, ck/1, vclk + ] ; Don't bother programming all 256 palette entries, we'll be here all night ; Since we're setting up a 1 bit-per-pixel mode, just do colours 0 and 1 @@ -333,7 +337,11 @@ VIDCTAB & &B1000001 ; SCR: sound disabled (+use 24MHz clock) & &C00F1003 ; EREG = comp sync, DACs on, ereg output ext lut + [ VCOstartfix + & &D0000302 ; FSYNREG, clk = (3+1)/(2+1) * 24MHz = 32MHz (higher frequency as part of fix) + | & &D0000305 ; FSYNREG, clk = (3+1)/(5+1) * 24MHz = 16MHz + ] & &F0013000 ; DCR: bus D[31:0], Hdisc ;RCM 29/9/94: changed from &F0012000 at PSwindells request & &FFFFFFFF ; That's the lot | @@ -496,6 +504,33 @@ Continue MOV R0, #timer0_bit STRB R0, [R1, #IOCIRQCLRA] ; Clear pending t0 interrupt j.i.c. + [ VCOstartfix + ;2nd part of fix for VCO failing to start on A7000 (esp. 7500FE) - forcing PCOMP high for about 3 ms + LDRB R0, [R1,#IOMD_ID0] + CMP R0, #&E7 + LDREQB R0, [R1,#IOMD_ID1] + CMPEQ R0, #&D4 + BEQ vcofix_notMorris ; risky to force PCOMP on Risc PC + MOV R0, #VIDCPhys + LDR R2, =&D0000342 ; VIDC20 FSYNREG, as in VIDCTAB but with force PCOMP high + STR R2, [R0] + MOV R0, #3072*2 ; time delay of about 3 ms (0.5 us units) + STRB R0, [R1, #Timer0LR] ; copy counter into output latch + LDRB R2, [R1, #Timer0CL] ; R2 := low output latch +vcofix_waitloop + STRB R0, [R1, #Timer0LR] ; copy counter into output latch + LDRB R3, [R1, #Timer0CL] ; R3 := low output latch + TEQ R3, R2 ; unchanged ? + BEQ vcofix_waitloop ; then loop + MOV R2, R3 ; copy anyway + SUBS R0, R0, #1 ; decrement count + BNE vcofix_waitloop ; loop if not finished + MOV R0, #VIDCPhys + LDR R2, =&D0000302 ; VIDC20 FSYNREG, as in VIDCTAB (PCOMP low again) + STR R2, [R0] +vcofix_notMorris + ] + ; now size memory BL MemSize ; out: r0 = page size, r1 = memory size, r2 = MEMC CR value, r3-r14 corrupt @@ -650,6 +685,9 @@ SetUpKbdReturn ARMA_drain_WB ARMA_flush_IC vectorpoke_notSA_1 + [ ARM810support + ARM8_branchpredict_flush ;IMB on ARM810, and harmless on other ARMs + ] ] BIC r0, r0, #I32_bit ; and enable IRQs @@ -844,6 +882,9 @@ conversionSWIfill ARMA_drain_WB ARMA_flush_IC afterpokingaround_notSA + [ ARM810support + ARM8_branchpredict_flush ;IMB on ARM810, and harmless on other ARMs + ] ] ; Initialise CAO ptr to none. @@ -874,7 +915,6 @@ kbdwait kbdthere ] - ; IF power-on bit set in IOC AND R/T/Del/Copy pressed THEN reset CMOS RAM ; note that memory cleared if POR, so key info has had plenty of time! MOV R0, #IOC @@ -970,10 +1010,10 @@ not_full_reset [ MorrisSupport MOV R8, #IOMD_Base LDRB R0, [R8, #IOMD_ID0] - CMP R0, #&98 + CMP R0, #&E7 LDRB R0, [R8, #IOMD_ID1] - CMPEQ r0, #&5B - BNE dont_program_mousetype + CMPEQ r0, #&D4 + BEQ dont_program_mousetype ; IOMD (not Morris) ; ; Morris based machines use PS2 mice/tracker balls ; @@ -1062,7 +1102,7 @@ DefaultCMOSTable ; list of non-zero options wanted : = SoundCMOS, &F0 ; speaker on, volume 7, channel 1 = LanguageCMOS, ConfiguredLang - = YearCMOS, 95 ; changed from 93 to 95 on 12-Jan-95 to fix MED-04318 + = YearCMOS, 97 ; changed from 95 to 97 on 02-Jan-97 = YearCMOS+1, 19 [ :LNOT: Select16BitSound = TutuCMOS, 2_0100 ; tbs chars valid, ctrlchars '|x' @@ -1865,6 +1905,9 @@ CopyDefaultIRQ1V ARMA_flush_IC MOV r0,#0 ;restore r0 as zero base furtherpoke_notSA + [ ARM810support + ARM8_branchpredict_flush ;IMB on ARM810, and harmless on other ARMs + ] ] [ CPU_Type = "ARM600" @@ -1959,7 +2002,9 @@ furtherpoke_notSA SWI XOS_NewLine ] SWI XOS_EnterOS ; switch back to SVC mode (IRQs, FIQs enabled) - + [ RO371Timings + BL finalmemoryspeed + ] ; end of added code [ International ; Open the kernel messages file. @@ -2155,7 +2200,12 @@ processor_names ALIGN 32 DCB "StrongARM Processor",10,13,10,0 ALIGN 32 - + [ MorrisIDString + DCB "ARM 7500 Processor",10,13,10,0 + ALIGN 32 + DCB "ARM 7500FE Processor",10,13,10,0 + ALIGN 32 + ] ; type, internal type, features cputable DCD &6000,0,0 @@ -2163,7 +2213,17 @@ cputable DCD &7000,2,0 DCD &7100,3,0 DCD &8100,4,2_11101 + [ {TRUE} + ;corrected for 3.71 (SA does not abort for vector reads in 26-bit mode) + DCD &a100,5,2_11011 + | + ;value for 3.70 DCD &a100,5,2_11111 + ] + [ MorrisIDString + DCD &7500,6,0 + DCD &7501,7,0 + ] DCD -1 ] @@ -2174,11 +2234,30 @@ MessageFileName DCB "Resources:$.Resources.Kernel.Messages",0 [ StrongARM Processor_Type + [ MorrisIDString + MOV r0,#IOMD_Base + LDRB r1,[r0,#IOMD_ID0] + CMP r1,#&E7 + LDRB r1,[r0,#IOMD_ID1] + CMPEQ r1,#&D4 + BEQ PT_RiscPC ; E7,D4 means Risc PC + CMP r1,#&5B + MOVEQ r0,#&7500 ; 5B means 7500 + BEQ PT_lookup + CMP r1,#&AA + MOVEQ r0,#&7500 + ORREQ r0,r0,#&0001 ; AA means 7500FE - mark as 7501 + BEQ PT_lookup +PT_RiscPC + ] ReadCop R0,CR_ID ; see data sheets for values ; ARM 600 funny TST R0,#&f000 MOVEQ R0,R0, LSL #4 AND R0,R0,#&ff00 + [ MorrisIDString +PT_lookup + ] ADR R1,cputable 66 LDR R2,[R1],#4 diff --git a/s/PMF/osinit b/s/PMF/osinit index 2b5c93b7..f546ed48 100644 --- a/s/PMF/osinit +++ b/s/PMF/osinit @@ -562,19 +562,21 @@ ReadMachineType ENTRY "r0-r12" [ MorrisSupport MOV r12, #IOMD_Base LDRB r0, [r12, #IOMD_ID0] - CMP r0, #&98 + CMP r0, #&E7 LDRB r0, [r12, #IOMD_ID1] - CMPEQ r0, #&5B - MOVEQ r11, #IOST_7500 ;EQ, Morris - MOVNE r11, #0 ;NE, assume Medusa + CMPEQ r0, #&D4 + MOVEQ r11, #0 ;EQ, Medusa + BEQ rmtype_nomorris + MOV r11, #IOST_7500 ;NE, assume Morris ; ; On Kryten, Morris pin Event2 is tied low so bit Nevent2 is a ONE ; On Stork, Morris pin Event2 is tied high so bit Nevent2 is a ZERO ; - LDREQB r0, [r12, #IOMD_IRQSTD] ;EQ, Morris - TSTEQ r0, #IOMD_Nevent2_bit + LDRB r0, [r12, #IOMD_IRQSTD] ;Morris + TST r0, #IOMD_Nevent2_bit ORREQ r11, r11, #IOST_BATMAN ;EQ, Stork ie Morris & BATMAN +rmtype_nomorris ORR r0, r11, #IOST_IOEB ; pretend we've got IOEB ; ; r11 holds 0 for IOMD (Risc PC) diff --git a/s/vdu/vdudriver b/s/vdu/vdudriver index 89eee2b4..475a5c5d 100644 --- a/s/vdu/vdudriver +++ b/s/vdu/vdudriver @@ -1015,11 +1015,11 @@ DbgFilename [ MorrisSupport ; MOV R10, #IOMD_Base ; LDRB R9, [R10, #IOMD_ID0] - ; CMP R9, #&98 + ; CMP R9, #&E7 ; LDRB R9, [R10, #IOMD_ID1] - ; CMPEQ R9, #&5B - ; MOVEQ R9, #32000 ;Morris clocks VIDC20L at 32Mhz - ; LDRNE R9, =24000 ;RISC PC clocks VIDC20 at 24MHz + ; CMPEQ R9, #&D4 + ; MOVNE R9, #32000 ;Morris clocks VIDC20L at 32Mhz + ; LDREQ R9, =24000 ;RISC PC clocks VIDC20 at 24MHz MOV R9, #0 LDRB R9, [R9, #IOSystemType] TST R9, #IOST_7500 @@ -1933,11 +1933,11 @@ ProcessVIDCListType3 ROUT [ MorrisSupport ; MOV R14, #IOMD_Base ; LDRB R1, [R14, #IOMD_ID0] - ; CMP R1, #&98 + ; CMP R1, #&E7 ; LDRB R1, [R14, #IOMD_ID1] - ; CMPEQ R1, #&5B - ; MOVEQ R1, #32000 ;Morris clocks VIDC20L at 32Mhz - ; LDRNE R1, =24000 ;RISC PC clocks VIDC20 at 24MHz + ; CMPEQ R1, #&D4 + ; MOVNE R1, #32000 ;Morris clocks VIDC20L at 32Mhz + ; LDREQ R1, =24000 ;RISC PC clocks VIDC20 at 24MHz MOV R1, #0 LDRB R1, [R1, #IOSystemType] TST R1, #IOST_7500 @@ -2323,8 +2323,15 @@ ComputeModuli ENTRY "r2-r12", ComputeModuliStack LDR r5, [r2, #BestVInRange - BestDInRange] ; r5 = Best V SUBS r4, r4, #1 ; values in FSyn are n-1 + [ VCOstartfix + ;do *not* do the very slow trick - this will stall the VCO and it may not restart + ;properly later (we don't give a fig for power consumption) + MOVEQ r4, #3 + MOVEQ r5, #8 ; after sub below, (7+1)/(3+1) so VCO runs at twice ref clock + | MOVEQ r4, #63 ; if R=V=1 then use max R MOVEQ r5, #2 ; and min V to make VCO go really slow + ] SUB r5, r5, #1 ; for both v and r ASSERT FSyn_RShift = 0 -- GitLab