1 // 2 // Copyright (c) 2010-2024 Antmicro 3 // Copyright (c) 2011-2015 Realtime Embedded 4 // 5 // This file is licensed under the MIT License. 6 // Full license text is available in 'licenses/MIT.txt'. 7 // 8 using System; 9 using Microsoft.Scripting.Hosting; 10 using Antmicro.Renode.Peripherals.Bus; 11 using Antmicro.Migrant.Hooks; 12 using Antmicro.Migrant; 13 using System.Linq; 14 using Antmicro.Renode.Core; 15 16 namespace Antmicro.Renode.Peripherals.Python 17 { 18 public class PeripheralPythonEngine : PythonEngine 19 { 20 private readonly static string[] Imports = 21 { 22 "from Antmicro.Renode.Logging import Logger as logger", 23 "from Antmicro.Renode.Logging import LogLevel", 24 }; 25 26 protected override string[] ReservedVariables 27 { 28 get { return base.ReservedVariables.Union(PeripheralPythonEngine.InnerReservedVariables).ToArray(); } 29 } 30 31 private readonly static string[] InnerReservedVariables = 32 { 33 "request", 34 "self", 35 "size", 36 "logger", 37 "LogLevel" 38 }; 39 InitScope(ScriptSource script)40 private void InitScope(ScriptSource script) 41 { 42 Request = new PythonRequest(); 43 44 Scope.SetVariable("request", Request); 45 Scope.SetVariable("self", peripheral); 46 Scope.SetVariable("size", peripheral.Size); 47 48 source = script; 49 code = Compile(source); 50 } 51 PeripheralPythonEngine(PythonPeripheral peripheral)52 public PeripheralPythonEngine(PythonPeripheral peripheral) 53 { 54 this.peripheral = peripheral; 55 InitScope(Engine.CreateScriptSourceFromString(Aggregate(Imports))); 56 } 57 PeripheralPythonEngine(PythonPeripheral peripheral, Func<ScriptEngine, ScriptSource> sourceGenerator)58 public PeripheralPythonEngine(PythonPeripheral peripheral, Func<ScriptEngine, ScriptSource> sourceGenerator) 59 { 60 this.peripheral = peripheral; 61 InitScope(sourceGenerator(Engine)); 62 } 63 64 public string Code 65 { 66 get 67 { 68 return source.GetCode(); 69 } 70 } 71 ExecuteCode()72 public void ExecuteCode() 73 { 74 Execute(code); 75 } 76 77 [Transient] 78 private ScriptSource source; 79 80 [Transient] 81 private CompiledCode code; 82 Init()83 protected override void Init() 84 { 85 base.Init(); 86 InitScope(Engine.CreateScriptSourceFromString(codeContent)); 87 codeContent = null; 88 } 89 90 #region Serialization 91 92 [PreSerialization] BeforeSerialization()93 protected void BeforeSerialization() 94 { 95 codeContent = Code; 96 } 97 98 [PostSerialization] AfterDeSerialization()99 private void AfterDeSerialization() 100 { 101 codeContent = null; 102 } 103 104 private string codeContent; 105 106 #endregion 107 108 [Transient] 109 private PythonRequest request; 110 111 public PythonRequest Request 112 { 113 get 114 { 115 return request; 116 } 117 private set 118 { 119 request = value; 120 } 121 } 122 123 private readonly PythonPeripheral peripheral; 124 125 // naming convention here is pythonic 126 public class PythonRequest 127 { 128 public ulong value { get; set; } 129 public byte length { get; set; } 130 public RequestType type { get; set; } 131 public long offset { get; set; } 132 public ulong absolute { get; set; } 133 public ulong counter { get; set; } 134 135 public bool isInit 136 { 137 get 138 { 139 return type == RequestType.INIT; 140 } 141 } 142 143 public bool isRead 144 { 145 get 146 { 147 return type == RequestType.READ; 148 } 149 } 150 151 public bool isWrite 152 { 153 get 154 { 155 return type == RequestType.WRITE; 156 } 157 } 158 159 public bool isUser 160 { 161 get 162 { 163 return type == RequestType.USER; 164 } 165 } 166 167 public enum RequestType 168 { 169 READ, 170 WRITE, 171 INIT, 172 USER 173 } 174 } 175 } 176 } 177