162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0-only 262306a36Sopenharmony_ci/* 362306a36Sopenharmony_ci * Copyright (C) 2012 Synopsys, Inc. (www.synopsys.com) 462306a36Sopenharmony_ci * 562306a36Sopenharmony_ci * Based on reduced version of METAG 662306a36Sopenharmony_ci */ 762306a36Sopenharmony_ci 862306a36Sopenharmony_ci 962306a36Sopenharmony_ci#include <linux/init.h> 1062306a36Sopenharmony_ci#include <linux/reboot.h> 1162306a36Sopenharmony_ci#include <linux/memblock.h> 1262306a36Sopenharmony_ci#include <linux/of.h> 1362306a36Sopenharmony_ci#include <linux/of_fdt.h> 1462306a36Sopenharmony_ci#include <asm/mach_desc.h> 1562306a36Sopenharmony_ci#include <asm/serial.h> 1662306a36Sopenharmony_ci 1762306a36Sopenharmony_ci#ifdef CONFIG_SERIAL_EARLYCON 1862306a36Sopenharmony_ci 1962306a36Sopenharmony_cistatic unsigned int __initdata arc_base_baud; 2062306a36Sopenharmony_ci 2162306a36Sopenharmony_ciunsigned int __init arc_early_base_baud(void) 2262306a36Sopenharmony_ci{ 2362306a36Sopenharmony_ci return arc_base_baud/16; 2462306a36Sopenharmony_ci} 2562306a36Sopenharmony_ci 2662306a36Sopenharmony_cistatic void __init arc_set_early_base_baud(unsigned long dt_root) 2762306a36Sopenharmony_ci{ 2862306a36Sopenharmony_ci if (of_flat_dt_is_compatible(dt_root, "abilis,arc-tb10x")) 2962306a36Sopenharmony_ci arc_base_baud = 166666666; /* Fixed 166.6MHz clk (TB10x) */ 3062306a36Sopenharmony_ci else if (of_flat_dt_is_compatible(dt_root, "snps,arc-sdp") || 3162306a36Sopenharmony_ci of_flat_dt_is_compatible(dt_root, "snps,hsdk")) 3262306a36Sopenharmony_ci arc_base_baud = 33333333; /* Fixed 33MHz clk (AXS10x & HSDK) */ 3362306a36Sopenharmony_ci else 3462306a36Sopenharmony_ci arc_base_baud = 50000000; /* Fixed default 50MHz */ 3562306a36Sopenharmony_ci} 3662306a36Sopenharmony_ci#else 3762306a36Sopenharmony_ci#define arc_set_early_base_baud(dt_root) 3862306a36Sopenharmony_ci#endif 3962306a36Sopenharmony_ci 4062306a36Sopenharmony_cistatic const void * __init arch_get_next_mach(const char *const **match) 4162306a36Sopenharmony_ci{ 4262306a36Sopenharmony_ci static const struct machine_desc *mdesc = __arch_info_begin; 4362306a36Sopenharmony_ci const struct machine_desc *m = mdesc; 4462306a36Sopenharmony_ci 4562306a36Sopenharmony_ci if (m >= __arch_info_end) 4662306a36Sopenharmony_ci return NULL; 4762306a36Sopenharmony_ci 4862306a36Sopenharmony_ci mdesc++; 4962306a36Sopenharmony_ci *match = m->dt_compat; 5062306a36Sopenharmony_ci return m; 5162306a36Sopenharmony_ci} 5262306a36Sopenharmony_ci 5362306a36Sopenharmony_ci/** 5462306a36Sopenharmony_ci * setup_machine_fdt - Machine setup when an dtb was passed to the kernel 5562306a36Sopenharmony_ci * @dt: virtual address pointer to dt blob 5662306a36Sopenharmony_ci * 5762306a36Sopenharmony_ci * If a dtb was passed to the kernel, then use it to choose the correct 5862306a36Sopenharmony_ci * machine_desc and to setup the system. 5962306a36Sopenharmony_ci */ 6062306a36Sopenharmony_ciconst struct machine_desc * __init setup_machine_fdt(void *dt) 6162306a36Sopenharmony_ci{ 6262306a36Sopenharmony_ci const struct machine_desc *mdesc; 6362306a36Sopenharmony_ci unsigned long dt_root; 6462306a36Sopenharmony_ci 6562306a36Sopenharmony_ci if (!early_init_dt_scan(dt)) 6662306a36Sopenharmony_ci return NULL; 6762306a36Sopenharmony_ci 6862306a36Sopenharmony_ci mdesc = of_flat_dt_match_machine(NULL, arch_get_next_mach); 6962306a36Sopenharmony_ci if (!mdesc) 7062306a36Sopenharmony_ci machine_halt(); 7162306a36Sopenharmony_ci 7262306a36Sopenharmony_ci dt_root = of_get_flat_dt_root(); 7362306a36Sopenharmony_ci arc_set_early_base_baud(dt_root); 7462306a36Sopenharmony_ci 7562306a36Sopenharmony_ci return mdesc; 7662306a36Sopenharmony_ci} 77