1/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
2/*
3 * Copyright (c) 2018 Microsemi Corporation
4 */
5
6#include <asm/asm.h>
7#include <asm/regdef.h>
8
9#define BASE_MACRO      0x600a0000
10#define REG_OFFSET(t, o) (t + (o*4))
11#define REG_MACRO(x) REG_OFFSET(BASE_MACRO, x)
12#define BIT(nr)			(1 << (nr))
13
14#define MACRO_CTRL_PLL5G_STATUS_PLL5G_STATUS0 REG_MACRO(6)
15#define MACRO_CTRL_PLL5G_STATUS_PLL5G_STATUS0_LOCK_STATUS BIT(0)
16#define MACRO_CTRL_PLL5G_CFG_PLL5G_CFG2 REG_MACRO(2)
17#define MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0 REG_MACRO(0)
18#define MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0_CPU_CLK_DIV (0x3F << 6)
19#define MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0_CPU_CLK_DIV_ENC(x) (x << 6)
20
21    .set noreorder
22LEAF(pll_init)
23	/* Make sure PLL is locked */
24	lw	v0, MACRO_CTRL_PLL5G_STATUS_PLL5G_STATUS0
25	andi	v1, v0, MACRO_CTRL_PLL5G_STATUS_PLL5G_STATUS0_LOCK_STATUS
26	bne	v1, zero, 1f
27	 nop
28
29	/* Black magic from frontend */
30	li	v1, 0x00610400
31	sw	v1, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG2
32
33	li	v1, 0x00610c00
34	sw	v1, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG2
35
36	li	v1, 0x00610800
37	sw	v1, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG2
38
39	li	v1, 0x00610000
40	sw	v1, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG2
41
42	/* Wait for lock */
432:	lw	v0, MACRO_CTRL_PLL5G_STATUS_PLL5G_STATUS0
44	andi	v1, v0, MACRO_CTRL_PLL5G_STATUS_PLL5G_STATUS0_LOCK_STATUS
45	/* Keep looping if zero (no lock bit yet) */
46	beq	v1, zero, 2b
47	 nop
48
49	/* Setup PLL CPU clock divider for 416MHz */
501:	lw	v0, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0
51
52	/* Keep reserved bits */
53	li	v1, ~MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0_CPU_CLK_DIV
54	and	v0, v0, v1
55
56	/* Set code 6 ~ 416.66 MHz */
57	ori	v0, v0, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0_CPU_CLK_DIV_ENC(6)
58
59	sw	v0, MACRO_CTRL_PLL5G_CFG_PLL5G_CFG0
60	jr      ra
61	 nop
62	END(pll_init)
63