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 
8 using System;
9 using Antmicro.Migrant;
10 using Antmicro.Renode.Debugging;
11 using Antmicro.Renode.Logging;
12 
13 namespace Antmicro.Renode.Peripherals.CPU
14 {
15     public abstract class CPUCore : IdentifiableObject, IEmulationElement
16     {
CPUCore(uint cpuId)17         protected CPUCore(uint cpuId)
18         {
19             MultiprocessingId = cpuId;
20         }
21 
Start()22         public virtual void Start()
23         {
24             Resume();
25         }
26 
Resume()27         public void Resume()
28         {
29             lock(pauseLock)
30             {
31                 if(isAborted || !isPaused)
32                 {
33                     return;
34                 }
35                 started = true;
36                 isPaused = false;
37                 OnResume();
38                 this.NoisyLog("Resumed.");
39             }
40         }
41 
Pause()42         public void Pause()
43         {
44             if(isAborted || isPaused)
45             {
46                 // cpu is already paused or aborted
47                 return;
48             }
49 
50             lock(pauseLock)
51             {
52                 OnPause();
53             }
54         }
55 
56         /// <summary>
57         /// An ID that can identify a CPU in a multicore environment. Its specific interpretation will depend on CPU architecture.
58         /// </summary>
59         /// <remarks>
60         /// This ID doesn't have to be either globally unique or sequential.
61         /// On certain heterogeneous systems, there might be processors with duplicate IDs, which can be valid, depending on the platform configuration.
62         /// </remarks>
63         public uint MultiprocessingId { get; }
64 
65         public bool IsStarted => started;
66 
67         public virtual bool IsHalted { get; set; }
68 
Abort()69         protected void Abort()
70         {
71             isAborted = true;
72             this.Log(LogLevel.Error, "CPU aborted");
73         }
74 
OnResume()75         protected virtual void OnResume()
76         {
77             // by default do nothing
78         }
79 
OnPause()80         protected virtual void OnPause()
81         {
82             // by default do nothing
83         }
84 
85         [Transient]
86         protected volatile bool started;
87 
88         protected volatile bool isAborted;
89         protected volatile bool isPaused;
90 
91         protected readonly object pauseLock = new object();
92         protected readonly object haltedLock = new object();
93     }
94 }
95