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 System; 8 using System.Text; 9 using Antmicro.Renode.Exceptions; 10 using Endianess = ELFSharp.ELF.Endianess; 11 12 namespace Antmicro.Renode.Utilities.GDB.Commands 13 { 14 internal class ReadMemoryCommand : Command 15 { ReadMemoryCommand(CommandsManager manager)16 public ReadMemoryCommand(CommandsManager manager) : base(manager) 17 { 18 } 19 20 [Execute("m")] Execute( [Argument(Separator = B, Encoding = ArgumentAttribute.ArgumentEncoding.HexNumber)]ulong address, [Argument(Encoding = ArgumentAttribute.ArgumentEncoding.HexNumber)]ulong length)21 public PacketData Execute( 22 [Argument(Separator = ',', Encoding = ArgumentAttribute.ArgumentEncoding.HexNumber)]ulong address, 23 [Argument(Encoding = ArgumentAttribute.ArgumentEncoding.HexNumber)]ulong length) 24 { 25 var content = new StringBuilder(); 26 var accesses = GetTranslatedAccesses(address, length, write: false); 27 28 if(accesses == null) 29 { 30 return PacketData.ErrorReply(Error.BadAddress); 31 } 32 33 foreach(var access in accesses) 34 { 35 if(manager.Machine.SystemBus.WhatIsAt(access.Address, context: manager.Cpu) == null) 36 { 37 return PacketData.ErrorReply(Error.BadAddress); 38 } 39 40 byte[] data; 41 ulong val; 42 try 43 { 44 switch(access.Length) 45 { 46 case 1: 47 val = manager.Machine.SystemBus.ReadByte(access.Address, context: manager.Cpu); 48 data = BytesFromValue(val, access.Length); 49 break; 50 case 2: 51 val = manager.Machine.SystemBus.ReadWord(access.Address, context: manager.Cpu); 52 data = BytesFromValue(val, access.Length); 53 break; 54 case 4: 55 val = manager.Machine.SystemBus.ReadDoubleWord(access.Address, context: manager.Cpu); 56 data = BytesFromValue(val, access.Length); 57 break; 58 case 8: 59 val = manager.Machine.SystemBus.ReadQuadWord(access.Address, context: manager.Cpu); 60 data = BytesFromValue(val, access.Length); 61 break; 62 default: 63 data = manager.Machine.SystemBus.ReadBytes(access.Address, (int)access.Length, context: manager.Cpu); 64 break; 65 } 66 } 67 catch(RecoverableException) 68 { 69 return PacketData.ErrorReply(Error.BadAddress); 70 } 71 72 foreach(var b in data) 73 { 74 content.AppendFormat("{0:x2}", b); 75 } 76 } 77 78 return new PacketData(content.ToString()); 79 } 80 BytesFromValue(ulong val, ulong length)81 private byte [] BytesFromValue(ulong val, ulong length) 82 { 83 return BitHelper.GetBytesFromValue(val, (int)length, manager.Cpu.Endianness == Endianess.LittleEndian); 84 } 85 } 86 } 87