@@ -25,33 +25,30 @@ class ProcessorAccess(
2525 val memoryX : Int ,
2626 val memoryY : Int ,
2727 val memoryWidth : Int ,
28- val romByteOffset : Int ,
29- val romProcSize : Int ,
30- val romStart : Int ,
31- val romEnd : Int ,
32- val ramProcSize : Int ,
33- val ramStart : Int ,
34- val ramEnd : Int ,
35- val resetSwitch : SwitchBuild ,
28+ val romSize : Int ,
29+ val ramSize : Int ,
3630 val errorOutput : MessageBuild ,
31+ val resetSwitch : SwitchBuild ,
3732) {
38- val romSize = romEnd - romStart
39- val ramSize = ramEnd - ramStart
33+ val romEnd = ROM_START + romSize.toUInt()
34+ val ramEnd = RAM_START + ramSize.toUInt()
35+
36+ val ramStartProc = (romEnd / ROM_PROC_BYTES .toUInt()).toInt()
4037
4138 fun flashRom (file : Fi ): Int {
4239 val data = file.readBytes()
4340 require(data.size.mod(4 ) == 0 ) { " Data length must be a multiple of 4 bytes." }
4441 require(data.size <= romSize) { " Data is too large to fit into the processor's ROM." }
4542
46- var address = romStart
43+ var address = ROM_START
4744 val bytes = mutableListOf<Byte >()
4845 for (byte in data) {
4946 bytes.add(byte)
5047
51- if (bytes.size == romProcSize ) {
48+ if (bytes.size == ROM_PROC_BYTES ) {
5249 flashRomProc(address, bytes)
5350 bytes.clear()
54- address + = romProcSize
51+ address + = ROM_PROC_BYTES .toUInt()
5552 }
5653 }
5754
@@ -64,11 +61,11 @@ class ProcessorAccess(
6461 }
6562
6663 fun dumpRam (file : Fi ): Int {
67- dumpRam(file, ramStart , ramSize)
64+ dumpRam(file, RAM_START , ramSize)
6865 return ramSize
6966 }
7067
71- fun dumpRam (file : Fi , startAddress : Int , bytes : Int ) {
68+ fun dumpRam (file : Fi , startAddress : UInt , bytes : Int ) {
7269 require(bytes > 0 ) { " Bytes must be positive." }
7370 require(bytes <= ramSize) { " Bytes must not be greater than the RAM size." }
7471 require(bytes.mod(4 ) == 0 ) { " Bytes must be aligned to 4 bytes." }
@@ -119,25 +116,24 @@ class ProcessorAccess(
119116 ProcessorAccess .stopServer()
120117 }
121118
122- private fun ramWordsSequence (startAddress : Int = 0 ) = sequence {
123- require(startAddress in ramStart .. < ramEnd) { " Start address must be within RAM." }
124- require(startAddress.mod(4 ) == 0 ) { " Start address must be aligned to 4 bytes." }
119+ private fun ramWordsSequence (startAddress : UInt ) = sequence {
120+ require(startAddress in RAM_START .. < ramEnd) { " Start address must be within RAM." }
121+ require(startAddress.mod(4u ) == 0u ) { " Start address must be aligned to 4 bytes." }
125122
126123 var address = startAddress
127124 while (address < ramEnd) {
128- val proc = getRamProc(address) ? : break
129- val startIndex = (address / 4 ).mod(ramProcSize) + 1
130- for (i in startIndex.. ramProcSize) {
131- yield (proc.executor.vars[i]!! to address)
132- address + = 4
125+ val (proc, startIndex) = getRamProc(address) ? : break
126+ for (i in startIndex.. <RAM_PROC_VARS ) {
127+ yield(proc.executor.vars[i + 1]!! to address)
128+ address + = 4u
133129 }
134130 }
135131 }
136132
137- private fun getRomProc (address : Int ): LogicBuild ? {
138- if (address !in romStart .. < romEnd) return null
133+ private fun getRomProc(address: UInt ): LogicBuild ? {
134+ if (address ! in ROM_START .. <romEnd) return null
139135
140- val index = address / romProcSize
136+ val index = ( address / ROM_PROC_BYTES .toUInt()).toInt()
141137 val x = memoryX + index.mod(memoryWidth)
142138 val y = memoryY + index / memoryWidth
143139
@@ -148,11 +144,11 @@ class ProcessorAccess(
148144 return proc
149145 }
150146
151- private fun flashRomProc (address : Int , data : Iterable <Byte >) {
147+ private fun flashRomProc(address: UInt , data: Iterable <Byte >) {
152148 val code = buildString {
153149 append(" set v \" " )
154150 for (byte in data) {
155- val char = (byte.toInt() and 0xff ) + romByteOffset
151+ val char = (byte.toInt() and 0xff ) + ROM_BYTE_OFFSET
156152 append(char.toChar())
157153 }
158154 append(" \"\n stop" )
@@ -164,22 +160,25 @@ class ProcessorAccess(
164160 proc.updateCode(code)
165161 }
166162
167- private fun getRamProc (address : Int ): LogicBuild ? {
168- if (address !in ramStart.. < ramEnd) return null
163+ private fun getRamProc (address : UInt ): Pair <LogicBuild , Int >? {
164+ if (address !in RAM_START .. < ramEnd) return null
165+
166+ val ramAddress = address - RAM_START
167+ val ramVariable = (ramAddress / 4u ).toInt()
169168
170169 // each ROM and RAM proc currently holds the same amount of data, so this doesn't matter too much
171- val index = address / 4 / ramProcSize
170+ val index = ramStartProc + ramVariable / RAM_PROC_VARS
172171 val x = memoryX + index.mod(memoryWidth)
173172 val y = memoryY + index / memoryWidth
174173
175174 val proc = Vars .world.build(x, y) as ? LogicBuild ? : return null
176175
177176 if (
178- proc.executor.vars.size != ramProcSize + 1
177+ proc.executor.vars.size != RAM_PROC_VARS + 1
179178 || proc.executor.vars[1 ].name != " !!"
180179 ) return null
181180
182- return proc
181+ return proc to ramVariable.mod( RAM_PROC_VARS )
183182 }
184183
185184 private suspend fun runServer (serverSocket : ServerSocket ) {
@@ -212,6 +211,13 @@ class ProcessorAccess(
212211 }
213212
214213 companion object {
214+ const val ROM_BYTE_OFFSET = 174
215+ const val ROM_PROC_BYTES = 16384
216+ const val RAM_PROC_VARS = 4096
217+
218+ const val ROM_START = 0x00000000u
219+ const val RAM_START = 0x80000000u
220+
215221 private var serverThread: Thread ? = null
216222 private var serverJob: Job ? = null
217223 private var serverBuildId: Int? = null
@@ -222,15 +228,10 @@ class ProcessorAccess(
222228 memoryX = nonZeroIntVar(build, " MEMORY_X" ) ? : return null ,
223229 memoryY = nonZeroIntVar(build, " MEMORY_Y" ) ? : return null ,
224230 memoryWidth = positiveIntVar(build, " MEMORY_WIDTH" ) ? : return null ,
225- romByteOffset = nonNegativeIntVar(build, " ROM_BYTE_OFFSET" ) ? : return null ,
226- romProcSize = positiveIntVar(build, " ROM_PROC_SIZE" ) ? : return null ,
227- romStart = nonNegativeIntVar(build, " ROM_START" ) ? : return null ,
228- romEnd = nonNegativeIntVar(build, " ROM_END" ) ? : return null ,
229- ramProcSize = positiveIntVar(build, " RAM_PROC_SIZE" ) ? : return null ,
230- ramStart = nonNegativeIntVar(build, " RAM_START" ) ? : return null ,
231- ramEnd = nonNegativeIntVar(build, " RAM_END" ) ? : return null ,
232- resetSwitch = buildVar<SwitchBuild >(build, " RESET_SWITCH" ) ? : return null ,
233- errorOutput = buildVar<MessageBuild >(build, " ERROR_OUTPUT" ) ? : return null ,
231+ romSize = positiveIntVar(build, " ROM_SIZE" ) ? : return null ,
232+ ramSize = positiveIntVar(build, " RAM_SIZE" ) ? : return null ,
233+ errorOutput = buildVar<MessageBuild >(build, " message1" ) ? : return null ,
234+ resetSwitch = buildVar<SwitchBuild >(build, " switch1" ) ? : return null ,
234235 )
235236 }
236237
@@ -250,18 +251,18 @@ private fun nonZeroIntVar(build: LogicBuild, name: String): Int? =
250251 ?.numi()
251252 ?.takeIf { it != 0 }
252253
253- private fun nonNegativeIntVar (build : LogicBuild , name : String ): Int? =
254- build.executor.optionalVar(name)
255- ?.takeIf { ! it.isobj }
256- ?.numi()
257- ?.takeIf { it >= 0 }
258-
259254private fun positiveIntVar (build : LogicBuild , name : String ): Int? =
260255 nonZeroIntVar(build, name)
261256 ?.takeIf { it > 0 }
262257
263258private inline fun <reified T : Building > buildVar (build : LogicBuild , name : String ): T ? =
264- build.executor.optionalVar(name)?.obj() as ? T
259+ (build.executor.optionalVar(name)?.obj() ? : linkedBuild(build, name)) as ? T
260+
261+ // why
262+ private fun linkedBuild (build : LogicBuild , name : String ) =
263+ build.links
264+ .firstOrNull { it.active && it.valid && it.name == name }
265+ ?.let { Vars .world.build(it.x, it.y) }
265266
266267@Serializable
267268sealed class Request {
@@ -296,15 +297,15 @@ data class FlashRequest(val path: String) : Request() {
296297@SerialName(" dump" )
297298data class DumpRequest (
298299 val path : String ,
299- val address : Int ? ,
300+ val address : UInt ? ,
300301 val bytes : Int? ,
301302) : Request() {
302303 override suspend fun handle (processor : ProcessorAccess ) = runOnMainThread {
303304 val file = Core .files.absolute(path)
304305 file.parent().mkdirs()
305306
306- val address = address ? : processor.ramStart
307- val bytes = bytes ? : (processor.ramEnd - address)
307+ val address = address ? : ProcessorAccess . RAM_START
308+ val bytes = bytes ? : (processor.ramEnd - address).toInt()
308309
309310 processor.dumpRam(file, address, bytes)
310311 SuccessResponse (" Successfully dumped $bytes bytes from RAM to $file ." )
0 commit comments