Merge tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm
[cascardo/linux.git] / drivers / clk / sunxi-ng / ccu_div.h
1 /*
2  * Copyright (c) 2016 Maxime Ripard. All rights reserved.
3  *
4  * This software is licensed under the terms of the GNU General Public
5  * License version 2, as published by the Free Software Foundation, and
6  * may be copied, distributed, and modified under those terms.
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11  * GNU General Public License for more details.
12  */
13
14 #ifndef _CCU_DIV_H_
15 #define _CCU_DIV_H_
16
17 #include <linux/clk-provider.h>
18
19 #include "ccu_common.h"
20 #include "ccu_mux.h"
21
22 struct _ccu_div {
23         u8                      shift;
24         u8                      width;
25
26         u32                     flags;
27
28         struct clk_div_table    *table;
29 };
30
31 #define _SUNXI_CCU_DIV_TABLE_FLAGS(_shift, _width, _table, _flags)      \
32         {                                                               \
33                 .shift  = _shift,                                       \
34                 .width  = _width,                                       \
35                 .flags  = _flags,                                       \
36                 .table  = _table,                                       \
37         }
38
39 #define _SUNXI_CCU_DIV_FLAGS(_shift, _width, _flags)                    \
40         _SUNXI_CCU_DIV_TABLE_FLAGS(_shift, _width, NULL, _flags)
41
42 #define _SUNXI_CCU_DIV_TABLE(_shift, _width, _table)                    \
43         _SUNXI_CCU_DIV_TABLE_FLAGS(_shift, _width, _table, 0)
44
45 #define _SUNXI_CCU_DIV(_shift, _width)                                  \
46         _SUNXI_CCU_DIV_TABLE_FLAGS(_shift, _width, NULL, 0)
47
48 struct ccu_div {
49         u32                     enable;
50
51         struct _ccu_div         div;
52         struct ccu_mux_internal mux;
53         struct ccu_common       common;
54 };
55
56 #define SUNXI_CCU_DIV_TABLE_WITH_GATE(_struct, _name, _parent, _reg,    \
57                                       _shift, _width,                   \
58                                       _table, _gate, _flags)            \
59         struct ccu_div _struct = {                                      \
60                 .div            = _SUNXI_CCU_DIV_TABLE(_shift, _width,  \
61                                                        _table),         \
62                 .enable         = _gate,                                \
63                 .common = {                                             \
64                         .reg            = _reg,                         \
65                         .hw.init        = CLK_HW_INIT(_name,            \
66                                                       _parent,          \
67                                                       &ccu_div_ops,     \
68                                                       _flags),          \
69                 }                                                       \
70         }
71
72
73 #define SUNXI_CCU_DIV_TABLE(_struct, _name, _parent, _reg,              \
74                             _shift, _width,                             \
75                             _table, _flags)                             \
76         SUNXI_CCU_DIV_TABLE_WITH_GATE(_struct, _name, _parent, _reg,    \
77                                       _shift, _width, _table, 0,        \
78                                       _flags)
79
80 #define SUNXI_CCU_M_WITH_MUX_GATE(_struct, _name, _parents, _reg,       \
81                                   _mshift, _mwidth, _muxshift, _muxwidth, \
82                                   _gate, _flags)                        \
83         struct ccu_div _struct = {                                      \
84                 .enable = _gate,                                        \
85                 .div    = _SUNXI_CCU_DIV(_mshift, _mwidth),             \
86                 .mux    = SUNXI_CLK_MUX(_muxshift, _muxwidth),          \
87                 .common = {                                             \
88                         .reg            = _reg,                         \
89                         .hw.init        = CLK_HW_INIT_PARENTS(_name,    \
90                                                               _parents, \
91                                                               &ccu_div_ops, \
92                                                               _flags),  \
93                 },                                                      \
94         }
95
96 #define SUNXI_CCU_M_WITH_MUX(_struct, _name, _parents, _reg,            \
97                              _mshift, _mwidth, _muxshift, _muxwidth,    \
98                              _flags)                                    \
99         SUNXI_CCU_M_WITH_MUX_GATE(_struct, _name, _parents, _reg,       \
100                                   _mshift, _mwidth, _muxshift, _muxwidth, \
101                                   0, _flags)
102
103
104 #define SUNXI_CCU_M_WITH_GATE(_struct, _name, _parent, _reg,            \
105                               _mshift, _mwidth, _gate,                  \
106                               _flags)                                   \
107         struct ccu_div _struct = {                                      \
108                 .enable = _gate,                                        \
109                 .div    = _SUNXI_CCU_DIV(_mshift, _mwidth),             \
110                 .common = {                                             \
111                         .reg            = _reg,                         \
112                         .hw.init        = CLK_HW_INIT(_name,            \
113                                                       _parent,          \
114                                                       &ccu_div_ops,     \
115                                                       _flags),          \
116                 },                                                      \
117         }
118
119 #define SUNXI_CCU_M(_struct, _name, _parent, _reg, _mshift, _mwidth,    \
120                     _flags)                                             \
121         SUNXI_CCU_M_WITH_GATE(_struct, _name, _parent, _reg,            \
122                               _mshift, _mwidth, 0, _flags)
123
124 static inline struct ccu_div *hw_to_ccu_div(struct clk_hw *hw)
125 {
126         struct ccu_common *common = hw_to_ccu_common(hw);
127
128         return container_of(common, struct ccu_div, common);
129 }
130
131 extern const struct clk_ops ccu_div_ops;
132
133 #endif /* _CCU_DIV_H_ */