1
2
3
4
5
6#include <common.h>
7#include <command.h>
8#include <env.h>
9#include <i2c.h>
10#include <irq_func.h>
11#include <asm/io.h>
12#ifdef CONFIG_FSL_LSCH2
13#include <asm/arch/immap_lsch2.h>
14#elif defined(CONFIG_FSL_LSCH3)
15#include <asm/arch/immap_lsch3.h>
16#else
17#include <asm/immap_85xx.h>
18#endif
19#include "vid.h"
20
21int __weak i2c_multiplexer_select_vid_channel(u8 channel)
22{
23 return 0;
24}
25
26
27
28
29
30int __weak board_vdd_drop_compensation(void)
31{
32 return 0;
33}
34
35
36
37
38int __weak board_adjust_vdd(int vdd)
39{
40 return 0;
41}
42
43#if defined(CONFIG_VOL_MONITOR_IR36021_SET) || \
44 defined(CONFIG_VOL_MONITOR_IR36021_READ)
45
46
47
48
49
50
51
52
53
54
55
56
57
58static int find_ir_chip_on_i2c(void)
59{
60 int i2caddress;
61 int ret;
62 u8 byte;
63 int i;
64 const int ir_i2c_addr[] = {0x38, 0x08, 0x09};
65#ifdef CONFIG_DM_I2C
66 struct udevice *dev;
67#endif
68
69
70 for (i = 0; i < (sizeof(ir_i2c_addr)/sizeof(ir_i2c_addr[0])); i++) {
71 i2caddress = ir_i2c_addr[i];
72#ifndef CONFIG_DM_I2C
73 ret = i2c_read(i2caddress,
74 IR36021_MFR_ID_OFFSET, 1, (void *)&byte,
75 sizeof(byte));
76#else
77 ret = i2c_get_chip_for_busnum(0, i2caddress, 1, &dev);
78 if (!ret)
79 ret = dm_i2c_read(dev, IR36021_MFR_ID_OFFSET,
80 (void *)&byte, sizeof(byte));
81#endif
82 if ((ret >= 0) && (byte == IR36021_MFR_ID))
83 return i2caddress;
84 }
85 return -1;
86}
87#endif
88
89
90#define MAX_LOOP_WAIT_NEW_VOL 100
91
92#define MAX_LOOP_WAIT_VOL_STABLE 100
93
94
95
96
97
98#define NUM_READINGS 4
99
100
101
102
103#ifdef CONFIG_VOL_MONITOR_INA220
104#define WAIT_FOR_ADC 532
105#define ADC_MIN_ACCURACY 4
106#else
107#define WAIT_FOR_ADC 138
108#define ADC_MIN_ACCURACY 4
109#endif
110
111#ifdef CONFIG_VOL_MONITOR_INA220
112static int read_voltage_from_INA220(int i2caddress)
113{
114 int i, ret, voltage_read = 0;
115 u16 vol_mon;
116 u8 buf[2];
117#ifdef CONFIG_DM_I2C
118 struct udevice *dev;
119#endif
120
121 for (i = 0; i < NUM_READINGS; i++) {
122#ifndef CONFIG_DM_I2C
123 ret = i2c_read(I2C_VOL_MONITOR_ADDR,
124 I2C_VOL_MONITOR_BUS_V_OFFSET, 1,
125 (void *)&buf, 2);
126#else
127 ret = i2c_get_chip_for_busnum(0, I2C_VOL_MONITOR_ADDR, 1, &dev);
128 if (!ret)
129 ret = dm_i2c_read(dev, I2C_VOL_MONITOR_BUS_V_OFFSET,
130 (void *)&buf, 2);
131#endif
132 if (ret) {
133 printf("VID: failed to read core voltage\n");
134 return ret;
135 }
136 vol_mon = (buf[0] << 8) | buf[1];
137 if (vol_mon & I2C_VOL_MONITOR_BUS_V_OVF) {
138 printf("VID: Core voltage sensor error\n");
139 return -1;
140 }
141 debug("VID: bus voltage reads 0x%04x\n", vol_mon);
142
143 voltage_read += (vol_mon >> I2C_VOL_MONITOR_BUS_V_SHIFT) * 4;
144 udelay(WAIT_FOR_ADC);
145 }
146
147 voltage_read /= NUM_READINGS;
148
149 return voltage_read;
150}
151#endif
152
153
154#ifdef CONFIG_VOL_MONITOR_IR36021_READ
155static int read_voltage_from_IR(int i2caddress)
156{
157 int i, ret, voltage_read = 0;
158 u16 vol_mon;
159 u8 buf;
160#ifdef CONFIG_DM_I2C
161 struct udevice *dev;
162#endif
163
164 for (i = 0; i < NUM_READINGS; i++) {
165#ifndef CONFIG_DM_I2C
166 ret = i2c_read(i2caddress,
167 IR36021_LOOP1_VOUT_OFFSET,
168 1, (void *)&buf, 1);
169#else
170 ret = i2c_get_chip_for_busnum(0, i2caddress, 1, &dev);
171 if (!ret)
172 ret = dm_i2c_read(dev, IR36021_LOOP1_VOUT_OFFSET,
173 (void *)&buf, 1);
174#endif
175 if (ret) {
176 printf("VID: failed to read vcpu\n");
177 return ret;
178 }
179 vol_mon = buf;
180 if (!vol_mon) {
181 printf("VID: Core voltage sensor error\n");
182 return -1;
183 }
184 debug("VID: bus voltage reads 0x%02x\n", vol_mon);
185
186
187
188 voltage_read += vol_mon * 1000;
189 udelay(WAIT_FOR_ADC);
190 }
191
192 voltage_read = DIV_ROUND_UP(voltage_read, 128);
193
194
195 voltage_read /= NUM_READINGS;
196
197
198
199
200 voltage_read -= board_vdd_drop_compensation();
201
202 return voltage_read;
203}
204#endif
205
206#ifdef CONFIG_VOL_MONITOR_LTC3882_READ
207
208static int read_voltage_from_LTC(int i2caddress)
209{
210 int ret, vcode = 0;
211 u8 chan = PWM_CHANNEL0;
212
213#ifndef CONFIG_DM_I2C
214
215 ret = i2c_write(I2C_VOL_MONITOR_ADDR,
216 PMBUS_CMD_PAGE, 1, &chan, 1);
217#else
218 struct udevice *dev;
219
220 ret = i2c_get_chip_for_busnum(0, I2C_VOL_MONITOR_ADDR, 1, &dev);
221 if (!ret)
222 ret = dm_i2c_write(dev, PMBUS_CMD_PAGE, &chan, 1);
223#endif
224 if (ret) {
225 printf("VID: failed to select VDD Page 0\n");
226 return ret;
227 }
228
229#ifndef CONFIG_DM_I2C
230
231 ret = i2c_read(I2C_VOL_MONITOR_ADDR,
232 PMBUS_CMD_READ_VOUT, 1, (void *)&vcode, 2);
233#else
234 ret = dm_i2c_read(dev, PMBUS_CMD_READ_VOUT, (void *)&vcode, 2);
235 if (ret) {
236 printf("VID: failed to read the volatge\n");
237 return ret;
238 }
239#endif
240 if (ret) {
241 printf("VID: failed to read the volatge\n");
242 return ret;
243 }
244
245
246 vcode = DIV_ROUND_UP(vcode * 1000, 4096);
247
248 return vcode;
249}
250#endif
251
252static int read_voltage(int i2caddress)
253{
254 int voltage_read;
255#ifdef CONFIG_VOL_MONITOR_INA220
256 voltage_read = read_voltage_from_INA220(i2caddress);
257#elif defined CONFIG_VOL_MONITOR_IR36021_READ
258 voltage_read = read_voltage_from_IR(i2caddress);
259#elif defined CONFIG_VOL_MONITOR_LTC3882_READ
260 voltage_read = read_voltage_from_LTC(i2caddress);
261#else
262 return -1;
263#endif
264 return voltage_read;
265}
266
267#ifdef CONFIG_VOL_MONITOR_IR36021_SET
268
269
270
271
272
273static int wait_for_new_voltage(int vdd, int i2caddress)
274{
275 int timeout, vdd_current;
276
277 vdd_current = read_voltage(i2caddress);
278
279
280
281
282
283
284
285
286
287 for (timeout = 0;
288 abs(vdd - vdd_current) > (IR_VDD_STEP_UP + IR_VDD_STEP_DOWN) &&
289 timeout < MAX_LOOP_WAIT_NEW_VOL; timeout++) {
290 vdd_current = read_voltage(i2caddress);
291 }
292 if (timeout >= MAX_LOOP_WAIT_NEW_VOL) {
293 printf("VID: Voltage adjustment timeout\n");
294 return -1;
295 }
296 return timeout;
297}
298
299
300
301
302
303static int wait_for_voltage_stable(int i2caddress)
304{
305 int timeout, vdd_current, vdd;
306
307 vdd = read_voltage(i2caddress);
308 udelay(NUM_READINGS * WAIT_FOR_ADC);
309
310
311 vdd_current = read_voltage(i2caddress);
312
313
314
315 for (timeout = MAX_LOOP_WAIT_VOL_STABLE;
316 abs(vdd - vdd_current) > ADC_MIN_ACCURACY &&
317 timeout > 0; timeout--) {
318 vdd = vdd_current;
319 udelay(NUM_READINGS * WAIT_FOR_ADC);
320 vdd_current = read_voltage(i2caddress);
321 }
322 if (timeout == 0)
323 return -1;
324 return vdd_current;
325}
326
327
328static int set_voltage_to_IR(int i2caddress, int vdd)
329{
330 int wait, vdd_last;
331 int ret;
332 u8 vid;
333
334
335
336
337 vdd += board_vdd_drop_compensation();
338#ifdef CONFIG_FSL_LSCH2
339 vid = DIV_ROUND_UP(vdd - 265, 5);
340#else
341 vid = DIV_ROUND_UP(vdd - 245, 5);
342#endif
343
344#ifndef CONFIG_DM_I2C
345 ret = i2c_write(i2caddress, IR36021_LOOP1_MANUAL_ID_OFFSET,
346 1, (void *)&vid, sizeof(vid));
347#else
348 struct udevice *dev;
349
350 ret = i2c_get_chip_for_busnum(0, i2caddress, 1, &dev);
351 if (!ret)
352 ret = dm_i2c_write(dev, IR36021_LOOP1_MANUAL_ID_OFFSET,
353 (void *)&vid, sizeof(vid));
354
355#endif
356 if (ret) {
357 printf("VID: failed to write VID\n");
358 return -1;
359 }
360 wait = wait_for_new_voltage(vdd, i2caddress);
361 if (wait < 0)
362 return -1;
363 debug("VID: Waited %d us\n", wait * NUM_READINGS * WAIT_FOR_ADC);
364
365 vdd_last = wait_for_voltage_stable(i2caddress);
366 if (vdd_last < 0)
367 return -1;
368 debug("VID: Current voltage is %d mV\n", vdd_last);
369 return vdd_last;
370}
371
372#endif
373
374#ifdef CONFIG_VOL_MONITOR_LTC3882_SET
375
376static int set_voltage_to_LTC(int i2caddress, int vdd)
377{
378 int ret, vdd_last, vdd_target = vdd;
379 int count = 100, temp = 0;
380
381
382 vdd = (vdd * 4096) / 1000;
383
384
385
386
387 u8 buff[5] = {0x04, PWM_CHANNEL0, PMBUS_CMD_VOUT_COMMAND,
388 vdd & 0xFF, (vdd & 0xFF00) >> 8};
389
390
391#ifndef CONFIG_DM_I2C
392 ret = i2c_write(I2C_VOL_MONITOR_ADDR,
393 PMBUS_CMD_PAGE_PLUS_WRITE, 1, (void *)&buff, 5);
394#else
395 struct udevice *dev;
396
397 ret = i2c_get_chip_for_busnum(0, I2C_VOL_MONITOR_ADDR, 1, &dev);
398 if (!ret)
399 ret = dm_i2c_write(dev, PMBUS_CMD_PAGE_PLUS_WRITE,
400 (void *)&buff, 5);
401#endif
402 if (ret) {
403 printf("VID: I2C failed to write to the volatge regulator\n");
404 return -1;
405 }
406
407
408 do {
409 vdd_last = read_voltage_from_LTC(i2caddress);
410 if (vdd_last < 0) {
411 printf("VID: Couldn't read sensor abort VID adjust\n");
412 return -1;
413 }
414 count--;
415 temp = vdd_last - vdd_target;
416 } while ((abs(temp) > 2) && (count > 0));
417
418 return vdd_last;
419}
420#endif
421
422static int set_voltage(int i2caddress, int vdd)
423{
424 int vdd_last = -1;
425
426#ifdef CONFIG_VOL_MONITOR_IR36021_SET
427 vdd_last = set_voltage_to_IR(i2caddress, vdd);
428#elif defined CONFIG_VOL_MONITOR_LTC3882_SET
429 vdd_last = set_voltage_to_LTC(i2caddress, vdd);
430#else
431 #error Specific voltage monitor must be defined
432#endif
433 return vdd_last;
434}
435
436#ifdef CONFIG_FSL_LSCH3
437int adjust_vdd(ulong vdd_override)
438{
439 int re_enable = disable_interrupts();
440 struct ccsr_gur *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
441 u32 fusesr;
442#if defined(CONFIG_VOL_MONITOR_IR36021_SET) || \
443 defined(CONFIG_VOL_MONITOR_IR36021_READ)
444 u8 vid, buf;
445#else
446 u8 vid;
447#endif
448 int vdd_target, vdd_current, vdd_last;
449 int ret, i2caddress;
450 unsigned long vdd_string_override;
451 char *vdd_string;
452#ifdef CONFIG_ARCH_LX2160A
453 static const u16 vdd[32] = {
454 8250,
455 7875,
456 7750,
457 0,
458 0,
459 0,
460 0,
461 0,
462 0,
463 0,
464 0,
465 0,
466 0,
467 0,
468 0,
469 0,
470 8000,
471 8125,
472 8250,
473 0,
474 8500,
475 0,
476 0,
477 0,
478 0,
479 0,
480 0,
481 0,
482 0,
483 0,
484 0,
485 0,
486 };
487#else
488#ifdef CONFIG_ARCH_LS1088A
489 static const uint16_t vdd[32] = {
490 10250,
491 9875,
492 9750,
493 0,
494 0,
495 0,
496 0,
497 0,
498 9000,
499 0,
500 0,
501 0,
502 0,
503 0,
504 0,
505 0,
506 10000,
507 10125,
508 10250,
509 0,
510 0,
511 0,
512 0,
513 0,
514 0,
515 0,
516 0,
517 0,
518 0,
519 0,
520 0,
521 0,
522 };
523
524#else
525 static const uint16_t vdd[32] = {
526 10500,
527 0,
528 9750,
529 0,
530 9500,
531 0,
532 0,
533 0,
534 0,
535 0,
536 0,
537 9000,
538 0,
539 0,
540 0,
541 0,
542 10000,
543 0,
544 10250,
545 0,
546 10500,
547 0,
548 0,
549 0,
550 0,
551 0,
552 0,
553 0,
554 0,
555 0,
556 0,
557 0,
558 };
559#endif
560#endif
561 struct vdd_drive {
562 u8 vid;
563 unsigned voltage;
564 };
565
566 ret = i2c_multiplexer_select_vid_channel(I2C_MUX_CH_VOL_MONITOR);
567 if (ret) {
568 debug("VID: I2C failed to switch channel\n");
569 ret = -1;
570 goto exit;
571 }
572#if defined(CONFIG_VOL_MONITOR_IR36021_SET) || \
573 defined(CONFIG_VOL_MONITOR_IR36021_READ)
574 ret = find_ir_chip_on_i2c();
575 if (ret < 0) {
576 printf("VID: Could not find voltage regulator on I2C.\n");
577 ret = -1;
578 goto exit;
579 } else {
580 i2caddress = ret;
581 debug("VID: IR Chip found on I2C address 0x%02x\n", i2caddress);
582 }
583
584
585#ifndef CONFIG_DM_I2C
586 ret = i2c_read(i2caddress,
587 IR36021_INTEL_MODE_OOFSET,
588 1, (void *)&buf, 1);
589#else
590 struct udevice *dev;
591
592 ret = i2c_get_chip_for_busnum(0, i2caddress, 1, &dev);
593 if (!ret)
594 ret = dm_i2c_read(dev, IR36021_INTEL_MODE_OOFSET,
595 (void *)&buf, 1);
596#endif
597 if (ret) {
598 printf("VID: failed to read IR chip mode.\n");
599 ret = -1;
600 goto exit;
601 }
602
603 if ((buf & IR36021_MODE_MASK) != IR36021_INTEL_MODE) {
604 printf("VID: IR Chip is not used in Intel mode.\n");
605 ret = -1;
606 goto exit;
607 }
608#endif
609
610
611 fusesr = in_le32(&gur->dcfg_fusesr);
612 vid = (fusesr >> FSL_CHASSIS3_DCFG_FUSESR_ALTVID_SHIFT) &
613 FSL_CHASSIS3_DCFG_FUSESR_ALTVID_MASK;
614 if ((vid == 0) || (vid == FSL_CHASSIS3_DCFG_FUSESR_ALTVID_MASK)) {
615 vid = (fusesr >> FSL_CHASSIS3_DCFG_FUSESR_VID_SHIFT) &
616 FSL_CHASSIS3_DCFG_FUSESR_VID_MASK;
617 }
618 vdd_target = vdd[vid];
619
620
621 vdd_string = env_get(CONFIG_VID_FLS_ENV);
622 if (vdd_override == 0 && vdd_string &&
623 !strict_strtoul(vdd_string, 10, &vdd_string_override))
624 vdd_override = vdd_string_override;
625
626 if (vdd_override >= VDD_MV_MIN && vdd_override <= VDD_MV_MAX) {
627 vdd_target = vdd_override * 10;
628 debug("VDD override is %lu\n", vdd_override);
629 } else if (vdd_override != 0) {
630 printf("Invalid value.\n");
631 }
632
633
634 vdd_target = DIV_ROUND_UP(vdd_target, 10);
635 if (vdd_target == 0) {
636 debug("VID: VID not used\n");
637 ret = 0;
638 goto exit;
639 } else if (vdd_target < VDD_MV_MIN || vdd_target > VDD_MV_MAX) {
640
641 printf("VID: Target VID %d mV is not in range.\n",
642 vdd_target);
643 ret = -1;
644 goto exit;
645 } else {
646 debug("VID: vid = %d mV\n", vdd_target);
647 }
648
649
650
651
652 vdd_last = read_voltage(i2caddress);
653 if (vdd_last < 0) {
654 printf("VID: Couldn't read sensor abort VID adjustment\n");
655 ret = -1;
656 goto exit;
657 }
658 vdd_current = vdd_last;
659 debug("VID: Core voltage is currently at %d mV\n", vdd_last);
660
661#ifdef CONFIG_VOL_MONITOR_LTC3882_SET
662
663 vdd_last = vdd_current = set_voltage(i2caddress, vdd_target);
664#else
665
666
667
668
669
670
671 while (vdd_last > 0 &&
672 vdd_last < vdd_target) {
673 vdd_current += IR_VDD_STEP_UP;
674 vdd_last = set_voltage(i2caddress, vdd_current);
675 }
676 while (vdd_last > 0 &&
677 vdd_last > vdd_target + (IR_VDD_STEP_DOWN - 1)) {
678 vdd_current -= IR_VDD_STEP_DOWN;
679 vdd_last = set_voltage(i2caddress, vdd_current);
680 }
681
682#endif
683 if (board_adjust_vdd(vdd_target) < 0) {
684 ret = -1;
685 goto exit;
686 }
687
688 if (vdd_last > 0)
689 printf("VID: Core voltage after adjustment is at %d mV\n",
690 vdd_last);
691 else
692 ret = -1;
693exit:
694 if (re_enable)
695 enable_interrupts();
696 i2c_multiplexer_select_vid_channel(I2C_MUX_CH_DEFAULT);
697 return ret;
698}
699#else
700int adjust_vdd(ulong vdd_override)
701{
702 int re_enable = disable_interrupts();
703#if defined(CONFIG_FSL_LSCH2)
704 struct ccsr_gur *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
705#else
706 ccsr_gur_t __iomem *gur =
707 (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
708#endif
709 u32 fusesr;
710 u8 vid, buf;
711 int vdd_target, vdd_current, vdd_last;
712 int ret, i2caddress;
713 unsigned long vdd_string_override;
714 char *vdd_string;
715 static const uint16_t vdd[32] = {
716 0,
717 9875,
718 9750,
719 9625,
720 9500,
721 9375,
722 9250,
723 9125,
724 9000,
725 8875,
726 8750,
727 8625,
728 8500,
729 8375,
730 8250,
731 8125,
732 10000,
733 10125,
734 10250,
735 10375,
736 10500,
737 10625,
738 10750,
739 10875,
740 11000,
741 0,
742 };
743 struct vdd_drive {
744 u8 vid;
745 unsigned voltage;
746 };
747
748 ret = i2c_multiplexer_select_vid_channel(I2C_MUX_CH_VOL_MONITOR);
749 if (ret) {
750 debug("VID: I2C failed to switch channel\n");
751 ret = -1;
752 goto exit;
753 }
754#if defined(CONFIG_VOL_MONITOR_IR36021_SET) || \
755 defined(CONFIG_VOL_MONITOR_IR36021_READ)
756 ret = find_ir_chip_on_i2c();
757 if (ret < 0) {
758 printf("VID: Could not find voltage regulator on I2C.\n");
759 ret = -1;
760 goto exit;
761 } else {
762 i2caddress = ret;
763 debug("VID: IR Chip found on I2C address 0x%02x\n", i2caddress);
764 }
765
766
767#ifndef CONFIG_DM_I2C
768 ret = i2c_read(i2caddress,
769 IR36021_INTEL_MODE_OOFSET,
770 1, (void *)&buf, 1);
771#else
772 struct udevice *dev;
773
774 ret = i2c_get_chip_for_busnum(0, i2caddress, 1, &dev);
775 if (!ret)
776 ret = dm_i2c_read(dev, IR36021_INTEL_MODE_OOFSET,
777 (void *)&buf, 1);
778#endif
779 if (ret) {
780 printf("VID: failed to read IR chip mode.\n");
781 ret = -1;
782 goto exit;
783 }
784 if ((buf & IR36021_MODE_MASK) != IR36021_INTEL_MODE) {
785 printf("VID: IR Chip is not used in Intel mode.\n");
786 ret = -1;
787 goto exit;
788 }
789#endif
790
791
792 fusesr = in_be32(&gur->dcfg_fusesr);
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810#ifdef CONFIG_FSL_LSCH2
811 vid = (fusesr >> FSL_CHASSIS2_DCFG_FUSESR_ALTVID_SHIFT) &
812 FSL_CHASSIS2_DCFG_FUSESR_ALTVID_MASK;
813 if ((vid == 0) || (vid == FSL_CHASSIS2_DCFG_FUSESR_ALTVID_MASK)) {
814 vid = (fusesr >> FSL_CHASSIS2_DCFG_FUSESR_VID_SHIFT) &
815 FSL_CHASSIS2_DCFG_FUSESR_VID_MASK;
816 }
817#else
818 vid = (fusesr >> FSL_CORENET_DCFG_FUSESR_ALTVID_SHIFT) &
819 FSL_CORENET_DCFG_FUSESR_ALTVID_MASK;
820 if ((vid == 0) || (vid == FSL_CORENET_DCFG_FUSESR_ALTVID_MASK)) {
821 vid = (fusesr >> FSL_CORENET_DCFG_FUSESR_VID_SHIFT) &
822 FSL_CORENET_DCFG_FUSESR_VID_MASK;
823 }
824#endif
825 vdd_target = vdd[vid];
826
827
828 vdd_string = env_get(CONFIG_VID_FLS_ENV);
829 if (vdd_override == 0 && vdd_string &&
830 !strict_strtoul(vdd_string, 10, &vdd_string_override))
831 vdd_override = vdd_string_override;
832 if (vdd_override >= VDD_MV_MIN && vdd_override <= VDD_MV_MAX) {
833 vdd_target = vdd_override * 10;
834 debug("VDD override is %lu\n", vdd_override);
835 } else if (vdd_override != 0) {
836 printf("Invalid value.\n");
837 }
838 if (vdd_target == 0) {
839 debug("VID: VID not used\n");
840 ret = 0;
841 goto exit;
842 } else {
843
844 vdd_target = DIV_ROUND_UP(vdd_target, 10);
845 debug("VID: vid = %d mV\n", vdd_target);
846 }
847
848
849
850
851 vdd_last = read_voltage(i2caddress);
852 if (vdd_last < 0) {
853 printf("VID: Couldn't read sensor abort VID adjustment\n");
854 ret = -1;
855 goto exit;
856 }
857 vdd_current = vdd_last;
858 debug("VID: Core voltage is currently at %d mV\n", vdd_last);
859
860
861
862
863
864
865 while (vdd_last > 0 &&
866 vdd_last < vdd_target) {
867 vdd_current += IR_VDD_STEP_UP;
868 vdd_last = set_voltage(i2caddress, vdd_current);
869 }
870 while (vdd_last > 0 &&
871 vdd_last > vdd_target + (IR_VDD_STEP_DOWN - 1)) {
872 vdd_current -= IR_VDD_STEP_DOWN;
873 vdd_last = set_voltage(i2caddress, vdd_current);
874 }
875
876 if (vdd_last > 0)
877 printf("VID: Core voltage after adjustment is at %d mV\n",
878 vdd_last);
879 else
880 ret = -1;
881exit:
882 if (re_enable)
883 enable_interrupts();
884
885 i2c_multiplexer_select_vid_channel(I2C_MUX_CH_DEFAULT);
886
887 return ret;
888}
889#endif
890
891static int print_vdd(void)
892{
893 int vdd_last, ret, i2caddress;
894
895 ret = i2c_multiplexer_select_vid_channel(I2C_MUX_CH_VOL_MONITOR);
896 if (ret) {
897 debug("VID : I2c failed to switch channel\n");
898 return -1;
899 }
900#if defined(CONFIG_VOL_MONITOR_IR36021_SET) || \
901 defined(CONFIG_VOL_MONITOR_IR36021_READ)
902 ret = find_ir_chip_on_i2c();
903 if (ret < 0) {
904 printf("VID: Could not find voltage regulator on I2C.\n");
905 goto exit;
906 } else {
907 i2caddress = ret;
908 debug("VID: IR Chip found on I2C address 0x%02x\n", i2caddress);
909 }
910#endif
911
912
913
914
915 vdd_last = read_voltage(i2caddress);
916 if (vdd_last < 0) {
917 printf("VID: Couldn't read sensor abort VID adjustment\n");
918 goto exit;
919 }
920 printf("VID: Core voltage is at %d mV\n", vdd_last);
921exit:
922 i2c_multiplexer_select_vid_channel(I2C_MUX_CH_DEFAULT);
923
924 return ret < 0 ? -1 : 0;
925
926}
927
928static int do_vdd_override(cmd_tbl_t *cmdtp,
929 int flag, int argc,
930 char * const argv[])
931{
932 ulong override;
933
934 if (argc < 2)
935 return CMD_RET_USAGE;
936
937 if (!strict_strtoul(argv[1], 10, &override))
938 adjust_vdd(override);
939 else
940 return CMD_RET_USAGE;
941 return 0;
942}
943
944static int do_vdd_read(cmd_tbl_t *cmdtp,
945 int flag, int argc,
946 char * const argv[])
947{
948 if (argc < 1)
949 return CMD_RET_USAGE;
950 print_vdd();
951
952 return 0;
953}
954
955U_BOOT_CMD(
956 vdd_override, 2, 0, do_vdd_override,
957 "override VDD",
958 " - override with the voltage specified in mV, eg. 1050"
959);
960
961U_BOOT_CMD(
962 vdd_read, 1, 0, do_vdd_read,
963 "read VDD",
964 " - Read the voltage specified in mV"
965)
966