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

📄 pci.c

📁 该文件是rt_linux
💻 C
📖 第 1 页 / 共 3 页
字号:
		if (0) { /* don't assign ROMs */			r = &dev->resource[PCI_ROM_RESOURCE];			r->end -= r->start;			r->start = 0;			if (r->end)				pci_assign_resource(dev, PCI_ROM_RESOURCE);		}	}}intpcibios_enable_resources(struct pci_dev *dev, int mask){	u16 cmd, old_cmd;	int idx;	struct resource *r;	pci_read_config_word(dev, PCI_COMMAND, &cmd);	old_cmd = cmd;	for(idx=0; idx<6; idx++) {		if(!(mask & (1<<idx)))			continue;		r = &dev->resource[idx];		if (!r->start && r->end) {			printk(KERN_ERR "PCI: Device %s not available because of resource collisions\n", dev->slot_name);			return -EINVAL;		}		if (r->flags & IORESOURCE_IO)			cmd |= PCI_COMMAND_IO;		if (r->flags & IORESOURCE_MEM)			cmd |= PCI_COMMAND_MEMORY;	}	if (dev->resource[PCI_ROM_RESOURCE].start)		cmd |= PCI_COMMAND_MEMORY;	if (cmd != old_cmd) {		printk("PCI: Enabling device %s (%04x -> %04x)\n", dev->slot_name, old_cmd, cmd);		pci_write_config_word(dev, PCI_COMMAND, cmd);	}	return 0;}/*  * Allocate pci_controller(phb) initialized common variables.  */struct pci_controller * __initpci_alloc_pci_controller(char *model, enum phb_types controller_type){        struct pci_controller *hose;        PPCDBG(PPCDBG_PHBINIT, "PCI: Allocate pci_controller for %s\n",model);        hose = (struct pci_controller *)alloc_bootmem(sizeof(struct pci_controller));        if(hose == NULL) {                printk(KERN_ERR "PCI: Allocate pci_controller failed.\n");                return NULL;        }        memset(hose, 0, sizeof(struct pci_controller));        if(strlen(model) < 8) strcpy(hose->what,model);        else                  memcpy(hose->what,model,7);        hose->type = controller_type;        hose->global_number = global_phb_number;	phbtab[global_phb_number++] = hose;                *hose_tail = hose;        hose_tail = &hose->next;        return hose;}/* * This fixup is arch independent and probably should go somewhere else. */void __initpcibios_generic_fixup(void){	struct pci_dev *dev;	/* Fix miss-identified vendor AMD pcnet32 adapters. */	dev = NULL;	while ((dev = pci_find_device(PCI_VENDOR_ID_TRIDENT, PCI_DEVICE_ID_AMD_LANCE, dev)) != NULL &&	       dev->class == (PCI_CLASS_NETWORK_ETHERNET << 8))		dev->vendor = PCI_VENDOR_ID_AMD;}/***********************************************************************  * * *  ***********************************************************************/void __initpcibios_init(void){	struct pci_controller *hose;	struct pci_bus *bus;	int    next_busno;#ifndef CONFIG_PPC_ISERIES	pSeries_pcibios_init();#else	iSeries_pcibios_init(); #endif	ppc64_boot_msg(0x40, "PCI Probe");	printk("PCI: Probing PCI hardware\n");	PPCDBG(PPCDBG_BUSWALK,"PCI: Probing PCI hardware\n");	/* Scan all of the recorded PCI controllers.  */	for (next_busno = 0, hose = hose_head; hose; hose = hose->next) {		hose->last_busno = 0xff;		bus = pci_scan_bus(hose->first_busno, hose->ops, hose->arch_data);		hose->bus = bus;		hose->last_busno = bus->subordinate;		if (pci_assign_all_busses || next_busno <= hose->last_busno)			next_busno = hose->last_busno+1;	}	pci_bus_count = next_busno;			/* Call machine dependant fixup */	if (ppc_md.pcibios_fixup) {		ppc_md.pcibios_fixup();	}	/* Generic fixups */	pcibios_generic_fixup();	/* Allocate and assign resources */	pcibios_allocate_bus_resources(&pci_root_buses);	pcibios_allocate_resources(0);	pcibios_allocate_resources(1);	pcibios_assign_resources();#ifndef CONFIG_PPC_ISERIES	pci_fix_bus_sysdata();	create_tce_tables();	PPCDBG(PPCDBG_BUSWALK,"pSeries create_tce_tables()\n");#endif	/* Cache the location of the ISA bridge (if we have one) */	ppc64_isabridge_dev = pci_find_class(PCI_CLASS_BRIDGE_ISA << 8, NULL);	if (ppc64_isabridge_dev != NULL )		printk("ISA bridge at %s\n", ppc64_isabridge_dev->slot_name);	printk("PCI: Probing PCI hardware done\n");	PPCDBG(PPCDBG_BUSWALK,"PCI: Probing PCI hardware done.\n");	ppc64_boot_msg(0x41, "PCI Done");}int __initpcibios_assign_all_busses(void){	return pci_assign_all_busses;}unsigned long resource_fixup(struct pci_dev * dev, struct resource * res,			     unsigned long start, unsigned long size){	return start;}void __init pcibios_fixup_bus(struct pci_bus *bus){#ifndef CONFIG_PPC_ISERIES	struct pci_controller *phb = PCI_GET_PHB_PTR(bus);	struct resource *res;	int i;	if (bus->parent == NULL) {		/* This is a host bridge - fill in its resources */		phb->bus = bus;		bus->resource[0] = res = &phb->io_resource;		if (!res->flags)			BUG();	/* No I/O resource for this PHB? */		for (i = 0; i < 3; ++i) {			res = &phb->mem_resources[i];			if (!res->flags) {				if (i == 0)					BUG();	/* No memory resource for this PHB? */			}			bus->resource[i+1] = res;		}	} else {		/* This is a subordinate bridge */		pci_read_bridge_bases(bus);		for (i = 0; i < 4; ++i) {			if ((res = bus->resource[i]) == NULL)				continue;			if (!res->flags)				continue;			if (res == pci_find_parent_resource(bus->self, res)) {				/* Transparent resource -- don't try to "fix" it. */				continue;			}			if (is_eeh_implemented()) {				if (res->flags & (IORESOURCE_IO|IORESOURCE_MEM)) {					res->start = eeh_token(phb->global_number, bus->number, 0, 0);					res->end = eeh_token(phb->global_number, bus->number, 0xff, 0xffffffff);				}			} else {				if (res->flags & IORESOURCE_IO) {					res->start += (unsigned long)phb->io_base_virt;					res->end += (unsigned long)phb->io_base_virt;				} else if (phb->pci_mem_offset					   && (res->flags & IORESOURCE_MEM)) {					if (res->start < phb->pci_mem_offset) {						res->start += phb->pci_mem_offset;						res->end += phb->pci_mem_offset;					}				}			}		}	}#endif		if ( ppc_md.pcibios_fixup_bus )		ppc_md.pcibios_fixup_bus(bus);}char __init *pcibios_setup(char *str){	return str;}int pcibios_enable_device(struct pci_dev *dev, int mask){	u16 cmd, old_cmd;	int idx;	struct resource *r;	PPCDBG(PPCDBG_BUSWALK,"PCI: %s for device %s \n",__FUNCTION__,dev->slot_name);	if (ppc_md.pcibios_enable_device_hook)		if (ppc_md.pcibios_enable_device_hook(dev, 0))			return -EINVAL;				pci_read_config_word(dev, PCI_COMMAND, &cmd);	old_cmd = cmd;	for (idx=0; idx<6; idx++) {		r = &dev->resource[idx];		if (!r->start && r->end) {			printk(KERN_ERR "PCI: Device %s not available because of resource collisions\n", dev->slot_name);			return -EINVAL;		}		if (r->flags & IORESOURCE_IO)			cmd |= PCI_COMMAND_IO;		if (r->flags & IORESOURCE_MEM)			cmd |= PCI_COMMAND_MEMORY;	}	if (cmd != old_cmd) {		printk("PCI: Enabling device %s (%04x -> %04x)\n",		       dev->slot_name, old_cmd, cmd);		PPCDBG(PPCDBG_BUSWALK,"PCI: Enabling device %s \n",dev->slot_name);		pci_write_config_word(dev, PCI_COMMAND, cmd);	}	return 0;}struct pci_controller*pci_bus_to_hose(int bus){	struct pci_controller* hose = hose_head;	for (; hose; hose = hose->next)		if (bus >= hose->first_busno && bus <= hose->last_busno)			return hose;	return NULL;}void*pci_bus_io_base(unsigned int bus){	struct pci_controller *hose;	hose = pci_bus_to_hose(bus);	if (!hose)		return NULL;	return hose->io_base_virt;}unsigned longpci_bus_io_base_phys(unsigned int bus){	struct pci_controller *hose;	hose = pci_bus_to_hose(bus);	if (!hose)		return 0;	return hose->io_base_phys;}unsigned longpci_bus_mem_base_phys(unsigned int bus){	struct pci_controller *hose;	hose = pci_bus_to_hose(bus);	if (!hose)		return 0;	return hose->pci_mem_offset;}/* * Return the index of the PCI controller for device pdev. */int pci_controller_num(struct pci_dev *dev){	struct pci_controller *hose = PCI_GET_PHB_PTR(dev);	return hose->global_number;}/* * Platform support for /proc/bus/pci/X/Y mmap()s, * modelled on the sparc64 implementation by Dave Miller. *  -- paulus. *//* * Adjust vm_pgoff of VMA such that it is the physical page offset * corresponding to the 32-bit pci bus offset for DEV requested by the user. * * Basically, the user finds the base address for his device which he wishes * to mmap.  They read the 32-bit value from the config space base register, * add whatever PAGE_SIZE multiple offset they wish, and feed this into the * offset parameter of mmap on /proc/bus/pci/XXX for that device. * * Returns negative error code on failure, zero on success. */static __inline__ int__pci_mmap_make_offset(struct pci_dev *dev, struct vm_area_struct *vma,		       enum pci_mmap_state mmap_state){	struct pci_controller *hose = PCI_GET_PHB_PTR(dev);	unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;	unsigned long io_offset = 0;	int i, res_bit;	if (hose == 0)		return -EINVAL;		/* should never happen */	/* If memory, add on the PCI bridge address offset */	if (mmap_state == pci_mmap_mem) {		offset += hose->pci_mem_offset;		res_bit = IORESOURCE_MEM;	} else {		io_offset = (unsigned long)hose->io_base_virt;		offset += io_offset;		res_bit = IORESOURCE_IO;	}	/*	 * Check that the offset requested corresponds to one of the

⌨️ 快捷键说明

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