1 /*
2  * Copyright (c) 2020 Antmicro <www.antmicro.com>
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #include <zephyr/types.h>
8 #include <zephyr/device.h>
9 #include <zephyr/devicetree.h>
10 #include <zephyr/drivers/clock_control.h>
11 #include <zephyr/drivers/clock_control/clock_control_litex.h>
12 #include "clock_control_litex.h"
13 #include <zephyr/logging/log.h>
14 #include <zephyr/logging/log_ctrl.h>
15 #include <zephyr/sys/util.h>
16 #include <errno.h>
17 #include <stdlib.h>
18 #include <stdio.h>
19 #include <zephyr/kernel.h>
20 
21 #include <soc.h>
22 
23 LOG_MODULE_REGISTER(CLK_CTRL_LITEX, CONFIG_CLOCK_CONTROL_LOG_LEVEL);
24 
25 static struct litex_clk_device *ldev;	/* global struct for whole driver */
26 static struct litex_clk_clkout *clkouts;/* clkout array for whole driver */
27 
28 /* All DRP regs addresses and sizes */
29 static const struct litex_drp_reg drp[] = {
30 	{DRP_ADDR_RESET,  1},
31 	{DRP_ADDR_LOCKED, 1},
32 	{DRP_ADDR_READ,   1},
33 	{DRP_ADDR_WRITE,  1},
34 	{DRP_ADDR_DRDY,   1},
35 	{DRP_ADDR_ADR,    1},
36 	{DRP_ADDR_DAT_W,  2},
37 	{DRP_ADDR_DAT_R,  2},
38 };
39 
litex_clk_regs_addr_init(void)40 struct litex_clk_regs_addr litex_clk_regs_addr_init(void)
41 {
42 	struct litex_clk_regs_addr m;
43 	uint32_t i, addr;
44 
45 	addr = CLKOUT0_REG1;
46 	for (i = 0; i <= CLKOUT_MAX; i++) {
47 		if (i == 5) {
48 		/*
49 		 *special case because CLKOUT5 have its reg addresses
50 		 *placed lower than other CLKOUTs
51 		 */
52 			m.clkout[5].reg1 = CLKOUT5_REG1;
53 			m.clkout[5].reg2 = CLKOUT5_REG2;
54 		} else {
55 			m.clkout[i].reg1 = addr;
56 			addr++;
57 			m.clkout[i].reg2 = addr;
58 			addr++;
59 		}
60 	}
61 	return m;
62 }
63 
64 /*
65  * These lookup tables are taken from:
66  * https://github.com/Digilent/Zybo-hdmi-out/blob/b991fff6e964420ae3c00c3dbee52f2ad748b3ba/sdk/displaydemo/src/dynclk/dynclk.h
67  *
68  *	2015 Copyright Digilent Incorporated
69  *	Author: Sam Bobrowicz
70  *
71  */
72 
73 /* MMCM loop filter lookup table */
74 static const uint32_t litex_clk_filter_table[] = {
75 	 0b0001011111,
76 	 0b0001010111,
77 	 0b0001111011,
78 	 0b0001011011,
79 	 0b0001101011,
80 	 0b0001110011,
81 	 0b0001110011,
82 	 0b0001110011,
83 	 0b0001110011,
84 	 0b0001001011,
85 	 0b0001001011,
86 	 0b0001001011,
87 	 0b0010110011,
88 	 0b0001010011,
89 	 0b0001010011,
90 	 0b0001010011,
91 	 0b0001010011,
92 	 0b0001010011,
93 	 0b0001010011,
94 	 0b0001010011,
95 	 0b0001010011,
96 	 0b0001010011,
97 	 0b0001010011,
98 	 0b0001100011,
99 	 0b0001100011,
100 	 0b0001100011,
101 	 0b0001100011,
102 	 0b0001100011,
103 	 0b0001100011,
104 	 0b0001100011,
105 	 0b0001100011,
106 	 0b0001100011,
107 	 0b0001100011,
108 	 0b0001100011,
109 	 0b0001100011,
110 	 0b0001100011,
111 	 0b0001100011,
112 	 0b0010010011,
113 	 0b0010010011,
114 	 0b0010010011,
115 	 0b0010010011,
116 	 0b0010010011,
117 	 0b0010010011,
118 	 0b0010010011,
119 	 0b0010010011,
120 	 0b0010010011,
121 	 0b0010010011,
122 	 0b0010100011,
123 	 0b0010100011,
124 	 0b0010100011,
125 	 0b0010100011,
126 	 0b0010100011,
127 	 0b0010100011,
128 	 0b0010100011,
129 	 0b0010100011,
130 	 0b0010100011,
131 	 0b0010100011,
132 	 0b0010100011,
133 	 0b0010100011,
134 	 0b0010100011,
135 	 0b0010100011,
136 	 0b0010100011,
137 	 0b0010100011,
138 	 0b0010100011
139 };
140 
141 /* MMCM lock detection lookup table */
142 static const uint64_t litex_clk_lock_table[] = {
143 	0b0011000110111110100011111010010000000001,
144 	0b0011000110111110100011111010010000000001,
145 	0b0100001000111110100011111010010000000001,
146 	0b0101101011111110100011111010010000000001,
147 	0b0111001110111110100011111010010000000001,
148 	0b1000110001111110100011111010010000000001,
149 	0b1001110011111110100011111010010000000001,
150 	0b1011010110111110100011111010010000000001,
151 	0b1100111001111110100011111010010000000001,
152 	0b1110011100111110100011111010010000000001,
153 	0b1111111111111000010011111010010000000001,
154 	0b1111111111110011100111111010010000000001,
155 	0b1111111111101110111011111010010000000001,
156 	0b1111111111101011110011111010010000000001,
157 	0b1111111111101000101011111010010000000001,
158 	0b1111111111100111000111111010010000000001,
159 	0b1111111111100011111111111010010000000001,
160 	0b1111111111100010011011111010010000000001,
161 	0b1111111111100000110111111010010000000001,
162 	0b1111111111011111010011111010010000000001,
163 	0b1111111111011101101111111010010000000001,
164 	0b1111111111011100001011111010010000000001,
165 	0b1111111111011010100111111010010000000001,
166 	0b1111111111011001000011111010010000000001,
167 	0b1111111111011001000011111010010000000001,
168 	0b1111111111010111011111111010010000000001,
169 	0b1111111111010101111011111010010000000001,
170 	0b1111111111010101111011111010010000000001,
171 	0b1111111111010100010111111010010000000001,
172 	0b1111111111010100010111111010010000000001,
173 	0b1111111111010010110011111010010000000001,
174 	0b1111111111010010110011111010010000000001,
175 	0b1111111111010010110011111010010000000001,
176 	0b1111111111010001001111111010010000000001,
177 	0b1111111111010001001111111010010000000001,
178 	0b1111111111010001001111111010010000000001,
179 	0b1111111111001111101011111010010000000001,
180 	0b1111111111001111101011111010010000000001,
181 	0b1111111111001111101011111010010000000001,
182 	0b1111111111001111101011111010010000000001,
183 	0b1111111111001111101011111010010000000001,
184 	0b1111111111001111101011111010010000000001,
185 	0b1111111111001111101011111010010000000001,
186 	0b1111111111001111101011111010010000000001,
187 	0b1111111111001111101011111010010000000001,
188 	0b1111111111001111101011111010010000000001,
189 	0b1111111111001111101011111010010000000001,
190 	0b1111111111001111101011111010010000000001,
191 	0b1111111111001111101011111010010000000001,
192 	0b1111111111001111101011111010010000000001,
193 	0b1111111111001111101011111010010000000001,
194 	0b1111111111001111101011111010010000000001,
195 	0b1111111111001111101011111010010000000001,
196 	0b1111111111001111101011111010010000000001,
197 	0b1111111111001111101011111010010000000001,
198 	0b1111111111001111101011111010010000000001,
199 	0b1111111111001111101011111010010000000001,
200 	0b1111111111001111101011111010010000000001,
201 	0b1111111111001111101011111010010000000001,
202 	0b1111111111001111101011111010010000000001,
203 	0b1111111111001111101011111010010000000001,
204 	0b1111111111001111101011111010010000000001,
205 	0b1111111111001111101011111010010000000001,
206 	0b1111111111001111101011111010010000000001
207 };
208 /* End of copied code */
209 
210 /* Helper function for filter lookup table */
litex_clk_lookup_filter(uint32_t glob_mul)211 static inline uint32_t litex_clk_lookup_filter(uint32_t glob_mul)
212 {
213 	return litex_clk_filter_table[glob_mul - 1];
214 }
215 
216 /* Helper function for lock lookup table */
litex_clk_lookup_lock(uint32_t glob_mul)217 static inline uint64_t litex_clk_lookup_lock(uint32_t glob_mul)
218 {
219 	return litex_clk_lock_table[glob_mul - 1];
220 }
221 
litex_clk_set_reg(uint32_t reg,uint32_t val)222 static inline void litex_clk_set_reg(uint32_t reg, uint32_t val)
223 {
224 	litex_write(drp[reg].addr, drp[reg].size, val);
225 }
226 
litex_clk_get_reg(uint32_t reg)227 static inline uint32_t litex_clk_get_reg(uint32_t reg)
228 {
229 	return litex_read(drp[reg].addr, drp[reg].size);
230 }
231 
litex_clk_assert_reg(uint32_t reg)232 static inline void litex_clk_assert_reg(uint32_t reg)
233 {
234 	int assert = (1 << (drp[reg].size * BITS_PER_BYTE)) - 1;
235 
236 	litex_clk_set_reg(reg, assert);
237 }
238 
litex_clk_deassert_reg(uint32_t reg)239 static inline void litex_clk_deassert_reg(uint32_t reg)
240 {
241 	litex_clk_set_reg(reg, ZERO_REG);
242 }
243 
litex_clk_wait(uint32_t reg)244 static int litex_clk_wait(uint32_t reg)
245 {
246 	uint32_t timeout;
247 
248 	__ASSERT(reg == DRP_LOCKED || reg == DRP_DRDY, "Unsupported register! Please provide DRP_LOCKED or DRP_DRDY");
249 
250 	if (reg == DRP_LOCKED) {
251 		timeout = ldev->timeout.lock;
252 	} else {
253 		timeout = ldev->timeout.drdy;
254 	}
255 	/*Waiting for signal to assert in reg*/
256 	while (!litex_clk_get_reg(reg) && timeout) {
257 		timeout--;
258 		k_sleep(K_MSEC(1));
259 	}
260 	if (timeout == 0) {
261 		LOG_WRN("Timeout occured when waiting for the register: 0x%x", reg);
262 		return -ETIME;
263 	}
264 	return 0;
265 }
266 
267 /* Read value written in given internal MMCM register*/
litex_clk_get_DO(uint8_t clk_reg_addr,uint16_t * res)268 static int litex_clk_get_DO(uint8_t clk_reg_addr, uint16_t *res)
269 {
270 	int ret;
271 
272 	litex_clk_set_reg(DRP_ADR, clk_reg_addr);
273 	litex_clk_assert_reg(DRP_READ);
274 
275 	litex_clk_deassert_reg(DRP_READ);
276 	ret = litex_clk_wait(DRP_DRDY);
277 	if (ret != 0) {
278 		return ret;
279 	}
280 
281 	*res = litex_clk_get_reg(DRP_DAT_R);
282 
283 	return 0;
284 }
285 
286 /* Get global divider and multiplier values and update global config */
litex_clk_update_global_config(void)287 static int litex_clk_update_global_config(void)
288 {
289 	int ret;
290 	uint16_t divreg, mult2;
291 	uint8_t low_time, high_time;
292 
293 	ret = litex_clk_get_DO(CLKFBOUT_REG2, &mult2);
294 	if (ret != 0) {
295 		return ret;
296 	}
297 	ret = litex_clk_get_DO(DIV_REG, &divreg);
298 	if (ret != 0) {
299 		return ret;
300 	}
301 
302 	if (mult2 & (NO_CNT_MASK << NO_CNT_POS)) {
303 		ldev->g_config.mul = 1;
304 	} else {
305 		uint16_t mult1;
306 
307 		ret = litex_clk_get_DO(CLKFBOUT_REG1, &mult1);
308 		if (ret != 0) {
309 			return ret;
310 		}
311 		low_time = mult1 & HL_TIME_MASK;
312 		high_time = (mult1 >> HIGH_TIME_POS) & HL_TIME_MASK;
313 		ldev->g_config.mul = low_time + high_time;
314 	}
315 
316 	if (divreg & (NO_CNT_MASK << NO_CNT_DIVREG_POS)) {
317 		ldev->g_config.div = 1;
318 	} else {
319 		low_time = divreg & HL_TIME_MASK;
320 		high_time = (divreg >> HIGH_TIME_POS) & HL_TIME_MASK;
321 		ldev->g_config.div = low_time + high_time;
322 	}
323 
324 	return 0;
325 }
326 
litex_clk_calc_global_frequency(uint32_t mul,uint32_t div)327 static uint64_t litex_clk_calc_global_frequency(uint32_t mul, uint32_t div)
328 {
329 	uint64_t f;
330 
331 	f = CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC * (uint64_t)mul;
332 	f /= div;
333 
334 	return f;
335 }
336 
337 /* Calculate frequency with real global params and update global config */
litex_clk_get_real_global_frequency(void)338 static uint64_t litex_clk_get_real_global_frequency(void)
339 {
340 	uint64_t f;
341 
342 	litex_clk_update_global_config();
343 	f = litex_clk_calc_global_frequency(ldev->g_config.mul,
344 					    ldev->g_config.div);
345 	ldev->g_config.freq = f;
346 	ldev->ts_g_config.div = ldev->g_config.div;
347 	ldev->ts_g_config.mul = ldev->g_config.mul;
348 	ldev->ts_g_config.freq = ldev->g_config.freq;
349 
350 	return f;
351 }
352 
353 /* Return dividers of given CLKOUT */
litex_clk_get_clkout_divider(struct litex_clk_clkout * lcko,uint32_t * divider,uint32_t * fract_cnt)354 static int litex_clk_get_clkout_divider(struct litex_clk_clkout *lcko,
355 					uint32_t *divider, uint32_t *fract_cnt)
356 {
357 	struct litex_clk_regs_addr drp_addr = litex_clk_regs_addr_init();
358 	int ret;
359 	uint16_t div, frac;
360 	uint8_t clkout_nr = lcko->id;
361 	uint8_t low_time, high_time;
362 
363 	ret = litex_clk_get_DO(drp_addr.clkout[clkout_nr].reg1, &div);
364 	if (ret != 0) {
365 		return ret;
366 	}
367 	ret = litex_clk_get_DO(drp_addr.clkout[clkout_nr].reg2, &frac);
368 	if (ret != 0) {
369 		return ret;
370 	}
371 
372 	low_time = div & HL_TIME_MASK;
373 	high_time = (div >> HIGH_TIME_POS) & HL_TIME_MASK;
374 	*divider = low_time + high_time;
375 	*fract_cnt = (frac >> FRAC_POS) & FRAC_MASK;
376 
377 	return 0;
378 }
379 
380 /* Debug functions */
381 #ifdef CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG
382 
litex_clk_check_DO(char * reg_name,uint8_t clk_reg_addr,uint16_t * res)383 static void litex_clk_check_DO(char *reg_name, uint8_t clk_reg_addr,
384 					       uint16_t *res)
385 {
386 	int ret;
387 
388 	ret = litex_clk_get_DO(clk_reg_addr, res);
389 	if (ret != 0) {
390 		LOG_ERR("%s: read error: %d", reg_name, ret);
391 	} else {
392 		LOG_DBG("%s:  0x%x", reg_name, *res);
393 	}
394 }
395 
litex_clk_print_general_regs(void)396 static void litex_clk_print_general_regs(void)
397 {
398 	uint16_t power_reg, div_reg, clkfbout_reg1, clkfbout_reg2,
399 	lock_reg1, lock_reg2, lock_reg3, filt_reg1, filt_reg2;
400 
401 	litex_clk_check_DO("POWER_REG", POWER_REG, &power_reg);
402 	litex_clk_check_DO("DIV_REG", DIV_REG, &div_reg);
403 	litex_clk_check_DO("MUL_REG1", CLKFBOUT_REG1, &clkfbout_reg1);
404 	litex_clk_check_DO("MUL_REG2", CLKFBOUT_REG2, &clkfbout_reg2);
405 	litex_clk_check_DO("LOCK_REG1", LOCK_REG1, &lock_reg1);
406 	litex_clk_check_DO("LOCK_REG2", LOCK_REG2, &lock_reg2);
407 	litex_clk_check_DO("LOCK_REG3", LOCK_REG3, &lock_reg3);
408 	litex_clk_check_DO("FILT_REG1", FILT_REG1, &filt_reg1);
409 	litex_clk_check_DO("FILT_REG2", FILT_REG2, &filt_reg2);
410 }
411 
litex_clk_print_clkout_regs(uint8_t clkout,uint8_t reg1,uint8_t reg2)412 static void litex_clk_print_clkout_regs(uint8_t clkout, uint8_t reg1,
413 							uint8_t reg2)
414 {
415 	uint16_t clkout_reg1, clkout_reg2;
416 	char reg_name[16];
417 
418 	sprintf(reg_name, "CLKOUT%u REG1", clkout);
419 	litex_clk_check_DO(reg_name, reg1, &clkout_reg1);
420 
421 	sprintf(reg_name, "CLKOUT%u REG2", clkout);
422 	litex_clk_check_DO(reg_name, reg2, &clkout_reg2);
423 }
424 
litex_clk_print_all_regs(void)425 static void litex_clk_print_all_regs(void)
426 {
427 	struct litex_clk_regs_addr drp_addr = litex_clk_regs_addr_init();
428 	uint32_t i;
429 
430 	litex_clk_print_general_regs();
431 	for (i = 0; i < ldev->nclkout; i++) {
432 		litex_clk_print_clkout_regs(i, drp_addr.clkout[i].reg1,
433 					       drp_addr.clkout[i].reg2);
434 	}
435 }
436 
litex_clk_print_params(struct litex_clk_clkout * lcko)437 static void litex_clk_print_params(struct litex_clk_clkout *lcko)
438 {
439 	LOG_DBG("CLKOUT%d DUMP:", lcko->id);
440 	LOG_DBG("Defaults:");
441 	LOG_DBG("f: %u d: %u/%u p: %u",
442 		lcko->def.freq, lcko->def.duty.num,
443 		lcko->def.duty.den, lcko->def.phase);
444 	LOG_DBG("Config to set:");
445 	LOG_DBG("div: %u freq: %u duty: %u/%u phase: %d per_off: %u",
446 		lcko->ts_config.div, lcko->ts_config.freq,
447 		lcko->ts_config.duty.num, lcko->ts_config.duty.den,
448 		lcko->ts_config.phase, lcko->config.period_off);
449 	LOG_DBG("Config:");
450 	LOG_DBG("div: %u freq: %u duty: %u/%u phase: %d per_off: %u",
451 		lcko->config.div, lcko->config.freq,
452 		lcko->config.duty.num, lcko->config.duty.den,
453 		lcko->config.phase, lcko->config.period_off);
454 	LOG_DBG("Divide group:");
455 	LOG_DBG("e: %u ht: %u lt: %u nc: %u",
456 		lcko->div.edge, lcko->div.high_time,
457 		lcko->div.low_time, lcko->div.no_cnt);
458 	LOG_DBG("Frac group:");
459 	LOG_DBG("f: %u fen: %u fwff: %u fwfr: %u pmf: %u",
460 		lcko->frac.frac, lcko->frac.frac_en, lcko->frac.frac_wf_f,
461 		lcko->frac.frac_wf_r, lcko->frac.phase_mux_f);
462 	LOG_DBG("Phase group:");
463 	LOG_DBG("dt: %u pm: %u mx: %u",
464 		lcko->phase.delay_time, lcko->phase.phase_mux, lcko->phase.mx);
465 }
466 
litex_clk_print_all_params(void)467 static void litex_clk_print_all_params(void)
468 {
469 	uint32_t c;
470 
471 	LOG_DBG("Global Config to set:");
472 	LOG_DBG("freq: %llu mul: %u div: %u",
473 		ldev->ts_g_config.freq, ldev->ts_g_config.mul,
474 					ldev->ts_g_config.div);
475 	LOG_DBG("Global Config:");
476 	LOG_DBG("freq: %llu mul: %u div: %u",
477 		ldev->g_config.freq, ldev->g_config.mul, ldev->g_config.div);
478 	for (c = 0; c < ldev->nclkout; c++) {
479 		litex_clk_print_params(&ldev->clkouts[c]);
480 	}
481 }
482 #endif /* CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG */
483 
484 /* Returns raw value ready to be written into MMCM */
litex_clk_calc_DI(uint16_t DO_val,uint16_t mask,uint16_t bitset)485 static inline uint16_t litex_clk_calc_DI(uint16_t DO_val, uint16_t mask,
486 							  uint16_t bitset)
487 {
488 	uint16_t DI_val;
489 
490 	DI_val = DO_val & mask;
491 	DI_val |= bitset;
492 
493 	return DI_val;
494 }
495 
496 /* Sets calculated DI value into DI DRP register */
litex_clk_set_DI(uint16_t DI_val)497 static int litex_clk_set_DI(uint16_t DI_val)
498 {
499 	int ret;
500 
501 	litex_clk_set_reg(DRP_DAT_W, DI_val);
502 	litex_clk_assert_reg(DRP_WRITE);
503 	litex_clk_deassert_reg(DRP_WRITE);
504 	ret = litex_clk_wait(DRP_DRDY);
505 	return ret;
506 }
507 
508 /*
509  * Change register value as specified in arguments
510  *
511  * mask:		preserve or zero MMCM register bits
512  *			by selecting 1 or 0 on desired specific mask positions
513  * bitset:		set those bits in MMCM register which are 1 in bitset
514  * clk_reg_addr:	internal MMCM address of control register
515  *
516  */
litex_clk_change_value(uint16_t mask,uint16_t bitset,uint8_t clk_reg_addr)517 static int litex_clk_change_value(uint16_t mask, uint16_t bitset,
518 						 uint8_t clk_reg_addr)
519 {
520 	uint16_t DO_val, DI_val;
521 	int ret;
522 
523 	litex_clk_assert_reg(DRP_RESET);
524 
525 	ret = litex_clk_get_DO(clk_reg_addr, &DO_val);
526 	if (ret != 0) {
527 		return ret;
528 	}
529 	DI_val = litex_clk_calc_DI(DO_val, mask, bitset);
530 	ret = litex_clk_set_DI(DI_val);
531 	if (ret != 0) {
532 		return ret;
533 	}
534 #ifdef CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG
535 	DI_val = litex_clk_get_reg(DRP_DAT_W);
536 	LOG_DBG("set 0x%x under: 0x%x", DI_val, clk_reg_addr);
537 #endif
538 	litex_clk_deassert_reg(DRP_DAT_W);
539 	litex_clk_deassert_reg(DRP_RESET);
540 	ret = litex_clk_wait(DRP_LOCKED);
541 	return ret;
542 }
543 
544 /*
545  * Set register values for given CLKOUT
546  *
547  * clkout_nr:		clock output number
548  * mask_regX:		preserve or zero MMCM register X bits
549  *			by selecting 1 or 0 on desired specific mask positions
550  * bitset_regX:		set those bits in MMCM register X which are 1 in bitset
551  *
552  */
litex_clk_set_clock(uint8_t clkout_nr,uint16_t mask_reg1,uint16_t bitset_reg1,uint16_t mask_reg2,uint16_t bitset_reg2)553 static int litex_clk_set_clock(uint8_t clkout_nr, uint16_t mask_reg1,
554 			      uint16_t bitset_reg1, uint16_t mask_reg2,
555 						 uint16_t bitset_reg2)
556 {
557 	struct litex_clk_regs_addr drp_addr = litex_clk_regs_addr_init();
558 	int ret;
559 
560 	if (!(mask_reg2 == FULL_REG_16 && bitset_reg2 == ZERO_REG)) {
561 		ret = litex_clk_change_value(mask_reg2, bitset_reg2,
562 					     drp_addr.clkout[clkout_nr].reg2);
563 		if (ret != 0) {
564 			return ret;
565 		}
566 	}
567 	if (!(mask_reg1 == FULL_REG_16 && bitset_reg1 == ZERO_REG)) {
568 		ret = litex_clk_change_value(mask_reg1, bitset_reg1,
569 					     drp_addr.clkout[clkout_nr].reg1);
570 		if (ret != 0) {
571 			return ret;
572 		}
573 	}
574 
575 	return 0;
576 }
577 
578 /* Set global divider for all CLKOUTs */
litex_clk_set_divreg(void)579 static int litex_clk_set_divreg(void)
580 {
581 	int ret;
582 	uint8_t no_cnt = 0, edge = 0, ht = 0, lt = 0,
583 		div = ldev->ts_g_config.div;
584 	uint16_t bitset = 0;
585 
586 	if (div == 1) {
587 		no_cnt = 1;
588 	} else {
589 		ht = div / 2;
590 		lt = ht;
591 		edge = div % 2;
592 		if (edge) {
593 			lt += edge;
594 		}
595 	}
596 
597 	bitset = (edge << EDGE_DIVREG_POS)	|
598 		 (no_cnt << NO_CNT_DIVREG_POS)	|
599 		 (ht << HIGH_TIME_POS)		|
600 		 (lt << LOW_TIME_POS);
601 
602 	ret = litex_clk_change_value(KEEP_IN_DIV, bitset, DIV_REG);
603 	if (ret != 0) {
604 		return ret;
605 	}
606 
607 	ldev->g_config.div = div;
608 	LOG_DBG("Global divider set to %u", div);
609 
610 	return 0;
611 }
612 
613 /* Set global multiplier for all CLKOUTs */
litex_clk_set_mulreg(void)614 static int litex_clk_set_mulreg(void)
615 {
616 	int ret;
617 	uint8_t no_cnt = 0, edge = 0, ht = 0, lt = 0,
618 		mul = ldev->ts_g_config.mul;
619 	uint16_t bitset1 = 0;
620 
621 	if (mul == 1) {
622 		no_cnt = 1;
623 	} else {
624 		ht = mul / 2;
625 		lt = ht;
626 		edge = mul % 2;
627 		if (edge) {
628 			lt += edge;
629 		}
630 	}
631 
632 	bitset1 = (ht << HIGH_TIME_POS) |
633 		  (lt << LOW_TIME_POS);
634 
635 	ret = litex_clk_change_value(KEEP_IN_MUL_REG1, bitset1, CLKFBOUT_REG1);
636 	if (ret != 0) {
637 		return ret;
638 	}
639 
640 	if (edge || no_cnt) {
641 		uint16_t bitset2 = (edge << EDGE_POS)	|
642 				(no_cnt << NO_CNT_POS);
643 
644 		ret = litex_clk_change_value(KEEP_IN_MUL_REG2,
645 				       bitset2, CLKFBOUT_REG2);
646 		if (ret != 0) {
647 			return ret;
648 		}
649 	}
650 
651 	ldev->g_config.mul = mul;
652 	LOG_DBG("Global multiplier set to %u", mul);
653 
654 	return 0;
655 }
656 
litex_clk_set_filt(void)657 static int litex_clk_set_filt(void)
658 {
659 	uint16_t filt_reg;
660 	uint32_t filt, mul;
661 	int ret;
662 
663 	mul = ldev->g_config.mul;
664 	filt = litex_clk_lookup_filter(mul);
665 
666 	/*
667 	 * Preparing and setting filter register values
668 	 * according to reg map form Xilinx XAPP888
669 	 */
670 	filt_reg = (((filt >> 9) & 0x1) << 15) |
671 		   (((filt >> 7) & 0x3) << 11) |
672 		   (((filt >> 6) & 0x1) << 8);
673 	ret = litex_clk_change_value(FILT1_MASK, filt_reg, FILT_REG1);
674 	if (ret != 0)  {
675 		return ret;
676 	}
677 
678 	filt_reg = (((filt >> 5) & 0x1) << 15) |
679 		   (((filt >> 3) & 0x3) << 11) |
680 		   (((filt >> 1) & 0x3) << 7) |
681 		   (((filt) & 0x1) << 4);
682 	ret = litex_clk_change_value(FILT2_MASK, filt_reg, FILT_REG2);
683 
684 	return ret;
685 }
686 
litex_clk_set_lock(void)687 static int litex_clk_set_lock(void)
688 {
689 	uint16_t lock_reg;
690 	uint32_t mul;
691 	uint64_t lock;
692 	int ret;
693 
694 	mul = ldev->g_config.mul;
695 	lock = litex_clk_lookup_lock(mul);
696 
697 	/*
698 	 * Preparing and setting lock register values
699 	 * according to reg map form Xilinx XAPP888
700 	 */
701 	lock_reg = (lock >> 20) & 0x3FF;
702 	ret = litex_clk_change_value(LOCK1_MASK, lock_reg, LOCK_REG1);
703 	if (ret != 0) {
704 		return ret;
705 	}
706 
707 	lock_reg = (((lock >> 30) & 0x1F) << 10) |
708 		     (lock & 0x3FF);
709 	ret = litex_clk_change_value(LOCK23_MASK, lock_reg, LOCK_REG2);
710 	if (ret != 0) {
711 		return ret;
712 	}
713 
714 	lock_reg = (((lock >> 35) & 0x1F) << 10) |
715 		   ((lock >> 10) & 0x3FF);
716 	ret = litex_clk_change_value(LOCK23_MASK, lock_reg, LOCK_REG3);
717 
718 	return ret;
719 }
720 
721 /* Set all multiplier-related regs: mul, filt and lock regs */
litex_clk_set_mul(void)722 static int litex_clk_set_mul(void)
723 {
724 	int ret;
725 
726 	ret = litex_clk_set_mulreg();
727 	if (ret != 0) {
728 		return ret;
729 	}
730 	ret = litex_clk_set_filt();
731 	if (ret != 0) {
732 		return ret;
733 	}
734 	ret = litex_clk_set_lock();
735 	return ret;
736 }
737 
litex_clk_set_both_globs(void)738 static int litex_clk_set_both_globs(void)
739 {
740 	/*
741 	 * we need to check what change first to prevent
742 	 * getting our VCO_FREQ out of possible range
743 	 */
744 	uint64_t vco_freq;
745 	int ret;
746 
747 	/* div-first case */
748 	vco_freq = litex_clk_calc_global_frequency(
749 					ldev->g_config.mul,
750 					ldev->ts_g_config.div);
751 	if (vco_freq > ldev->vco.max || vco_freq < ldev->vco.min) {
752 		/* div-first not safe */
753 		vco_freq = litex_clk_calc_global_frequency(
754 					ldev->ts_g_config.mul,
755 					ldev->g_config.div);
756 		if (vco_freq > ldev->vco.max || vco_freq < ldev->vco.min) {
757 			/* mul-first not safe */
758 			ret = litex_clk_set_divreg();
759 			/* Ignore timeout because we expect that to happen */
760 			if (ret != -ETIME && ret != 0) {
761 				return ret;
762 			} else if (ret == -ETIME) {
763 				ldev->g_config.div = ldev->ts_g_config.div;
764 				LOG_DBG("Global divider set to %u",
765 					 ldev->g_config.div);
766 			}
767 			ret = litex_clk_set_mul();
768 			if (ret != 0) {
769 				return ret;
770 			}
771 		} else {
772 			/* mul-first safe */
773 			ret = litex_clk_set_mul();
774 			if (ret != 0) {
775 				return ret;
776 			}
777 			ret = litex_clk_set_divreg();
778 			if (ret != 0) {
779 				return ret;
780 			}
781 		}
782 	} else {
783 		/* div-first safe */
784 		ret = litex_clk_set_divreg();
785 		if (ret != 0) {
786 			return ret;
787 		}
788 		ret = litex_clk_set_mul();
789 		if (ret != 0) {
790 			return ret;
791 		}
792 	}
793 	return 0;
794 }
795 
796 /* Set global divider, multiplier, filt and lock values */
litex_clk_set_globs(void)797 static int litex_clk_set_globs(void)
798 {
799 	int ret;
800 	uint8_t set_div = 0,
801 	   set_mul = 0;
802 
803 	set_div = ldev->ts_g_config.div != ldev->g_config.div;
804 	set_mul = ldev->ts_g_config.mul != ldev->g_config.mul;
805 
806 	if (set_div || set_mul) {
807 		if (set_div && set_mul) {
808 			ret = litex_clk_set_both_globs();
809 			if (ret != 0) {
810 				return ret;
811 			}
812 		} else if (set_div) {
813 			/* set divider only */
814 			ret = litex_clk_set_divreg();
815 			if (ret != 0) {
816 				return ret;
817 			}
818 		} else {
819 			/* set multiplier only */
820 			ret = litex_clk_set_mul();
821 			if (ret != 0) {
822 				return ret;
823 			}
824 		}
825 		ldev->g_config.freq = ldev->ts_g_config.freq;
826 	}
827 	return 0;
828 }
829 
830 /* Round scaled value*/
litex_round(uint32_t val,uint32_t mod)831 static inline uint32_t litex_round(uint32_t val, uint32_t mod)
832 {
833 	if (val % mod > mod / 2) {
834 		return val / mod + 1;
835 	}
836 	return val / mod;
837 }
838 
839 /*
840  *	Duty Cycle
841  */
842 
843 /* Returns accurate duty ratio of given clkout*/
litex_clk_get_duty_cycle(struct litex_clk_clkout * lcko,struct clk_duty * duty)844 int litex_clk_get_duty_cycle(struct litex_clk_clkout *lcko,
845 			     struct clk_duty *duty)
846 {
847 	struct litex_clk_regs_addr drp_addr = litex_clk_regs_addr_init();
848 	int ret;
849 	uint32_t divider;
850 	uint16_t clkout_reg1, clkout_reg2;
851 	uint8_t clkout_nr, high_time, edge, no_cnt, frac_en, frac_cnt;
852 
853 	clkout_nr = lcko->id;
854 	/* Check if divider is off */
855 	ret = litex_clk_get_DO(drp_addr.clkout[clkout_nr].reg2, &clkout_reg2);
856 	if (ret != 0) {
857 		return ret;
858 	}
859 
860 	edge = (clkout_reg2 >> EDGE_POS) & EDGE_MASK;
861 	no_cnt = (clkout_reg2 >> NO_CNT_POS) & NO_CNT_MASK;
862 	frac_en = (clkout_reg2 >> FRAC_EN_POS) & FRAC_EN_MASK;
863 	frac_cnt = (clkout_reg2 >> FRAC_POS) & FRAC_MASK;
864 
865 	/* get duty 50% when divider is off or fractional is enabled */
866 	if (no_cnt || (frac_en && frac_cnt)) {
867 		duty->num = 1;
868 		duty->den = 2;
869 		return 0;
870 	}
871 
872 	ret = litex_clk_get_DO(drp_addr.clkout[clkout_nr].reg1, &clkout_reg1);
873 	if (ret != 0) {
874 		return ret;
875 	}
876 
877 	divider = clkout_reg1 & HL_TIME_MASK;
878 	high_time = (clkout_reg1 >> HIGH_TIME_POS) & HL_TIME_MASK;
879 	divider += high_time;
880 
881 	/* Scaling to consider edge control bit */
882 	duty->num = high_time * 10 + edge * 5;
883 	duty->den = (divider + edge) * 10;
884 
885 	return 0;
886 }
887 
888 /* Calculates duty cycle for given ratio in percent, 1% accuracy */
litex_clk_calc_duty_percent(struct clk_duty * duty)889 static inline uint8_t litex_clk_calc_duty_percent(struct clk_duty *duty)
890 {
891 	uint32_t div, duty_ratio, ht;
892 
893 	ht = duty->num;
894 	div = duty->den;
895 	duty_ratio = ht * 10000 / div;
896 
897 	return (uint8_t)litex_round(duty_ratio, 100);
898 }
899 
900 /* Calculate necessary values for setting duty cycle in normal mode */
litex_clk_calc_duty_normal(struct litex_clk_clkout * lcko,int calc_new)901 static int litex_clk_calc_duty_normal(struct litex_clk_clkout *lcko,
902 					 int calc_new)
903 {
904 	struct clk_duty duty;
905 	int delta_d;
906 	uint32_t ht_aprox, synth_duty, min_d;
907 	uint8_t high_time_it, edge_it, high_duty,
908 	   divider = lcko->config.div;
909 	int err;
910 
911 	if (calc_new) {
912 		duty = lcko->ts_config.duty;
913 	} else {
914 		err = litex_clk_get_duty_cycle(lcko, &duty);
915 		if (err != 0) {
916 			return err;
917 		}
918 	}
919 
920 	high_duty = litex_clk_calc_duty_percent(&duty);
921 	min_d = INT_MAX;
922 	/* check if duty is available to set */
923 	ht_aprox = high_duty * divider;
924 
925 	if (ht_aprox > ((HIGH_LOW_TIME_REG_MAX * 100) + 50) ||
926 		       ((HIGH_LOW_TIME_REG_MAX * 100) + 50) <
927 			(divider * 100) - ht_aprox) {
928 		return -EINVAL;
929 	}
930 
931 	/* to prevent high_time == 0 or low_time == 0 */
932 	for (high_time_it = 1; high_time_it < divider; high_time_it++) {
933 		for (edge_it = 0; edge_it < 2; edge_it++) {
934 			synth_duty = (high_time_it * 100 + 50 * edge_it) /
935 								  divider;
936 			delta_d = synth_duty - high_duty;
937 			delta_d = abs(delta_d);
938 			/* check if low_time won't be above acceptable range */
939 			if (delta_d < min_d && (divider - high_time_it) <=
940 						  HIGH_LOW_TIME_REG_MAX) {
941 				min_d = delta_d;
942 				lcko->div.high_time = high_time_it;
943 				lcko->div.low_time = divider - high_time_it;
944 				lcko->div.edge = edge_it;
945 				lcko->config.duty.num = high_time_it * 100 + 50
946 								     * edge_it;
947 				lcko->config.duty.den = divider * 100;
948 			}
949 		}
950 	}
951 	/*
952 	 * Calculating values in normal mode,
953 	 * clear control bits of fractional part
954 	 */
955 	lcko->frac.frac_wf_f = 0;
956 	lcko->frac.frac_wf_r = 0;
957 
958 	return 0;
959 }
960 
961 /* Calculates duty high_time for given divider and ratio */
litex_clk_calc_duty_high_time(struct clk_duty * duty,uint32_t divider)962 static inline int litex_clk_calc_duty_high_time(struct clk_duty *duty,
963 						   uint32_t divider)
964 {
965 	uint32_t high_duty;
966 
967 	high_duty = litex_clk_calc_duty_percent(duty) * divider;
968 
969 	return litex_round(high_duty, 100);
970 }
971 
972 /* Set duty cycle with given ratio */
litex_clk_set_duty_cycle(struct litex_clk_clkout * lcko,struct clk_duty * duty)973 static int litex_clk_set_duty_cycle(struct litex_clk_clkout *lcko,
974 			     struct clk_duty *duty)
975 {
976 	int ret;
977 	uint16_t bitset1, bitset2;
978 	uint8_t clkout_nr = lcko->id,
979 	   *edge = &lcko->div.edge,
980 	   *high_time = &lcko->div.high_time,
981 	    high_duty = litex_clk_calc_duty_percent(duty),
982 	   *low_time = &lcko->div.low_time;
983 
984 	if (lcko->frac.frac == 0) {
985 		lcko->ts_config.duty = *duty;
986 		LOG_DBG("CLKOUT%d: setting duty: %u/%u",
987 			lcko->id, duty->num, duty->den);
988 		ret = litex_clk_calc_duty_normal(lcko, true);
989 		if (ret != 0) {
990 			LOG_ERR("CLKOUT%d: cannot set %d%% duty cycle",
991 				clkout_nr, high_duty);
992 			return ret;
993 		}
994 	} else {
995 		LOG_ERR("CLKOUT%d: cannot set duty cycle when fractional divider enabled",
996 								     clkout_nr);
997 		return -EACCES;
998 	}
999 
1000 	bitset1 = (*high_time << HIGH_TIME_POS) |
1001 		  (*low_time << LOW_TIME_POS);
1002 	bitset2 = (*edge << EDGE_POS);
1003 
1004 	LOG_DBG("SET DUTY CYCLE: e:%u ht:%u lt:%u\nbitset1: 0x%x bitset2: 0x%x",
1005 		*edge, *high_time, *low_time, bitset1, bitset2);
1006 
1007 	ret = litex_clk_set_clock(clkout_nr, REG1_DUTY_MASK, bitset1,
1008 					     REG2_DUTY_MASK, bitset2);
1009 	if (ret != 0) {
1010 		return ret;
1011 	}
1012 
1013 	LOG_INF("CLKOUT%d: set duty: %d%%", lcko->id,
1014 		litex_clk_calc_duty_percent(&lcko->config.duty));
1015 	return 0;
1016 }
1017 
1018 /*
1019  *	Phase
1020  */
1021 
1022 /* Calculate necessary values for setting phase in normal mode */
litex_clk_calc_phase_normal(struct litex_clk_clkout * lcko)1023 static int litex_clk_calc_phase_normal(struct litex_clk_clkout *lcko)
1024 {
1025 	uint64_t period_buff;
1026 	uint32_t post_glob_div_f, global_period,  clkout_period,
1027 	    *period_off = &lcko->ts_config.period_off;
1028 	uint8_t divider = lcko->config.div;
1029 	/* ps unit */
1030 
1031 	post_glob_div_f = (uint32_t)litex_clk_get_real_global_frequency();
1032 	period_buff = PICOS_IN_SEC;
1033 	period_buff /= post_glob_div_f;
1034 	global_period = (uint32_t)period_buff;
1035 	clkout_period = global_period * divider;
1036 
1037 	if (lcko->ts_config.phase != 0) {
1038 		int synth_phase, delta_p, min_p, p_o;
1039 		uint8_t delay, p_m;
1040 
1041 		*period_off = litex_round(clkout_period * (*period_off), 10000);
1042 
1043 		if (*period_off / global_period > DELAY_TIME_MAX) {
1044 			return -EINVAL;
1045 		}
1046 
1047 		min_p = INT_MAX;
1048 		p_o = *period_off;
1049 		/* Delay_time: (0-63) */
1050 		for (delay = 0; delay <= DELAY_TIME_MAX; delay++) {
1051 			/* phase_mux: (0-7) */
1052 			for (p_m = 0; p_m <= PHASE_MUX_MAX; p_m++) {
1053 				synth_phase = (delay * global_period) +
1054 				((p_m * ((global_period * 100) / 8) / 100));
1055 
1056 				delta_p = synth_phase - p_o;
1057 				delta_p = abs(delta_p);
1058 				if (delta_p < min_p) {
1059 					min_p = delta_p;
1060 					lcko->phase.phase_mux = p_m;
1061 					lcko->phase.delay_time = delay;
1062 					lcko->config.period_off = synth_phase;
1063 				}
1064 			}
1065 		}
1066 	} else {
1067 		/* Don't change phase offset*/
1068 		lcko->phase.phase_mux = 0;
1069 		lcko->phase.delay_time = 0;
1070 	}
1071 	/*
1072 	 * Calculating values in normal mode,
1073 	 * fractional control bits need to be zero
1074 	 */
1075 	lcko->frac.phase_mux_f = 0;
1076 
1077 	return 0;
1078 }
1079 
1080 /* Convert phase offset to positive lower than 360 deg. and calculate period */
litex_clk_prepare_phase(struct litex_clk_clkout * lcko)1081 static int litex_clk_prepare_phase(struct litex_clk_clkout *lcko)
1082 {
1083 	int *phase = &lcko->ts_config.phase;
1084 
1085 	*phase %= 360;
1086 
1087 	if (*phase < 0) {
1088 		*phase += 360;
1089 	}
1090 
1091 	lcko->ts_config.period_off = ((*phase * 10000) / 360);
1092 
1093 	return 0;
1094 }
1095 
1096 /* Calculate necessary values for setting phase */
litex_clk_calc_phase(struct litex_clk_clkout * lcko)1097 static int litex_clk_calc_phase(struct litex_clk_clkout *lcko)
1098 {
1099 	litex_clk_prepare_phase(lcko);
1100 
1101 	return litex_clk_calc_phase_normal(lcko);
1102 }
1103 
1104 /* Returns phase-specific values of given clock output */
litex_clk_get_phase_data(struct litex_clk_clkout * lcko,uint8_t * phase_mux,uint8_t * delay_time)1105 static int litex_clk_get_phase_data(struct litex_clk_clkout *lcko,
1106 				    uint8_t *phase_mux, uint8_t *delay_time)
1107 {
1108 	struct litex_clk_regs_addr drp_addr = litex_clk_regs_addr_init();
1109 	int ret;
1110 	uint16_t r1, r2;
1111 	uint8_t clkout_nr = lcko->id;
1112 
1113 	ret = litex_clk_get_DO(drp_addr.clkout[clkout_nr].reg1, &r1);
1114 	if (ret != 0) {
1115 		return ret;
1116 	}
1117 	ret = litex_clk_get_DO(drp_addr.clkout[clkout_nr].reg2, &r2);
1118 	if (ret != 0) {
1119 		return ret;
1120 	}
1121 
1122 	*phase_mux = (r1 >> PHASE_MUX_POS) & PHASE_MUX_MASK;
1123 	*delay_time = (r2 >> DELAY_TIME_POS) & HL_TIME_MASK;
1124 
1125 	return 0;
1126 }
1127 
1128 /* Returns phase of given clock output in time offset */
litex_clk_get_phase(struct litex_clk_clkout * lcko)1129 int litex_clk_get_phase(struct litex_clk_clkout *lcko)
1130 {
1131 	uint64_t period_buff;
1132 	uint32_t divider = 0, fract_cnt, post_glob_div_f,
1133 	    pm, global_period, clkout_period, period;
1134 	uint8_t phase_mux = 0, delay_time = 0;
1135 	int err = 0;
1136 
1137 	litex_clk_get_phase_data(lcko, &phase_mux, &delay_time);
1138 	err = litex_clk_get_clkout_divider(lcko, &divider, &fract_cnt);
1139 	if (err != 0) {
1140 		return err;
1141 	}
1142 
1143 	post_glob_div_f = (uint32_t)litex_clk_get_real_global_frequency();
1144 	period_buff = PICOS_IN_SEC;
1145 	period_buff /= post_glob_div_f;
1146 	/* ps unit */
1147 	global_period = (uint32_t)period_buff;
1148 	clkout_period = global_period * divider;
1149 
1150 	pm = (phase_mux * global_period * 1000) / PHASE_MUX_RES_FACTOR;
1151 	pm = litex_round(pm, 1000);
1152 
1153 	period = delay_time * global_period + pm;
1154 
1155 	period = period * 1000 / clkout_period;
1156 	period = period * 360;
1157 
1158 	return litex_round(period, 1000);
1159 }
1160 
1161 /* Returns phase of given clock output in degrees */
litex_clk_get_phase_deg(struct litex_clk_clkout * lcko)1162 int litex_clk_get_phase_deg(struct litex_clk_clkout *lcko)
1163 {
1164 	uint64_t post_glob_div_f, buff, clkout_period;
1165 
1166 	post_glob_div_f = (uint32_t)litex_clk_get_real_global_frequency();
1167 	buff = PICOS_IN_SEC;
1168 	buff /= post_glob_div_f;
1169 	clkout_period = (uint32_t)buff;
1170 	clkout_period *= lcko->config.div;
1171 
1172 	buff = lcko->config.period_off * 1000 / clkout_period;
1173 	buff *= 360;
1174 	buff = litex_round(buff, 1000);
1175 
1176 	return (int)buff;
1177 }
1178 /* Sets phase given in degrees on given clock output */
litex_clk_set_phase(struct litex_clk_clkout * lcko,int degrees)1179 int litex_clk_set_phase(struct litex_clk_clkout *lcko, int degrees)
1180 {
1181 	int ret;
1182 	uint16_t bitset1, bitset2, reg2_mask;
1183 	uint8_t *phase_mux = &lcko->phase.phase_mux,
1184 	   *delay_time = &lcko->phase.delay_time,
1185 	   clkout_nr = lcko->id;
1186 
1187 	lcko->ts_config.phase = degrees;
1188 	reg2_mask = REG2_PHASE_MASK;
1189 	LOG_DBG("CLKOUT%d: setting phase: %u deg", lcko->id, degrees);
1190 
1191 	ret = litex_clk_calc_phase(lcko);
1192 	if (ret != 0) {
1193 		LOG_ERR("CLKOUT%d: phase offset %d deg is too high",
1194 			 clkout_nr, degrees);
1195 		return ret;
1196 	}
1197 
1198 	bitset1 = (*phase_mux << PHASE_MUX_POS);
1199 	bitset2 = (*delay_time << DELAY_TIME_POS);
1200 
1201 	ret = litex_clk_set_clock(clkout_nr, REG1_PHASE_MASK, bitset1,
1202 						   reg2_mask, bitset2);
1203 	if (ret != 0) {
1204 		return ret;
1205 	}
1206 	lcko->config.phase = litex_clk_get_phase_deg(lcko);
1207 	LOG_INF("CLKOUT%d: set phase: %d deg", lcko->id, lcko->config.phase);
1208 	LOG_DBG("SET PHASE: pm:%u dt:%u\nbitset1: 0x%x bitset2: 0x%x",
1209 		*phase_mux, *delay_time, bitset1, bitset2);
1210 
1211 	return 0;
1212 }
1213 
1214 /*
1215  *	Frequency
1216  */
1217 
1218 /* Returns rate in Hz */
litex_clk_calc_rate(struct litex_clk_clkout * lcko)1219 static inline uint32_t litex_clk_calc_rate(struct litex_clk_clkout *lcko)
1220 {
1221 	uint64_t f = litex_clk_calc_global_frequency(ldev->ts_g_config.mul,
1222 						  ldev->ts_g_config.div);
1223 
1224 	f /= lcko->config.div;
1225 
1226 	return (uint32_t)f;
1227 }
1228 
1229 /*
1230  * Written since there is no pow() in math.h. Only for exponent
1231  * and base above 0. Used for calculating scaling factor for
1232  * frequency margin
1233  *
1234  */
litex_clk_pow(uint32_t base,uint32_t exp)1235 static uint32_t litex_clk_pow(uint32_t base, uint32_t exp)
1236 {
1237 	int ret = 1;
1238 
1239 	while (exp--) {
1240 		ret *= base;
1241 	}
1242 
1243 	return ret;
1244 }
1245 
1246 /* Returns true when possible to set frequency with given global settings */
litex_clk_calc_clkout_params(struct litex_clk_clkout * lcko,uint64_t vco_freq)1247 static int litex_clk_calc_clkout_params(struct litex_clk_clkout *lcko,
1248 					 uint64_t vco_freq)
1249 {
1250 	int delta_f;
1251 	uint64_t m, clk_freq = 0;
1252 	uint32_t d, margin = 1;
1253 
1254 	if (lcko->margin.exp) {
1255 		margin = litex_clk_pow(10, lcko->margin.exp);
1256 	}
1257 
1258 	lcko->div.no_cnt = 0;
1259 
1260 	for (d = lcko->clkout_div.min; d <= lcko->clkout_div.max; d++) {
1261 		clk_freq = vco_freq;
1262 		clk_freq /= d;
1263 		m = lcko->ts_config.freq * lcko->margin.m;
1264 		/* Scale margin according to its exponent */
1265 		if (lcko->margin.exp) {
1266 			m /= margin;
1267 		}
1268 
1269 		delta_f = clk_freq - lcko->ts_config.freq;
1270 		delta_f = abs(delta_f);
1271 		if (delta_f <= m) {
1272 			lcko->config.freq = (uint32_t)clk_freq;
1273 			if (lcko->config.div != d) {
1274 				ldev->update_clkout[lcko->id] = 1;
1275 			}
1276 			lcko->config.div = d;
1277 			/* for sake of completeness */
1278 			lcko->ts_config.div = d;
1279 			/* we are not using fractional divider */
1280 			lcko->frac.frac_en = 0;
1281 			lcko->frac.frac = 0;
1282 			if (d == 1) {
1283 				lcko->div.no_cnt = 1;
1284 			}
1285 			LOG_DBG("CLKOUT%d: freq:%u div:%u gdiv:%u gmul:%u",
1286 				 lcko->id, lcko->config.freq, lcko->config.div,
1287 				 ldev->ts_g_config.div, ldev->ts_g_config.mul);
1288 			return true;
1289 		}
1290 	}
1291 
1292 	return false;
1293 }
1294 
1295 /* Compute dividers for all active clock outputs */
litex_clk_calc_all_clkout_params(uint64_t vco_freq)1296 static int litex_clk_calc_all_clkout_params(uint64_t vco_freq)
1297 {
1298 	struct litex_clk_clkout *lcko;
1299 	uint32_t c;
1300 
1301 	for (c = 0; c < ldev->nclkout; c++) {
1302 		lcko = &ldev->clkouts[c];
1303 		if (!litex_clk_calc_clkout_params(lcko, vco_freq)) {
1304 			return false;
1305 		}
1306 	}
1307 	return true;
1308 }
1309 
1310 /* Calculate parameters for whole active part of MMCM */
litex_clk_calc_all_params(void)1311 static int litex_clk_calc_all_params(void)
1312 {
1313 	uint32_t div, mul;
1314 	uint64_t vco_freq = 0;
1315 
1316 	for (div = ldev->divclk.min; div <= ldev->divclk.max; div++) {
1317 		ldev->ts_g_config.div = div;
1318 		for (mul = ldev->clkfbout.max; mul >= ldev->clkfbout.min;
1319 								 mul--) {
1320 			int below, above, all_valid = true;
1321 
1322 			vco_freq = CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC * (uint64_t)mul;
1323 			vco_freq /= div;
1324 			below = vco_freq < (ldev->vco.min
1325 					     * (1 + ldev->vco_margin));
1326 			above = vco_freq > (ldev->vco.max
1327 					    * (1 - ldev->vco_margin));
1328 
1329 			if (!below && !above) {
1330 				all_valid = litex_clk_calc_all_clkout_params
1331 								     (vco_freq);
1332 				if (all_valid) {
1333 					ldev->ts_g_config.mul = mul;
1334 					ldev->ts_g_config.freq = vco_freq;
1335 					LOG_DBG("GLOBAL: freq:%llu g_div:%u g_mul:%u",
1336 						ldev->ts_g_config.freq,
1337 						ldev->ts_g_config.div,
1338 						ldev->ts_g_config.mul);
1339 					return 0;
1340 				}
1341 			}
1342 		}
1343 	}
1344 	LOG_ERR("Cannot find correct settings for all clock outputs!");
1345 	return -ENOTSUP;
1346 }
1347 
litex_clk_check_rate_range(struct litex_clk_clkout * lcko,uint32_t rate)1348 int litex_clk_check_rate_range(struct litex_clk_clkout *lcko, uint32_t rate)
1349 {
1350 	uint64_t max, min, m;
1351 	uint32_t div, margin;
1352 
1353 	m = rate * lcko->margin.m;
1354 	if (lcko->margin.exp) {
1355 		margin = litex_clk_pow(10, lcko->margin.exp);
1356 	}
1357 
1358 	max = CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC * (uint64_t)ldev->clkfbout.max;
1359 	div = ldev->divclk.min * lcko->clkout_div.min;
1360 	max /= div;
1361 	max += m;
1362 
1363 	min = CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC * ldev->clkfbout.min;
1364 	div = ldev->divclk.max * lcko->clkout_div.max;
1365 	min /= div;
1366 
1367 	if (min < m) {
1368 		min = 0;
1369 	} else {
1370 		min -= m;
1371 	}
1372 
1373 	if ((uint64_t)rate < min || (uint64_t)rate > max) {
1374 		return -EINVAL;
1375 	}
1376 	return 0;
1377 }
1378 
1379 /* Returns closest available clock rate in Hz */
litex_clk_round_rate(struct litex_clk_clkout * lcko,unsigned long rate)1380 long litex_clk_round_rate(struct litex_clk_clkout *lcko, unsigned long rate)
1381 {
1382 	int ret;
1383 
1384 	ret = litex_clk_check_rate_range(lcko, rate);
1385 	if (ret != 0) {
1386 		return -EINVAL;
1387 	}
1388 
1389 	lcko->ts_config.freq = rate;
1390 
1391 	ret = litex_clk_calc_all_params();
1392 	if (ret != 0) {
1393 		return ret;
1394 	}
1395 
1396 	return litex_clk_calc_rate(lcko);
1397 }
1398 
litex_clk_write_rate(struct litex_clk_clkout * lcko)1399 int litex_clk_write_rate(struct litex_clk_clkout *lcko)
1400 {
1401 	int ret;
1402 	uint16_t bitset1, bitset2;
1403 	uint8_t *divider = &lcko->config.div,
1404 	   *edge = &lcko->div.edge,
1405 	   *high_time = &lcko->div.high_time,
1406 	   *low_time = &lcko->div.low_time,
1407 	   *no_cnt = &lcko->div.no_cnt,
1408 	   *frac = &lcko->frac.frac,
1409 	   *frac_en = &lcko->frac.frac_en,
1410 	   *frac_wf_r = &lcko->frac.frac_wf_r;
1411 
1412 	bitset1 = (*high_time << HIGH_TIME_POS)	|
1413 		  (*low_time << LOW_TIME_POS);
1414 
1415 	bitset2 = (*frac << FRAC_POS)		|
1416 		  (*frac_en << FRAC_EN_POS)	|
1417 		  (*frac_wf_r << FRAC_WF_R_POS)	|
1418 		  (*edge << EDGE_POS)		|
1419 		  (*no_cnt << NO_CNT_POS);
1420 
1421 	LOG_DBG("SET RATE: div:%u f:%u fwfr:%u fen:%u nc:%u e:%u ht:%u lt:%u\nbitset1: 0x%x bitset2: 0x%x",
1422 		*divider, *frac, *frac_wf_r, *frac_en,
1423 		*no_cnt, *edge, *high_time, *low_time, bitset1, bitset2);
1424 
1425 	ret = litex_clk_set_clock(lcko->id, REG1_FREQ_MASK, bitset1,
1426 					    REG2_FREQ_MASK, bitset2);
1427 	if (ret != 0) {
1428 		return ret;
1429 	}
1430 
1431 	ldev->update_clkout[lcko->id] = 0;
1432 
1433 	return 0;
1434 }
1435 
litex_clk_update_clkouts(void)1436 int litex_clk_update_clkouts(void)
1437 {
1438 	struct litex_clk_clkout *lcko;
1439 	int ret;
1440 	uint8_t c;
1441 
1442 	for (c = 0; c < ldev->nclkout; c++) {
1443 		if (ldev->update_clkout[c]) {
1444 			lcko = &ldev->clkouts[c];
1445 			ret = litex_clk_calc_duty_normal(lcko, false);
1446 			if (ret != 0) {
1447 				return ret;
1448 			}
1449 			ret = litex_clk_write_rate(lcko);
1450 			if (ret != 0) {
1451 				return ret;
1452 			}
1453 			LOG_INF("CLKOUT%d: updated rate: %u to %u HZ",
1454 					lcko->id, lcko->ts_config.freq,
1455 						     lcko->config.freq);
1456 		}
1457 	}
1458 
1459 	return 0;
1460 }
1461 /* Set closest available clock rate in Hz, parent_rate ignored */
litex_clk_set_rate(struct litex_clk_clkout * lcko,unsigned long rate)1462 int litex_clk_set_rate(struct litex_clk_clkout *lcko, unsigned long rate)
1463 {
1464 	int ret;
1465 
1466 	LOG_DBG("CLKOUT%d: setting rate: %lu", lcko->id, rate);
1467 	ret = litex_clk_round_rate(lcko, rate);
1468 	if (ret < 0) {
1469 		return ret;
1470 	}
1471 	ret = litex_clk_set_globs();
1472 	if (ret != 0) {
1473 		return ret;
1474 	}
1475 	ret = litex_clk_calc_duty_normal(lcko, false);
1476 	if (ret != 0) {
1477 		return ret;
1478 	}
1479 	ret = litex_clk_write_rate(lcko);
1480 	if (ret != 0) {
1481 		return ret;
1482 	}
1483 	LOG_INF("CLKOUT%d: set rate: %u HZ", lcko->id, lcko->config.freq);
1484 	ret = litex_clk_update_clkouts();
1485 	if (ret != 0) {
1486 		return ret;
1487 	}
1488 
1489 #ifdef CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG
1490 	litex_clk_print_all_params();
1491 	litex_clk_print_all_regs();
1492 #endif /* CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG */
1493 
1494 	return 0;
1495 }
1496 
1497 /* Set default clock value from device tree for given clkout*/
litex_clk_set_def_clkout(int clkout_nr)1498 static int litex_clk_set_def_clkout(int clkout_nr)
1499 {
1500 	struct litex_clk_clkout *lcko = &ldev->clkouts[clkout_nr];
1501 	int ret;
1502 
1503 	ret = litex_clk_set_rate(lcko, lcko->def.freq);
1504 	if (ret != 0) {
1505 		return ret;
1506 	}
1507 	ret = litex_clk_set_duty_cycle(lcko, &lcko->def.duty);
1508 	if (ret != 0) {
1509 		return ret;
1510 	}
1511 	return litex_clk_set_phase(lcko, lcko->def.phase);
1512 }
1513 
litex_clk_set_all_def_clkouts(void)1514 static int litex_clk_set_all_def_clkouts(void)
1515 {
1516 	int c, ret;
1517 
1518 	for (c = 0; c < ldev->nclkout; c++) {
1519 		ret = litex_clk_set_def_clkout(c);
1520 		if (ret != 0) {
1521 			return ret;
1522 		}
1523 	}
1524 	return 0;
1525 }
1526 
1527 /*
1528  * Returns parameters of given clock output
1529  *
1530  * clock:		device structure for driver
1531  * sub_system:		pointer to struct litex_clk_clkout
1532  *			casted to clock_control_subsys with
1533  *			all clkout parameters
1534  */
litex_clk_get_subsys_rate(const struct device * clock,clock_control_subsys_t sys,uint32_t * rate)1535 static int litex_clk_get_subsys_rate(const struct device *clock,
1536 				     clock_control_subsys_t sys, uint32_t *rate)
1537 {
1538 	struct litex_clk_setup *setup = sys;
1539 	struct litex_clk_clkout *lcko;
1540 
1541 	lcko = &ldev->clkouts[setup->clkout_nr];
1542 	*rate = litex_clk_calc_rate(lcko);
1543 
1544 	return 0;
1545 }
1546 
litex_clk_get_status(const struct device * dev,clock_control_subsys_t sys)1547 static enum clock_control_status litex_clk_get_status(const struct device *dev,
1548 						     clock_control_subsys_t sys)
1549 {
1550 	struct litex_clk_setup *setup = sys;
1551 	struct clk_duty duty;
1552 	struct litex_clk_clkout *lcko;
1553 	int ret;
1554 
1555 	lcko = &ldev->clkouts[setup->clkout_nr];
1556 
1557 	setup->rate = litex_clk_calc_rate(lcko);
1558 	ret = litex_clk_get_duty_cycle(lcko, &duty);
1559 	if (ret != 0) {
1560 		return ret;
1561 	}
1562 	setup->duty = litex_clk_calc_duty_percent(&duty);
1563 	setup->phase = litex_clk_get_phase(lcko);
1564 
1565 	return CLOCK_CONTROL_STATUS_ON;
1566 }
1567 
litex_clk_on(const struct device * dev,clock_control_subsys_t sys)1568 static inline int litex_clk_on(const struct device *dev, clock_control_subsys_t sys)
1569 {
1570 	struct litex_clk_setup *setup = sys;
1571 	struct clk_duty duty;
1572 	struct litex_clk_clkout *lcko;
1573 	uint8_t duty_perc;
1574 	int ret;
1575 
1576 	lcko = &ldev->clkouts[setup->clkout_nr];
1577 
1578 	if (lcko->config.freq != setup->rate) {
1579 		ret = litex_clk_set_rate(lcko, setup->rate);
1580 		if (ret != 0) {
1581 			return ret;
1582 		}
1583 	}
1584 	if (lcko->config.phase != setup->phase) {
1585 		ret = litex_clk_set_phase(lcko, setup->phase);
1586 		if (ret != 0) {
1587 			return ret;
1588 		}
1589 	}
1590 	duty_perc = litex_clk_calc_duty_percent(&lcko->config.duty);
1591 	if (duty_perc != setup->duty) {
1592 		duty.num = setup->duty;
1593 		duty.den = 100;
1594 		ret = litex_clk_set_duty_cycle(lcko, &duty);
1595 		if (ret != 0) {
1596 			return ret;
1597 		}
1598 	}
1599 	return 0;
1600 }
1601 
litex_clk_off(const struct device * dev,clock_control_subsys_t sub_system)1602 static inline int litex_clk_off(const struct device *dev,
1603 				clock_control_subsys_t sub_system)
1604 {
1605 	return litex_clk_change_value(ZERO_REG, ZERO_REG, POWER_REG);
1606 }
1607 
1608 static DEVICE_API(clock_control, litex_clk_api) = {
1609 	.on = litex_clk_on,
1610 	.off = litex_clk_off,
1611 	.get_rate = litex_clk_get_subsys_rate,
1612 	.get_status = litex_clk_get_status
1613 };
1614 
litex_clk_dts_clkout_ranges_read(struct litex_clk_range * clkout_div)1615 static void litex_clk_dts_clkout_ranges_read(struct litex_clk_range *clkout_div)
1616 {
1617 	clkout_div->min = CLKOUT_DIVIDE_MIN;
1618 	clkout_div->max = CLKOUT_DIVIDE_MAX;
1619 }
1620 
litex_clk_dts_timeout_read(struct litex_clk_timeout * timeout)1621 static int litex_clk_dts_timeout_read(struct litex_clk_timeout *timeout)
1622 {
1623 	/* Read wait_lock timeout from device property*/
1624 	timeout->lock = LOCK_TIMEOUT;
1625 	if (timeout->lock < 1) {
1626 		LOG_ERR("LiteX CLK driver cannot wait shorter than ca. 1ms\n");
1627 		return -EINVAL;
1628 	}
1629 
1630 	/* Read wait_drdy timeout from device property*/
1631 	timeout->drdy = DRDY_TIMEOUT;
1632 	if (timeout->drdy < 1) {
1633 		LOG_ERR("LiteX CLK driver cannot wait shorter than ca. 1ms\n");
1634 		return -EINVAL;
1635 	}
1636 
1637 	return 0;
1638 }
1639 
litex_clk_dts_clkouts_read(void)1640 static int litex_clk_dts_clkouts_read(void)
1641 {
1642 	struct litex_clk_range clkout_div;
1643 	struct litex_clk_clkout *lcko;
1644 
1645 	litex_clk_dts_clkout_ranges_read(&clkout_div);
1646 
1647 #if CLKOUT_EXIST(0) == 1
1648 		CLKOUT_INIT(0)
1649 #endif
1650 #if CLKOUT_EXIST(1) == 1
1651 		CLKOUT_INIT(1)
1652 #endif
1653 #if CLKOUT_EXIST(2) == 1
1654 		CLKOUT_INIT(2)
1655 #endif
1656 #if CLKOUT_EXIST(3) == 1
1657 		CLKOUT_INIT(3)
1658 #endif
1659 #if CLKOUT_EXIST(4) == 1
1660 		CLKOUT_INIT(4)
1661 #endif
1662 #if CLKOUT_EXIST(5) == 1
1663 		CLKOUT_INIT(5)
1664 #endif
1665 #if CLKOUT_EXIST(6) == 1
1666 		CLKOUT_INIT(6)
1667 #endif
1668 	return 0;
1669 }
1670 
litex_clk_init_clkouts(void)1671 static void litex_clk_init_clkouts(void)
1672 {
1673 	struct litex_clk_clkout *lcko;
1674 	int i;
1675 
1676 	for (i = 0; i < ldev->nclkout; i++) {
1677 		lcko = &ldev->clkouts[i];
1678 		lcko->base = ldev->base;
1679 		/* mark defaults to set */
1680 		lcko->ts_config.freq = lcko->def.freq;
1681 		lcko->ts_config.duty = lcko->def.duty;
1682 		lcko->ts_config.phase = lcko->def.phase;
1683 	}
1684 }
1685 
litex_clk_dts_cnt_clocks(void)1686 static int litex_clk_dts_cnt_clocks(void)
1687 {
1688 	return NCLKOUT;
1689 }
1690 
litex_clk_dts_global_ranges_read(void)1691 static void litex_clk_dts_global_ranges_read(void)
1692 {
1693 	ldev->divclk.min = DIVCLK_DIVIDE_MIN;
1694 	ldev->divclk.max = DIVCLK_DIVIDE_MAX;
1695 	ldev->clkfbout.min = CLKFBOUT_MULT_MIN;
1696 	ldev->clkfbout.max = CLKFBOUT_MULT_MAX;
1697 	ldev->vco.min = VCO_FREQ_MIN;
1698 	ldev->vco.max = VCO_FREQ_MAX;
1699 	ldev->vco_margin = VCO_MARGIN;
1700 }
1701 
litex_clk_dts_global_read(void)1702 static int litex_clk_dts_global_read(void)
1703 {
1704 	int ret;
1705 
1706 	ldev->nclkout = litex_clk_dts_cnt_clocks();
1707 
1708 	clkouts = k_malloc(sizeof(struct litex_clk_clkout) * ldev->nclkout);
1709 	ldev->update_clkout = k_malloc(sizeof(uint8_t) * ldev->nclkout);
1710 	if (!clkouts || !ldev->update_clkout) {
1711 		LOG_ERR("CLKOUT memory allocation failure!");
1712 		return -ENOMEM;
1713 	}
1714 	ldev->clkouts = clkouts;
1715 
1716 	ret = litex_clk_dts_timeout_read(&ldev->timeout);
1717 	if (ret != 0) {
1718 		return ret;
1719 	}
1720 
1721 	litex_clk_dts_global_ranges_read();
1722 
1723 	return 0;
1724 }
1725 
litex_clk_init_glob_clk(void)1726 static int litex_clk_init_glob_clk(void)
1727 {
1728 	int ret;
1729 
1730 	/* Power on MMCM module */
1731 	ret = litex_clk_change_value(FULL_REG_16, FULL_REG_16, POWER_REG);
1732 	if (ret != 0) {
1733 		LOG_ERR("MMCM initialization failure, ret: %d", ret);
1734 		return ret;
1735 	}
1736 
1737 	return 0;
1738 }
1739 /* Enable module, set global divider, multiplier, default clkout parameters */
litex_clk_init(const struct device * dev)1740 static int litex_clk_init(const struct device *dev)
1741 {
1742 	int ret;
1743 
1744 	ldev = k_malloc(sizeof(struct litex_clk_device));
1745 	if (ldev == NULL) {
1746 		return -ENOMEM;
1747 	}
1748 
1749 	ldev->base = (uint32_t *)DRP_BASE;
1750 	if (ldev->base == NULL) {
1751 		return -EIO;
1752 	}
1753 
1754 	ret = litex_clk_dts_global_read();
1755 	if (ret != 0) {
1756 		return ret;
1757 	}
1758 
1759 	ret = litex_clk_dts_clkouts_read();
1760 	if (ret != 0) {
1761 		return ret;
1762 	}
1763 
1764 	litex_clk_init_clkouts();
1765 
1766 	ret = litex_clk_init_glob_clk();
1767 	if (ret != 0) {
1768 		return ret;
1769 	}
1770 
1771 	ret = litex_clk_set_all_def_clkouts();
1772 	if (ret != 0) {
1773 		return ret;
1774 	}
1775 
1776 #ifdef CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG
1777 	litex_clk_print_all_params();
1778 	litex_clk_print_all_regs();
1779 #endif /* CONFIG_CLOCK_CONTROL_LOG_LEVEL_DBG */
1780 
1781 	LOG_INF("LiteX Clock Control driver initialized");
1782 	return 0;
1783 }
1784 
1785 static const struct litex_clk_device ldev_init = {
1786 	.base = (uint32_t *)DRP_BASE,
1787 	.timeout = {LOCK_TIMEOUT, DRDY_TIMEOUT},
1788 	.divclk = {DIVCLK_DIVIDE_MIN, DIVCLK_DIVIDE_MAX},
1789 	.clkfbout = {CLKFBOUT_MULT_MIN, CLKFBOUT_MULT_MAX},
1790 	.vco = {VCO_FREQ_MIN, VCO_FREQ_MAX},
1791 	.vco_margin = VCO_MARGIN,
1792 	.nclkout = NCLKOUT
1793 };
1794 
1795 DEVICE_DT_DEFINE(DT_NODELABEL(clock0), litex_clk_init, NULL,
1796 		    NULL, &ldev_init, POST_KERNEL,
1797 		    CONFIG_CLOCK_CONTROL_INIT_PRIORITY, &litex_clk_api);
1798