Use ByteReader in BatchFile
Abstracts away file management in BatchFile. Prevents a crash when attempting to read a file without the necessary permissions.
This commit is contained in:
parent
525002e769
commit
039532b95b
4 changed files with 30 additions and 50 deletions
|
@ -54,7 +54,7 @@ public:
|
|||
|
||||
class BatchFile {
|
||||
public:
|
||||
BatchFile(DOS_Shell* host, const char* const resolved_name,
|
||||
BatchFile(DOS_Shell* host, std::unique_ptr<ByteReader> input_reader,
|
||||
const char* const entered_name, const char* const cmd_line);
|
||||
BatchFile(const BatchFile&) = delete; // prevent copying
|
||||
BatchFile& operator=(const BatchFile&) = delete; // prevent assignment
|
||||
|
@ -62,17 +62,16 @@ public:
|
|||
virtual bool ReadLine(char* line);
|
||||
bool Goto(std::string_view label);
|
||||
void Shift();
|
||||
uint16_t file_handle = 0;
|
||||
uint32_t location = 0;
|
||||
bool echo = false;
|
||||
DOS_Shell* shell = nullptr;
|
||||
std::shared_ptr<BatchFile> prev = {}; // shared with Shell.bf
|
||||
std::unique_ptr<CommandLine> cmd = {};
|
||||
std::string filename{};
|
||||
|
||||
private:
|
||||
[[nodiscard]] std::string ExpandedBatchLine(std::string_view line) const;
|
||||
[[nodiscard]] std::string GetLine();
|
||||
|
||||
std::unique_ptr<ByteReader> reader;
|
||||
};
|
||||
|
||||
class AutoexecEditor;
|
||||
|
|
|
@ -72,13 +72,6 @@ void MOUNT::Move_Z(char new_z)
|
|||
tempenv += "COMMAND.COM";
|
||||
first_shell->SetEnv("COMSPEC",tempenv.c_str());
|
||||
|
||||
/* Update batch file if running from Z: (very likely: autoexec) */
|
||||
if (first_shell->bf) {
|
||||
std::string &name = first_shell->bf->filename;
|
||||
if (starts_with(name, "Z:")) {
|
||||
name[0] = new_drive_z;
|
||||
}
|
||||
}
|
||||
/* Change the active drive */
|
||||
if (DOS_GetDefaultDrive() == 25)
|
||||
DOS_SetDrive(new_idx);
|
||||
|
|
|
@ -24,31 +24,19 @@
|
|||
#include "string_utils.h"
|
||||
|
||||
// Permitted ASCII control characters in batch files
|
||||
constexpr uint8_t Esc = 27;
|
||||
constexpr uint8_t UnitSeparator = 31;
|
||||
constexpr char Esc = 27;
|
||||
constexpr char UnitSeparator = 31;
|
||||
|
||||
[[nodiscard]] static bool found_label(std::string_view line, std::string_view label);
|
||||
|
||||
BatchFile::BatchFile(DOS_Shell* const host, const char* const resolved_name,
|
||||
BatchFile::BatchFile(DOS_Shell* const host, std::unique_ptr<ByteReader> input_reader,
|
||||
const char* const entered_name, const char* const cmd_line)
|
||||
: echo(host->echo),
|
||||
shell(host),
|
||||
prev(host->bf),
|
||||
cmd(new CommandLine(entered_name, cmd_line))
|
||||
cmd(new CommandLine(entered_name, cmd_line)),
|
||||
reader(std::move(input_reader))
|
||||
{
|
||||
char totalname[DOS_PATHLENGTH + 4];
|
||||
|
||||
// Get fullname including drive specification
|
||||
if (!DOS_Canonicalize(resolved_name, totalname)) {
|
||||
E_Exit("SHELL: Can't determine path to batch file %s", resolved_name);
|
||||
}
|
||||
|
||||
filename = totalname;
|
||||
// Test if file is openable
|
||||
if (!DOS_OpenFile(totalname, (DOS_NOT_INHERIT | OPEN_READ), &file_handle)) {
|
||||
shell->WriteOut("SHELL: Can't open BatchFile %s\n", totalname);
|
||||
}
|
||||
DOS_CloseFile(file_handle);
|
||||
}
|
||||
|
||||
BatchFile::~BatchFile()
|
||||
|
@ -87,25 +75,19 @@ bool BatchFile::ReadLine(char* lineout)
|
|||
|
||||
std::string BatchFile::GetLine()
|
||||
{
|
||||
if (!DOS_OpenFile(filename.c_str(), (DOS_NOT_INHERIT | OPEN_READ), &file_handle)) {
|
||||
LOG(LOG_MISC, LOG_ERROR)
|
||||
("ReadLine Can't open BatchFile %s", filename.c_str());
|
||||
return "";
|
||||
}
|
||||
DOS_SeekFile(file_handle, &(this->location), DOS_SEEK_SET);
|
||||
|
||||
uint8_t data = 0;
|
||||
uint16_t bytes_read = 1;
|
||||
std::string line = {};
|
||||
char data = 0;
|
||||
std::string line = {};
|
||||
|
||||
while (data != '\n') {
|
||||
DOS_ReadFile(file_handle, &data, &bytes_read);
|
||||
const auto result = reader->Read();
|
||||
|
||||
// EOF
|
||||
if (bytes_read == 0) {
|
||||
if (!result) {
|
||||
break;
|
||||
}
|
||||
|
||||
data = *result;
|
||||
|
||||
/* Inclusion criteria:
|
||||
* - backspace for alien odyssey
|
||||
* - tab for batch files
|
||||
|
@ -117,14 +99,10 @@ std::string BatchFile::GetLine()
|
|||
data,
|
||||
data);
|
||||
} else {
|
||||
line += static_cast<char>(data);
|
||||
line += data;
|
||||
}
|
||||
}
|
||||
|
||||
this->location = 0;
|
||||
DOS_SeekFile(file_handle, &(this->location), DOS_SEEK_CUR);
|
||||
DOS_CloseFile(file_handle);
|
||||
|
||||
return line;
|
||||
}
|
||||
|
||||
|
@ -175,7 +153,7 @@ std::string BatchFile::ExpandedBatchLine(std::string_view line) const
|
|||
bool BatchFile::Goto(const std::string_view label)
|
||||
{
|
||||
std::string line = " ";
|
||||
this->location = 0;
|
||||
reader->Reset();
|
||||
|
||||
while (!line.empty()) {
|
||||
line = GetLine();
|
||||
|
|
|
@ -21,9 +21,11 @@
|
|||
|
||||
#include <algorithm>
|
||||
#include <cstring>
|
||||
#include <memory>
|
||||
|
||||
#include "../ints/int10.h"
|
||||
#include "callback.h"
|
||||
#include "file_reader.h"
|
||||
#include "keyboard.h"
|
||||
#include "regs.h"
|
||||
#include "string_utils.h"
|
||||
|
@ -468,11 +470,19 @@ bool DOS_Shell::Execute(std::string_view name, std::string_view args)
|
|||
if (bf && !call) {
|
||||
bf.reset();
|
||||
}
|
||||
bf = std::make_shared<BatchFile>(this,
|
||||
fullname.c_str(),
|
||||
std::string(name).c_str(),
|
||||
std::string(args).c_str());
|
||||
|
||||
auto reader = FileReader::GetFileReader(fullname);
|
||||
if (reader) {
|
||||
bf = std::make_shared<BatchFile>(this,
|
||||
std::move(*reader),
|
||||
std::string(name).c_str(),
|
||||
std::string(args).c_str());
|
||||
} else {
|
||||
WriteOut("Could not open %s", fullname.c_str());
|
||||
}
|
||||
|
||||
echo = temp_echo;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue