xref: /openbmc/u-boot/cmd/fsi.c (revision 18b134e0)
1 #include <common.h>
2 #include <command.h>
3 #include <aspeed_fsi.h>
4 #include <dm/device.h>
5 #include <dm/uclass.h>
6 
7 struct fsi_master_aspeed *fsi;
8 
do_break(void)9 static void do_break(void)
10 {
11 	debug("%s\n", __func__);
12 	aspeed_fsi_break(fsi, 0);
13 }
14 
do_status(void)15 static void do_status(void)
16 {
17 	debug("%s\n", __func__);
18 	aspeed_fsi_status(fsi);
19 }
20 
do_getcfam(int argc,char * const argv[])21 static void do_getcfam(int argc, char *const argv[])
22 {
23 	int rc;
24 	uint32_t addr, val;
25 
26 	if (argc != 3) {
27 		printf("invalid arguments to getcfam\n");
28 		return;
29 	}
30 
31 	addr = simple_strtoul(argv[2], NULL, 16);
32 
33 	debug("%s %08x\n", __func__, addr);
34 	rc = aspeed_fsi_read(fsi, 0, addr, &val, 4);
35 	if (rc) {
36 		printf("error reading: %d\n", rc);
37 		return;
38 	}
39 
40 	printf("0x%08x\n", be32_to_cpu(val));
41 }
42 
do_putcfam(int argc,char * const argv[])43 static void do_putcfam(int argc, char *const argv[])
44 {
45 	int rc;
46 	uint32_t addr, val;
47 
48 	if (argc != 4) {
49 		printf("invalid arguments to putcfam\n");
50 		return;
51 	}
52 
53 	addr = simple_strtoul(argv[2], NULL, 16);
54 	val = simple_strtoul(argv[3], NULL, 16);
55 
56 	debug("%s %08x %08x\n", __func__, addr, val);
57 	rc = aspeed_fsi_write(fsi, 0, addr, &val, 4);
58 	if (rc)
59 		printf("error writing: %d\n", rc);
60 }
61 
do_divisor(int argc,char * const argv[])62 static void do_divisor(int argc, char *const argv[])
63 {
64 	int rc;
65 	uint32_t val;
66 
67 	if (argc == 2) {
68 		rc = aspeed_fsi_divisor(fsi, 0);
69 		if (rc > 0)
70 			printf("divsior: %d\n", rc);
71 	} else if (argc == 3) {
72 		val = simple_strtoul(argv[2], NULL, 0);
73 		rc = aspeed_fsi_divisor(fsi, val);
74 	} else {
75 		printf("invalid arguments to divisor\n");
76 		return;
77 	}
78 
79 	if (rc < 0)
80 		printf("divisor error: %d\n", rc);
81 }
82 
do_probe(int argc,char * const argv[])83 static struct fsi_master_aspeed *do_probe(int argc, char *const argv[])
84 {
85 	struct udevice *dev;
86 	const char *devices[] = {"fsi@1e79b000", "fsi@1e79b100"};
87 	int rc, id;
88 
89 	if (argc > 3) {
90 		printf("invalid arguments to probe\n");
91 		return NULL;
92 	}
93 
94 	if (argc == 2)
95 		id = 0;
96 	else
97 		id = simple_strtoul(argv[2], NULL, 10);
98 
99 	if (id > 1) {
100 		printf("valid devices: 0, 1\n");
101 		return NULL;
102 	}
103 
104 	rc = uclass_get_device_by_name(UCLASS_MISC, devices[id], &dev);
105 	if (rc) {
106 		printf("fsi device %s not found\n", devices[id]);
107 		return NULL;
108 	}
109 	return dev_get_priv(dev);
110 }
111 
112 
do_fsi(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])113 static int do_fsi(cmd_tbl_t *cmdtp, int flag, int argc, char *const argv[])
114 {
115 
116 	if (!strcmp(argv[1], "probe")) {
117 		fsi = do_probe(argc, argv);
118 		return 0;
119 	}
120 
121 	if (fsi == NULL) {
122 		printf("Run probe first\n");
123 		return -EINVAL;
124 	}
125 
126 	if (!strcmp(argv[1], "break"))
127 		do_break();
128 	else if (!strcmp(argv[1], "status"))
129 		do_status();
130 	else if (!strncmp(argv[1], "put", 3))
131 		do_putcfam(argc, argv);
132 	else if (!strncmp(argv[1], "get", 3))
133 		do_getcfam(argc, argv);
134 	else if (!strncmp(argv[1], "div", 3))
135 		do_divisor(argc, argv);
136 
137 	return 0;
138 }
139 
140 static char fsi_help_text[] =
141 	"fsi probe [<n>]\n"
142 	"fsi break\n"
143 	"fsi getcfam <addr>\n"
144 	"fsi putcfam <addr> <value>\n"
145 	"fsi divisor [<divisor>]\n"
146 	"fsi status\n";
147 
148 U_BOOT_CMD(
149 	fsi, 4, 1, do_fsi,
150 	"IBM FSI commands",
151 	fsi_help_text
152 );
153 
154