1 //
2 // Copyright (c) 2010-2018 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 AntShell.Commands;
10 using Antmicro.Renode.UserInterface.Tokenizer;
11 using Antmicro.Renode.Core;
12 using System.Linq;
13 using Antmicro.Renode.Peripherals;
14 using System.Text;
15 using Antmicro.Renode.Exceptions;
16 
17 namespace Antmicro.Renode.UserInterface.Commands
18 {
19     public class ShowBackendAnalyzerCommand : AutoLoadCommand
20     {
PrintHelp(ICommandInteraction writer)21         public override void PrintHelp(ICommandInteraction writer)
22         {
23             writer.WriteLine("Usage:");
24             writer.WriteLine("------");
25             writer.WriteLine("showAnalyzer ([externalName]) [peripheral] ([typeName])");
26             writer.WriteLine("\tshows analyzer for [peripheral]");
27             writer.WriteLine("");
28             writer.WriteLine("[externalName] (optional) - if set, command will create external named [externalName]; this can be used only for analyzers implementing IExternal interface");
29             writer.WriteLine("[typeName] (optional) - if set, command will select analyzer provided in class [typeName]; this must be used when there are more than one analyzers available and no default is set");
30         }
31 
32         [Runnable]
Run(ICommandInteraction writer, StringToken analyzerName, LiteralToken peripheral, LiteralToken analyzerTypeName)33         public void Run(ICommandInteraction writer, StringToken analyzerName, LiteralToken peripheral, LiteralToken analyzerTypeName)
34         {
35             if(!Emulator.ShowAnalyzers)
36             {
37                 return;
38             }
39             try
40             {
41                 var analyzer = GetAnalyzer(peripheral.Value, analyzerTypeName == null ? null : analyzerTypeName.Value);
42                 if (analyzerName != null)
43                 {
44                     EmulationManager.Instance.CurrentEmulation.ExternalsManager.AddExternal((IExternal)analyzer, analyzerName.Value);
45                 }
46                 analyzer.Show();
47             }
48             catch (Exception e)
49             {
50                 throw new RecoverableException(string.Format("Received '{0}' error while initializing analyzer for: {1}. Are you missing a required plugin?", e.Message, peripheral.Value));
51             }
52         }
53 
54         [Runnable]
Run(ICommandInteraction writer, StringToken analyzerName, LiteralToken peripheral)55         public void Run(ICommandInteraction writer, StringToken analyzerName, LiteralToken peripheral)
56         {
57             Run(writer, analyzerName, peripheral, null);
58         }
59 
60         [Runnable]
Run(ICommandInteraction writer, LiteralToken peripheral)61         public void Run(ICommandInteraction writer, LiteralToken peripheral)
62         {
63             Run(writer, peripheral, null);
64         }
65 
66         [Runnable]
Run(ICommandInteraction writer, LiteralToken peripheral, LiteralToken analyzerTypeName)67         public void Run(ICommandInteraction writer, LiteralToken peripheral, LiteralToken analyzerTypeName)
68         {
69             Run(writer, null, peripheral, analyzerTypeName);
70         }
71 
GetAnalyzer(string peripheralName, string analyzerTypeName)72         public IAnalyzableBackendAnalyzer GetAnalyzer(string peripheralName, string analyzerTypeName)
73         {
74             var emu = EmulationManager.Instance.CurrentEmulation;
75             IPeripheral p;
76 
77             var m = monitor.Machine;
78             try
79             {
80                 p = (IPeripheral)monitor.ConvertValueOrThrowRecoverable(peripheralName, typeof(IPeripheral));
81             }
82             catch(RecoverableException)
83             {
84                 throw new Exception(string.Format("Peripheral not found: {0}", peripheralName));
85             }
86 
87             IAnalyzableBackend backend;
88             if(!emu.BackendManager.TryGetBackendFor(p, out backend))
89             {
90                 throw new Exception(string.Format("No backend found for {0}", peripheralName));
91             }
92 
93             IAnalyzableBackendAnalyzer analyzer;
94             var available = emu.BackendManager.GetAvailableAnalyzersFor(backend).ToArray();
95             if(!available.Any())
96             {
97                 throw new Exception(string.Format("No suitable analyzer found for {0}", peripheralName));
98             }
99 
100             if(analyzerTypeName != null)
101             {
102                 if(!available.Contains(analyzerTypeName))
103                 {
104                     throw new Exception(string.Format("{0}: analyzer not found.", analyzerTypeName));
105                 }
106 
107                 if(!emu.BackendManager.TryCreateAnalyzerForBackend(backend, analyzerTypeName, out analyzer))
108                 {
109                     throw new Exception(string.Format("Couldn't create analyzer {0}.", analyzerTypeName));
110                 }
111             }
112             else if(!emu.BackendManager.TryCreateAnalyzerForBackend(backend, out analyzer))
113             {
114                 var buffer = new StringBuilder();
115                 buffer.AppendFormat("More than one analyzer available for {0}. Please choose which one to use:\r\n", peripheralName);
116                 foreach(var x in available)
117                 {
118                     buffer.AppendFormat(string.Format("\t{0}\r\n", x));
119                 }
120                 throw new Exception(buffer.ToString());
121             }
122 
123             return analyzer;
124         }
125 
ShowBackendAnalyzerCommand(Monitor monitor)126         public ShowBackendAnalyzerCommand(Monitor monitor) : base(monitor, "showAnalyzer", "opens a peripheral backend analyzer.", "sa")
127         {
128         }
129     }
130 }
131 
132