int serial_init(void) {
	u32 rdata;
	u32 baudRateDivisor, clock_step;
	u32 fcEnable = 0;
	u32 ahb_freq, ddr_freq, cpu_freq;

	ar7240_sys_frequency(&cpu_freq, &ddr_freq, &ahb_freq);

	/* GPIO Configuration */
	ar7240_reg_wr(AR7240_GPIO_OE, 0xcff);
	rdata = ar7240_reg_rd(AR7240_GPIO_OUT);
	rdata |= 0x400; // GPIO 10 (UART_SOUT) must output 1
	ar7240_reg_wr(AR7240_GPIO_OUT, rdata);

	rdata = ar7240_reg_rd(AR7240_GPIO_FUNC);
	/* GPIO_FUN, bit1/UART_EN, bit2/UART_RTS_CTS_EN, bit15(disable_s26_uart) */
	rdata |= (0x3 << 1) | (0x1 << 15);
	ar7240_reg_wr(AR7240_GPIO_FUNC, rdata);

	/* Get reference clock rate, then set baud rate to 115200 */
	// TODO: check the following code
	rdata = ar7240_reg_rd(HORNET_BOOTSTRAP_STATUS);
	rdata &= HORNET_BOOTSTRAP_SEL_25M_40M_MASK;

	if (rdata) {
		baudRateDivisor = (40000000 / (16 * 115200)) - 1; // 40 MHz clock is taken as UART clock
	} else {
		baudRateDivisor = (25000000 / (16 * 115200)) - 1; // 25 MHz clock is taken as UART clock
	}

	clock_step = 8192;

	rdata = UARTCLOCK_UARTCLOCKSCALE_SET(baudRateDivisor) | UARTCLOCK_UARTCLOCKSTEP_SET(clock_step);
	uart_reg_write(UARTCLOCK_ADDRESS, rdata);

	/* Config Uart Controller */
	/* No interrupt */
	rdata = UARTCS_UARTDMAEN_SET(0) | UARTCS_UARTHOSTINTEN_SET(0) | UARTCS_UARTHOSTINT_SET(0) | UARTCS_UARTSERIATXREADY_SET(0) | UARTCS_UARTTXREADYORIDE_SET(~fcEnable) | UARTCS_UARTRXREADYORIDE_SET(~fcEnable) | UARTCS_UARTHOSTINTEN_SET(0);

	/* is_dte == 1 */
	rdata = rdata | UARTCS_UARTINTERFACEMODE_SET(2);

	if (fcEnable) {
		rdata = rdata | UARTCS_UARTFLOWCONTROLMODE_SET(2);
	}

	/* invert_fc ==0 (Inverted Flow Control) */
	//rdata = rdata | UARTCS_UARTFLOWCONTROLMODE_SET(3);
	/* parityEnable == 0 */
	//rdata = rdata | UARTCS_UARTPARITYMODE_SET(2); -->Parity Odd
	//rdata = rdata | UARTCS_UARTPARITYMODE_SET(3); -->Parity Even
	uart_reg_write(UARTCS_ADDRESS, rdata);

	return 0;
}
Пример #2
0
Файл: ag934x.c Проект: jhbsz/102
void ag7240_mii_setup(ag7240_mac_t *mac)
{
    u32 mgmt_cfg_val;
    u32 cpu_freq,ddr_freq,ahb_freq;
    u32 check_cnt,revid_val;

    if ((ar7240_reg_rd(WASP_BOOTSTRAP_REG) & WASP_REF_CLK_25) == 0) {
#ifndef CFG_DUAL_PHY_SUPPORT
        ar7240_reg_wr(AR934X_SWITCH_CLOCK_SPARE, 0x271);
#endif
    } else {
        ar7240_reg_wr(AR934X_SWITCH_CLOCK_SPARE, 0x570);
    }

#if defined(CONFIG_AR7242_S16_PHY) || defined(CONFIG_ATHRS17_PHY)
    if (is_wasp() && mac->mac_unit == 0) {
#ifdef CONFIG_AR7242_S16_PHY
        printf("WASP  ----> S16 PHY *\n");
#else
        printf("WASP  ----> S17 PHY *\n");
#endif
        mgmt_cfg_val = 4;
        if(mac->mac_unit == 0)
            ar7240_reg_wr(AG7240_ETH_CFG, AG7240_ETH_CFG_RGMII_GE0);

        udelay(1000);

        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);

        return;
    }
#endif

