mirror of
https://github.com/curioustorvald/tsvm.git
synced 2026-06-10 06:54:04 +09:00
tevd: bootloader is now entry id 1
This commit is contained in:
Binary file not shown.
Binary file not shown.
@@ -23,7 +23,17 @@ function copyFiles(destDrive) {
|
|||||||
})
|
})
|
||||||
|
|
||||||
// bare files in the root dir
|
// bare files in the root dir
|
||||||
;["!BOOTSEC", "AUTOEXEC.BAT"].forEach((name)=>{
|
;["AUTOEXEC.BAT"].forEach((name)=>{
|
||||||
dos.cp(`A:\\tvdos\\installer\\${name}`, `${destDrive}:\\${name}`)
|
dos.cp(`A:\\tvdos\\installer\\${name}`, `${destDrive}:\\${name}`)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// install bootloader
|
||||||
|
val bootloader = files.open("A:\\tvdos\\installer\\!BOOTSEC").sread()
|
||||||
|
let [port, poru] = _TVDOS.DRV.FS.SERIAL._toPorts(destDrive)[0]
|
||||||
|
com.sendMessage(port, "FLUSH");com.sendMessage(port, "CLOSE")
|
||||||
|
com.sendMessage(port, `NEWTEVDBOOT,${poru}`) // read-only check will be performed by the other writes
|
||||||
|
com.sendMessage(port, bootloader)
|
||||||
|
com.sendMessage(port, "FLUSH");com.sendMessage(port, "CLOSE")
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -150,6 +150,16 @@ class TestDiskDrive(private val vm: VM, private val driveNum: Int, theRootPath:
|
|||||||
appendMode = false
|
appendMode = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (fileOpenMode == 17) {
|
||||||
|
if (!fileOpen) throw InternalError("Bootloader file is not open but the drive is in boot write mode")
|
||||||
|
|
||||||
|
val inputData = if (inputData.size != BLOCK_SIZE) ByteArray(BLOCK_SIZE) { if (it < inputData.size) inputData[it] else 0 }
|
||||||
|
else inputData
|
||||||
|
|
||||||
|
file.writeBytes(inputData)
|
||||||
|
|
||||||
|
fileOpenMode = -1
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
val inputString = inputData.trimNull().toString(VM.CHARSET)
|
val inputString = inputData.trimNull().toString(VM.CHARSET)
|
||||||
|
|
||||||
@@ -311,6 +321,21 @@ class TestDiskDrive(private val vm: VM, private val driveNum: Int, theRootPath:
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (inputString.startsWith("NEWTEVDBOOT")) {
|
||||||
|
var commaIndex = 0
|
||||||
|
while (commaIndex < inputString.length) {
|
||||||
|
if (inputString[commaIndex] == ',') break
|
||||||
|
commaIndex += 1
|
||||||
|
}
|
||||||
|
val driveNum = if (commaIndex >= inputString.length) null else commaIndex
|
||||||
|
|
||||||
|
// TODO driveNum is for disk drives that may have two or more slots built; for testing purposes we'll ignore it
|
||||||
|
|
||||||
|
statusCode.set(STATE_CODE_STANDBY)
|
||||||
|
fileOpen = true
|
||||||
|
fileOpenMode = 17
|
||||||
|
blockSendCount = 0
|
||||||
|
}
|
||||||
else if (inputString.startsWith("LOADBOOT")) {
|
else if (inputString.startsWith("LOADBOOT")) {
|
||||||
var commaIndex = 0
|
var commaIndex = 0
|
||||||
while (commaIndex < inputString.length) {
|
while (commaIndex < inputString.length) {
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ import java.util.concurrent.atomic.AtomicBoolean
|
|||||||
class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val theTevdPath: String, val diskUUIDstr: String) : BlockTransferInterface(false, true) {
|
class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val theTevdPath: String, val diskUUIDstr: String) : BlockTransferInterface(false, true) {
|
||||||
|
|
||||||
|
|
||||||
private val DBGPRN = false
|
private val DBGPRN = true
|
||||||
|
|
||||||
val diskID: UUID = UUID.fromString(diskUUIDstr)
|
val diskID: UUID = UUID.fromString(diskUUIDstr)
|
||||||
|
|
||||||
@@ -30,8 +30,10 @@ class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val t
|
|||||||
private var fileOpenMode = -1 // 1: 'W", 2: 'A'
|
private var fileOpenMode = -1 // 1: 'W", 2: 'A'
|
||||||
private var file: TevdFileDescriptor = TevdFileDescriptor(DOM, "")
|
private var file: TevdFileDescriptor = TevdFileDescriptor(DOM, "")
|
||||||
//private var readModeLength = -1 // always 4096
|
//private var readModeLength = -1 // always 4096
|
||||||
private var writeMode = false
|
private val writeMode
|
||||||
private var appendMode = false
|
get() = fileOpenMode == 1
|
||||||
|
private val appendMode
|
||||||
|
get() = fileOpenMode == 2
|
||||||
private var writeModeLength = -1
|
private var writeModeLength = -1
|
||||||
|
|
||||||
private val messageComposeBuffer = ByteArrayOutputStream(BLOCK_SIZE) // always use this and don't alter blockSendBuffer please
|
private val messageComposeBuffer = ByteArrayOutputStream(BLOCK_SIZE) // always use this and don't alter blockSendBuffer please
|
||||||
@@ -113,13 +115,25 @@ class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val t
|
|||||||
else if (writeMode)
|
else if (writeMode)
|
||||||
file.writeBytes(writeBuffer)
|
file.writeBytes(writeBuffer)
|
||||||
|
|
||||||
writeMode = false
|
fileOpenMode = -1
|
||||||
appendMode = false
|
|
||||||
|
|
||||||
printdbg("Notifying disk commit (end of write)")
|
printdbg("Notifying disk commit (end of write)")
|
||||||
notifyDiskCommit()
|
notifyDiskCommit()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (fileOpenMode == 17) {
|
||||||
|
if (!fileOpen) throw InternalError("Bootloader file is not open but the drive is in boot write mode")
|
||||||
|
|
||||||
|
val inputData = if (inputData.size != BLOCK_SIZE) ByteArray(BLOCK_SIZE) { if (it < inputData.size) inputData[it] else 0 }
|
||||||
|
else inputData
|
||||||
|
|
||||||
|
file.writeBytes(inputData)
|
||||||
|
|
||||||
|
fileOpenMode = -1
|
||||||
|
|
||||||
|
printdbg("Notifying disk commit (end of bootloader write)")
|
||||||
|
notifyDiskCommit()
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
val inputString = inputData.trimNull().toString(VM.CHARSET)
|
val inputString = inputData.trimNull().toString(VM.CHARSET)
|
||||||
|
|
||||||
@@ -131,7 +145,6 @@ class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val t
|
|||||||
file = TevdFileDescriptor(DOM, "")
|
file = TevdFileDescriptor(DOM, "")
|
||||||
blockSendCount = 0
|
blockSendCount = 0
|
||||||
statusCode.set(TestDiskDrive.STATE_CODE_STANDBY)
|
statusCode.set(TestDiskDrive.STATE_CODE_STANDBY)
|
||||||
writeMode = false
|
|
||||||
writeModeLength = -1
|
writeModeLength = -1
|
||||||
}
|
}
|
||||||
else if (inputString.startsWith("DEVSTU\u0017"))
|
else if (inputString.startsWith("DEVSTU\u0017"))
|
||||||
@@ -297,6 +310,27 @@ class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val t
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (inputString.startsWith("NEWTEVDBOOT")) {
|
||||||
|
var commaIndex = 0
|
||||||
|
while (commaIndex < inputString.length) {
|
||||||
|
if (inputString[commaIndex] == ',') break
|
||||||
|
commaIndex += 1
|
||||||
|
}
|
||||||
|
val driveNum = if (commaIndex >= inputString.length) null else commaIndex
|
||||||
|
|
||||||
|
// TODO driveNum is for disk drives that may have two or more slots built; for testing purposes we'll ignore it
|
||||||
|
|
||||||
|
if (DOM.isReadOnly) {
|
||||||
|
printdbg("! disk is read-only")
|
||||||
|
statusCode.set(TestDiskDrive.STATE_CODE_READ_ONLY)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
statusCode.set(TestDiskDrive.STATE_CODE_STANDBY)
|
||||||
|
fileOpen = true
|
||||||
|
fileOpenMode = 17
|
||||||
|
blockSendCount = 0
|
||||||
|
}
|
||||||
else if (inputString.startsWith("LOADBOOT")) {
|
else if (inputString.startsWith("LOADBOOT")) {
|
||||||
var commaIndex = 0
|
var commaIndex = 0
|
||||||
while (commaIndex < inputString.length) {
|
while (commaIndex < inputString.length) {
|
||||||
@@ -307,17 +341,17 @@ class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val t
|
|||||||
|
|
||||||
// TODO driveNum is for disk drives that may have two or more slots built; for testing purposes we'll ignore it
|
// TODO driveNum is for disk drives that may have two or more slots built; for testing purposes we'll ignore it
|
||||||
|
|
||||||
val bootFile = TevdFileDescriptor(DOM, "!BOOTSEC")
|
val bootFile = DOM.entries[1]
|
||||||
|
|
||||||
printdbg("bootFile = $bootFile, ID: ${bootFile.entryID}, exists = ${bootFile.exists()}")
|
printdbg("bootFile = $bootFile, ID: 1, exists = ${bootFile != null}")
|
||||||
|
|
||||||
if (!bootFile.exists()) {
|
if (bootFile == null) {
|
||||||
printdbg("bootfile not exists!")
|
printdbg("bootfile not exists!")
|
||||||
statusCode.set(TestDiskDrive.STATE_CODE_NO_SUCH_FILE_EXISTS)
|
statusCode.set(TestDiskDrive.STATE_CODE_NO_SUCH_FILE_EXISTS)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
val retMsg = bootFile.getHeadBytes(BLOCK_SIZE)
|
val retMsg = VDUtil.getAsNormalFile(DOM, 1).getContent().sliceArray(0 until BLOCK_SIZE)
|
||||||
|
|
||||||
printdbg("retMsg = ${retMsg.toString(VM.CHARSET)}")
|
printdbg("retMsg = ${retMsg.toString(VM.CHARSET)}")
|
||||||
|
|
||||||
@@ -412,8 +446,6 @@ class TevdDiskDrive(private val vm: VM, private val driveNum: Int, private val t
|
|||||||
statusCode.set(TestDiskDrive.STATE_CODE_OPERATION_NOT_PERMITTED)
|
statusCode.set(TestDiskDrive.STATE_CODE_OPERATION_NOT_PERMITTED)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if (fileOpenMode == 1) { writeMode = true; appendMode = false }
|
|
||||||
else if (fileOpenMode == 2) { writeMode = false; appendMode = true }
|
|
||||||
if (!file.exists()) {
|
if (!file.exists()) {
|
||||||
val f1 = file.createNewFile()
|
val f1 = file.createNewFile()
|
||||||
statusCode.set(if (f1) TestDiskDrive.STATE_CODE_STANDBY else TestDiskDrive.STATE_CODE_OPERATION_FAILED)
|
statusCode.set(if (f1) TestDiskDrive.STATE_CODE_STANDBY else TestDiskDrive.STATE_CODE_OPERATION_FAILED)
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
package net.torvald.tsvm
|
package net.torvald.tsvm
|
||||||
|
|
||||||
|
import net.torvald.terrarum.modulecomputers.virtualcomputer.tvd.EntryFile
|
||||||
import net.torvald.terrarum.modulecomputers.virtualcomputer.tvd.VDUtil
|
import net.torvald.terrarum.modulecomputers.virtualcomputer.tvd.VDUtil
|
||||||
import net.torvald.tsvm.VM
|
import net.torvald.terrarum.modulecomputers.virtualcomputer.tvd.VDUtil.checkReadOnly
|
||||||
import java.io.File
|
import java.io.File
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -33,12 +34,22 @@ fun main(args: Array<String>) {
|
|||||||
|
|
||||||
// bare file in root dir
|
// bare file in root dir
|
||||||
listOf(
|
listOf(
|
||||||
VDUtil.importFile(File("assets/disk0/root.bootable/!BOOTSEC"), disk.generateUniqueID(), VM.CHARSET),
|
|
||||||
VDUtil.importFile(File("assets/disk0/root.bootable/AUTOEXEC.BAT"), disk.generateUniqueID(), VM.CHARSET),
|
VDUtil.importFile(File("assets/disk0/root.bootable/AUTOEXEC.BAT"), disk.generateUniqueID(), VM.CHARSET),
|
||||||
).forEach {
|
).forEach {
|
||||||
VDUtil.addFile(disk, 0, it)
|
VDUtil.addFile(disk, 0, it)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
VDUtil.importFile(File("assets/disk0/root.bootable/!BOOTSEC"), 1, VM.CHARSET).let {
|
||||||
|
disk.checkReadOnly()
|
||||||
|
// disk.checkCapacity(4096)
|
||||||
|
|
||||||
|
(it.contents as EntryFile).let { file ->
|
||||||
|
val bytes = file.getContent()
|
||||||
|
bytes.appendBytes(ByteArray(4096 - bytes.size.toInt()))
|
||||||
|
}
|
||||||
|
|
||||||
|
disk.entries[1] = it
|
||||||
|
}
|
||||||
|
|
||||||
VDUtil.dumpToRealMachine(disk, File(args[0]))
|
VDUtil.dumpToRealMachine(disk, File(args[0]))
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user