static int __init enable_spu(struct spu *spu) { int result; result = lv1_enable_logical_spe(spu_pdata(spu)->spe_id, spu_pdata(spu)->resource_id); if (result) { pr_debug("%s:%d: lv1_enable_logical_spe failed: %s\n", __func__, __LINE__, ps3_result(result)); goto fail_enable; } result = setup_areas(spu); if (result) goto fail_areas; result = setup_interrupts(spu); if (result) goto fail_interrupts; return 0; fail_interrupts: spu_unmap(spu); fail_areas: lv1_disable_logical_spe(spu_pdata(spu)->spe_id, 0); fail_enable: return result; }
static int ps3_destroy_spu(struct spu *spu) { int result; pr_debug("%s:%d spu_%d\n", __func__, __LINE__, spu->number); result = lv1_disable_logical_spe(spu_pdata(spu)->spe_id, 0); BUG_ON(result); ps3_spe_irq_destroy(spu->irqs[2]); ps3_spe_irq_destroy(spu->irqs[1]); ps3_spe_irq_destroy(spu->irqs[0]); spu->irqs[0] = spu->irqs[1] = spu->irqs[2] = NO_IRQ; spu_unmap(spu); result = lv1_destruct_logical_spe(spu_pdata(spu)->spe_id); BUG_ON(result); kfree(spu->pdata); spu->pdata = NULL; return 0; }
static int __init setup_interrupts(struct spu *spu) { int result; result = ps3_spe_irq_setup(PS3_BINDING_CPU_ANY, spu_pdata(spu)->spe_id, 0, &spu->irqs[0]); if (result) goto fail_alloc_0; result = ps3_spe_irq_setup(PS3_BINDING_CPU_ANY, spu_pdata(spu)->spe_id, 1, &spu->irqs[1]); if (result) goto fail_alloc_1; result = ps3_spe_irq_setup(PS3_BINDING_CPU_ANY, spu_pdata(spu)->spe_id, 2, &spu->irqs[2]); if (result) goto fail_alloc_2; return result; fail_alloc_2: ps3_spe_irq_destroy(spu->irqs[1]); fail_alloc_1: ps3_spe_irq_destroy(spu->irqs[0]); fail_alloc_0: spu->irqs[0] = spu->irqs[1] = spu->irqs[2] = NO_IRQ; return result; }
static int __init setup_areas(struct spu *spu) { struct table {char* name; unsigned long addr; unsigned long size;}; static const unsigned long shadow_flags = _PAGE_NO_CACHE | 3; spu_pdata(spu)->shadow = __ioremap(spu_pdata(spu)->shadow_addr, sizeof(struct spe_shadow), shadow_flags); if (!spu_pdata(spu)->shadow) { pr_debug("%s:%d: ioremap shadow failed\n", __func__, __LINE__); goto fail_ioremap; } <<<<<<< HEAD
static void spu_unmap(struct spu *spu) { iounmap(spu->priv2); iounmap(spu->problem); iounmap((__force u8 __iomem *)spu->local_store); iounmap(spu_pdata(spu)->shadow); }
static int __init ps3_create_spu(struct spu *spu, void *data) { int result; pr_debug("%s:%d spu_%d\n", __func__, __LINE__, spu->number); spu->pdata = kzalloc(sizeof(struct spu_pdata), GFP_KERNEL); if (!spu->pdata) { result = -ENOMEM; goto fail_malloc; } spu_pdata(spu)->resource_id = (unsigned long)data; /* Init cached reg values to HV defaults. */ spu_pdata(spu)->cache.sr1 = 0x33; result = construct_spu(spu); if (result) goto fail_construct; /* For now, just go ahead and enable it. */ result = enable_spu(spu); if (result) goto fail_enable; /* Make sure the spu is in SPE_EX_STATE_EXECUTED. */ /* need something better here!!! */ while (in_be64(&spu_pdata(spu)->shadow->spe_execution_status) != SPE_EX_STATE_EXECUTED) (void)0; return result; fail_enable: fail_construct: ps3_destroy_spu(spu); fail_malloc: return result; }
static int __init setup_areas(struct spu *spu) { struct table {char* name; unsigned long addr; unsigned long size;}; static const unsigned long shadow_flags = _PAGE_NO_CACHE | 3; spu_pdata(spu)->shadow = __ioremap(spu_pdata(spu)->shadow_addr, sizeof(struct spe_shadow), shadow_flags); if (!spu_pdata(spu)->shadow) { pr_debug("%s:%d: ioremap shadow failed\n", __func__, __LINE__); goto fail_ioremap; } spu->local_store = (__force void *)ioremap_flags(spu->local_store_phys, LS_SIZE, _PAGE_NO_CACHE); if (!spu->local_store) { pr_debug("%s:%d: ioremap local_store failed\n", __func__, __LINE__); goto fail_ioremap; } spu->problem = ioremap(spu->problem_phys, sizeof(struct spu_problem)); if (!spu->problem) { pr_debug("%s:%d: ioremap problem failed\n", __func__, __LINE__); goto fail_ioremap; } spu->priv2 = ioremap(spu_pdata(spu)->priv2_addr, sizeof(struct spu_priv2)); if (!spu->priv2) { pr_debug("%s:%d: ioremap priv2 failed\n", __func__, __LINE__); goto fail_ioremap; } dump_areas(spu_pdata(spu)->spe_id, spu_pdata(spu)->priv2_addr, spu->problem_phys, spu->local_store_phys, spu_pdata(spu)->shadow_addr); dump_areas(spu_pdata(spu)->spe_id, (unsigned long)spu->priv2, (unsigned long)spu->problem, (unsigned long)spu->local_store, (unsigned long)spu_pdata(spu)->shadow); return 0; fail_ioremap: spu_unmap(spu); return -ENOMEM; }
static int __init ps3_create_spu(struct spu *spu, void *data) { int result; pr_debug("%s:%d spu_%d\n", __func__, __LINE__, spu->number); spu->pdata = kzalloc(sizeof(struct spu_pdata), GFP_KERNEL); if (!spu->pdata) { result = -ENOMEM; goto fail_malloc; } spu_pdata(spu)->resource_id = (unsigned long)data; spu_pdata(spu)->cache.sr1 = 0x33; result = construct_spu(spu); if (result) goto fail_construct; result = enable_spu(spu); if (result) goto fail_enable; while (in_be64(&spu_pdata(spu)->shadow->spe_execution_status) != SPE_EX_STATE_EXECUTED) (void)0; return result; fail_enable: fail_construct: ps3_destroy_spu(spu); fail_malloc: return result; }
static int __init construct_spu(struct spu *spu) { int result; unsigned long unused; result = lv1_construct_logical_spe(PAGE_SHIFT, PAGE_SHIFT, PAGE_SHIFT, PAGE_SHIFT, PAGE_SHIFT, get_vas_id(), SPE_TYPE_LOGICAL, &spu_pdata(spu)->priv2_addr, &spu->problem_phys, &spu->local_store_phys, &unused, &spu_pdata(spu)->shadow_addr, &spu_pdata(spu)->spe_id); if (result) { pr_debug("%s:%d: lv1_construct_logical_spe failed: %s\n", __func__, __LINE__, ps3_result(result)); return result; } return result; }
inline u64 ps3_get_spe_id(void *arg) { return spu_pdata(arg)->spe_id; }