1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0 */
2*4882a593Smuzhiyun #ifndef __ASMARM_CTI_H
3*4882a593Smuzhiyun #define __ASMARM_CTI_H
4*4882a593Smuzhiyun
5*4882a593Smuzhiyun #include <asm/io.h>
6*4882a593Smuzhiyun #include <asm/hardware/coresight.h>
7*4882a593Smuzhiyun
8*4882a593Smuzhiyun /* The registers' definition is from section 3.2 of
9*4882a593Smuzhiyun * Embedded Cross Trigger Revision: r0p0
10*4882a593Smuzhiyun */
11*4882a593Smuzhiyun #define CTICONTROL 0x000
12*4882a593Smuzhiyun #define CTISTATUS 0x004
13*4882a593Smuzhiyun #define CTILOCK 0x008
14*4882a593Smuzhiyun #define CTIPROTECTION 0x00C
15*4882a593Smuzhiyun #define CTIINTACK 0x010
16*4882a593Smuzhiyun #define CTIAPPSET 0x014
17*4882a593Smuzhiyun #define CTIAPPCLEAR 0x018
18*4882a593Smuzhiyun #define CTIAPPPULSE 0x01c
19*4882a593Smuzhiyun #define CTIINEN 0x020
20*4882a593Smuzhiyun #define CTIOUTEN 0x0A0
21*4882a593Smuzhiyun #define CTITRIGINSTATUS 0x130
22*4882a593Smuzhiyun #define CTITRIGOUTSTATUS 0x134
23*4882a593Smuzhiyun #define CTICHINSTATUS 0x138
24*4882a593Smuzhiyun #define CTICHOUTSTATUS 0x13c
25*4882a593Smuzhiyun #define CTIPERIPHID0 0xFE0
26*4882a593Smuzhiyun #define CTIPERIPHID1 0xFE4
27*4882a593Smuzhiyun #define CTIPERIPHID2 0xFE8
28*4882a593Smuzhiyun #define CTIPERIPHID3 0xFEC
29*4882a593Smuzhiyun #define CTIPCELLID0 0xFF0
30*4882a593Smuzhiyun #define CTIPCELLID1 0xFF4
31*4882a593Smuzhiyun #define CTIPCELLID2 0xFF8
32*4882a593Smuzhiyun #define CTIPCELLID3 0xFFC
33*4882a593Smuzhiyun
34*4882a593Smuzhiyun /* The below are from section 3.6.4 of
35*4882a593Smuzhiyun * CoreSight v1.0 Architecture Specification
36*4882a593Smuzhiyun */
37*4882a593Smuzhiyun #define LOCKACCESS 0xFB0
38*4882a593Smuzhiyun #define LOCKSTATUS 0xFB4
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun /**
41*4882a593Smuzhiyun * struct cti - cross trigger interface struct
42*4882a593Smuzhiyun * @base: mapped virtual address for the cti base
43*4882a593Smuzhiyun * @irq: irq number for the cti
44*4882a593Smuzhiyun * @trig_out_for_irq: triger out number which will cause
45*4882a593Smuzhiyun * the @irq happen
46*4882a593Smuzhiyun *
47*4882a593Smuzhiyun * cti struct used to operate cti registers.
48*4882a593Smuzhiyun */
49*4882a593Smuzhiyun struct cti {
50*4882a593Smuzhiyun void __iomem *base;
51*4882a593Smuzhiyun int irq;
52*4882a593Smuzhiyun int trig_out_for_irq;
53*4882a593Smuzhiyun };
54*4882a593Smuzhiyun
55*4882a593Smuzhiyun /**
56*4882a593Smuzhiyun * cti_init - initialize the cti instance
57*4882a593Smuzhiyun * @cti: cti instance
58*4882a593Smuzhiyun * @base: mapped virtual address for the cti base
59*4882a593Smuzhiyun * @irq: irq number for the cti
60*4882a593Smuzhiyun * @trig_out: triger out number which will cause
61*4882a593Smuzhiyun * the @irq happen
62*4882a593Smuzhiyun *
63*4882a593Smuzhiyun * called by machine code to pass the board dependent
64*4882a593Smuzhiyun * @base, @irq and @trig_out to cti.
65*4882a593Smuzhiyun */
cti_init(struct cti * cti,void __iomem * base,int irq,int trig_out)66*4882a593Smuzhiyun static inline void cti_init(struct cti *cti,
67*4882a593Smuzhiyun void __iomem *base, int irq, int trig_out)
68*4882a593Smuzhiyun {
69*4882a593Smuzhiyun cti->base = base;
70*4882a593Smuzhiyun cti->irq = irq;
71*4882a593Smuzhiyun cti->trig_out_for_irq = trig_out;
72*4882a593Smuzhiyun }
73*4882a593Smuzhiyun
74*4882a593Smuzhiyun /**
75*4882a593Smuzhiyun * cti_map_trigger - use the @chan to map @trig_in to @trig_out
76*4882a593Smuzhiyun * @cti: cti instance
77*4882a593Smuzhiyun * @trig_in: trigger in number
78*4882a593Smuzhiyun * @trig_out: trigger out number
79*4882a593Smuzhiyun * @channel: channel number
80*4882a593Smuzhiyun *
81*4882a593Smuzhiyun * This function maps one trigger in of @trig_in to one trigger
82*4882a593Smuzhiyun * out of @trig_out using the channel @chan.
83*4882a593Smuzhiyun */
cti_map_trigger(struct cti * cti,int trig_in,int trig_out,int chan)84*4882a593Smuzhiyun static inline void cti_map_trigger(struct cti *cti,
85*4882a593Smuzhiyun int trig_in, int trig_out, int chan)
86*4882a593Smuzhiyun {
87*4882a593Smuzhiyun void __iomem *base = cti->base;
88*4882a593Smuzhiyun unsigned long val;
89*4882a593Smuzhiyun
90*4882a593Smuzhiyun val = __raw_readl(base + CTIINEN + trig_in * 4);
91*4882a593Smuzhiyun val |= BIT(chan);
92*4882a593Smuzhiyun __raw_writel(val, base + CTIINEN + trig_in * 4);
93*4882a593Smuzhiyun
94*4882a593Smuzhiyun val = __raw_readl(base + CTIOUTEN + trig_out * 4);
95*4882a593Smuzhiyun val |= BIT(chan);
96*4882a593Smuzhiyun __raw_writel(val, base + CTIOUTEN + trig_out * 4);
97*4882a593Smuzhiyun }
98*4882a593Smuzhiyun
99*4882a593Smuzhiyun /**
100*4882a593Smuzhiyun * cti_enable - enable the cti module
101*4882a593Smuzhiyun * @cti: cti instance
102*4882a593Smuzhiyun *
103*4882a593Smuzhiyun * enable the cti module
104*4882a593Smuzhiyun */
cti_enable(struct cti * cti)105*4882a593Smuzhiyun static inline void cti_enable(struct cti *cti)
106*4882a593Smuzhiyun {
107*4882a593Smuzhiyun __raw_writel(0x1, cti->base + CTICONTROL);
108*4882a593Smuzhiyun }
109*4882a593Smuzhiyun
110*4882a593Smuzhiyun /**
111*4882a593Smuzhiyun * cti_disable - disable the cti module
112*4882a593Smuzhiyun * @cti: cti instance
113*4882a593Smuzhiyun *
114*4882a593Smuzhiyun * enable the cti module
115*4882a593Smuzhiyun */
cti_disable(struct cti * cti)116*4882a593Smuzhiyun static inline void cti_disable(struct cti *cti)
117*4882a593Smuzhiyun {
118*4882a593Smuzhiyun __raw_writel(0, cti->base + CTICONTROL);
119*4882a593Smuzhiyun }
120*4882a593Smuzhiyun
121*4882a593Smuzhiyun /**
122*4882a593Smuzhiyun * cti_irq_ack - clear the cti irq
123*4882a593Smuzhiyun * @cti: cti instance
124*4882a593Smuzhiyun *
125*4882a593Smuzhiyun * clear the cti irq
126*4882a593Smuzhiyun */
cti_irq_ack(struct cti * cti)127*4882a593Smuzhiyun static inline void cti_irq_ack(struct cti *cti)
128*4882a593Smuzhiyun {
129*4882a593Smuzhiyun void __iomem *base = cti->base;
130*4882a593Smuzhiyun unsigned long val;
131*4882a593Smuzhiyun
132*4882a593Smuzhiyun val = __raw_readl(base + CTIINTACK);
133*4882a593Smuzhiyun val |= BIT(cti->trig_out_for_irq);
134*4882a593Smuzhiyun __raw_writel(val, base + CTIINTACK);
135*4882a593Smuzhiyun }
136*4882a593Smuzhiyun
137*4882a593Smuzhiyun /**
138*4882a593Smuzhiyun * cti_unlock - unlock cti module
139*4882a593Smuzhiyun * @cti: cti instance
140*4882a593Smuzhiyun *
141*4882a593Smuzhiyun * unlock the cti module, or else any writes to the cti
142*4882a593Smuzhiyun * module is not allowed.
143*4882a593Smuzhiyun */
cti_unlock(struct cti * cti)144*4882a593Smuzhiyun static inline void cti_unlock(struct cti *cti)
145*4882a593Smuzhiyun {
146*4882a593Smuzhiyun __raw_writel(CS_LAR_KEY, cti->base + LOCKACCESS);
147*4882a593Smuzhiyun }
148*4882a593Smuzhiyun
149*4882a593Smuzhiyun /**
150*4882a593Smuzhiyun * cti_lock - lock cti module
151*4882a593Smuzhiyun * @cti: cti instance
152*4882a593Smuzhiyun *
153*4882a593Smuzhiyun * lock the cti module, so any writes to the cti
154*4882a593Smuzhiyun * module will be not allowed.
155*4882a593Smuzhiyun */
cti_lock(struct cti * cti)156*4882a593Smuzhiyun static inline void cti_lock(struct cti *cti)
157*4882a593Smuzhiyun {
158*4882a593Smuzhiyun __raw_writel(~CS_LAR_KEY, cti->base + LOCKACCESS);
159*4882a593Smuzhiyun }
160*4882a593Smuzhiyun #endif
161