summaryrefslogtreecommitdiff
path: root/board/phytec/common/k3/k3_ddrss_patch.c
blob: 5afe5a20c7f3da4ca83f12ad43798d4cf01321e5 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
/* SPDX-License-Identifier: GPL-2.0-or-later */
/*
 * Copyright (C) 2024 PHYTEC Messtechnik GmbH
 * Author: Wadim Egorov <w.egorov@phytec.de>
 */

#include "k3_ddrss_patch.h"

#include <fdt_support.h>
#include <linux/errno.h>

#ifdef CONFIG_K3_AM64_DDRSS
#define LPDDR4_INTR_CTL_REG_COUNT (423U)
#define LPDDR4_INTR_PHY_INDEP_REG_COUNT (345U)
#define LPDDR4_INTR_PHY_REG_COUNT (1406U)
#endif

static int fdt_setprop_inplace_idx_u32(void *fdt, int nodeoffset,
				       const char *name, uint32_t idx, u32 val)
{
	val = cpu_to_be32(val);
	return fdt_setprop_inplace_namelen_partial(fdt, nodeoffset, name,
						   strlen(name),
						   idx * sizeof(val), &val,
						   sizeof(val));
}

int fdt_apply_ddrss_timings_patch(void *fdt, struct ddrss *ddrss)
{
	int i, j;
	int ret;
	int mem_offset;

	mem_offset = fdt_path_offset(fdt, "/memorycontroller@f300000");
	if (mem_offset < 0)
		return -ENODEV;

	for (i = 0; i < LPDDR4_INTR_CTL_REG_COUNT; i++)
		for (j = 0; j < ddrss->ctl_regs_num; j++)
			if (i == ddrss->ctl_regs[j].off) {
				ret = fdt_setprop_inplace_idx_u32(fdt,
						mem_offset, "ti,ctl-data", i,
						ddrss->ctl_regs[j].val);
				if (ret)
					return ret;
			}

	for (i = 0; i < LPDDR4_INTR_PHY_INDEP_REG_COUNT; i++)
		for (j = 0; j < ddrss->pi_regs_num; j++)
			if (i == ddrss->pi_regs[j].off) {
				ret = fdt_setprop_inplace_idx_u32(fdt,
						mem_offset, "ti,pi-data", i,
						ddrss->pi_regs[j].val);
				if (ret)
					return ret;
			}

	for (i = 0; i < LPDDR4_INTR_PHY_REG_COUNT; i++)
		for (j = 0; j < ddrss->phy_regs_num; j++)
			if (i == ddrss->phy_regs[j].off) {
				ret = fdt_setprop_inplace_idx_u32(fdt,
						mem_offset, "ti,phy-data", i,
						ddrss->phy_regs[j].val);
				if (ret)
					return ret;
			}

	return 0;
}