summaryrefslogtreecommitdiffstats
path: root/board/gdsys/405ep/io.c
blob: 0974019ef7f2be64023e27ad349b6572c7dfd15f (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
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
/*
 * (C) Copyright 2010
 * Dirk Eibach,  Guntermann & Drunck GmbH, eibach@gdsys.de
 *
 * See file CREDITS for list of people who contributed to this
 * project.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of
 * the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 * MA 02111-1307 USA
 */

#include <common.h>
#include <command.h>
#include <asm/processor.h>
#include <asm/io.h>
#include <asm/ppc4xx-gpio.h>

#include <miiphy.h>

#include <gdsys_fpga.h>

#define PHYREG_CONTROL				0
#define PHYREG_PAGE_ADDRESS			22
#define PHYREG_PG0_COPPER_SPECIFIC_CONTROL_1	16
#define PHYREG_PG2_COPPER_SPECIFIC_CONTROL_2	26

enum {
	UNITTYPE_CCD_SWITCH = 1,
};

enum {
	HWVER_100 = 0,
	HWVER_110 = 1,
	HWVER_121 = 2,
	HWVER_122 = 3,
};

int configure_gbit_phy(unsigned char addr)
{
	unsigned short value;

	/* select page 2 */
	if (miiphy_write(CONFIG_SYS_GBIT_MII_BUSNAME, addr,
		PHYREG_PAGE_ADDRESS, 0x0002))
		goto err_out;
	/* disable SGMII autonegotiation */
	if (miiphy_write(CONFIG_SYS_GBIT_MII_BUSNAME, addr,
		PHYREG_PG2_COPPER_SPECIFIC_CONTROL_2, 0x800a))
		goto err_out;
	/* select page 0 */
	if (miiphy_write(CONFIG_SYS_GBIT_MII_BUSNAME, addr,
		PHYREG_PAGE_ADDRESS, 0x0000))
		goto err_out;
	/* switch from powerdown to normal operation */
	if (miiphy_read(CONFIG_SYS_GBIT_MII_BUSNAME, addr,
		PHYREG_PG0_COPPER_SPECIFIC_CONTROL_1, &value))
		goto err_out;
	if (miiphy_write(CONFIG_SYS_GBIT_MII_BUSNAME, addr,
		PHYREG_PG0_COPPER_SPECIFIC_CONTROL_1, value & ~0x0004))
		goto err_out;
	/* reset phy so settings take effect */
	if (miiphy_write(CONFIG_SYS_GBIT_MII_BUSNAME, addr,
		PHYREG_CONTROL, 0x9140))
		goto err_out;

	return 0;

err_out:
	printf("Error writing to the PHY addr=%02x\n", addr);
	return -1;
}

/*
 * Check Board Identity:
 */
int checkboard(void)
{
	ihs_fpga_t *fpga = (ihs_fpga_t *) CONFIG_SYS_FPGA_BASE(0);
	char *s = getenv("serial#");
	u16 versions = in_le16(&fpga->versions);
	u16 fpga_version = in_le16(&fpga->fpga_version);
	u16 fpga_features = in_le16(&fpga->fpga_features);
	unsigned unit_type;
	unsigned hardware_version;
	unsigned feature_channels;
	unsigned feature_expansion;

	unit_type = (versions & 0xf000) >> 12;
	hardware_version = versions & 0x000f;
	feature_channels = fpga_features & 0x007f;
	feature_expansion = fpga_features & (1<<15);

	printf("Board: ");

	printf("CATCenter Io");

	if (s != NULL) {
		puts(", serial# ");
		puts(s);
	}
	puts("\n       ");

	switch (unit_type) {
	case UNITTYPE_CCD_SWITCH:
		printf("CCD-Switch");
		break;

	default:
		printf("UnitType %d(not supported)", unit_type);
		break;
	}

	switch (hardware_version) {
	case HWVER_100:
		printf(" HW-Ver 1.00\n");
		break;

	case HWVER_110:
		printf(" HW-Ver 1.10\n");
		break;

	case HWVER_121:
		printf(" HW-Ver 1.21\n");
		break;

	case HWVER_122:
		printf(" HW-Ver 1.22\n");
		break;

	default:
		printf(" HW-Ver %d(not supported)\n",
		       hardware_version);
		break;
	}

	printf("       FPGA V %d.%02d, features:",
		fpga_version / 100, fpga_version % 100);

	printf(" %d channel(s)", feature_channels);

	printf(", expansion %ssupported\n", feature_expansion ? "" : "un");

	return 0;
}

/*
 * setup Gbit PHYs
 */
int last_stage_init(void)
{
	ihs_fpga_t *fpga = (ihs_fpga_t *) CONFIG_SYS_FPGA_BASE(0);
	unsigned int k;

	miiphy_register(CONFIG_SYS_GBIT_MII_BUSNAME,
		bb_miiphy_read, bb_miiphy_write);

	for (k = 0; k < 32; ++k)
		configure_gbit_phy(k);

	/* take fpga serdes blocks out of reset */
	out_le16(&fpga->quad_serdes_reset, 0);

	return 0;
}