#ifdef CFG_ATHRS27_PHY
    if (is_wasp()) {
        printf("WASP ----> S27 PHY \n");
        mgmt_cfg_val = 2;
        ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
        return;
    }
#endif

#ifdef CONFIG_F2E_PHY
    if (is_wasp()) {
        printf("WASP  ----> F2 PHY *\n");
        ar7240_reg_wr(AG7240_ETH_CFG, (AG7240_ETH_CFG_RMII_MASTER_MODE | AG7240_ETH_CFG_RMII_GE0
                                       | AG7240_ETH_CFG_RMII_HISPD_GE0));

        mgmt_cfg_val = 6;

        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);

        return;
    }
#endif


#if defined(CONFIG_F1E_PHY) || defined(CONFIG_VIR_PHY)
    if (is_wasp()) {
#ifdef CONFIG_VIR_PHY
        printf("WASP  ----> VIR PHY *\n");
#else
        printf("WASP  ----> F1 PHY *\n");
#endif
        if(mac->mac_unit == 0)
            ar7240_reg_wr(AG7240_ETH_CFG, AG7240_ETH_CFG_RGMII_GE0);

        mgmt_cfg_val = 6;

        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);

        return;
    }
#endif

    if ((ar7240_reg_rd(AR7240_REV_ID) & AR7240_REV_ID_MASK) == AR7240_REV_1_2) {
        mgmt_cfg_val = 0x2;
        if (mac->mac_unit == 0) {
            ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
            ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
        }
    }
    else {
        ar7240_sys_frequency(&cpu_freq, &ddr_freq, &ahb_freq);
        switch (ahb_freq/1000000) {
        case 150:
            mgmt_cfg_val = 0x7;
            break;
        case 175:
            mgmt_cfg_val = 0x5;
            break;
        case 200:
            mgmt_cfg_val = 0x4;
            break;
        case 210:
            mgmt_cfg_val = 0x9;
            break;
        case 220:
            mgmt_cfg_val = 0x9;
            break;
        default:
            mgmt_cfg_val = 0x7;
        }
        if ((is_ar7241() || is_ar7242())) {

            /* External MII mode */
            if (mac->mac_unit == 0 && is_ar7242()) {
                mgmt_cfg_val = 0x6;
                ar7240_reg_rmw_set(AG7240_ETH_CFG, AG7240_ETH_CFG_RGMII_GE0);
                ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
                ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
            }
            /* Virian */
            mgmt_cfg_val = 0x4;
            ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
            ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
            printf("Virian MDC CFG Value ==> %x\n",mgmt_cfg_val);

        }
        else if(is_ar933x()) {
            //GE0 receives Rx/Tx clock, and use S26 phy
            ar7240_reg_rmw_set(AG7240_ETH_CFG, AG7240_ETH_CFG_MII_GE0_SLAVE);
            mgmt_cfg_val = 0xF;
            if (mac->mac_unit == 1) {
                check_cnt = 0;
                while (check_cnt++ < 10) {
                    ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
                    ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
#ifdef CFG_ATHRS26_PHY
                    if(athrs26_mdc_check() == 0)
                        break;
#endif
                }
                if(check_cnt == 11)
                    printf("%s: MDC check failed\n", __func__);
            }
        }
        else { /* Python 1.0 & 1.1 */
            if (mac->mac_unit == 0) {
                check_cnt = 0;
                while (check_cnt++ < 10) {
                    ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
                    ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
#ifdef CFG_ATHRS26_PHY
                    if(athrs26_mdc_check() == 0)
                        break;
#endif
                }
                if(check_cnt == 11)
                    printf("%s: MDC check failed\n", __func__);
            }
        }

    }
}
Пример #3
0
void ag7240_mii_setup(ag7240_mac_t *mac)
{
    u32 mgmt_cfg_val;
    u32 cpu_freq,ddr_freq,ahb_freq;
    u32 check_cnt,revid_val;
#ifdef CFG_ATHRS27_PHY
    if (is_wasp()) {
        printf("WASP ----> S27 PHY \n");
        mgmt_cfg_val = 2;
        ar7240_reg_wr(0xb8050024, 0x271);	// 25MHz ref clock
        //ar7240_reg_wr(0xb8050024, 0x570);	// 40MHz ref clock
        ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
        return;
    }
#endif
#ifdef CONFIG_AR7242_S16_PHY
    if (is_wasp()) {
        printf("WASP  ----> S16 PHY *\n");
        mgmt_cfg_val = 4;
        if(mac->mac_unit == 0)
            ar7240_reg_wr(AG7240_ETH_CFG, AG7240_ETH_CFG_RGMII_GE0);

        ar7240_reg_rmw_clear(AG7240_ETH_SWITCH_CLK_SPARE, (1 << 6));
        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);

        return;
    }
