Compare commits

..

No commits in common. '4d19738072502cfacc05946600888b4c516da4da' and '1c2dad94e29104a4ee6c2a57805ab6b0a1c441a2' have entirely different histories.

@ -19,7 +19,7 @@ jobs:
runs-on: ubuntu-latest
strategy:
matrix:
python-version: ['3.8','3.10']
python-version: ['3.10']
steps:
- uses: actions/checkout@v3

10
.gitignore vendored

@ -1,8 +1,6 @@
venv
__pycache__
.mypy_cache
.pytest_cache
/venv*
/dist
/riscemu.egg-info
/build
dist/
riscemu.egg-info
build/

@ -1,18 +1,14 @@
# Changelog
## 2.1.1
- Bugfix: Allow infinite registers with more than two digits in load/store ins
- Bugfix: Fix how floating point registers are displayed in the debugger
- Bugfix: Various semantic problems in RV32F
## 2.1.0
## Upcoming 2.0.6
- Added a very basic libc containing a `crt0.s`, and a few functions
such as `malloc`, `rand`, and `memcpy`.
- Added a subset of the `mmap2` syscall (code 192) to allocate new memory
- Refactored the launching code to improve using riscemu from code
- Added floating point support (enabled by default). The RV32F extension is now available
**Planned:**
- Add a floating point unit
## 2.0.5

@ -348,7 +348,7 @@ class MMU:
return InstructionContext()
def find_entrypoint(self) -> Optional[int]:
def find_entrypoint(self) -> int | None:
# try to find the global entrypoint
if "_start" in self.global_symbols:
return self.global_symbols["_start"]

@ -34,4 +34,4 @@ from .parser import tokenize, parse_tokens, AssemblyFileLoader
__author__ = "Anton Lydike <Anton@Lydike.com>"
__copyright__ = "Copyright 2023 Anton Lydike"
__version__ = "2.1.1"
__version__ = "2.0.5"

@ -12,7 +12,7 @@ from riscemu.riscemu_main import RiscemuMain
try:
main = RiscemuMain()
main.run_from_cli(sys.argv[1:])
main.run(sys.argv[1:])
sys.exit(main.cpu.exit_code if not main.cfg.ignore_exit_code else 0)
except RiscemuBaseException as e:

@ -2,7 +2,7 @@ import argparse
import glob
import os
import sys
from typing import Type, Dict, List, Optional
from typing import List, Type
from riscemu import AssemblyFileLoader, __version__, __copyright__
from riscemu.types import CPU, ProgramLoader, Program
@ -17,21 +17,21 @@ class RiscemuMain:
interoperability.
"""
available_ins_sets: Dict[str, Type[InstructionSet]]
available_file_loaders: List[Type[ProgramLoader]]
available_ins_sets: dict[str, type[InstructionSet]]
available_file_loaders: list[type[ProgramLoader]]
cfg: Optional[RunConfig]
cpu: Optional[CPU]
cfg: RunConfig | None
cpu: CPU | None
input_files: List[str]
selected_ins_sets: List[Type[InstructionSet]]
input_files: list[str]
selected_ins_sets: list[Type[InstructionSet]]
def __init__(self, cfg: Optional[RunConfig] = None):
def __init__(self):
self.available_ins_sets = dict()
self.selected_ins_sets = []
self.available_file_loaders = []
self.cfg: Optional[RunConfig] = cfg
self.cpu: Optional[CPU] = None
self.cfg: RunConfig | None = None
self.cpu: CPU | None = None
self.input_files = []
self.selected_ins_sets = []
@ -129,7 +129,7 @@ class RiscemuMain:
def register_all_program_loaders(self):
self.available_file_loaders.append(AssemblyFileLoader)
def parse_argv(self, argv: List[str]):
def parse_argv(self, argv: list[str]):
parser = argparse.ArgumentParser(
description="RISC-V Userspace emulator",
prog="riscemu",
@ -153,7 +153,7 @@ class RiscemuMain:
setattr(args, "ins", {k: True for k in self.available_ins_sets})
# create RunConfig
self.cfg = self.create_config(args)
self.cfg = self.config_from_parsed_args(args)
# set input files
self.input_files = args.files
@ -167,23 +167,16 @@ class RiscemuMain:
# if use_libc is given, attach libc to path
if self.cfg.use_libc:
self.add_libc_to_input_files()
def add_libc_to_input_files(self):
"""
This adds the provided riscemu libc to the programs runtime.
"""
libc_path = os.path.join(
os.path.dirname(__file__),
"..",
"libc",
"*.s",
)
for path in glob.iglob(libc_path):
if path not in self.input_files:
libc_path = os.path.join(
os.path.dirname(__file__),
"..",
"libc",
"*.s",
)
for path in glob.iglob(libc_path):
self.input_files.append(path)
def create_config(self, args: argparse.Namespace) -> RunConfig:
def config_from_parsed_args(self, args: argparse.Namespace) -> RunConfig:
# create a RunConfig from the cli args
cfg_dict = dict(
stack_size=args.stack_size,
@ -215,7 +208,7 @@ class RiscemuMain:
for p in programs:
self.cpu.mmu.load_program(p)
def run_from_cli(self, argv: List[str]):
def run(self, argv: list[str]):
# register everything
self.register_all_isas()
self.register_all_program_loaders()
@ -228,29 +221,6 @@ class RiscemuMain:
# run the program
self.cpu.launch(self.cfg.verbosity > 1)
def run(self):
"""
This assumes that these values were set externally:
- available_file_loaders: A list of available file loaders.
Can be set using .register_all_program_loaders()
- cfg: The RunConfig object. Can be directly assigned to the attribute
- input_files: A list of assembly files to load.
- selected_ins_sets: A list of instruction sets the CPU should support.
"""
assert self.cfg is not None, "self.cfg must be set before calling run()"
assert self.selected_ins_sets, "self.selected_ins_sets cannot be empty"
assert self.input_files, "self.input_files cannot be empty"
if self.cfg.use_libc:
self.add_libc_to_input_files()
self.instantiate_cpu()
self.load_programs()
# run the program
self.cpu.launch(self.cfg.verbosity > 1)
class OptionStringAction(argparse.Action):
def __init__(self, option_strings, dest, keys=None, omit_empty=False, **kwargs):

@ -7,7 +7,7 @@ SPDX-License-Identifier: MIT
import sys
from dataclasses import dataclass
from math import log2, ceil
from typing import Dict, IO, Union
from typing import Dict, IO
from .types import BinaryDataMemorySection, MemoryFlags
from .colors import FMT_SYSCALL, FMT_NONE
@ -70,7 +70,7 @@ class Syscall:
def __repr__(self):
return "Syscall(id={}, name={})".format(self.id, self.name)
def ret(self, code: Union[int, Int32]):
def ret(self, code: int | Int32):
self.cpu.regs.set("a0", Int32(code))

Loading…
Cancel
Save