⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 katana.c

📁 linux-2.6.15.6
💻 C
📖 第 1 页 / 共 2 页
字号:
	/* Enable access to IPMI ctlr by clearing IPMI PORTSEL bit in CPLD */	reset_out = in_8(cpld_base + KATANA_CPLD_RESET_OUT);	reset_out &= ~KATANA_CPLD_RESET_OUT_PORTSEL;	out_8(cpld_base + KATANA_CPLD_RESET_OUT, reset_out);}static void __initkatana_setup_arch(void){	if (ppc_md.progress)		ppc_md.progress("katana_setup_arch: enter", 0);	set_tb(0, 0);#ifdef CONFIG_BLK_DEV_INITRD	if (initrd_start)		ROOT_DEV = Root_RAM0;	else#endif#ifdef   CONFIG_ROOT_NFS		ROOT_DEV = Root_NFS;#else		ROOT_DEV = Root_SDA2;#endif	/*	 * Set up the L2CR register.	 *	 * 750FX has only L2E, L2PE (bits 2-8 are reserved)	 * DD2.0 has bug that requires the L2 to be in WRT mode	 * avoid dirty data in cache	 */	if (PVR_REV(mfspr(SPRN_PVR)) == 0x0200) {		printk(KERN_INFO "DD2.0 detected. Setting L2 cache"			"to Writethrough mode\n");		_set_L2CR(L2CR_L2E | L2CR_L2PE | L2CR_L2WT);	} else		_set_L2CR(L2CR_L2E | L2CR_L2PE);	if (ppc_md.progress)		ppc_md.progress("katana_setup_arch: calling setup_bridge", 0);	katana_setup_bridge();	katana_setup_peripherals();	katana_enable_ipmi();	katana_bus_frequency = katana_bus_freq(cpld_base);	printk(KERN_INFO "Artesyn Communication Products, LLC - Katana(TM)\n");	if (ppc_md.progress)		ppc_md.progress("katana_setup_arch: exit", 0);}voidkatana_fixup_resources(struct pci_dev *dev){	u16	v16;	pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE, L1_CACHE_BYTES>>2);	pci_read_config_word(dev, PCI_COMMAND, &v16);	v16 |= PCI_COMMAND_INVALIDATE | PCI_COMMAND_FAST_BACK;	pci_write_config_word(dev, PCI_COMMAND, v16);}static const unsigned int cpu_750xx[32] = { /* 750FX & 750GX */	 0,  0,  2,  2,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15,/* 0-15*/	16, 17, 18, 19, 20, 22, 24, 26, 28, 30, 32, 34, 36, 38, 40,  0 /*16-31*/};static intkatana_get_cpu_freq(void){	unsigned long	pll_cfg;	pll_cfg = (mfspr(SPRN_HID1) & 0xf8000000) >> 27;	return katana_bus_frequency * cpu_750xx[pll_cfg]/2;}/* Platform device data fixup routines. */#if defined(CONFIG_SERIAL_MPSC)static void __initkatana_fixup_mpsc_pdata(struct platform_device *pdev){	struct mpsc_pdata *pdata = (struct mpsc_pdata *)pdev->dev.platform_data;	bd_t *bdp = (bd_t *)__res;	if (bdp->bi_baudrate)		pdata->default_baud = bdp->bi_baudrate;	else		pdata->default_baud = KATANA_DEFAULT_BAUD;	pdata->max_idle = 40;	pdata->brg_clk_src = KATANA_MPSC_CLK_SRC;	/*	 * TCLK (not SysCLk) is routed to BRG, then to the MPSC.  On most parts,	 * TCLK == SysCLK but on 64460, they are separate pins.	 * SysCLK can go up to 200 MHz but TCLK can only go up to 133 MHz.	 */	pdata->brg_clk_freq = min(katana_bus_frequency, MV64x60_TCLK_FREQ_MAX);}#endif#if defined(CONFIG_MV643XX_ETH)static void __initkatana_fixup_eth_pdata(struct platform_device *pdev){	struct mv643xx_eth_platform_data *eth_pd;	static u16 phy_addr[] = {		KATANA_ETH0_PHY_ADDR,		KATANA_ETH1_PHY_ADDR,		KATANA_ETH2_PHY_ADDR,	};	eth_pd = pdev->dev.platform_data;	eth_pd->force_phy_addr = 1;	eth_pd->phy_addr = phy_addr[pdev->id];	eth_pd->tx_queue_size = KATANA_ETH_TX_QUEUE_SIZE;	eth_pd->rx_queue_size = KATANA_ETH_RX_QUEUE_SIZE;}#endif#if defined(CONFIG_SYSFS)static void __initkatana_fixup_mv64xxx_pdata(struct platform_device *pdev){	struct mv64xxx_pdata *pdata = (struct mv64xxx_pdata *)		pdev->dev.platform_data;	/* Katana supports the mv64xxx hotswap register */	pdata->hs_reg_valid = 1;}#endifstatic int __initkatana_platform_notify(struct device *dev){	static struct {		char	*bus_id;		void	((*rtn)(struct platform_device *pdev));	} dev_map[] = {#if defined(CONFIG_SERIAL_MPSC)		{ MPSC_CTLR_NAME ".0", katana_fixup_mpsc_pdata },		{ MPSC_CTLR_NAME ".1", katana_fixup_mpsc_pdata },#endif#if defined(CONFIG_MV643XX_ETH)		{ MV643XX_ETH_NAME ".0", katana_fixup_eth_pdata },		{ MV643XX_ETH_NAME ".1", katana_fixup_eth_pdata },		{ MV643XX_ETH_NAME ".2", katana_fixup_eth_pdata },#endif#if defined(CONFIG_SYSFS)		{ MV64XXX_DEV_NAME ".0", katana_fixup_mv64xxx_pdata },#endif	};	struct platform_device	*pdev;	int	i;	if (dev && dev->bus_id)		for (i=0; i<ARRAY_SIZE(dev_map); i++)			if (!strncmp(dev->bus_id, dev_map[i].bus_id,					BUS_ID_SIZE)) {				pdev = container_of(dev,					struct platform_device, dev);				dev_map[i].rtn(pdev);			}	return 0;}#ifdef CONFIG_MTD_PHYSMAP#ifndef MB#define MB	(1 << 20)#endif/* * MTD Layout depends on amount of soldered FLASH in system. Sizes in MB. * * FLASH Amount:	128	64	32	16 * -------------	---	--	--	-- * Monitor:		1	1	1	1 * Primary Kernel:	1.5	1.5	1.5	1.5 * Primary fs:		30	30	<end>	<end> * Secondary Kernel:	1.5	1.5	N/A	N/A * Secondary fs:	<end>	<end>	N/A	N/A * User: 		<overlays entire FLASH except for "Monitor" section> */static int __initkatana_setup_mtd(void){	u32	size;	int	ptbl_entries;	static struct mtd_partition	*ptbl;	size = katana_flash_size_0 + katana_flash_size_1;	if (!size)		return -ENOMEM;	ptbl_entries = (size >= (64*MB)) ? 6 : 4;	if ((ptbl = kmalloc(ptbl_entries * sizeof(struct mtd_partition),			GFP_KERNEL)) == NULL) {		printk(KERN_WARNING "Can't alloc MTD partition table\n");		return -ENOMEM;	}	memset(ptbl, 0, ptbl_entries * sizeof(struct mtd_partition));	ptbl[0].name = "Monitor";	ptbl[0].size = KATANA_MTD_MONITOR_SIZE;	ptbl[1].name = "Primary Kernel";	ptbl[1].offset = MTDPART_OFS_NXTBLK;	ptbl[1].size = 0x00180000; /* 1.5 MB */	ptbl[2].name = "Primary Filesystem";	ptbl[2].offset = MTDPART_OFS_APPEND;	ptbl[2].size = MTDPART_SIZ_FULL; /* Correct for 16 & 32 MB */	ptbl[ptbl_entries-1].name = "User FLASH";	ptbl[ptbl_entries-1].offset = KATANA_MTD_MONITOR_SIZE;	ptbl[ptbl_entries-1].size = MTDPART_SIZ_FULL;	if (size >= (64*MB)) {		ptbl[2].size = 30*MB;		ptbl[3].name = "Secondary Kernel";		ptbl[3].offset = MTDPART_OFS_NXTBLK;		ptbl[3].size = 0x00180000; /* 1.5 MB */		ptbl[4].name = "Secondary Filesystem";		ptbl[4].offset = MTDPART_OFS_APPEND;		ptbl[4].size = MTDPART_SIZ_FULL;	}	physmap_map.size = size;	physmap_set_partitions(ptbl, ptbl_entries);	return 0;}arch_initcall(katana_setup_mtd);#endifstatic voidkatana_restart(char *cmd){	ulong	i = 10000000;	/* issue hard reset to the reset command register */	out_8(cpld_base + KATANA_CPLD_RST_CMD, KATANA_CPLD_RST_CMD_HR);	while (i-- > 0) ;	panic("restart failed\n");}static voidkatana_halt(void){	u8	v;	/* Turn on blue LED to indicate its okay to remove */	if (katana_id == KATANA_ID_750I) {		u32	v;		u8	save_exclude;		/* Set LOO bit in cPCI HotSwap reg of hose 0 to turn on LED. */		save_exclude = mv64x60_pci_exclude_bridge;		mv64x60_pci_exclude_bridge = 0;		early_read_config_dword(bh.hose_a, 0, PCI_DEVFN(0, 0),			MV64360_PCICFG_CPCI_HOTSWAP, &v);		v &= 0xff;		v |= (1 << 19);		early_write_config_dword(bh.hose_a, 0, PCI_DEVFN(0, 0),			MV64360_PCICFG_CPCI_HOTSWAP, v);		mv64x60_pci_exclude_bridge = save_exclude;	} else if (katana_id == KATANA_ID_752I) {		   v = in_8(cpld_base + HSL_PLD_BASE + HSL_PLD_HOT_SWAP_OFF);		   v |= HSL_PLD_HOT_SWAP_LED_BIT;		   out_8(cpld_base + HSL_PLD_BASE + HSL_PLD_HOT_SWAP_OFF, v);	}	while (1) ;	/* NOTREACHED */}static voidkatana_power_off(void){	katana_halt();	/* NOTREACHED */}static intkatana_show_cpuinfo(struct seq_file *m){	char	*s;	seq_printf(m, "cpu freq\t: %dMHz\n",		(katana_get_cpu_freq() + 500000) / 1000000);	seq_printf(m, "bus freq\t: %ldMHz\n",		((long)katana_bus_frequency + 500000) / 1000000);	seq_printf(m, "vendor\t\t: Artesyn Communication Products, LLC\n");	seq_printf(m, "board\t\t: ");	switch (katana_id) {	case KATANA_ID_3750:		seq_printf(m, "Katana 3750");		break;	case KATANA_ID_750I:		seq_printf(m, "Katana 750i");		break;	case KATANA_ID_752I:		seq_printf(m, "Katana 752i");		break;	default:		seq_printf(m, "Unknown");		break;	}	seq_printf(m, " (product id: 0x%x)\n",		   in_8(cpld_base + KATANA_CPLD_PRODUCT_ID));	seq_printf(m, "pci mode\t: %sMonarch\n",		katana_is_monarch()? "" : "Non-");	seq_printf(m, "hardware rev\t: 0x%x\n",		   in_8(cpld_base+KATANA_CPLD_HARDWARE_VER));	seq_printf(m, "pld rev\t\t: 0x%x\n",		   in_8(cpld_base + KATANA_CPLD_PLD_VER));	switch(bh.type) {	case MV64x60_TYPE_GT64260A:		s = "gt64260a";		break;	case MV64x60_TYPE_GT64260B:		s = "gt64260b";		break;	case MV64x60_TYPE_MV64360:		s = "mv64360";		break;	case MV64x60_TYPE_MV64460:		s = "mv64460";		break;	default:		s = "Unknown";	}	seq_printf(m, "bridge type\t: %s\n", s);	seq_printf(m, "bridge rev\t: 0x%x\n", bh.rev);#if defined(CONFIG_NOT_COHERENT_CACHE)	seq_printf(m, "coherency\t: %s\n", "off");#else	seq_printf(m, "coherency\t: %s\n", "on");#endif	return 0;}static void __initkatana_calibrate_decr(void){	u32 freq;	freq = katana_bus_frequency / 4;	printk(KERN_INFO "time_init: decrementer frequency = %lu.%.6lu MHz\n",	       (long)freq / 1000000, (long)freq % 1000000);	tb_ticks_per_jiffy = freq / HZ;	tb_to_us = mulhwu_scale_factor(freq, 1000000);}/* * The katana supports both uImage and zImage.  If uImage, get the mem size * from the bd info.  If zImage, the bootwrapper adds a BI_MEMSIZE entry in * the bi_rec data which is sucked out and put into boot_mem_size by * parse_bootinfo().  MMU_init() will then use the boot_mem_size for the mem * size and not call this routine.  The only way this will fail is when a uImage * is used but the fw doesn't pass in a valid bi_memsize.  This should never * happen, though. */unsigned long __initkatana_find_end_of_memory(void){	bd_t *bdp = (bd_t *)__res;	return bdp->bi_memsize;}#if defined(CONFIG_I2C_MV64XXX) && defined(CONFIG_SENSORS_M41T00)extern ulong	m41t00_get_rtc_time(void);extern int	m41t00_set_rtc_time(ulong);static int __initkatana_rtc_hookup(void){	struct timespec	tv;	ppc_md.get_rtc_time = m41t00_get_rtc_time;	ppc_md.set_rtc_time = m41t00_set_rtc_time;	tv.tv_nsec = 0;	tv.tv_sec = (ppc_md.get_rtc_time)();	do_settimeofday(&tv);	return 0;}late_initcall(katana_rtc_hookup);#endif#if defined(CONFIG_SERIAL_TEXT_DEBUG) && defined(CONFIG_SERIAL_MPSC_CONSOLE)static void __initkatana_map_io(void){	io_block_mapping(0xf8100000, 0xf8100000, 0x00020000, _PAGE_IO);}#endifvoid __initplatform_init(unsigned long r3, unsigned long r4, unsigned long r5,	      unsigned long r6, unsigned long r7){	parse_bootinfo(find_bootinfo());	/* ASSUMPTION:  If both r3 (bd_t pointer) and r6 (cmdline pointer)	 * are non-zero, then we should use the board info from the bd_t	 * structure and the cmdline pointed to by r6 instead of the	 * information from birecs, if any.  Otherwise, use the information	 * from birecs as discovered by the preceeding call to	 * parse_bootinfo().  This rule should work with both PPCBoot, which	 * uses a bd_t board info structure, and the kernel boot wrapper,	 * which uses birecs.	 */	if (r3 && r6) {		/* copy board info structure */		memcpy((void *)__res, (void *)(r3+KERNELBASE), sizeof(bd_t));		/* copy command line */		*(char *)(r7+KERNELBASE) = 0;		strcpy(cmd_line, (char *)(r6+KERNELBASE));	}#ifdef CONFIG_BLK_DEV_INITRD	/* take care of initrd if we have one */	if (r4) {		initrd_start = r4 + KERNELBASE;		initrd_end = r5 + KERNELBASE;	}#endif /* CONFIG_BLK_DEV_INITRD */	isa_mem_base = 0;	ppc_md.setup_arch = katana_setup_arch;	ppc_md.pcibios_fixup_resources = katana_fixup_resources;	ppc_md.show_cpuinfo = katana_show_cpuinfo;	ppc_md.init_IRQ = mv64360_init_irq;	ppc_md.get_irq = mv64360_get_irq;	ppc_md.restart = katana_restart;	ppc_md.power_off = katana_power_off;	ppc_md.halt = katana_halt;	ppc_md.find_end_of_memory = katana_find_end_of_memory;	ppc_md.calibrate_decr = katana_calibrate_decr;#if defined(CONFIG_SERIAL_TEXT_DEBUG) && defined(CONFIG_SERIAL_MPSC_CONSOLE)	ppc_md.setup_io_mappings = katana_map_io;	ppc_md.progress = mv64x60_mpsc_progress;	mv64x60_progress_init(CONFIG_MV64X60_NEW_BASE);#endif#if defined(CONFIG_SERIAL_MPSC) || defined(CONFIG_MV643XX_ETH)	platform_notify = katana_platform_notify;#endif}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -