rrcc/src/rrcas.cpp
DataHoarder e76befaed7
All checks were successful
continuous-integration/drone/push Build is passing
Added full image format, include some debug information at the tail of functions
2021-01-04 08:16:20 +01:00

106 lines
3.8 KiB
C++

#include <iostream>
#include <fstream>
#include <vector>
#include <sstream>
#include <iomanip>
#include "Parser.h"
#include "Assembler.h"
#include "instructions/virtual/Stack.h"
#include "EmbeddedResource.h"
int main(int argc, char *argv[]) {
if (argc < 3) {
std::cout << "Usage: " << argv[0] << " code.asm [code2.asm ...] output.bin\n";
return 1;
}
try {
Linker linker;
std::vector<EmbeddedResource> embeddedResources = {
LOAD_RESOURCE(asm_registers_asm),
LOAD_RESOURCE(asm_config_asm),
LOAD_RESOURCE(asm_api_asm),
LOAD_RESOURCE(asm_stdlib_asm)
};
Instruction::Instruction::addDefaultOperators();
linker.addVariable("rrcc_STACK_START",
{Token(Token::Type::RegisterLocation, std::to_string(Instruction::Stack::stackRegisterStart),
Instruction::Stack::stackRegisterStart)});
linker.addVariable("rrcc_STACK_POINTER", {Token(Token::Type::RegisterLocation,
std::to_string(Instruction::Stack::stackOffsetRegisterAddress),
Instruction::Stack::stackOffsetRegisterAddress)});
for (auto &r : embeddedResources) {
std::vector<uint8_t> bytes(r.begin(), r.end());
Parser parser(bytes, linker.getVariables());
parser.parse();
linker.addFromParser(parser);
}
for (int inputIndex = 1; inputIndex < (argc - 1); ++inputIndex) {
try {
std::ifstream image(argv[inputIndex]);
if (image.is_open()) {
std::vector<uint8_t> bytes;
int c;
while (!image.eof() && (c = image.get()) != EOF) {
bytes.push_back(c);
}
Parser parser(bytes, linker.getVariables());
parser.parse();
linker.addFromParser(parser);
} else {
throw std::runtime_error("Could not open " + std::string(argv[inputIndex]));
}
}catch (const std::exception& e){
std::cerr << "Exception: " << e.what() << " on input file " << argv[inputIndex] << "\n";
return 1;
}
}
//Load base init
auto res = LOAD_RESOURCE(asm_init_asm);
std::vector<uint8_t> bytes(res.begin(), res.end());
Parser parser(bytes, linker.getVariables());
parser.parse();
linker.addFromParser(parser);
Assembler assembler(linker);
Assembler::ImageConfig config;
config.header.baseAddress = linker.getIntegerConstant("rrcc_BASE_ADDRESS", 0x080000, false);
config.header.spiTransferMode = linker.getIntegerConstant("rrcc_SPI_TRANSFER_MODE", 0, false);
config.header.spiTransferSpeed = linker.getIntegerConstant("rrcc_SPI_TRANSFER_SPEED", 7, false);
config.buildVersion = linker.getIntegerConstant("rrcc_IMAGE_VERSION", 0, false);
std::stringstream s;
s << "Image generated with rrc-as. EEPROM Image Version: 0x" << std::hex << std::setw(4) << std::setfill('0') << config.buildVersion;
config.buildSignature = s.str();
auto entrypointName = linker.getTextConstant("rrcc_ENTRYPOINT", "", true);
assembler.assemble(entrypointName, config);
std::ofstream patchedImage(argv[argc - 1]);
if (patchedImage.is_open()) {
auto &result = assembler.getImage();
for (auto c : result) {
patchedImage.put(c);
}
patchedImage.close();
}
} catch (const std::exception &e) {
std::cerr << "Exception: " << e.what() << "\n";
return 1;
}
return 0;
}