示例#1
0
int ps3_sb_event_receive_port_setup(struct ps3_system_bus_device *dev,
	enum ps3_cpu_binding cpu, unsigned int *virq)
{
	/* this should go in system-bus.c */

	int result;

	result = ps3_event_receive_port_setup(cpu, virq);

	if (result)
		return result;

	result = lv1_connect_interrupt_event_receive_port(dev->bus_id,
		dev->dev_id, virq_to_hw(*virq), dev->interrupt_id);

	if (result) {
		pr_debug("%s:%d: lv1_connect_interrupt_event_receive_port"
			" failed: %s\n", __func__, __LINE__,
			ps3_result(result));
		ps3_event_receive_port_destroy(*virq);
		*virq = NO_IRQ;
		return result;
	}

	pr_debug("%s:%d: interrupt_id %u, virq %u\n", __func__, __LINE__,
		dev->interrupt_id, *virq);

	return 0;
}
示例#2
0
文件: interrupt.c 项目: ivucica/linux
int ps3_connect_event_irq(const struct ps3_device_id *did,
	unsigned int interrupt_id, unsigned int *virq)
{
	int result;

	result = ps3_alloc_event_irq(virq);

	if (result)
		return result;

	result = lv1_connect_interrupt_event_receive_port(did->bus_id,
		did->dev_id, virq_to_hw(*virq), interrupt_id);

	if (result) {
		pr_debug("%s:%d: lv1_connect_interrupt_event_receive_port"
			" failed: %s\n", __func__, __LINE__,
			ps3_result(result));
		ps3_free_event_irq(*virq);
		*virq = NO_IRQ;
		return result;
	}

	pr_debug("%s:%d: interrupt_id %u, virq %u\n", __func__, __LINE__,
		interrupt_id, *virq);

	return 0;
}
示例#3
0
static void
ps3bus_resources_init(struct rman *rm, int bus_index, int dev_index,
    struct ps3bus_devinfo *dinfo)
{
	uint64_t irq_type, irq, outlet;
	uint64_t reg_type, paddr, len;
	uint64_t ppe, junk;
	int i, result;
	int thread;

	resource_list_init(&dinfo->resources);

	lv1_get_logical_ppe_id(&ppe);
	thread = 32 - fls(mfctrl());

	/* Scan for interrupts */
	for (i = 0; i < 10; i++) {
		result = lv1_get_repository_node_value(PS3_LPAR_ID_PME,
		    (lv1_repository_string("bus") >> 32) | bus_index,
		    lv1_repository_string("dev") | dev_index,
		    lv1_repository_string("intr") | i, 0, &irq_type, &irq);

		if (result != 0)
			break;

		switch (irq_type) {
		case SB_IRQ:
			lv1_construct_event_receive_port(&outlet);
			lv1_connect_irq_plug_ext(ppe, thread, outlet, outlet,
			    0);
			lv1_connect_interrupt_event_receive_port(dinfo->bus,
			    dinfo->dev, outlet, irq);
			break;
		case OHCI_IRQ:
		case EHCI_IRQ:
			lv1_construct_io_irq_outlet(irq, &outlet);
			lv1_connect_irq_plug_ext(ppe, thread, outlet, outlet,
			    0);
			break;
		default:
			printf("Unknown IRQ type %ld for device %d.%d\n",
			    irq_type, dinfo->bus, dinfo->dev);
			break;
		}

		resource_list_add(&dinfo->resources, SYS_RES_IRQ, i,
		    outlet, outlet, 1);
	}

	/* Scan for registers */
	for (i = 0; i < 10; i++) {
		result = lv1_get_repository_node_value(PS3_LPAR_ID_PME,
		    (lv1_repository_string("bus") >> 32) | bus_index,
		    lv1_repository_string("dev") | dev_index,
		    lv1_repository_string("reg") | i, 
		    lv1_repository_string("type"), &reg_type, &junk);

		if (result != 0)
			break;

		result = lv1_get_repository_node_value(PS3_LPAR_ID_PME,
		    (lv1_repository_string("bus") >> 32) | bus_index,
		    lv1_repository_string("dev") | dev_index,
		    lv1_repository_string("reg") | i, 
		    lv1_repository_string("data"), &paddr, &len);

		result = lv1_map_device_mmio_region(dinfo->bus, dinfo->dev,
		    paddr, len, 12 /* log_2(4 KB) */, &paddr);

		if (result != 0) {
			printf("Mapping registers failed for device "
			    "%d.%d (%ld.%ld): %d\n", dinfo->bus, dinfo->dev,
			    dinfo->bustype, dinfo->devtype, result);
			continue;
		}

		rman_manage_region(rm, paddr, paddr + len - 1);
		resource_list_add(&dinfo->resources, SYS_RES_MEMORY, i,
		    paddr, paddr + len, len);
	}
}