#endif
#ifdef CONFIG_F1E_PHY
    if (is_wasp()) {
        printf("WASP  ----> F1 PHY *\n");
        mgmt_cfg_val = 6;
        if(mac->mac_unit == 0)
            ar7240_reg_wr(AG7240_ETH_CFG, AG7240_ETH_CFG_RGMII_GE0);

        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
        ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);

        return;
    }
#endif

    if ((ar7240_reg_rd(AR7240_REV_ID) & AR7240_REV_ID_MASK) == AR7240_REV_1_2) {
        mgmt_cfg_val = 0x2;
        if (mac->mac_unit == 0) {
            ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
            ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
        }
    }
    else {
        ar7240_sys_frequency(&cpu_freq, &ddr_freq, &ahb_freq);
        switch (ahb_freq/1000000) {
            case 150:
                     mgmt_cfg_val = 0x7;
                     break;
            case 175:
                     mgmt_cfg_val = 0x5;
                     break;
            case 200:
                     mgmt_cfg_val = 0x4;
                     break;
            case 210:
                      mgmt_cfg_val = 0x9;
                      break;
            case 220:
                      mgmt_cfg_val = 0x9;
                      break;
            default:
                     mgmt_cfg_val = 0x7;
        }
        if ((is_ar7241() || is_ar7242())) {

            /* External MII mode */
            if (mac->mac_unit == 0 && is_ar7242()) {
                 mgmt_cfg_val = 0x6;
                 ar7240_reg_rmw_set(AG7240_ETH_CFG, AG7240_ETH_CFG_RGMII_GE0);
                 ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
                 ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
            }
            /* Virian */
            mgmt_cfg_val = 0x4;
            ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
            ag7240_reg_wr(ag7240_macs[1], AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
            printf("Virian MDC CFG Value ==> %x\n",mgmt_cfg_val);

        }
      else if(is_ar933x()){
                //GE0 receives Rx/Tx clock, and use S26 phy
                ar7240_reg_rmw_set(AG7240_ETH_CFG, AG7240_ETH_CFG_MII_GE0_SLAVE);
                mgmt_cfg_val = 0xF;
                if (mac->mac_unit == 1) {
                        check_cnt = 0;
                        while (check_cnt++ < 10) {
                                ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
                                ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
#ifdef CFG_ATHRS26_PHY
                                if(athrs26_mdc_check() == 0)
                                        break;
#endif
                        }
                        if(check_cnt == 11)
                                printf("%s: MDC check failed\n", __func__);
                }
      }
        else { /* Python 1.0 & 1.1 */
             if (mac->mac_unit == 0) {
                     check_cnt = 0;
                     while (check_cnt++ < 10) {
                             ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val | (1 << 31));
                             ag7240_reg_wr(mac, AG7240_MAC_MII_MGMT_CFG, mgmt_cfg_val);
#ifdef CFG_ATHRS26_PHY
                             if(athrs26_mdc_check() == 0)
                                     break;
#endif
                     }
                     if(check_cnt == 11)
                             printf("%s: MDC check failed\n", __func__);
             }
	}

    }
}
Пример #4
0
/*
 * Set and store PLL configuration in FLASH
 */
