1/* SPDX-License-Identifier: GPL-2.0-only */
2/*
3 *  longhaul.h
4 *  (C) 2003 Dave Jones.
5 *
6 *  VIA-specific information
7 */
8
9union msr_bcr2 {
10	struct {
11		unsigned Reseved:19,	// 18:0
12		ESOFTBF:1,		// 19
13		Reserved2:3,		// 22:20
14		CLOCKMUL:4,		// 26:23
15		Reserved3:5;		// 31:27
16	} bits;
17	unsigned long val;
18};
19
20union msr_longhaul {
21	struct {
22		unsigned RevisionID:4,	// 3:0
23		RevisionKey:4,		// 7:4
24		EnableSoftBusRatio:1,	// 8
25		EnableSoftVID:1,	// 9
26		EnableSoftBSEL:1,	// 10
27		Reserved:3,		// 11:13
28		SoftBusRatio4:1,	// 14
29		VRMRev:1,		// 15
30		SoftBusRatio:4,		// 19:16
31		SoftVID:5,		// 24:20
32		Reserved2:3,		// 27:25
33		SoftBSEL:2,		// 29:28
34		Reserved3:2,		// 31:30
35		MaxMHzBR:4,		// 35:32
36		MaximumVID:5,		// 40:36
37		MaxMHzFSB:2,		// 42:41
38		MaxMHzBR4:1,		// 43
39		Reserved4:4,		// 47:44
40		MinMHzBR:4,		// 51:48
41		MinimumVID:5,		// 56:52
42		MinMHzFSB:2,		// 58:57
43		MinMHzBR4:1,		// 59
44		Reserved5:4;		// 63:60
45	} bits;
46	unsigned long long val;
47};
48
49/*
50 * Clock ratio tables. Div/Mod by 10 to get ratio.
51 * The eblcr values specify the ratio read from the CPU.
52 * The mults values specify what to write to the CPU.
53 */
54
55/*
56 * VIA C3 Samuel 1  & Samuel 2 (stepping 0)
57 */
58static const int samuel1_mults[16] = {
59	-1, /* 0000 -> RESERVED */
60	30, /* 0001 ->  3.0x */
61	40, /* 0010 ->  4.0x */
62	-1, /* 0011 -> RESERVED */
63	-1, /* 0100 -> RESERVED */
64	35, /* 0101 ->  3.5x */
65	45, /* 0110 ->  4.5x */
66	55, /* 0111 ->  5.5x */
67	60, /* 1000 ->  6.0x */
68	70, /* 1001 ->  7.0x */
69	80, /* 1010 ->  8.0x */
70	50, /* 1011 ->  5.0x */
71	65, /* 1100 ->  6.5x */
72	75, /* 1101 ->  7.5x */
73	-1, /* 1110 -> RESERVED */
74	-1, /* 1111 -> RESERVED */
75};
76
77static const int samuel1_eblcr[16] = {
78	50, /* 0000 -> RESERVED */
79	30, /* 0001 ->  3.0x */
80	40, /* 0010 ->  4.0x */
81	-1, /* 0011 -> RESERVED */
82	55, /* 0100 ->  5.5x */
83	35, /* 0101 ->  3.5x */
84	45, /* 0110 ->  4.5x */
85	-1, /* 0111 -> RESERVED */
86	-1, /* 1000 -> RESERVED */
87	70, /* 1001 ->  7.0x */
88	80, /* 1010 ->  8.0x */
89	60, /* 1011 ->  6.0x */
90	-1, /* 1100 -> RESERVED */
91	75, /* 1101 ->  7.5x */
92	-1, /* 1110 -> RESERVED */
93	65, /* 1111 ->  6.5x */
94};
95
96/*
97 * VIA C3 Samuel2 Stepping 1->15
98 */
99static const int samuel2_eblcr[16] = {
100	50,  /* 0000 ->  5.0x */
101	30,  /* 0001 ->  3.0x */
102	40,  /* 0010 ->  4.0x */
103	100, /* 0011 -> 10.0x */
104	55,  /* 0100 ->  5.5x */
105	35,  /* 0101 ->  3.5x */
106	45,  /* 0110 ->  4.5x */
107	110, /* 0111 -> 11.0x */
108	90,  /* 1000 ->  9.0x */
109	70,  /* 1001 ->  7.0x */
110	80,  /* 1010 ->  8.0x */
111	60,  /* 1011 ->  6.0x */
112	120, /* 1100 -> 12.0x */
113	75,  /* 1101 ->  7.5x */
114	130, /* 1110 -> 13.0x */
115	65,  /* 1111 ->  6.5x */
116};
117
118/*
119 * VIA C3 Ezra
120 */
121static const int ezra_mults[16] = {
122	100, /* 0000 -> 10.0x */
123	30,  /* 0001 ->  3.0x */
124	40,  /* 0010 ->  4.0x */
125	90,  /* 0011 ->  9.0x */
126	95,  /* 0100 ->  9.5x */
127	35,  /* 0101 ->  3.5x */
128	45,  /* 0110 ->  4.5x */
129	55,  /* 0111 ->  5.5x */
130	60,  /* 1000 ->  6.0x */
131	70,  /* 1001 ->  7.0x */
132	80,  /* 1010 ->  8.0x */
133	50,  /* 1011 ->  5.0x */
134	65,  /* 1100 ->  6.5x */
135	75,  /* 1101 ->  7.5x */
136	85,  /* 1110 ->  8.5x */
137	120, /* 1111 -> 12.0x */
138};
139
140static const int ezra_eblcr[16] = {
141	50,  /* 0000 ->  5.0x */
142	30,  /* 0001 ->  3.0x */
143	40,  /* 0010 ->  4.0x */
144	100, /* 0011 -> 10.0x */
145	55,  /* 0100 ->  5.5x */
146	35,  /* 0101 ->  3.5x */
147	45,  /* 0110 ->  4.5x */
148	95,  /* 0111 ->  9.5x */
149	90,  /* 1000 ->  9.0x */
150	70,  /* 1001 ->  7.0x */
151	80,  /* 1010 ->  8.0x */
152	60,  /* 1011 ->  6.0x */
153	120, /* 1100 -> 12.0x */
154	75,  /* 1101 ->  7.5x */
155	85,  /* 1110 ->  8.5x */
156	65,  /* 1111 ->  6.5x */
157};
158
159/*
160 * VIA C3 (Ezra-T) [C5M].
161 */
162static const int ezrat_mults[32] = {
163	100, /* 0000 -> 10.0x */
164	30,  /* 0001 ->  3.0x */
165	40,  /* 0010 ->  4.0x */
166	90,  /* 0011 ->  9.0x */
167	95,  /* 0100 ->  9.5x */
168	35,  /* 0101 ->  3.5x */
169	45,  /* 0110 ->  4.5x */
170	55,  /* 0111 ->  5.5x */
171	60,  /* 1000 ->  6.0x */
172	70,  /* 1001 ->  7.0x */
173	80,  /* 1010 ->  8.0x */
174	50,  /* 1011 ->  5.0x */
175	65,  /* 1100 ->  6.5x */
176	75,  /* 1101 ->  7.5x */
177	85,  /* 1110 ->  8.5x */
178	120, /* 1111 ->  12.0x */
179
180	-1,  /* 0000 -> RESERVED (10.0x) */
181	110, /* 0001 -> 11.0x */
182	-1, /* 0010 -> 12.0x */
183	-1,  /* 0011 -> RESERVED (9.0x)*/
184	105, /* 0100 -> 10.5x */
185	115, /* 0101 -> 11.5x */
186	125, /* 0110 -> 12.5x */
187	135, /* 0111 -> 13.5x */
188	140, /* 1000 -> 14.0x */
189	150, /* 1001 -> 15.0x */
190	160, /* 1010 -> 16.0x */
191	130, /* 1011 -> 13.0x */
192	145, /* 1100 -> 14.5x */
193	155, /* 1101 -> 15.5x */
194	-1,  /* 1110 -> RESERVED (13.0x) */
195	-1,  /* 1111 -> RESERVED (12.0x) */
196};
197
198static const int ezrat_eblcr[32] = {
199	50,  /* 0000 ->  5.0x */
200	30,  /* 0001 ->  3.0x */
201	40,  /* 0010 ->  4.0x */
202	100, /* 0011 -> 10.0x */
203	55,  /* 0100 ->  5.5x */
204	35,  /* 0101 ->  3.5x */
205	45,  /* 0110 ->  4.5x */
206	95,  /* 0111 ->  9.5x */
207	90,  /* 1000 ->  9.0x */
208	70,  /* 1001 ->  7.0x */
209	80,  /* 1010 ->  8.0x */
210	60,  /* 1011 ->  6.0x */
211	120, /* 1100 -> 12.0x */
212	75,  /* 1101 ->  7.5x */
213	85,  /* 1110 ->  8.5x */
214	65,  /* 1111 ->  6.5x */
215
216	-1,  /* 0000 -> RESERVED (9.0x) */
217	110, /* 0001 -> 11.0x */
218	120, /* 0010 -> 12.0x */
219	-1,  /* 0011 -> RESERVED (10.0x)*/
220	135, /* 0100 -> 13.5x */
221	115, /* 0101 -> 11.5x */
222	125, /* 0110 -> 12.5x */
223	105, /* 0111 -> 10.5x */
224	130, /* 1000 -> 13.0x */
225	150, /* 1001 -> 15.0x */
226	160, /* 1010 -> 16.0x */
227	140, /* 1011 -> 14.0x */
228	-1,  /* 1100 -> RESERVED (12.0x) */
229	155, /* 1101 -> 15.5x */
230	-1,  /* 1110 -> RESERVED (13.0x) */
231	145, /* 1111 -> 14.5x */
232};
233
234/*
235 * VIA C3 Nehemiah */
236
237static const int nehemiah_mults[32] = {
238	100, /* 0000 -> 10.0x */
239	-1, /* 0001 -> 16.0x */
240	40,  /* 0010 ->  4.0x */
241	90,  /* 0011 ->  9.0x */
242	95,  /* 0100 ->  9.5x */
243	-1,  /* 0101 ->  RESERVED */
244	45,  /* 0110 ->  4.5x */
245	55,  /* 0111 ->  5.5x */
246	60,  /* 1000 ->  6.0x */
247	70,  /* 1001 ->  7.0x */
248	80,  /* 1010 ->  8.0x */
249	50,  /* 1011 ->  5.0x */
250	65,  /* 1100 ->  6.5x */
251	75,  /* 1101 ->  7.5x */
252	85,  /* 1110 ->  8.5x */
253	120, /* 1111 -> 12.0x */
254	-1, /* 0000 -> 10.0x */
255	110, /* 0001 -> 11.0x */
256	-1, /* 0010 -> 12.0x */
257	-1,  /* 0011 ->  9.0x */
258	105, /* 0100 -> 10.5x */
259	115, /* 0101 -> 11.5x */
260	125, /* 0110 -> 12.5x */
261	135, /* 0111 -> 13.5x */
262	140, /* 1000 -> 14.0x */
263	150, /* 1001 -> 15.0x */
264	160, /* 1010 -> 16.0x */
265	130, /* 1011 -> 13.0x */
266	145, /* 1100 -> 14.5x */
267	155, /* 1101 -> 15.5x */
268	-1,  /* 1110 -> RESERVED (13.0x) */
269	-1, /* 1111 -> 12.0x */
270};
271
272static const int nehemiah_eblcr[32] = {
273	50,  /* 0000 ->  5.0x */
274	160, /* 0001 -> 16.0x */
275	40,  /* 0010 ->  4.0x */
276	100, /* 0011 -> 10.0x */
277	55,  /* 0100 ->  5.5x */
278	-1,  /* 0101 ->  RESERVED */
279	45,  /* 0110 ->  4.5x */
280	95,  /* 0111 ->  9.5x */
281	90,  /* 1000 ->  9.0x */
282	70,  /* 1001 ->  7.0x */
283	80,  /* 1010 ->  8.0x */
284	60,  /* 1011 ->  6.0x */
285	120, /* 1100 -> 12.0x */
286	75,  /* 1101 ->  7.5x */
287	85,  /* 1110 ->  8.5x */
288	65,  /* 1111 ->  6.5x */
289	90,  /* 0000 ->  9.0x */
290	110, /* 0001 -> 11.0x */
291	120, /* 0010 -> 12.0x */
292	100, /* 0011 -> 10.0x */
293	135, /* 0100 -> 13.5x */
294	115, /* 0101 -> 11.5x */
295	125, /* 0110 -> 12.5x */
296	105, /* 0111 -> 10.5x */
297	130, /* 1000 -> 13.0x */
298	150, /* 1001 -> 15.0x */
299	160, /* 1010 -> 16.0x */
300	140, /* 1011 -> 14.0x */
301	120, /* 1100 -> 12.0x */
302	155, /* 1101 -> 15.5x */
303	-1,  /* 1110 -> RESERVED (13.0x) */
304	145 /* 1111 -> 14.5x */
305};
306
307/*
308 * Voltage scales. Div/Mod by 1000 to get actual voltage.
309 * Which scale to use depends on the VRM type in use.
310 */
311
312struct mV_pos {
313	unsigned short mV;
314	unsigned short pos;
315};
316
317static const struct mV_pos vrm85_mV[32] = {
318	{1250, 8},	{1200, 6},	{1150, 4},	{1100, 2},
319	{1050, 0},	{1800, 30},	{1750, 28},	{1700, 26},
320	{1650, 24},	{1600, 22},	{1550, 20},	{1500, 18},
321	{1450, 16},	{1400, 14},	{1350, 12},	{1300, 10},
322	{1275, 9},	{1225, 7},	{1175, 5},	{1125, 3},
323	{1075, 1},	{1825, 31},	{1775, 29},	{1725, 27},
324	{1675, 25},	{1625, 23},	{1575, 21},	{1525, 19},
325	{1475, 17},	{1425, 15},	{1375, 13},	{1325, 11}
326};
327
328static const unsigned char mV_vrm85[32] = {
329	0x04,	0x14,	0x03,	0x13,	0x02,	0x12,	0x01,	0x11,
330	0x00,	0x10,	0x0f,	0x1f,	0x0e,	0x1e,	0x0d,	0x1d,
331	0x0c,	0x1c,	0x0b,	0x1b,	0x0a,	0x1a,	0x09,	0x19,
332	0x08,	0x18,	0x07,	0x17,	0x06,	0x16,	0x05,	0x15
333};
334
335static const struct mV_pos mobilevrm_mV[32] = {
336	{1750, 31},	{1700, 30},	{1650, 29},	{1600, 28},
337	{1550, 27},	{1500, 26},	{1450, 25},	{1400, 24},
338	{1350, 23},	{1300, 22},	{1250, 21},	{1200, 20},
339	{1150, 19},	{1100, 18},	{1050, 17},	{1000, 16},
340	{975, 15},	{950, 14},	{925, 13},	{900, 12},
341	{875, 11},	{850, 10},	{825, 9},	{800, 8},
342	{775, 7},	{750, 6},	{725, 5},	{700, 4},
343	{675, 3},	{650, 2},	{625, 1},	{600, 0}
344};
345
346static const unsigned char mV_mobilevrm[32] = {
347	0x1f,	0x1e,	0x1d,	0x1c,	0x1b,	0x1a,	0x19,	0x18,
348	0x17,	0x16,	0x15,	0x14,	0x13,	0x12,	0x11,	0x10,
349	0x0f,	0x0e,	0x0d,	0x0c,	0x0b,	0x0a,	0x09,	0x08,
350	0x07,	0x06,	0x05,	0x04,	0x03,	0x02,	0x01,	0x00
351};
352
353