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.Collections.Generic;
8 using Antmicro.Renode.Core;
9 using Antmicro.Renode.Core.Structure;
10 using Antmicro.Renode.Core.Structure.Registers;
11 using Antmicro.Renode.Peripherals.Bus;
12 using Antmicro.Renode.Peripherals.MTD;
13 
14 namespace Antmicro.Renode.Peripherals.SPI
15 {
16     public class SynopsysSSI : NullRegistrationPointPeripheralContainer<ISPIPeripheral>, IDoubleWordPeripheral, IProvidesRegisterCollection<DoubleWordRegisterCollection>, IKnownSize
17     {
SynopsysSSI(IMachine machine)18         SynopsysSSI(IMachine machine): base(machine)
19         {
20             RegistersCollection = new DoubleWordRegisterCollection(this);
21 
22             DefineRegisters();
23         }
24 
Reset()25         public override void Reset()
26         {
27             RegistersCollection.Reset();
28         }
29 
ReadDoubleWord(long offset)30         public uint ReadDoubleWord(long offset)
31         {
32             return RegistersCollection.Read(offset);
33         }
34 
WriteDoubleWord(long offset, uint value)35         public void WriteDoubleWord(long offset, uint value)
36         {
37             RegistersCollection.Write(offset, value);
38         }
39 
40         public long Size
41         {
42             get
43             {
44                 return 0x118;
45             }
46         }
47 
48         public DoubleWordRegisterCollection RegistersCollection { get; }
49 
DefineRegisters()50         private void DefineRegisters()
51         {
52             Registers.Control0.Define(this)
53                 .WithTag("Data Frame Size", 0, 5)
54                 .WithReservedBits(5, 1)
55                 .WithTag("Frame Format", 6, 2)
56                 .WithTaggedFlag("Serial Clock Phase", 8)
57                 .WithTaggedFlag("Serial Clock Polarity", 9)
58                 .WithTag("Transfer Mode", 10, 2)
59                 .WithTaggedFlag("Slave Output Enable", 12)
60                 .WithTaggedFlag("Shift Register Loop", 13)
61                 .WithTaggedFlag("Slave Select Toggle Enable", 14)
62                 .WithReservedBits(15, 1)
63                 .WithTag("Control Frame Size", 16, 4)
64                 .WithReservedBits(20, 2)
65                 .WithTag("SPI Frame Format", 22, 2)
66                 .WithTaggedFlag("SPI Hyperbus Frame format enable", 24)
67                 .WithReservedBits(25, 6)
68             ;
69 
70             Registers.Control1.Define(this)
71                 .WithTag("Number of Data Frames", 0, 16)
72                 .WithReservedBits(16, 16)
73             ;
74 
75             Registers.SSIEnable.Define(this)
76                 .WithTaggedFlag("SSI Enable", 0)
77                 .WithReservedBits(1, 31)
78             ;
79 
80             Registers.MicrowireControl.Define(this)
81                 .WithTaggedFlag("Microwire Transfer Mode", 0)
82                 .WithTaggedFlag("Microwire Control", 1)
83                 .WithTaggedFlag("Microwire Handshaking", 2)
84                 .WithReservedBits(3, 29)
85             ;
86 
87             Registers.SlaveEnable.Define(this)
88                 .WithTaggedFlags("Slave Select Enable", 0, 32)
89             ;
90 
91             Registers.BaudRateSelect.Define(this)
92                 .WithTag("SSI Clock Divider", 0, 16)
93                 .WithReservedBits(16, 16)
94             ;
95 
96             Registers.TransmitFIFOThreshold.Define(this)
97                 .WithTag("Transmit FIFO Threshold", 0, 16)
98                 .WithTag("Transfer start FIFO level", 16, 16)
99             ;
100 
101             Registers.ReceiveFIFOThreshold.Define(this)
102                 .WithTag("Receive FIFO Threshold", 0, 32)
103             ;
104 
105             Registers.TransmitFIFOLevel.Define(this)
106                 .WithTag("Transmit FIFO Level", 0, 32)
107             ;
108 
109             Registers.ReceiveFIFOLevel.Define(this)
110                 .WithTag("Receive FIFO Level", 0, 32)
111             ;
112 
113             Registers.Status.Define(this)
114                 .WithTaggedFlag("SSI Busy", 0)
115                 .WithTaggedFlag("Transmit FIFO Not Full", 1)
116                 .WithTaggedFlag("Transmit FIFO Empty", 2)
117                 .WithTaggedFlag("Receive FIFO Not Empty", 3)
118                 .WithTaggedFlag("Receive FIFO Full", 4)
119                 .WithTaggedFlag("Transmission Error", 5)
120                 .WithTaggedFlag("Data Collision Error", 6)
121                 .WithReservedBits(7, 26)
122             ;
123 
124             Registers.InterruptMask.Define(this)
125                 .WithTaggedFlag("Transmit FIFO Empty Interrupt Mask", 0)
126                 .WithTaggedFlag("Transmit FIFO Overflow Interrupt Mask", 1)
127                 .WithTaggedFlag("Receive FIFO Underflow Interrupt Mask", 2)
128                 .WithTaggedFlag("Receive FIFO Overflow Interrupt Mask", 3)
129                 .WithTaggedFlag("Receive FIFO Full Interrupt Mask", 4)
130                 .WithTaggedFlag("Multi-Master Contention Interrupt Mask", 5)
131                 .WithTaggedFlag("XIR Receive FIFO Overflow Interrupt Mask", 6)
132                 .WithReservedBits(7, 26)
133             ;
134 
135             Registers.InterruptStatus.Define(this)
136                 .WithTaggedFlag("Transmit FIFO Empty Interrupt Status", 0)
137                 .WithTaggedFlag("Transmit FIFO Overflow Interrupt Status", 1)
138                 .WithTaggedFlag("Receive FIFO Underflow Interrupt Status", 2)
139                 .WithTaggedFlag("Receive FIFO Overflow Interrupt Status", 3)
140                 .WithTaggedFlag("Receive FIFO Full Interrupt Status", 4)
141                 .WithTaggedFlag("Multi-Master Contention Interrupt Status", 5)
142                 .WithTaggedFlag("XIP Receive FIFO Overflow Interrupt Status", 6)
143                 .WithReservedBits(7, 26)
144             ;
145 
146             Registers.RawInterruptStatus.Define(this)
147                 .WithTaggedFlag("Transmit FIFO Empty Raw Interrupt Status", 0)
148                 .WithTaggedFlag("Transmit FIFO Overflow Raw Interrupt Status", 1)
149                 .WithTaggedFlag("Receive FIFO Underflow Raw Interrupt Status", 2)
150                 .WithTaggedFlag("Receive FIFO Overflow Raw Interrupt Status", 3)
151                 .WithTaggedFlag("Receive FIFO Full Raw Interrupt Status", 4)
152                 .WithTaggedFlag("Multi-Master Contention Raw Interrupt Status", 5)
153                 .WithTaggedFlag("XIP Receive FIFO Overflow Raw Interrupt Status", 6)
154                 .WithReservedBits(7, 26)
155             ;
156 
157             Registers.TransmitFIFOOverflowInterruptClear.Define(this)
158                 .WithTaggedFlag("Clear Transmit FIFO Overflow Interrupt", 0)
159                 .WithReservedBits(1, 31)
160             ;
161 
162             Registers.ReceiveFIFOOverflowInterruptClear.Define(this)
163                 .WithTaggedFlag("Clear Receive FIFO Overflow Interrupt", 0)
164                 .WithReservedBits(1, 31)
165             ;
166 
167             Registers.ReceiveFIFOUnderflowInterruptClear.Define(this)
168                 .WithTaggedFlag("Clear Receive FIFO Underflow Interrupt", 0)
169                 .WithReservedBits(1, 31)
170             ;
171 
172             Registers.MultiMasterInterruptClear.Define(this)
173                 .WithTaggedFlag("Clear Multi-Master Contention Interrupt", 0)
174                 .WithReservedBits(1, 31)
175             ;
176 
177             Registers.InterruptClear.Define(this)
178                 .WithTaggedFlag("Clear Interrupts", 0)
179                 .WithReservedBits(1, 31)
180             ;
181 
182             Registers.DMAControl.Define(this)
183                 .WithTaggedFlag("Receive DMA Enable", 0)
184                 .WithTaggedFlag("Transmit DMA Enable", 1)
185                 .WithReservedBits(2, 30)
186             ;
187 
188             Registers.DMATransmitDataLevel.Define(this)
189                 .WithTag("Transmit Data Level", 0, 32)
190             ;
191 
192             Registers.DMAReceiveDataLevel.Define(this)
193                 .WithTag("Receive Data Level", 0, 32)
194             ;
195 
196             Registers.Identification.Define(this)
197                 .WithTag("Identification Code", 0, 32)
198             ;
199 
200             Registers.VersionID.Define(this)
201                 .WithTag("Synopsys Component Version", 0, 32)
202             ;
203 
204             Registers.Data_0.DefineMany(this, 36,
205                 (register, registerIndex) =>
206                     register.WithTag($"Data {registerIndex}", 0, 32)
207             );
208 
209             Registers.RXSampleDelay.Define(this)
210                 .WithTag("Receive Data (rxd) Sample Delay", 0, 8)
211                 .WithReservedBits(8, 8)
212                 .WithTaggedFlag("Receive Data (rxd) Sampling Edge", 16)
213                 .WithReservedBits(17, 15)
214             ;
215 
216             Registers.SPIControl.Define(this)
217                 .WithTag("Transfer format", 0, 2)
218                 .WithTag("Length of Address", 2, 4)
219                 .WithReservedBits(6, 1)
220                 .WithTaggedFlag("XIP Mode Bits Enable", 7)
221                 .WithTag("D/Q/O instruction length", 8, 2)
222                 .WithReservedBits(10, 1)
223                 .WithTag("D/Q/O Wait Cycles", 11, 5)
224                 .WithTaggedFlag("SPI DDR Enable", 16)
225                 .WithTaggedFlag("Instruction DDR Enable", 17)
226                 .WithTaggedFlag("Read Data Strobe Enable", 18)
227                 .WithTaggedFlag("Fix DFS for XIP Transfers", 19)
228                 .WithTaggedFlag("XIP Instruction Enable", 20)
229                 .WithTaggedFlag("XIP Continuous Transfer Enable", 21)
230                 .WithReservedBits(22, 2)
231                 .WithTaggedFlag("SPI Data Mast Enable", 24)
232                 .WithTaggedFlag("Hypebus Enable rxds Signaling", 25)
233                 .WithTag("XIP Mode Bits Length", 26, 2)
234                 .WithReservedBits(28, 1)
235                 .WithTaggedFlag("Enable XIP Pre-fetch", 29)
236                 .WithTaggedFlag("Enable Clock Stretching in SPI", 30)
237                 .WithReservedBits(31, 1)
238             ;
239 
240             Registers.TransmitDriveEdge.Define(this)
241                 .WithTag("TXD Drive Edge", 0, 8)
242                 .WithReservedBits(8, 24)
243             ;
244 
245             Registers.XIPModeBits.Define(this)
246                 .WithTag("XIP Mode Bits To Send", 0, 16)
247                 .WithReservedBits(16, 16)
248             ;
249 
250             Registers.XIPINCRTransferOpcode.Define(this)
251                 .WithTag("XIP INCR Transfer Opcode", 0, 16)
252                 .WithReservedBits(16, 16)
253             ;
254 
255             Registers.XIPWRAPTransferOpcode.Define(this)
256                 .WithTag("XIP WRAP Transfer Opcode", 0, 16)
257                 .WithReservedBits(16, 16)
258             ;
259 
260             Registers.XIPControl.Define(this)
261                 .WithTag("SPI Frame Format", 0, 2)
262                 .WithTag("Address and Instruction Transfer Format", 2, 2)
263                 .WithTag("Length of Address", 4, 4)
264                 .WithReservedBits(8, 1)
265                 .WithTag("D/Q/O Mode Instruction Length", 9, 2)
266                 .WithReservedBits(11, 1)
267                 .WithTaggedFlag("XIP Mode Bits Enable", 12)
268                 .WithTag("D/Q/O Wait Cycles", 13, 5)
269                 .WithTaggedFlag("XIP Transfers DFS Fix", 18)
270                 .WithTaggedFlag("SPI DDR Enable", 19)
271                 .WithTaggedFlag("Instruction DDR Enable", 20)
272                 .WithTaggedFlag("Read Data Strobe Enable", 21)
273                 .WithTaggedFlag("XIP Instruction Enable", 22)
274                 .WithTaggedFlag("XIP Continuous Transfer Enable", 23)
275                 .WithTaggedFlag("XIP SPI Hybperbus Frame Format Enable", 24)
276                 .WithTaggedFlag("Hypebus Enable rxds Signaling", 25)
277                 .WithTag("XIP Mode Bits Length", 26, 2)
278                 .WithReservedBits(27, 1)
279                 .WithTaggedFlag("XIP Pre-fetch Enable", 29)
280                 .WithReservedBits(30, 2)
281             ;
282 
283             Registers.XIPSlaveEnable.Define(this)
284                 .WithTaggedFlags("Slave Select Enable", 0, 32)
285             ;
286 
287             Registers.XIPReceiveFifoOverflowInterruptClear.Define(this)
288                 .WithTaggedFlag("Clear XIP Receive FIFO Overflow Interrupt", 0)
289                 .WithReservedBits(1, 31)
290             ;
291 
292             Registers.XIPTimeOut.Define(this)
293                 .WithTag("XIP Time Out", 0, 8)
294                 .WithReservedBits(9, 23)
295             ;
296         }
297 
298         private enum Registers : long
299         {
300             Control0 = 0x0, // CTRLR0
301             Control1 = 0x4, // CTRLR1
302             SSIEnable = 0x8, // SSIENR
303             MicrowireControl = 0xC, // MWCR
304             SlaveEnable = 0x10, // SER
305             BaudRateSelect = 0x14, // BAUDR
306             TransmitFIFOThreshold = 0x18, // TXFTLR
307             ReceiveFIFOThreshold = 0x1C, // RXFTLR
308             TransmitFIFOLevel = 0x20, // TXFLR
309             ReceiveFIFOLevel = 0x24, // RXFLR
310             Status = 0x28, // SR
311             InterruptMask = 0x2C, // IMR
312             InterruptStatus = 0x30, // ISR
313             RawInterruptStatus = 0x34, // RISR
314             TransmitFIFOOverflowInterruptClear = 0x38, // TXOICR
315             ReceiveFIFOOverflowInterruptClear = 0x3C, // RXOICR
316             ReceiveFIFOUnderflowInterruptClear = 0x40, // RXUICR
317             MultiMasterInterruptClear = 0x44, // MSTICR
318             InterruptClear = 0x48, // ICR
319             DMAControl = 0x4C, // DMACR
320             DMATransmitDataLevel = 0x50, // DMATDLR
321             DMAReceiveDataLevel = 0x54, // DMARDLR
322             Identification = 0x58, // IDR
323             VersionID = 0x5C, // SSIC_VERSION_ID
324             Data_0 = 0x60, // DRx (0x60 + i*0x4, 0 <= i <= 35)
325             RXSampleDelay = 0xF0, // RX_SAMPLE_DELAY
326             SPIControl = 0xF4, // SPI_CTRLR0
327             TransmitDriveEdge = 0xF8, // DDR_DRIVE_EDGE
328             // XIP
329             XIPModeBits = 0xFC, // XIP_MODE_BITS
330             XIPINCRTransferOpcode = 0x100, // XIP_INCR_INST
331             XIPWRAPTransferOpcode = 0x104, // XIP_WRAP_INST
332             XIPControl = 0x108, // XIP_CTRL
333             XIPSlaveEnable = 0x10C, // XIP_SER
334             XIPReceiveFifoOverflowInterruptClear = 0x110, // XRXOICR
335             XIPTimeOut = 0x114, // XIP_CNT_TIME_OUT
336         }
337     }
338 }
339