int do_set_clocks(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
	unsigned int cpu_pll_config_flash, cpu_clock_control_flash, spi_control_flash, reg;
	unsigned int ahb_freq, ddr_freq, cpu_freq, spi_freq;
	unsigned int *data_pointer;
	int i, index, profiles_count;
	char buf[128];

	profiles_count = sizeof(oc_profiles) / sizeof(ar9331_clock_profile);

	// print all available profiles and current settings
	if(argc == 1){

		// read clocks
		ar7240_sys_frequency(&cpu_freq, &ddr_freq, &ahb_freq);

		// calculate SPI clock (we need to set bit 0 to 1 in SPI_FUNC_SELECT to access SPI registers)
		ar7240_reg_wr(AR7240_SPI_FS, 0x01);
		spi_freq = ahb_freq / (((ar7240_reg_rd(AR7240_SPI_CLOCK) & 0x3F) + 1) * 2);
		ar7240_reg_wr(AR7240_SPI_FS, 0x0);

		// make MHz from Hz
		cpu_freq /= 1000000;
		ddr_freq /= 1000000;
		ahb_freq /= 1000000;
		spi_freq /= 1000000;

		printf("Current clocks (approximated):\n- CPU: %3d MHz\n", cpu_freq);
		printf("- RAM: %3d MHz\n", ddr_freq);
		printf("- AHB: %3d MHz\n", ahb_freq);
		printf("- SPI: %3d MHz\n", spi_freq);

		// reference clock
		if(ar7240_reg_rd(HORNET_BOOTSTRAP_STATUS) & HORNET_BOOTSTRAP_SEL_25M_40M_MASK){
			puts("- REF:  40 MHz\n\n");
		} else {
			puts("- REF:  25 MHz\n\n");
		}

		// do we have PLL_MAGIC in FLASH?
		reg = ar7240_reg_rd(CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET + PLL_IN_FLASH_MAGIC_OFFSET);

		// read all register values stored in FLASH
		cpu_pll_config_flash = ar7240_reg_rd(CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET + PLL_IN_FLASH_MAGIC_OFFSET + 4);
		cpu_clock_control_flash = ar7240_reg_rd(CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET + PLL_IN_FLASH_MAGIC_OFFSET + 8);
		spi_control_flash = ar7240_reg_rd(CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET + PLL_IN_FLASH_MAGIC_OFFSET + 12);

		printf("Available PLL and clocks configurations: %d\n\n", profiles_count);

		puts("      | CPU | RAM | AHB | SPI | [ ]\n  ---------------------------------\n");

		for(i = 0; i <  profiles_count; i++){
			printf("%4d. |%4d |%4d |%4d |%4d | ", i + 1,
												  oc_profiles[i].cpu_clock,
												  oc_profiles[i].ram_clock,
												  oc_profiles[i].ahb_clock,
												  oc_profiles[i].spi_clock);

			if(reg == PLL_IN_FLASH_MAGIC &&
			   oc_profiles[i].cpu_pll_config == cpu_pll_config_flash &&
			   oc_profiles[i].cpu_clk_control == cpu_clock_control_flash &&
			   oc_profiles[i].spi_control == spi_control_flash){
				puts("[*]\n");
			} else {
				puts("[ ]\n");
			}
		}

		puts("\n[*] = currently selected profile (stored in FLASH).\nAll clocks in MHz, run 'setclk X' to choose one.\n\n");
		puts("** Notice:\n   you should always make a backup of your device\n   entire FLASH content before making any changes\n\n");

		return(0);
	} else {
		// selected index
		index = simple_strtoul(argv[1], NULL, 10);

		if(index > profiles_count || index < 1){
			printf("## Error: selected index should be in range 1..%d!\n", profiles_count);
			return(1);
		}

		printf("You have selected profile: %d.\n\n", index);

		// array is zero-based indexing
		index--;

		// backup entire block in which we store PLL/CLK settings
		data_pointer = (unsigned int *)WEBFAILSAFE_UPLOAD_RAM_ADDRESS;

		if(!data_pointer){
			puts("## Error: couldn't allocate RAM for data block backup!\n");
			return(1);
		}

		memcpy((void *)data_pointer, (void *)(CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET), PLL_IN_FLASH_DATA_BLOCK_LENGTH);

		// save PLL_IN_FLASH_MAGIC and PLL/clocks registers values
		data_pointer = (unsigned int *)(WEBFAILSAFE_UPLOAD_RAM_ADDRESS + PLL_IN_FLASH_MAGIC_OFFSET);
		*data_pointer = PLL_IN_FLASH_MAGIC;

		data_pointer++;
		*data_pointer = oc_profiles[index].cpu_pll_config;

		data_pointer++;
		*data_pointer = oc_profiles[index].cpu_clk_control;

		data_pointer++;
		*data_pointer = oc_profiles[index].spi_control;

		// erase FLASH, copy data from RAM
		sprintf(buf,
				"erase 0x%lX +0x%lX; cp.b 0x%lX 0x%lX 0x%lX",
				CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET,
				PLL_IN_FLASH_DATA_BLOCK_LENGTH,
				WEBFAILSAFE_UPLOAD_RAM_ADDRESS,
				CFG_FLASH_BASE + PLL_IN_FLASH_DATA_BLOCK_OFFSET,
				PLL_IN_FLASH_DATA_BLOCK_LENGTH);

		printf("Executing: %s\n\n", buf);

		return(run_command(buf, 0));
	}
}