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

📄 setup.c

📁 上传linux-jx2410的源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
/* * Architecture-specific setup. * * Copyright (C) 1998-2001 Hewlett-Packard Co *	David Mosberger-Tang <davidm@hpl.hp.com> * Copyright (C) 1998, 1999, 2001 Stephane Eranian <eranian@hpl.hp.com> * Copyright (C) 2000, Rohit Seth <rohit.seth@intel.com> * Copyright (C) 1999 VA Linux Systems * Copyright (C) 1999 Walt Drummond <drummond@valinux.com> * * 11/12/01 D.Mosberger Convert get_cpuinfo() to seq_file based show_cpuinfo(). * 04/04/00 D.Mosberger renamed cpu_initialized to cpu_online_map * 03/31/00 R.Seth	cpu_initialized and current->processor fixes * 02/04/00 D.Mosberger	some more get_cpuinfo fixes... * 02/01/00 R.Seth	fixed get_cpuinfo for SMP * 01/07/99 S.Eranian	added the support for command line argument * 06/24/99 W.Drummond	added boot_cpu_data. */#include <linux/config.h>#include <linux/init.h>#include <linux/bootmem.h>#include <linux/delay.h>#include <linux/kernel.h>#include <linux/reboot.h>#include <linux/sched.h>#include <linux/seq_file.h>#include <linux/string.h>#include <linux/threads.h>#include <linux/console.h>#include <asm/acpi-ext.h>#include <asm/ia32.h>#include <asm/page.h>#include <asm/machvec.h>#include <asm/processor.h>#include <asm/sal.h>#include <asm/system.h>#include <asm/efi.h>#include <asm/mca.h>#include <asm/smp.h>#ifdef CONFIG_BLK_DEV_RAM# include <linux/blk.h>#endif#if defined(CONFIG_SMP) && (IA64_CPU_SIZE > PAGE_SIZE)# error "struct cpuinfo_ia64 too big!"#endif#define MIN(a,b)	((a) < (b) ? (a) : (b))#define MAX(a,b)	((a) > (b) ? (a) : (b))extern char _end;#ifdef CONFIG_NUMA struct cpuinfo_ia64 *boot_cpu_data;#else struct cpuinfo_ia64 _cpu_data[NR_CPUS] __attribute__ ((section ("__special_page_section")));#endifunsigned long ia64_cycles_per_usec;struct ia64_boot_param *ia64_boot_param;struct screen_info screen_info;unsigned long ia64_iobase;	/* virtual address for I/O accesses */#define COMMAND_LINE_SIZE	512char saved_command_line[COMMAND_LINE_SIZE]; /* used in proc filesystem *//* * Entries defined so far: * 	- boot param structure itself * 	- memory map * 	- initrd (optional) * 	- command line string * 	- kernel code & data * * More could be added if necessary */#define IA64_MAX_RSVD_REGIONS 5struct rsvd_region {	unsigned long start;	/* virtual address of beginning of element */	unsigned long end;	/* virtual address of end of element + 1 */};/* * We use a special marker for the end of memory and it uses the extra (+1) slot */static struct rsvd_region rsvd_region[IA64_MAX_RSVD_REGIONS + 1];static int num_rsvd_regions;static unsigned long bootmap_start; /* physical address where the bootmem map is located */static intfind_max_pfn (unsigned long start, unsigned long end, void *arg){	unsigned long *max_pfn = arg, pfn;	pfn = (PAGE_ALIGN(end - 1) - PAGE_OFFSET) >> PAGE_SHIFT;	if (pfn > *max_pfn)		*max_pfn = pfn;	return 0;}#define IGNORE_PFN0	1	/* XXX fix me: ignore pfn 0 until TLB miss handler is updated... *//* * Free available memory based on the primitive map created from * the boot parameters. This routine does not assume the incoming * segments are sorted. */static intfree_available_memory (unsigned long start, unsigned long end, void *arg){	unsigned long range_start, range_end, prev_start;	int i;#if IGNORE_PFN0	if (start == PAGE_OFFSET) {		printk("warning: skipping physical page 0\n");		start += PAGE_SIZE;		if (start >= end) return 0;	}#endif	/*	 * lowest possible address(walker uses virtual)	 */	prev_start = PAGE_OFFSET;	for (i = 0; i < num_rsvd_regions; ++i) {		range_start = MAX(start, prev_start);		range_end   = MIN(end, rsvd_region[i].start);		if (range_start < range_end)			free_bootmem(__pa(range_start), range_end - range_start);		/* nothing more available in this segment */		if (range_end == end) return 0;		prev_start = rsvd_region[i].end;	}	/* end of memory marker allows full processing inside loop body */	return 0;}static intfind_bootmap_location (unsigned long start, unsigned long end, void *arg){	unsigned long needed = *(unsigned long *)arg;	unsigned long range_start, range_end, free_start;	int i;#if IGNORE_PFN0	if (start == PAGE_OFFSET) {		start += PAGE_SIZE;		if (start >= end) return 0;	}#endif	free_start = PAGE_OFFSET;	for (i = 0; i < num_rsvd_regions; i++) {		range_start = MAX(start, free_start);		range_end   = MIN(end, rsvd_region[i].start);		if (range_end <= range_start) continue;	/* skip over empty range */	       	if (range_end - range_start >= needed) {			bootmap_start = __pa(range_start);			return 1;	/* done */		}		/* nothing more available in this segment */		if (range_end == end) return 0;		free_start = rsvd_region[i].end;	}	return 0;}static voidsort_regions (struct rsvd_region *rsvd_region, int max){	int j;	/* simple bubble sorting */	while (max--) {		for (j = 0; j < max; ++j) {			if (rsvd_region[j].start > rsvd_region[j+1].start) {				struct rsvd_region tmp;				tmp = rsvd_region[j];				rsvd_region[j] = rsvd_region[j + 1];				rsvd_region[j + 1] = tmp;			}		}	}}static voidfind_memory (void){#	define KERNEL_END	((unsigned long) &_end)	unsigned long bootmap_size;	unsigned long max_pfn;	int n = 0;	/*	 * none of the entries in this table overlap	 */	rsvd_region[n].start = (unsigned long) ia64_boot_param;	rsvd_region[n].end   = rsvd_region[n].start + sizeof(*ia64_boot_param);	n++;	rsvd_region[n].start = (unsigned long) __va(ia64_boot_param->efi_memmap);	rsvd_region[n].end   = rsvd_region[n].start + ia64_boot_param->efi_memmap_size;	n++;	rsvd_region[n].start = (unsigned long) __va(ia64_boot_param->command_line);	rsvd_region[n].end   = (rsvd_region[n].start				+ strlen(__va(ia64_boot_param->command_line)) + 1);	n++;	rsvd_region[n].start = KERNEL_START;	rsvd_region[n].end   = KERNEL_END;	n++;#ifdef CONFIG_BLK_DEV_INITRD	if (ia64_boot_param->initrd_start) {		rsvd_region[n].start = (unsigned long)__va(ia64_boot_param->initrd_start);		rsvd_region[n].end   = rsvd_region[n].start + ia64_boot_param->initrd_size;		n++;	}#endif	/* end of memory marker */	rsvd_region[n].start = ~0UL;	rsvd_region[n].end   = ~0UL;	n++;	num_rsvd_regions = n;	sort_regions(rsvd_region, num_rsvd_regions);	/* first find highest page frame number */	max_pfn = 0;	efi_memmap_walk(find_max_pfn, &max_pfn);	/* how many bytes to cover all the pages */	bootmap_size = bootmem_bootmap_pages(max_pfn) << PAGE_SHIFT;	/* look for a location to hold the bootmap */	bootmap_start = ~0UL;	efi_memmap_walk(find_bootmap_location, &bootmap_size);	if (bootmap_start == ~0UL)		panic("Cannot find %ld bytes for bootmap\n", bootmap_size);	bootmap_size = init_bootmem(bootmap_start >> PAGE_SHIFT, max_pfn);	/* Free all available memory, then mark bootmem-map as being in use.  */	efi_memmap_walk(free_available_memory, 0);	reserve_bootmem(bootmap_start, bootmap_size);#ifdef CONFIG_BLK_DEV_INITRD	if (ia64_boot_param->initrd_start) {		initrd_start = (unsigned long)__va(ia64_boot_param->initrd_start);		initrd_end   = initrd_start+ia64_boot_param->initrd_size;		printk("Initial ramdisk at: 0x%lx (%lu bytes)\n",		       initrd_start, ia64_boot_param->initrd_size);	}#endif}void __initsetup_arch (char **cmdline_p){	extern unsigned long ia64_iobase;	unw_init();	*cmdline_p = __va(ia64_boot_param->command_line);	strncpy(saved_command_line, *cmdline_p, sizeof(saved_command_line));	saved_command_line[COMMAND_LINE_SIZE-1] = '\0';		/* for safety */	efi_init();	find_memory();#if 0	/* XXX fix me */	init_mm.start_code = (unsigned long) &_stext;	init_mm.end_code = (unsigned long) &_etext;	init_mm.end_data = (unsigned long) &_edata;	init_mm.brk = (unsigned long) &_end;	code_resource.start = virt_to_bus(&_text);	code_resource.end = virt_to_bus(&_etext) - 1;	data_resource.start = virt_to_bus(&_etext);	data_resource.end = virt_to_bus(&_edata) - 1;#endif	/* process SAL system table: */	ia64_sal_init(efi.sal_systab);	/*	 *  Set `iobase' to the appropriate address in region 6

⌨️ 快捷键说明

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