1 // 2 // Copyright (c) 2010-2024 Antmicro 3 // 4 // This file is licensed under the MIT License. 5 // Full license text is available in 'licenses/MIT.txt'. 6 // 7 using Antmicro.Renode.Core; 8 using ELFSharp.ELF; 9 using Antmicro.Renode.Utilities; 10 using Antmicro.Renode.Logging; 11 using Antmicro.Renode.Peripherals.Timers; 12 13 namespace Antmicro.Renode.Peripherals.CPU 14 { 15 public partial class Minerva : RiscV32 16 { Minerva(IMachine machine, uint hartId = 0, IRiscVTimeProvider timeProvider = null)17 public Minerva(IMachine machine, uint hartId = 0, IRiscVTimeProvider timeProvider = null) : base(machine, "rv32i", timeProvider, hartId, PrivilegedArchitecture.Priv1_09, Endianess.LittleEndian) 18 { 19 CSRValidation = CSRValidationLevel.None; 20 21 RegisterCSR((ulong)CSRs.IrqMask, () => (ulong)irqMask, value => 22 { 23 lock(locker) 24 { 25 irqMask = (uint)value; 26 this.Log(LogLevel.Noisy, "IRQ mask set to 0x{0:X}", irqMask); 27 Update(); 28 } 29 }); 30 RegisterCSR((ulong)CSRs.IrqPending, () => (ulong)irqPending, value => 31 { 32 lock(locker) 33 { 34 irqPending = (uint)value; 35 this.Log(LogLevel.Noisy, "IRQ pending set to 0x{0:X}", irqPending); 36 Update(); 37 } 38 }); 39 } 40 OnGPIO(int number, bool value)41 public override void OnGPIO(int number, bool value) 42 { 43 lock(locker) 44 { 45 this.Log(LogLevel.Noisy, "GPIO #{0} set to: {1}", number, value); 46 BitHelper.SetBit(ref irqPending, (byte)number, value); 47 Update(); 48 } 49 } 50 Update()51 private void Update() 52 { 53 //We support only Machine mode, with external interrupts. An additional interrupt controller would be required to have more advanced handling. 54 base.OnGPIO((int)IrqType.MachineExternalInterrupt, (irqPending & irqMask) != 0); 55 } 56 57 private uint irqMask; 58 private uint irqPending; 59 60 private readonly object locker = new object(); 61 62 private enum CSRs 63 { 64 IrqMask = 0x330, 65 IrqPending = 0x360, 66 } 67 } 68 } 69