/* * (C) Copyright 2000, 2001 * Wolfgang Denk, DENX Software Engineering, wd@denx.de. * * SPDX-License-Identifier: GPL-2.0+ */ /* * ehnus: change pll frequency. * Wed Sep 5 11:45:17 CST 2007 * hsun@udtech.com.cn */ #include #include #include #include #ifdef CONFIG_CMD_EEPROM #define EEPROM_CONF_OFFSET 0 #define EEPROM_TEST_OFFSET 16 #define EEPROM_SDSTP_PARAM 16 #define PLL_NAME_MAX 12 #define BUF_STEP 8 /* eeprom_wirtes 8Byte per op. */ #define EEPROM_ALTER_FREQ(freq) \ do { \ int __i; \ for (__i = 0; __i < 2; __i++) \ eeprom_write (CONFIG_SYS_I2C_EEPROM_ADDR, \ EEPROM_CONF_OFFSET + __i*BUF_STEP, \ pll_select[freq], \ BUF_STEP + __i*BUF_STEP); \ } while (0) #define PDEBUG #ifdef PDEBUG #define PLL_DEBUG pll_debug(EEPROM_CONF_OFFSET) #else #define PLL_DEBUG #endif typedef enum { PLL_ebc20, PLL_333, PLL_4001, PLL_4002, PLL_533, PLL_600, PLL_666, /* For now, kilauea can't support */ RCONF, WTEST, PLL_TOTAL } pll_freq_t; static const char pll_name[][PLL_NAME_MAX] = { "PLL_ebc20", "PLL_333", "PLL_400@1", "PLL_400@2", "PLL_533", "PLL_600", "PLL_666", "RCONF", "WTEST", "" }; /* * ehnus: */ static uchar pll_select[][EEPROM_SDSTP_PARAM] = { /* 0: CPU 333MHz EBC 20MHz, for test only */ { 0x8c, 0x12, 0xec, 0x12, 0x88, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, /* 0: 333 */ { 0x8c, 0x12, 0xec, 0x12, 0x98, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, /* 1: 400_266 */ { 0x8e, 0x0e, 0xe8, 0x13, 0x98, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, /* 2: 400 */ { 0x8e, 0x0e, 0xe8, 0x12, 0x98, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, /* 3: 533 */ { 0x8e, 0x43, 0x60, 0x13, 0x98, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, /* 4: 600 */ { 0x8d, 0x02, 0x34, 0x13, 0x98, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, /* 5: 666 */ { 0x8d, 0x03, 0x78, 0x13, 0x98, 0x00, 0x0a, 0x00, 0x40, 0x08, 0x23, 0x50, 0x00, 0x05, 0x00, 0x00 }, {} }; static uchar testbuf[EEPROM_SDSTP_PARAM] = { 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff }; static void pll_debug(int off) { int i; uchar buffer[EEPROM_SDSTP_PARAM]; memset(buffer, 0, sizeof(buffer)); eeprom_read(CONFIG_SYS_I2C_EEPROM_ADDR, off, buffer, EEPROM_SDSTP_PARAM); printf("Debug: SDSTP[0-3] at offset \"0x%02x\" lists as follows: \n", off); for (i = 0; i < EEPROM_SDSTP_PARAM; i++) printf("%02x ", buffer[i]); printf("\n"); } static void test_write(void) { printf("Debug: test eeprom_write ... "); /* * Write twice, 8 bytes per write */ eeprom_write (CONFIG_SYS_I2C_EEPROM_ADDR, EEPROM_TEST_OFFSET, testbuf, 8); eeprom_write (CONFIG_SYS_I2C_EEPROM_ADDR, EEPROM_TEST_OFFSET+8, testbuf, 16); printf("done\n"); pll_debug(EEPROM_TEST_OFFSET); } int do_pll_alter (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { char c = '\0'; pll_freq_t pll_freq; if (argc < 2) return cmd_usage(cmdtp); for (pll_freq = PLL_ebc20; pll_freq < PLL_TOTAL; pll_freq++) { if (!strcmp(pll_name[pll_freq], argv[1])) break; } switch (pll_freq) { case PLL_ebc20: case PLL_333: case PLL_4001: case PLL_4002: case PLL_533: case PLL_600: EEPROM_ALTER_FREQ(pll_freq); break; case PLL_666: /* not support */ printf("Choose this option will result in a boot failure." "\nContinue? (Y/N): "); c = getc(); putc('\n'); if ((c == 'y') || (c == 'Y')) { EEPROM_ALTER_FREQ(pll_freq); break; } goto ret; case RCONF: pll_debug(EEPROM_CONF_OFFSET); goto ret; case WTEST: printf("DEBUG: write test\n"); test_write(); goto ret; default: printf("Invalid options\n\n"); return cmd_usage(cmdtp); } printf("PLL set to %s, " "reset the board to take effect\n", pll_name[pll_freq]); PLL_DEBUG; ret: return 0; } U_BOOT_CMD( pllalter, CONFIG_SYS_MAXARGS, 1, do_pll_alter, "change pll frequence", "pllalter - change pll frequence \n\n\ ** New freq take effect after reset. ** \n\ ----------------------------------------------\n\ PLL_ebc20: Board: AMCC 405EX(r) Evaluation Board\n\ \t Same as PLL_333 \n\ \t except \n\ \t EBC: 20 MHz \n\ ----------------------------------------------\n\ PLL_333: Board: AMCC 405EX(r) Evaluation Board\n\ \t VCO: 666 MHz \n\ \t CPU: 333 MHz \n\ \t PLB: 166 MHz \n\ \t OPB: 83 MHz \n\ \t DDR: 83 MHz \n\ ------------------------------------------------\n\ PLL_400@1: Board: AMCC 405EX(r) Evaluation Board\n\ \t VCO: 800 MHz \n\ \t CPU: 400 MHz \n\ \t PLB: 133 MHz \n\ \t OPB: 66 MHz \n\ \t DDR: 133 MHz \n\ ------------------------------------------------\n\ PLL_400@2: Board: AMCC 405EX(r) Evaluation Board\n\ \t VCO: 800 MHz \n\ \t CPU: 400 MHz \n\ \t PLB: 200 MHz \n\ \t OPB: 100 MHz \n\ \t DDR: 200 MHz \n\ ----------------------------------------------\n\ PLL_533: Board: AMCC 405EX(r) Evaluation Board\n\ \t VCO: 1066 MHz \n\ \t CPU: 533 MHz \n\ \t PLB: 177 MHz \n\ \t OPB: 88 MHz \n\ \t DDR: 177 MHz \n\ ----------------------------------------------\n\ PLL_600: Board: AMCC 405EX(r) Evaluation Board\n\ \t VCO: 1200 MHz \n\ \t CPU: 600 MHz \n\ \t PLB: 200 MHz \n\ \t OPB: 100 MHz \n\ \t DDR: 200 MHz \n\ ----------------------------------------------\n\ PLL_666: Board: AMCC 405EX(r) Evaluation Board\n\ \t VCO: 1333 MHz \n\ \t CPU: 666 MHz \n\ \t PLB: 166 MHz \n\ \t OPB: 83 MHz \n\ \t DDR: 166 MHz \n\ -----------------------------------------------\n\ RCONF: Read current eeprom configuration. \n\ -----------------------------------------------\n\ WTEST: Test EEPROM write with predefined values\n\ -----------------------------------------------" ); #endif /* CONFIG_CMD_EEPROM */