Commit 2512fd29 authored by Tony Lindgren's avatar Tony Lindgren

REMOVE OMAP LEGACY CODE: Remove dspgateway

This is moved into a dspgateway branch against the
mainline tree.
Signed-off-by: default avatarTony Lindgren <tony@atomide.com>
parent 3eae3ea7
......@@ -1329,7 +1329,6 @@ source "drivers/staging/Kconfig"
if ARCH_OMAP
source "drivers/cbus/Kconfig"
source "drivers/dsp/dspgateway/Kconfig"
endif
endmenu
......
......@@ -317,7 +317,6 @@ static inline pte_t pte_mkspecial(pte_t pte) { return pte; }
#define pmd_none(pmd) (!pmd_val(pmd))
#define pmd_present(pmd) (pmd_val(pmd))
#define pmd_bad(pmd) (pmd_val(pmd) & 2)
#define pmd_table(pmd) ((pmd_val(pmd) & PMD_TYPE_MASK) == PMD_TYPE_TABLE)
#define copy_pmd(pmdpd,pmdps) \
do { \
......
......@@ -14,10 +14,8 @@ obj-$(CONFIG_OMAP_32K_TIMER) += timer32k.o
obj-$(CONFIG_PM) += pm.o sleep.o
# DSP
obj-$(CONFIG_OMAP_MMU_FWK) += mmu_mach.o
obj-$(CONFIG_OMAP_MBOX_FWK) += mailbox_mach.o
mailbox_mach-objs := mailbox.o
mmu_mach-objs := mmu.o
led-y := leds.o
......
/*
* linux/arch/arm/mach-omap1/mmu.c
*
* Support for non-MPU OMAP1 MMUs.
*
* Copyright (C) 2002-2005 Nokia Corporation
*
* Written by Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
* and Paul Mundt <paul.mundt@nokia.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/types.h>
#include <linux/init.h>
#include <linux/rwsem.h>
#include <linux/device.h>
#include <linux/kernel.h>
#include <linux/mm.h>
#include <linux/interrupt.h>
#include <linux/err.h>
#include "mmu.h"
#include <asm/tlbflush.h>
#include <mach/dsp_common.h>
static void *dspvect_page;
#define DSP_INIT_PAGE 0xfff000
#define MMUFAULT_MASK (OMAP_MMU_FAULT_ST_PERM |\
OMAP_MMU_FAULT_ST_TLB_MISS |\
OMAP_MMU_FAULT_ST_TRANS)
static unsigned int get_cam_l_va_mask(u16 pgsz)
{
switch (pgsz) {
case OMAP_MMU_CAM_PAGESIZE_1MB:
return OMAP_MMU_CAM_L_VA_TAG_L1_MASK |
OMAP_MMU_CAM_L_VA_TAG_L2_MASK_1MB;
case OMAP_MMU_CAM_PAGESIZE_64KB:
return OMAP_MMU_CAM_L_VA_TAG_L1_MASK |
OMAP_MMU_CAM_L_VA_TAG_L2_MASK_64KB;
case OMAP_MMU_CAM_PAGESIZE_4KB:
return OMAP_MMU_CAM_L_VA_TAG_L1_MASK |
OMAP_MMU_CAM_L_VA_TAG_L2_MASK_4KB;
case OMAP_MMU_CAM_PAGESIZE_1KB:
return OMAP_MMU_CAM_L_VA_TAG_L1_MASK |
OMAP_MMU_CAM_L_VA_TAG_L2_MASK_1KB;
}
return 0;
}
#define get_cam_va_mask(pgsz) \
((u32)OMAP_MMU_CAM_H_VA_TAG_H_MASK << 22 | \
(u32)get_cam_l_va_mask(pgsz) << 6)
static int intmem_usecount;
/* for safety */
void dsp_mem_usecount_clear(void)
{
if (intmem_usecount != 0) {
printk(KERN_WARNING
"MMU: unbalanced memory request/release detected.\n"
" intmem_usecount is not zero at where "
"it should be! ... fixed to be zero.\n");
intmem_usecount = 0;
omap_dsp_release_mem();
}
}
EXPORT_SYMBOL_GPL(dsp_mem_usecount_clear);
void omap_mmu_itack(struct omap_mmu *mmu)
{
omap_mmu_write_reg(mmu, OMAP_MMU_IT_ACK_IT_ACK, OMAP_MMU_IT_ACK);
}
EXPORT_SYMBOL(omap_mmu_itack);
static int omap1_mmu_mem_enable(struct omap_mmu *mmu, void *addr)
{
int ret = 0;
if (omap_mmu_internal_memory(mmu, addr)) {
if (intmem_usecount++ == 0)
ret = omap_dsp_request_mem();
}
return ret;
}
static int omap1_mmu_mem_disable(struct omap_mmu *mmu, void *addr)
{
int ret = 0;
if (omap_mmu_internal_memory(mmu, addr)) {
if (--intmem_usecount == 0)
omap_dsp_release_mem();
} else
ret = -EIO;
return ret;
}
static inline void
omap1_mmu_read_tlb(struct omap_mmu *mmu, struct cam_ram_regset *cr)
{
/* read a TLB entry */
omap_mmu_write_reg(mmu, OMAP_MMU_LD_TLB_RD, OMAP_MMU_LD_TLB);
cr->cam_h = omap_mmu_read_reg(mmu, OMAP_MMU_READ_CAM_H);
cr->cam_l = omap_mmu_read_reg(mmu, OMAP_MMU_READ_CAM_L);
cr->ram_h = omap_mmu_read_reg(mmu, OMAP_MMU_READ_RAM_H);
cr->ram_l = omap_mmu_read_reg(mmu, OMAP_MMU_READ_RAM_L);
}
static inline void
omap1_mmu_load_tlb(struct omap_mmu *mmu, struct cam_ram_regset *cr)
{
/* Set the CAM and RAM entries */
omap_mmu_write_reg(mmu, cr->cam_h, OMAP_MMU_CAM_H);
omap_mmu_write_reg(mmu, cr->cam_l, OMAP_MMU_CAM_L);
omap_mmu_write_reg(mmu, cr->ram_h, OMAP_MMU_RAM_H);
omap_mmu_write_reg(mmu, cr->ram_l, OMAP_MMU_RAM_L);
}
static ssize_t omap1_mmu_show(struct omap_mmu *mmu, char *buf,
struct omap_mmu_tlb_lock *tlb_lock)
{
int i, len;
len = sprintf(buf, "P: preserved, V: valid\n"
"ety P V size cam_va ram_pa ap\n");
/* 00: P V 4KB 0x300000 0x10171800 FA */
for (i = 0; i < mmu->nr_tlb_entries; i++) {
struct omap_mmu_tlb_entry ent;
struct cam_ram_regset cr;
struct omap_mmu_tlb_lock entry_lock;
char *pgsz_str, *ap_str;
/* read a TLB entry */
entry_lock.base = tlb_lock->base;
entry_lock.victim = i;
omap_mmu_read_tlb(mmu, &entry_lock, &cr);
ent.pgsz = cr.cam_l & OMAP_MMU_CAM_PAGESIZE_MASK;
ent.prsvd = cr.cam_l & OMAP_MMU_CAM_P;
ent.valid = cr.cam_l & OMAP_MMU_CAM_V;
ent.ap = cr.ram_l & OMAP_MMU_RAM_L_AP_MASK;
ent.va = (u32)(cr.cam_h & OMAP_MMU_CAM_H_VA_TAG_H_MASK) << 22 |
(u32)(cr.cam_l & get_cam_l_va_mask(ent.pgsz)) << 6;
ent.pa = (unsigned long)cr.ram_h << 16 |
(cr.ram_l & OMAP_MMU_RAM_L_RAM_LSB_MASK);
pgsz_str = (ent.pgsz == OMAP_MMU_CAM_PAGESIZE_1MB) ? " 1MB":
(ent.pgsz == OMAP_MMU_CAM_PAGESIZE_64KB) ? "64KB":
(ent.pgsz == OMAP_MMU_CAM_PAGESIZE_4KB) ? " 4KB":
(ent.pgsz == OMAP_MMU_CAM_PAGESIZE_1KB) ? " 1KB":
" ???";
ap_str = (ent.ap == OMAP_MMU_RAM_L_AP_RO) ? "RO":
(ent.ap == OMAP_MMU_RAM_L_AP_FA) ? "FA":
(ent.ap == OMAP_MMU_RAM_L_AP_NA) ? "NA":
"??";
if (i == tlb_lock->base)
len += sprintf(buf + len, "lock base = %d\n",
tlb_lock->base);
if (i == tlb_lock->victim)
len += sprintf(buf + len, "victim = %d\n",
tlb_lock->victim);
len += sprintf(buf + len,
/* 00: P V 4KB 0x300000 0x10171800 FA */
"%02d: %c %c %s 0x%06lx 0x%08lx %s\n",
i,
ent.prsvd ? 'P' : ' ',
ent.valid ? 'V' : ' ',
pgsz_str, ent.va, ent.pa, ap_str);
}
return len;
}
static int exmap_setup_preserved_entries(struct omap_mmu *mmu)
{
int n = 0;
exmap_setup_preserved_mem_page(mmu, dspvect_page, DSP_INIT_PAGE, n++);
return n;
}
static void exmap_clear_preserved_entries(struct omap_mmu *mmu)
{
exmap_clear_mem_page(mmu, DSP_INIT_PAGE);
}
static int omap1_mmu_startup(struct omap_mmu *mmu)
{
dspvect_page = (void *)__get_dma_pages(GFP_KERNEL, 0);
if (dspvect_page == NULL) {
dev_err(mmu->dev, "MMU %s: failed to allocate memory "
"for vector table\n", mmu->name);
return -ENOMEM;
}
mmu->nr_exmap_preserved = exmap_setup_preserved_entries(mmu);
return 0;
}
static void omap1_mmu_shutdown(struct omap_mmu *mmu)
{
exmap_clear_preserved_entries(mmu);
if (dspvect_page != NULL) {
unsigned long virt;
down_read(&mmu->exmap_sem);
virt = (unsigned long)omap_mmu_to_virt(mmu, DSP_INIT_PAGE);
flush_tlb_kernel_range(virt, virt + PAGE_SIZE);
free_page((unsigned long)dspvect_page);
dspvect_page = NULL;
up_read(&mmu->exmap_sem);
}
}
static inline unsigned long omap1_mmu_cam_va(struct cam_ram_regset *cr)
{
unsigned int page_size = cr->cam_l & OMAP_MMU_CAM_PAGESIZE_MASK;
return (u32)(cr->cam_h & OMAP_MMU_CAM_H_VA_TAG_H_MASK) << 22 |
(u32)(cr->cam_l & get_cam_l_va_mask(page_size)) << 6;
}
static struct cam_ram_regset *
omap1_mmu_cam_ram_alloc(struct omap_mmu *mmu, struct omap_mmu_tlb_entry *entry)
{
struct cam_ram_regset *cr;
if (entry->va & ~(get_cam_va_mask(entry->pgsz))) {
dev_err(mmu->dev, "MMU %s: mapping vadr (0x%06lx) is not on"
" an aligned boundary\n", mmu->name, entry->va);
return ERR_PTR(-EINVAL);
}
cr = kmalloc(sizeof(struct cam_ram_regset), GFP_KERNEL);
cr->cam_h = entry->va >> 22;
cr->cam_l = (entry->va >> 6 & get_cam_l_va_mask(entry->pgsz)) |
entry->prsvd | entry->pgsz;
cr->ram_h = entry->pa >> 16;
cr->ram_l = (entry->pa & OMAP_MMU_RAM_L_RAM_LSB_MASK) | entry->ap;
return cr;
}
static inline int omap1_mmu_cam_ram_valid(struct cam_ram_regset *cr)
{
return cr->cam_l & OMAP_MMU_CAM_V;
}
static void omap1_mmu_interrupt(struct omap_mmu *mmu)
{
unsigned long status;
unsigned long adh, adl;
unsigned long dp;
unsigned long va;
status = omap_mmu_read_reg(mmu, OMAP_MMU_FAULT_ST);
adh = omap_mmu_read_reg(mmu, OMAP_MMU_FAULT_AD_H);
adl = omap_mmu_read_reg(mmu, OMAP_MMU_FAULT_AD_L);
dp = adh & OMAP_MMU_FAULT_AD_H_DP;
va = (((adh & OMAP_MMU_FAULT_AD_H_ADR_MASK) << 16) | adl);
/* if the fault is masked, nothing to do */
if ((status & MMUFAULT_MASK) == 0) {
pr_debug("MMU interrupt, but ignoring.\n");
/*
* note: in OMAP1710,
* when CACHE + DMA domain gets out of idle in DSP,
* MMU interrupt occurs but MMU_FAULT_ST is not set.
* in this case, we just ignore the interrupt.
*/
if (status) {
pr_debug("%s%s%s%s\n",
(status & OMAP_MMU_FAULT_ST_PREF)?
" (prefetch err)" : "",
(status & OMAP_MMU_FAULT_ST_PERM)?
" (permission fault)" : "",
(status & OMAP_MMU_FAULT_ST_TLB_MISS)?
" (TLB miss)" : "",
(status & OMAP_MMU_FAULT_ST_TRANS) ?
" (translation fault)": "");
pr_debug("fault address = %#08lx\n", va);
}
enable_irq(mmu->irq);
return;
}
pr_info("%s%s%s%s\n",
(status & OMAP_MMU_FAULT_ST_PREF)?
(MMUFAULT_MASK & OMAP_MMU_FAULT_ST_PREF)?
" prefetch err":
" (prefetch err)":
"",
(status & OMAP_MMU_FAULT_ST_PERM)?
(MMUFAULT_MASK & OMAP_MMU_FAULT_ST_PERM)?
" permission fault":
" (permission fault)":
"",
(status & OMAP_MMU_FAULT_ST_TLB_MISS)?
(MMUFAULT_MASK & OMAP_MMU_FAULT_ST_TLB_MISS)?
" TLB miss":
" (TLB miss)":
"",
(status & OMAP_MMU_FAULT_ST_TRANS)?
(MMUFAULT_MASK & OMAP_MMU_FAULT_ST_TRANS)?
" translation fault":
" (translation fault)":
"");
pr_info("fault address = %#08lx\n", va);
mmu->fault_address = va;
schedule_work(&mmu->irq_work);
}
static pgprot_t omap1_mmu_pte_get_attr(struct omap_mmu_tlb_entry *entry)
{
/* 4KB AP position as default */
u32 attr = entry->ap >> 4;
attr <<= ((entry->pgsz == OMAP_MMU_CAM_PAGESIZE_1MB) ? 6:0);
return attr;
}
struct omap_mmu_ops omap1_mmu_ops = {
.startup = omap1_mmu_startup,
.shutdown = omap1_mmu_shutdown,
.mem_enable = omap1_mmu_mem_enable,
.mem_disable = omap1_mmu_mem_disable,
.read_tlb = omap1_mmu_read_tlb,
.load_tlb = omap1_mmu_load_tlb,
.show = omap1_mmu_show,
.cam_va = omap1_mmu_cam_va,
.cam_ram_alloc = omap1_mmu_cam_ram_alloc,
.cam_ram_valid = omap1_mmu_cam_ram_valid,
.interrupt = omap1_mmu_interrupt,
.pte_get_attr = omap1_mmu_pte_get_attr,
};
EXPORT_SYMBOL_GPL(omap1_mmu_ops);
#ifndef __MACH_OMAP1_MMU_H
#define __MACH_OMAP1_MMU_H
#include <linux/io.h>
#include <mach/mmu.h>
#define MMU_LOCK_BASE_MASK (0x3f << 10)
#define MMU_LOCK_VICTIM_MASK (0x3f << 4)
#define OMAP_MMU_PREFETCH 0x00
#define OMAP_MMU_WALKING_ST 0x04
#define OMAP_MMU_CNTL 0x08
#define OMAP_MMU_FAULT_AD_H 0x0c
#define OMAP_MMU_FAULT_AD_L 0x10
#define OMAP_MMU_FAULT_ST 0x14
#define OMAP_MMU_IT_ACK 0x18
#define OMAP_MMU_TTB_H 0x1c
#define OMAP_MMU_TTB_L 0x20
#define OMAP_MMU_LOCK 0x24
#define OMAP_MMU_LD_TLB 0x28
#define OMAP_MMU_CAM_H 0x2c
#define OMAP_MMU_CAM_L 0x30
#define OMAP_MMU_RAM_H 0x34
#define OMAP_MMU_RAM_L 0x38
#define OMAP_MMU_GFLUSH 0x3c
#define OMAP_MMU_FLUSH_ENTRY 0x40
#define OMAP_MMU_READ_CAM_H 0x44
#define OMAP_MMU_READ_CAM_L 0x48
#define OMAP_MMU_READ_RAM_H 0x4c
#define OMAP_MMU_READ_RAM_L 0x50
#define OMAP_MMU_CNTL_BURST_16MNGT_EN 0x0020
#define OMAP_MMU_CNTL_WTL_EN 0x0004
#define OMAP_MMU_CNTL_MMU_EN 0x0002
#define OMAP_MMU_CNTL_RESET_SW 0x0001
#define OMAP_MMU_FAULT_AD_H_DP 0x0100
#define OMAP_MMU_FAULT_AD_H_ADR_MASK 0x00ff
#define OMAP_MMU_FAULT_ST_PREF 0x0008
#define OMAP_MMU_FAULT_ST_PERM 0x0004
#define OMAP_MMU_FAULT_ST_TLB_MISS 0x0002
#define OMAP_MMU_FAULT_ST_TRANS 0x0001
#define OMAP_MMU_IT_ACK_IT_ACK 0x0001
#define OMAP_MMU_CAM_H_VA_TAG_H_MASK 0x0003
#define OMAP_MMU_CAM_L_VA_TAG_L1_MASK 0xc000
#define OMAP_MMU_CAM_L_VA_TAG_L2_MASK_1MB 0x0000
#define OMAP_MMU_CAM_L_VA_TAG_L2_MASK_64KB 0x3c00
#define OMAP_MMU_CAM_L_VA_TAG_L2_MASK_4KB 0x3fc0
#define OMAP_MMU_CAM_L_VA_TAG_L2_MASK_1KB 0x3ff0
#define OMAP_MMU_CAM_L_P 0x0008
#define OMAP_MMU_CAM_L_V 0x0004
#define OMAP_MMU_CAM_L_PAGESIZE_MASK 0x0003
#define OMAP_MMU_CAM_L_PAGESIZE_1MB 0x0000
#define OMAP_MMU_CAM_L_PAGESIZE_64KB 0x0001
#define OMAP_MMU_CAM_L_PAGESIZE_4KB 0x0002
#define OMAP_MMU_CAM_L_PAGESIZE_1KB 0x0003
#define OMAP_MMU_CAM_P OMAP_MMU_CAM_L_P
#define OMAP_MMU_CAM_V OMAP_MMU_CAM_L_V
#define OMAP_MMU_CAM_PAGESIZE_MASK OMAP_MMU_CAM_L_PAGESIZE_MASK
#define OMAP_MMU_CAM_PAGESIZE_1MB OMAP_MMU_CAM_L_PAGESIZE_1MB
#define OMAP_MMU_CAM_PAGESIZE_64KB OMAP_MMU_CAM_L_PAGESIZE_64KB
#define OMAP_MMU_CAM_PAGESIZE_4KB OMAP_MMU_CAM_L_PAGESIZE_4KB
#define OMAP_MMU_CAM_PAGESIZE_1KB OMAP_MMU_CAM_L_PAGESIZE_1KB
#define OMAP_MMU_CAM_PAGESIZE_16MB -1 /* unused in omap1 */
#define OMAP_MMU_RAM_L_RAM_LSB_MASK 0xfc00
#define OMAP_MMU_RAM_L_AP_MASK 0x0300
#define OMAP_MMU_RAM_L_AP_NA 0x0000
#define OMAP_MMU_RAM_L_AP_RO 0x0200
#define OMAP_MMU_RAM_L_AP_FA 0x0300
#define OMAP_MMU_LD_TLB_RD 0x0002
#define INIT_TLB_ENTRY(ent, v, p, ps) \
do { \
(ent)->va = (v); \
(ent)->pa = (p); \
(ent)->pgsz = (ps); \
(ent)->prsvd = 0; \
(ent)->ap = OMAP_MMU_RAM_L_AP_FA; \
(ent)->tlb = 1; \
} while (0)
#define INIT_TLB_ENTRY_4KB_PRESERVED(ent, v, p) \
do { \
(ent)->va = (v); \
(ent)->pa = (p); \
(ent)->pgsz = OMAP_MMU_CAM_PAGESIZE_4KB; \
(ent)->prsvd = OMAP_MMU_CAM_P; \
(ent)->ap = OMAP_MMU_RAM_L_AP_FA; \
} while (0)
struct omap_mmu_tlb_entry {
unsigned long va;
unsigned long pa;
unsigned int pgsz, prsvd, valid;
u16 ap;
unsigned int tlb;
};
static inline unsigned short
omap_mmu_read_reg(struct omap_mmu *mmu, unsigned long reg)
{
return __raw_readw(mmu->base + reg);
}
static inline void omap_mmu_write_reg(struct omap_mmu *mmu,
unsigned short val, unsigned long reg)
{
__raw_writew(val, mmu->base + reg);
}
#endif /* __MACH_OMAP1_MMU_H */
......@@ -35,10 +35,8 @@ obj-$(CONFIG_ARCH_OMAP2) += clock24xx.o
obj-$(CONFIG_ARCH_OMAP3) += clock34xx.o
# DSP
obj-$(CONFIG_OMAP_MMU_FWK) += mmu_mach.o
obj-$(CONFIG_OMAP_MBOX_FWK) += mailbox_mach.o
mailbox_mach-objs := mailbox.o
mmu_mach-objs := mmu.o
# Specific board support
obj-$(CONFIG_MACH_OMAP_GENERIC) += board-generic.o
......
/*
* linux/arch/arm/mach-omap2/mmu.c
*
* Support for non-MPU OMAP2 MMUs.
*
* Copyright (C) 2002-2007 Nokia Corporation
*
* Written by Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
* and Paul Mundt <paul.mundt@nokia.com>
*
* TWL support: Hiroshi DOYU <Hiroshi.DOYU@nokia.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/types.h>
#include <linux/init.h>
#include <linux/rwsem.h>
#include <linux/device.h>
#include <linux/mm.h>
#include <linux/interrupt.h>
#include <linux/err.h>
#include <linux/io.h>
#include "mmu.h"
#include <mach/mmu.h>
#include <asm/tlbflush.h>
#include <asm/sizes.h>
static void *dspvect_page;
#define DSP_INIT_PAGE 0xfff000
static inline void
omap2_mmu_read_tlb(struct omap_mmu *mmu, struct cam_ram_regset *cr)
{
cr->cam = omap_mmu_read_reg(mmu, OMAP_MMU_READ_CAM);
cr->ram = omap_mmu_read_reg(mmu, OMAP_MMU_READ_RAM);
}
static inline void
omap2_mmu_load_tlb(struct omap_mmu *mmu, struct cam_ram_regset *cr)
{
/* Set the CAM and RAM entries */
omap_mmu_write_reg(mmu, cr->cam | OMAP_MMU_CAM_V, OMAP_MMU_CAM);
omap_mmu_write_reg(mmu, cr->ram, OMAP_MMU_RAM);
}
static void exmap_setup_iomap_page(struct omap_mmu *mmu, unsigned long phys,
unsigned long dsp_io_adr, int index)
{
unsigned long dspadr;
void *virt;
struct omap_mmu_tlb_entry tlb_ent;
dspadr = (IOMAP_VAL << 18) + (dsp_io_adr << 1);
virt = omap_mmu_to_virt(mmu, dspadr);
exmap_set_armmmu(mmu, (unsigned long)virt, phys, PAGE_SIZE);
INIT_EXMAP_TBL_ENTRY_4KB_PRESERVED(mmu->exmap_tbl + index, NULL, virt);
INIT_TLB_ENTRY_4KB_ES32_PRESERVED(&tlb_ent, dspadr, phys);
omap_mmu_load_pte_entry(mmu, &tlb_ent);
}
static void exmap_clear_iomap_page(struct omap_mmu *mmu,
unsigned long dsp_io_adr)
{
unsigned long dspadr;
void *virt;
dspadr = (IOMAP_VAL << 18) + (dsp_io_adr << 1);
virt = omap_mmu_to_virt(mmu, dspadr);
exmap_clear_armmmu(mmu, (unsigned long)virt, PAGE_SIZE);
/* DSP MMU is shutting down. not handled here. */
}
#define OMAP24XX_MAILBOX_BASE (L4_24XX_BASE + 0x94000)
#define OMAP2420_GPT5_BASE (L4_24XX_BASE + 0x7c000)
#define OMAP2420_GPT6_BASE (L4_24XX_BASE + 0x7e000)
#define OMAP2420_GPT7_BASE (L4_24XX_BASE + 0x80000)
#define OMAP2420_GPT8_BASE (L4_24XX_BASE + 0x82000)
#define OMAP24XX_EAC_BASE (L4_24XX_BASE + 0x90000)
#define OMAP24XX_STI_BASE (L4_24XX_BASE + 0x68000)
#define OMAP24XX_STI_CH_BASE (L4_24XX_BASE + 0x0c000000)
static int exmap_setup_preserved_entries(struct omap_mmu *mmu)
{
int i, n = 0;
exmap_setup_preserved_mem_page(mmu, dspvect_page, DSP_INIT_PAGE, n++);
/* REVISIT: This will need to be revisited for 3430 */
exmap_setup_iomap_page(mmu, OMAP2_PRCM_BASE, 0x7000, n++);
exmap_setup_iomap_page(mmu, OMAP24XX_MAILBOX_BASE, 0x11000, n++);
if (cpu_is_omap2420()) {
exmap_setup_iomap_page(mmu, OMAP2420_GPT5_BASE, 0xe000, n++);
exmap_setup_iomap_page(mmu, OMAP2420_GPT6_BASE, 0xe800, n++);
exmap_setup_iomap_page(mmu, OMAP2420_GPT7_BASE, 0xf000, n++);
exmap_setup_iomap_page(mmu, OMAP2420_GPT8_BASE, 0xf800, n++);
exmap_setup_iomap_page(mmu, OMAP24XX_EAC_BASE, 0x10000, n++);
exmap_setup_iomap_page(mmu, OMAP24XX_STI_BASE, 0xc800, n++);
for (i = 0; i < 5; i++)
exmap_setup_preserved_mem_page(mmu,
__va(OMAP24XX_STI_CH_BASE + i*SZ_4K),
0xfb0000 + i*SZ_4K, n++);
}
return n;
}
static void exmap_clear_preserved_entries(struct omap_mmu *mmu)
{
int i;
exmap_clear_iomap_page(mmu, 0x7000); /* PRCM registers */
exmap_clear_iomap_page(mmu, 0x11000); /* MAILBOX registers */
if (cpu_is_omap2420()) {
exmap_clear_iomap_page(mmu, 0xe000); /* GPT5 */
exmap_clear_iomap_page(mmu, 0xe800); /* GPT6 */
exmap_clear_iomap_page(mmu, 0xf000); /* GPT7 */
exmap_clear_iomap_page(mmu, 0xf800); /* GPT8 */
exmap_clear_iomap_page(mmu, 0x10000); /* EAC */
exmap_clear_iomap_page(mmu, 0xc800); /* STI */
for (i = 0; i < 5; i++) /* STI CH */
exmap_clear_mem_page(mmu, 0xfb0000 + i*SZ_4K);
}
exmap_clear_mem_page(mmu, DSP_INIT_PAGE);
}
#define MMU_IRQ_MASK \
(OMAP_MMU_IRQ_MULTIHITFAULT | \
OMAP_MMU_IRQ_TABLEWALKFAULT | \
OMAP_MMU_IRQ_EMUMISS | \
OMAP_MMU_IRQ_TRANSLATIONFAULT)
static int omap2_mmu_startup(struct omap_mmu *mmu)
{
u32 rev = omap_mmu_read_reg(mmu, OMAP_MMU_REVISION);
pr_info("MMU: OMAP %s MMU initialized (HW v%d.%d)\n", mmu->name,
(rev >> 4) & 0xf, rev & 0xf);
dspvect_page = (void *)__get_dma_pages(GFP_KERNEL, 0);
if (dspvect_page == NULL) {
dev_err(mmu->dev, "MMU %s: failed to allocate memory "
"for vector table\n", mmu->name);
return -ENOMEM;
}
mmu->nr_exmap_preserved = exmap_setup_preserved_entries(mmu);
omap_mmu_write_reg(mmu, MMU_IRQ_MASK, OMAP_MMU_IRQENABLE);
return 0;
}
static void omap2_mmu_shutdown(struct omap_mmu *mmu)
{
exmap_clear_preserved_entries(mmu);
if (dspvect_page != NULL) {
unsigned long virt;
down_read(&mmu->exmap_sem);
virt = (unsigned long)omap_mmu_to_virt(mmu, DSP_INIT_PAGE);
flush_tlb_kernel_range(virt, virt + PAGE_SIZE);
free_page((unsigned long)dspvect_page);
dspvect_page = NULL;
up_read(&mmu->exmap_sem);
}
}
static ssize_t omap2_mmu_show(struct omap_mmu *mmu, char *buf,
struct omap_mmu_tlb_lock *tlb_lock)
{
int i, len;
len = sprintf(buf, "P: preserved, V: valid\n"
"B: big endian, L:little endian, "
"M: mixed page attribute\n"
"ety P V size cam_va ram_pa E ES M\n");
/* 00: P V 4KB 0x300000 0x10171800 B 16 M */
for (i = 0; i < mmu->nr_tlb_entries; i++) {
struct omap_mmu_tlb_entry ent;
struct cam_ram_regset cr;
struct omap_mmu_tlb_lock entry_lock;
char *pgsz_str, *elsz_str;
/* read a TLB entry */
entry_lock.base = tlb_lock->base;
entry_lock.victim = i;
omap_mmu_read_tlb(mmu, &entry_lock, &cr);
ent.pgsz = cr.cam & OMAP_MMU_CAM_PAGESIZE_MASK;
ent.prsvd = cr.cam & OMAP_MMU_CAM_P;
ent.valid = cr.cam & OMAP_MMU_CAM_V;
ent.va = cr.cam & OMAP_MMU_CAM_VATAG_MASK;
ent.endian = cr.ram & OMAP_MMU_RAM_ENDIANNESS;
ent.elsz = cr.ram & OMAP_MMU_RAM_ELEMENTSIZE_MASK;
ent.pa = cr.ram & OMAP_MMU_RAM_PADDR_MASK;
ent.mixed = cr.ram & OMAP_MMU_RAM_MIXED;
pgsz_str = (ent.pgsz == OMAP_MMU_CAM_PAGESIZE_16MB) ? "64MB":
(ent.pgsz == OMAP_MMU_CAM_PAGESIZE_1MB) ? " 1MB":
(ent.pgsz == OMAP_MMU_CAM_PAGESIZE_64KB) ? "64KB":
(ent.pgsz == OMAP_MMU_CAM_PAGESIZE_4KB) ? " 4KB":
" ???";
elsz_str = (ent.elsz == OMAP_MMU_RAM_ELEMENTSIZE_8) ? " 8":
(ent.elsz == OMAP_MMU_RAM_ELEMENTSIZE_16) ? "16":
(ent.elsz == OMAP_MMU_RAM_ELEMENTSIZE_32) ? "32":
"??";
if (i == tlb_lock->base)
len += sprintf(buf + len, "lock base = %d\n",
tlb_lock->base);
if (i == tlb_lock->victim)
len += sprintf(buf + len, "victim = %d\n",
tlb_lock->victim);
len += sprintf(buf + len,
/* 00: P V 4KB 0x300000 0x10171800 B 16 M */
"%02d: %c %c %s 0x%06lx 0x%08lx %c %s %c\n",
i,
ent.prsvd ? 'P' : ' ',
ent.valid ? 'V' : ' ',
pgsz_str, ent.va, ent.pa,
ent.endian ? 'B' : 'L',
elsz_str,
ent.mixed ? 'M' : ' ');
}
return len;
}
#define get_cam_va_mask(pgsz) \
(((pgsz) == OMAP_MMU_CAM_PAGESIZE_16MB) ? 0xff000000 : \
((pgsz) == OMAP_MMU_CAM_PAGESIZE_1MB) ? 0xfff00000 : \
((pgsz) == OMAP_MMU_CAM_PAGESIZE_64KB) ? 0xffff0000 : \
((pgsz) == OMAP_MMU_CAM_PAGESIZE_4KB) ? 0xfffff000 : 0)
static inline unsigned long omap2_mmu_cam_va(struct cam_ram_regset *cr)
{
unsigned int page_size = cr->cam & OMAP_MMU_CAM_PAGESIZE_MASK;
unsigned int mask = get_cam_va_mask(cr->cam & page_size);
return cr->cam & mask;
}
static struct cam_ram_regset *
omap2_mmu_cam_ram_alloc(struct omap_mmu *mmu, struct omap_mmu_tlb_entry *entry)
{
struct cam_ram_regset *cr;
if (entry->va & ~(get_cam_va_mask(entry->pgsz))) {
dev_err(mmu->dev, "MMU %s: mapping vadr (0x%06lx) is not on"
" an aligned boundary\n", mmu->name, entry->va);
return ERR_PTR(-EINVAL);
}
cr = kmalloc(sizeof(struct cam_ram_regset), GFP_KERNEL);
cr->cam = (entry->va & OMAP_MMU_CAM_VATAG_MASK) |
entry->prsvd | entry->pgsz;
cr->ram = entry->pa | entry->endian | entry->elsz;
return cr;
}
static inline int omap2_mmu_cam_ram_valid(struct cam_ram_regset *cr)
{
return cr->cam & OMAP_MMU_CAM_V;
}
static void omap2_mmu_interrupt(struct omap_mmu *mmu)
{
unsigned long status, va;
status = MMU_IRQ_MASK & omap_mmu_read_reg(mmu, OMAP_MMU_IRQSTATUS);
va = omap_mmu_read_reg(mmu, OMAP_MMU_FAULT_AD);
pr_info("%s\n", (status & OMAP_MMU_IRQ_MULTIHITFAULT)?
"multi hit":"");
pr_info("%s\n", (status & OMAP_MMU_IRQ_TABLEWALKFAULT)?
"table walk fault":"");
pr_info("%s\n", (status & OMAP_MMU_IRQ_EMUMISS)?
"EMU miss":"");
pr_info("%s\n", (status & OMAP_MMU_IRQ_TRANSLATIONFAULT)?
"translation fault":"");
pr_info("%s\n", (status & OMAP_MMU_IRQ_TLBMISS)?
"TLB miss":"");
pr_info("fault address = %#08lx\n", va);
omap_mmu_disable(mmu);
omap_mmu_write_reg(mmu, status, OMAP_MMU_IRQSTATUS);
mmu->fault_address = va;
schedule_work(&mmu->irq_work);
}
static pgprot_t omap2_mmu_pte_get_attr(struct omap_mmu_tlb_entry *entry)
{
u32 attr;
attr = entry->mixed << 5;
attr |= entry->endian;
attr |= entry->elsz >> 3;
attr <<= ((entry->pgsz & OMAP_MMU_CAM_PAGESIZE_4KB) ? 0:6);
return attr;
}
struct omap_mmu_ops omap2_mmu_ops = {
.startup = omap2_mmu_startup,
.shutdown = omap2_mmu_shutdown,
.read_tlb = omap2_mmu_read_tlb,
.load_tlb = omap2_mmu_load_tlb,
.show = omap2_mmu_show,
.cam_va = omap2_mmu_cam_va,
.cam_ram_alloc = omap2_mmu_cam_ram_alloc,
.cam_ram_valid = omap2_mmu_cam_ram_valid,
.interrupt = omap2_mmu_interrupt,
.pte_get_attr = omap2_mmu_pte_get_attr,
};
EXPORT_SYMBOL_GPL(omap2_mmu_ops);
MODULE_LICENSE("GPL");
#ifndef __MACH_OMAP2_MMU_H
#define __MACH_OMAP2_MMU_H
#include <linux/io.h>
#include <mach/mmu.h>
#define MMU_LOCK_BASE_MASK (0x1f << 10)
#define MMU_LOCK_VICTIM_MASK (0x1f << 4)
#define OMAP_MMU_REVISION 0x00
#define OMAP_MMU_SYSCONFIG 0x10
#define OMAP_MMU_SYSSTATUS 0x14
#define OMAP_MMU_IRQSTATUS 0x18
#define OMAP_MMU_IRQENABLE 0x1c
#define OMAP_MMU_WALKING_ST 0x40
#define OMAP_MMU_CNTL 0x44
#define OMAP_MMU_FAULT_AD 0x48
#define OMAP_MMU_TTB 0x4c
#define OMAP_MMU_LOCK 0x50
#define OMAP_MMU_LD_TLB 0x54
#define OMAP_MMU_CAM 0x58
#define OMAP_MMU_RAM 0x5c
#define OMAP_MMU_GFLUSH 0x60
#define OMAP_MMU_FLUSH_ENTRY 0x64
#define OMAP_MMU_READ_CAM 0x68
#define OMAP_MMU_READ_RAM 0x6c
#define OMAP_MMU_EMU_FAULT_AD 0x70
#define OMAP_MMU_CNTL_BURST_16MNGT_EN 0x0020
#define OMAP_MMU_CNTL_WTL_EN 0x0004
#define OMAP_MMU_CNTL_MMU_EN 0x0002
#define OMAP_MMU_CNTL_RESET_SW 0x0001
#define OMAP_MMU_IRQ_MULTIHITFAULT 0x00000010
#define OMAP_MMU_IRQ_TABLEWALKFAULT 0x00000008
#define OMAP_MMU_IRQ_EMUMISS 0x00000004
#define OMAP_MMU_IRQ_TRANSLATIONFAULT 0x00000002
#define OMAP_MMU_IRQ_TLBMISS 0x00000001
#define OMAP_MMU_CAM_VATAG_MASK 0xfffff000
#define OMAP_MMU_CAM_P 0x00000008
#define OMAP_MMU_CAM_V 0x00000004
#define OMAP_MMU_CAM_PAGESIZE_MASK 0x00000003
#define OMAP_MMU_CAM_PAGESIZE_1MB 0x00000000
#define OMAP_MMU_CAM_PAGESIZE_64KB 0x00000001
#define OMAP_MMU_CAM_PAGESIZE_4KB 0x00000002
#define OMAP_MMU_CAM_PAGESIZE_16MB 0x00000003
#define OMAP_MMU_RAM_PADDR_MASK 0xfffff000
#define OMAP_MMU_RAM_ENDIANNESS 0x00000200
#define OMAP_MMU_RAM_ENDIANNESS_BIG 0x00000200
#define OMAP_MMU_RAM_ENDIANNESS_LITTLE 0x00000000
#define OMAP_MMU_RAM_ELEMENTSIZE_MASK 0x00000180
#define OMAP_MMU_RAM_ELEMENTSIZE_8 0x00000000
#define OMAP_MMU_RAM_ELEMENTSIZE_16 0x00000080
#define OMAP_MMU_RAM_ELEMENTSIZE_32 0x00000100
#define OMAP_MMU_RAM_ELEMENTSIZE_NONE 0x00000180
#define OMAP_MMU_RAM_MIXED 0x00000040
#define IOMAP_VAL 0x3f
#define INIT_TLB_ENTRY(ent, v, p, ps) \
do { \
(ent)->va = (v); \
(ent)->pa = (p); \
(ent)->pgsz = (ps); \
(ent)->prsvd = 0; \
(ent)->endian = OMAP_MMU_RAM_ENDIANNESS_LITTLE; \
(ent)->elsz = OMAP_MMU_RAM_ELEMENTSIZE_16; \
(ent)->mixed = 0; \
(ent)->tlb = 1; \
} while (0)
#define INIT_TLB_ENTRY_4KB_PRESERVED(ent, v, p) \
do { \
(ent)->va = (v); \
(ent)->pa = (p); \
(ent)->pgsz = OMAP_MMU_CAM_PAGESIZE_4KB; \
(ent)->prsvd = OMAP_MMU_CAM_P; \
(ent)->endian = OMAP_MMU_RAM_ENDIANNESS_LITTLE; \
(ent)->elsz = OMAP_MMU_RAM_ELEMENTSIZE_16; \
(ent)->mixed = 0; \
} while (0)
#define INIT_TLB_ENTRY_4KB_ES32_PRESERVED(ent, v, p) \
do { \
(ent)->va = (v); \
(ent)->pa = (p); \
(ent)->pgsz = OMAP_MMU_CAM_PAGESIZE_4KB; \
(ent)->prsvd = OMAP_MMU_CAM_P; \
(ent)->endian = OMAP_MMU_RAM_ENDIANNESS_LITTLE; \
(ent)->elsz = OMAP_MMU_RAM_ELEMENTSIZE_32; \
(ent)->mixed = 0; \
} while (0)
struct omap_mmu_tlb_entry {
unsigned long va;
unsigned long pa;
unsigned int pgsz, prsvd, valid;
u32 endian, elsz, mixed;
unsigned int tlb;
};
static inline unsigned long
omap_mmu_read_reg(struct omap_mmu *mmu, unsigned long reg)
{
return __raw_readl((void __iomem *)(mmu->base + reg));
}
static inline void omap_mmu_write_reg(struct omap_mmu *mmu,
unsigned long val, unsigned long reg)
{
__raw_writel(val, (void __iomem *)(mmu->base + reg));
}
#endif /* __MACH_OMAP2_MMU_H */
......@@ -168,14 +168,6 @@ config OMAP_MCBSP
Say Y here if you want support for the OMAP Multichannel
Buffered Serial Port.
config OMAP_MMU_FWK
bool "MMU framework support"
depends on ARCH_OMAP
default n
help
Say Y here if you want to use OMAP MMU framework support for
DSP, IVA1.0 and Camera in OMAP1/2.
config OMAP_MBOX_FWK
tristate "Mailbox framework support"
depends on ARCH_OMAP
......
......@@ -23,9 +23,6 @@ obj-$(CONFIG_OMAP_DEBUG_DEVICES) += debug-devices.o
obj-$(CONFIG_OMAP_DEBUG_LEDS) += debug-leds.o
obj-$(CONFIG_I2C_OMAP) += i2c.o
# OMAP MMU framework
obj-$(CONFIG_OMAP_MMU_FWK) += mmu.o
# OMAP mailbox framework
obj-$(CONFIG_OMAP_MBOX_FWK) += mailbox.o
/*
* This file is part of OMAP DSP driver (DSP Gateway version 3.3.1)
*
* Copyright (C) 2002-2006 Nokia Corporation. All rights reserved.
*
* Contact: Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA
*
*/
#ifndef __ARCH_OMAP_DSP_H
#define __ARCH_OMAP_DSP_H
/*
* for /dev/dspctl/ctl
*/
#define DSPCTL_IOCTL_RESET 1
#define DSPCTL_IOCTL_RUN 2
#define DSPCTL_IOCTL_SETRSTVECT 3
#ifdef CONFIG_ARCH_OMAP1
#define DSPCTL_IOCTL_CPU_IDLE 4
#define DSPCTL_IOCTL_MPUI_WORDSWAP_ON 5
#define DSPCTL_IOCTL_MPUI_WORDSWAP_OFF 6
#define DSPCTL_IOCTL_MPUI_BYTESWAP_ON 7
#define DSPCTL_IOCTL_MPUI_BYTESWAP_OFF 8
#define DSPCTL_IOCTL_GBL_IDLE 9
#endif /* CONFIG_ARCH_OMAP1 */
#define DSPCTL_IOCTL_DSPCFG 10
#define DSPCTL_IOCTL_DSPUNCFG 11
#define DSPCTL_IOCTL_TASKCNT 12
#define DSPCTL_IOCTL_POLL 13
#define DSPCTL_IOCTL_REGMEMR 40
#define DSPCTL_IOCTL_REGMEMW 41
#define DSPCTL_IOCTL_REGIOR 42
#define DSPCTL_IOCTL_REGIOW 43
#define DSPCTL_IOCTL_GETVAR 44
#define DSPCTL_IOCTL_SETVAR 45
#define DSPCTL_IOCTL_RUNLEVEL 50
#define DSPCTL_IOCTL_SUSPEND 51
#define DSPCTL_IOCTL_RESUME 52
#ifdef CONFIG_OMAP_DSP_FBEXPORT
#define DSPCTL_IOCTL_FBEN 53
#define DSPCTL_IOCTL_FBDIS 54
#endif /* CONFIG_OMAP_DSP_FBEXPORT */
#define DSPCTL_IOCTL_MBSEND 99
struct omap_dsp_mailbox_cmd {
__u16 cmd;
__u16 data;
};
struct omap_dsp_reginfo {
__u16 adr;
__u16 val;
};
struct omap_dsp_varinfo {
__u8 varid;
__u16 val[0];
};
/*
* for taskdev
* (ioctls below should be >= 0x10000)
*/
#define TASK_IOCTL_BFLSH 0x10000
#define TASK_IOCTL_SETBSZ 0x10001
#define TASK_IOCTL_LOCK 0x10002
#define TASK_IOCTL_UNLOCK 0x10003
#define TASK_IOCTL_GETNAME 0x10004
/*
* for /dev/dspctl/mem
*/
#define MEM_IOCTL_EXMAP 1
#define MEM_IOCTL_EXUNMAP 2
#define MEM_IOCTL_EXMAP_FLUSH 3
#define MEM_IOCTL_FBEXPORT 5
#define MEM_IOCTL_MMUITACK 7
#define MEM_IOCTL_MMUINIT 9
#define MEM_IOCTL_KMEM_RESERVE 11
#define MEM_IOCTL_KMEM_RELEASE 12
struct omap_dsp_mapinfo {
__u32 dspadr;
__u32 size;
};
/*
* for /dev/dspctl/twch
*/
#define TWCH_IOCTL_MKDEV 1
#define TWCH_IOCTL_RMDEV 2
#define TWCH_IOCTL_TADD 11
#define TWCH_IOCTL_TDEL 12
#define TWCH_IOCTL_TKILL 13
struct omap_dsp_taddinfo {
__u8 minor;
__u32 taskadr;
};
#define TADD_ABORTADR 0xffffffff
#endif /* __ARCH_OMAP_DSP_H */
......@@ -5,50 +5,25 @@
*
* Contact: Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA
*
*/
#ifndef ASM_ARCH_DSP_COMMON_H
#define ASM_ARCH_DSP_COMMON_H
#include <linux/clk.h>
struct dsp_kfunc_device {
char *name;
struct clk *fck;
struct clk *ick;;
spinlock_t lock;
int enabled;
int type;
#define DSP_KFUNC_DEV_TYPE_COMMON 1
#define DSP_KFUNC_DEV_TYPE_AUDIO 2
struct list_head entry;
int (*probe)(struct dsp_kfunc_device *, int);
int (*remove)(struct dsp_kfunc_device *, int);
int (*enable)(struct dsp_kfunc_device *, int);
int (*disable)(struct dsp_kfunc_device *, int);
};
extern int dsp_kfunc_device_register(struct dsp_kfunc_device *);
struct dsp_platform_data {
struct list_head kdev_list;
};
struct omap_dsp {
struct mutex lock;
int enabled; /* stored peripheral status */
struct omap_mmu *mmu;
struct omap_mbox *mbox;
struct device *dev;
struct list_head *kdev_list;
int initialized;
};
#if defined(CONFIG_ARCH_OMAP1) && defined(CONFIG_OMAP_MMU_FWK)
extern void omap_dsp_request_mpui(void);
extern void omap_dsp_release_mpui(void);
......
#ifndef __ARCH_OMAP_MMU_H
#define __ARCH_OMAP_MMU_H
#include <linux/device.h>
#include <linux/workqueue.h>
enum exmap_type {
EXMAP_TYPE_MEM,
EXMAP_TYPE_FB
};
enum omap_mmu_type {
OMAP_MMU_DSP,
OMAP_MMU_IVA1,
OMAP_MMU_CAMERA,
};
struct exmap_tbl {
unsigned int valid:1;
unsigned int prsvd:1;
int usecount; /* reference count by mmap */
enum exmap_type type;
void *buf; /* virtual address of the buffer,
* i.e. 0xc0000000 - */
void *vadr; /* DSP shadow space,
* i.e. 0xe0000000 - 0xe0ffffff */
unsigned int order;
struct {
int prev;
int next;
} link; /* grouping */
};
struct cam_ram_regset {
union {
struct {
u16 cam_l;
u16 cam_h;
};
u32 cam;
};
union {
struct {
u16 ram_l;
u16 ram_h;
};
u32 ram;
};
};
struct omap_mmu_tlb_lock {
int base;
int victim;
};
struct omap_mmu;
struct omap_mmu_tlb_entry;
#ifdef CONFIG_ARCH_OMAP1
extern struct omap_mmu_ops omap1_mmu_ops;
extern void omap_mmu_itack(struct omap_mmu *mmu);
#elif defined(CONFIG_ARCH_OMAP2)
extern struct omap_mmu_ops omap2_mmu_ops;
static inline void omap_mmu_itack(struct omap_mmu *mmu)
{
}
#endif
struct omap_mmu_ops {
int (*startup)(struct omap_mmu *mmu);
void (*shutdown)(struct omap_mmu *mmu);
/* TLB operations */
void (*read_tlb)(struct omap_mmu *, struct cam_ram_regset *);
void (*load_tlb)(struct omap_mmu *, struct cam_ram_regset *);
ssize_t (*show)(struct omap_mmu *, char *, struct omap_mmu_tlb_lock *);
/* CAM / RAM operations */
struct cam_ram_regset *(*cam_ram_alloc)(struct omap_mmu *,
struct omap_mmu_tlb_entry *);
int (*cam_ram_valid)(struct cam_ram_regset *);
unsigned long (*cam_va)(struct cam_ram_regset *);
/* Memory operations */
int (*mem_enable)(struct omap_mmu *, void *);
int (*mem_disable)(struct omap_mmu *, void *);
void (*interrupt)(struct omap_mmu *);
/* PTE attribute operations */
pgprot_t (*pte_get_attr)(struct omap_mmu_tlb_entry *);
};
struct omap_mmu {
const char *name;
unsigned long base;
struct clk *clk;
unsigned long membase, memsize;
struct clk *memclk;
enum omap_mmu_type type;
struct device *dev;
struct rw_semaphore exmap_sem;
struct exmap_tbl *exmap_tbl;
unsigned int nr_tlb_entries;
unsigned int nr_exmap_preserved;
struct mm_struct *twl_mm;
/* Size of virtual address space, in bits */
unsigned int addrspace;
/* Interrupt */
unsigned int irq;
unsigned long fault_address;
struct work_struct irq_work;
struct omap_mmu_ops *ops;
};
#define omap_mmu_internal_memory(mmu, addr) \
(likely(mmu->membase) && (((unsigned long)(addr) >= mmu->membase) && \
((unsigned long)(addr) < mmu->membase + mmu->memsize)))
#define INIT_EXMAP_TBL_ENTRY(ent, b, v, typ, od) \
do { \
(ent)->buf = (b); \
(ent)->vadr = (v); \
(ent)->valid = 1; \
(ent)->prsvd = 0; \
(ent)->usecount = 0; \
(ent)->type = (typ); \
(ent)->order = (od); \
(ent)->link.next = -1; \
(ent)->link.prev = -1; \
} while (0)
#define INIT_EXMAP_TBL_ENTRY_4KB_PRESERVED(ent, b, v) \
do { \
(ent)->buf = (b); \
(ent)->vadr = (v); \
(ent)->valid = 1; \
(ent)->prsvd = 1; \
(ent)->usecount = 0; \
(ent)->type = EXMAP_TYPE_MEM; \
(ent)->order = 0; \
(ent)->link.next = -1; \
(ent)->link.prev = -1; \
} while (0)
#define omap_mmu_to_virt(mmu, db) ((void *)((mmu)->membase + (db)))
#define virt_to_omap_mmu(mmu, va) \
(((unsigned long)(va) - (mmu)->membase))
/* arch/arm/plat-omap/mmu.c */
int omap_mmu_register(struct omap_mmu *mmu);
void omap_mmu_unregister(struct omap_mmu *mmu);
void omap_mmu_enable(struct omap_mmu *mmu, int reset);
void omap_mmu_disable(struct omap_mmu *mmu);
int omap_mmu_mem_enable(struct omap_mmu *mmu, void *addr);
void omap_mmu_mem_disable(struct omap_mmu *mmu, void *addr);
void omap_mmu_read_tlb(struct omap_mmu *mmu, struct omap_mmu_tlb_lock *lock,
struct cam_ram_regset *cr);
int omap_mmu_load_tlb_entry(struct omap_mmu *, struct omap_mmu_tlb_entry *);
int omap_mmu_clear_tlb_entry(struct omap_mmu *, unsigned long vadr);
int omap_mmu_load_pte_entry(struct omap_mmu *mmu,
struct omap_mmu_tlb_entry *entry);
int omap_mmu_clear_pte_entry(struct omap_mmu *mmu, unsigned long vadr);
int omap_mmu_kmem_reserve(struct omap_mmu *mmu, unsigned long size);
void omap_mmu_kmem_release(void);
unsigned long omap_mmu_virt_to_phys(struct omap_mmu *mmu, void *vadr,
size_t *len);
int omap_mmu_exmap(struct omap_mmu *mmu, unsigned long dspadr,
unsigned long padr, unsigned long size,
enum exmap_type type);
int omap_mmu_exunmap(struct omap_mmu *mmu, unsigned long dspadr);
void omap_mmu_exmap_flush(struct omap_mmu *mmu);
void omap_mmu_exmap_use(struct omap_mmu *mmu, void *vadr, size_t len);
void omap_mmu_exmap_unuse(struct omap_mmu *mmu, void *vadr, size_t len);
int exmap_set_armmmu(struct omap_mmu *mmu, unsigned long virt,
unsigned long phys, unsigned long size);
void exmap_clear_armmmu(struct omap_mmu *mmu, unsigned long virt,
unsigned long size);
void exmap_setup_preserved_mem_page(struct omap_mmu *mmu, void *buf,
unsigned long dspadr, int index);
void exmap_clear_mem_page(struct omap_mmu *mmu, unsigned long dspadr);
int exmap_valid(struct omap_mmu *mmu, void *vadr, size_t len);
/* To be obsolete for backward compatibility */
ssize_t __omap_mmu_mem_read(struct omap_mmu *mmu, struct bin_attribute *,
char *buf, loff_t offset, size_t count);
ssize_t __omap_mmu_mem_write(struct omap_mmu *mmu, struct bin_attribute *,
char *buf, loff_t offset, size_t count);
#endif /* __ARCH_OMAP_MMU_H */
This diff is collapsed.
......@@ -42,7 +42,6 @@ obj-$(CONFIG_PARPORT) += parport/
obj-y += base/ block/ misc/ mfd/ net/ media/ cbus/
obj-y += i2c/
obj-y += cbus/
obj-$(CONFIG_ARCH_OMAP) += dsp/dspgateway/
obj-$(CONFIG_NUBUS) += nubus/
obj-$(CONFIG_ATM) += atm/
obj-y += macintosh/
......
config OMAP_DSP
tristate "OMAP DSP driver (DSP Gateway)"
depends on ARCH_OMAP15XX || ARCH_OMAP16XX || ARCH_OMAP24XX
select OMAP_MMU_FWK
select OMAP_MBOX_FWK
help
This enables OMAP DSP driver, DSP Gateway.
config OMAP_DSP_MBCMD_VERBOSE
bool "Mailbox Command Verbose LOG"
depends on OMAP_DSP
help
This enables kernel log output in the Mailbox command exchanges
in the DSP Gateway driver.
config OMAP_DSP_FBEXPORT
bool "Framebuffer export to DSP"
depends on OMAP_DSP && FB
help
This enables to map the frame buffer to DSP.
By doing this, DSP can access the frame buffer directly without
bothering ARM.
#
# Makefile for the OMAP DSP driver.
#
# The target object and module list name.
obj-y := dsp_common.o
obj-$(CONFIG_OMAP_DSP) += dsp.o
# Declare multi-part drivers
dsp-objs := dsp_core.o ipbuf.o mblog.o task.o \
dsp_ctl_core.o dsp_ctl.o taskwatch.o error.o dsp_mem.o \
uaccess_dsp.o
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
/*
* This file is part of OMAP DSP driver (DSP Gateway version 3.3.1)
*
* Copyright (C) 2004-2006 Nokia Corporation. All rights reserved.
*
* Contact: Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA
*
*/
#include <linux/major.h>
#include <linux/fs.h>
#include <linux/device.h>
#include <linux/init.h>
#include <asm/io.h>
#include "dsp.h"
#define CTL_MINOR 0
#define MEM_MINOR 1
#define TWCH_MINOR 2
#define ERR_MINOR 3
static struct class *dsp_ctl_class;
extern struct file_operations dsp_ctl_fops,
dsp_mem_fops,
dsp_twch_fops,
dsp_err_fops;
static int dsp_ctl_core_open(struct inode *inode, struct file *file)
{
static DEFINE_MUTEX(open_lock);
int ret = 0;
if (mutex_lock_interruptible(&open_lock))
return -EINTR;
if (omap_dsp->initialized == 0) {
ret = dsp_late_init();
if (ret != 0) {
mutex_unlock(&open_lock);
return ret;
}
omap_dsp->initialized = 1;
}
mutex_unlock(&open_lock);
switch (iminor(inode)) {
case CTL_MINOR:
file->f_op = &dsp_ctl_fops;
break;
case MEM_MINOR:
file->f_op = &dsp_mem_fops;
break;
case TWCH_MINOR:
file->f_op = &dsp_twch_fops;
break;
case ERR_MINOR:
file->f_op = &dsp_err_fops;
break;
default:
return -ENXIO;
}
if (file->f_op && file->f_op->open)
return file->f_op->open(inode, file);
return 0;
}
static struct file_operations dsp_ctl_core_fops = {
.owner = THIS_MODULE,
.open = dsp_ctl_core_open,
};
static const struct dev_list {
unsigned int minor;
char *devname;
umode_t mode;
} dev_list[] = {
{CTL_MINOR, "dspctl", S_IRUSR | S_IWUSR},
{MEM_MINOR, "dspmem", S_IRUSR | S_IWUSR | S_IRGRP},
{TWCH_MINOR, "dsptwch", S_IRUSR | S_IWUSR | S_IRGRP},
{ERR_MINOR, "dsperr", S_IRUSR | S_IRGRP},
};
int __init dsp_ctl_core_init(void)
{
int retval;
int i;
retval = register_chrdev(OMAP_DSP_CTL_MAJOR, "dspctl",
&dsp_ctl_core_fops);
if (retval < 0) {
printk(KERN_ERR
"omapdsp: failed to register dspctl device: %d\n",
retval);
return retval;
}
dsp_ctl_class = class_create(THIS_MODULE, "dspctl");
for (i = 0; i < ARRAY_SIZE(dev_list); i++) {
device_create(dsp_ctl_class, NULL,
MKDEV(OMAP_DSP_CTL_MAJOR, dev_list[i].minor),
NULL, dev_list[i].devname);
}
return 0;
}
void dsp_ctl_core_exit(void)
{
int i;
for (i = 0; i < ARRAY_SIZE(dev_list); i++) {
device_destroy(dsp_ctl_class,
MKDEV(OMAP_DSP_CTL_MAJOR,
dev_list[i].minor));
}
class_destroy(dsp_ctl_class);
unregister_chrdev(OMAP_DSP_CTL_MAJOR, "dspctl");
}
/*
* This file is part of OMAP DSP driver (DSP Gateway version 3.3.1)
*
* Copyright (C) 2002-2006 Nokia Corporation. All rights reserved.
*
* Contact: Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA
*
*/
#ifndef __PLAT_OMAP_DSP_MBCMD_H
#define __PLAT_OMAP_DSP_MBCMD_H
/*
* mailbox command: 0x00 - 0x7f
* when a driver wants to use mailbox, it must reserve mailbox commands here.
*/
#define MBOX_CMD_DSP_WDSND 0x10
#define MBOX_CMD_DSP_WDREQ 0x11
#define MBOX_CMD_DSP_BKSND 0x20
#define MBOX_CMD_DSP_BKREQ 0x21
#define MBOX_CMD_DSP_BKYLD 0x23
#define MBOX_CMD_DSP_BKSNDP 0x24
#define MBOX_CMD_DSP_BKREQP 0x25
#define MBOX_CMD_DSP_TCTL 0x30
#define MBOX_CMD_DSP_TCTLDATA 0x31
#define MBOX_CMD_DSP_POLL 0x32
#define MBOX_CMD_DSP_WDT 0x50
#define MBOX_CMD_DSP_RUNLEVEL 0x51
#define MBOX_CMD_DSP_PM 0x52
#define MBOX_CMD_DSP_SUSPEND 0x53
#define MBOX_CMD_DSP_KFUNC 0x54
#define MBOX_CMD_DSP_TCFG 0x60
#define MBOX_CMD_DSP_TADD 0x62
#define MBOX_CMD_DSP_TDEL 0x63
#define MBOX_CMD_DSP_TSTOP 0x65
#define MBOX_CMD_DSP_DSPCFG 0x70
#define MBOX_CMD_DSP_REGRW 0x72
#define MBOX_CMD_DSP_GETVAR 0x74
#define MBOX_CMD_DSP_SETVAR 0x75
#define MBOX_CMD_DSP_ERR 0x78
#define MBOX_CMD_DSP_DBG 0x79
/*
* DSP mailbox protocol definitions
*/
#define MBPROT_REVISION 0x0019
#define TCTL_TINIT 0x0000
#define TCTL_TEN 0x0001
#define TCTL_TDIS 0x0002
#define TCTL_TCLR 0x0003
#define TCTL_TCLR_FORCE 0x0004
#define RUNLEVEL_USER 0x01
#define RUNLEVEL_SUPER 0x0e
#define RUNLEVEL_RECOVERY 0x10
#define PM_DISABLE 0x00
#define PM_ENABLE 0x01
#define KFUNC_FBCTL 0x00
#define KFUNC_POWER 0x01
#define FBCTL_UPD 0x0000
#define FBCTL_ENABLE 0x0002
#define FBCTL_DISABLE 0x0003
/* KFUNC_POWER */
#define AUDIO_PWR_UP 0x0000 /* ARM(exe/ack) <-> DSP(req) */
#define AUDIO_PWR_DOWN 0x0001 /* ARM(exe) <- DSP(req) */
#define AUDIO_PWR_DOWN1 AUDIO_PWR_DOWN
#define AUDIO_PWR_DOWN2 0x0002
#define DSP_PWR_UP 0x0003 /* ARM(exe/snd) -> DSP(exe) */
#define DSP_PWR_DOWN 0x0004 /* ARM(exe) <- DSP(req) */
#define DVFS_START 0x0006 /* ARM(req) <-> DSP(exe/ack)*/
#define DVFS_STOP 0x0007 /* ARM(req) -> DSP(exe) */
#define TDEL_SAFE 0x0000
#define TDEL_KILL 0x0001
#define DSPCFG_REQ 0x00
#define DSPCFG_SYSADRH 0x28
#define DSPCFG_SYSADRL 0x29
#define DSPCFG_PROTREV 0x70
#define DSPCFG_ABORT 0x78
#define DSPCFG_LAST 0x80
#define REGRW_MEMR 0x00
#define REGRW_MEMW 0x01
#define REGRW_IOR 0x02
#define REGRW_IOW 0x03
#define REGRW_DATA 0x04
#define VARID_ICRMASK 0x00
#define VARID_LOADINFO 0x01
#define TTYP_ARCV 0x0001
#define TTYP_ASND 0x0002
#define TTYP_BKMD 0x0004
#define TTYP_BKDM 0x0008
#define TTYP_PVMD 0x0010
#define TTYP_PVDM 0x0020
#define EID_BADTID 0x10
#define EID_BADTCN 0x11
#define EID_BADBID 0x20
#define EID_BADCNT 0x21
#define EID_NOTLOCKED 0x22
#define EID_STVBUF 0x23
#define EID_BADADR 0x24
#define EID_BADTCTL 0x30
#define EID_BADPARAM 0x50
#define EID_FATAL 0x58
#define EID_NOMEM 0xc0
#define EID_NORES 0xc1
#define EID_IPBFULL 0xc2
#define EID_WDT 0xd0
#define EID_TASKNOTRDY 0xe0
#define EID_TASKBSY 0xe1
#define EID_TASKERR 0xef
#define EID_BADCFGTYP 0xf0
#define EID_DEBUG 0xf8
#define EID_BADSEQ 0xfe
#define EID_BADCMD 0xff
#define TNM_LEN 16
#define TID_FREE 0xff
#define TID_ANON 0xfe
#define BID_NULL 0xffff
#define BID_PVT 0xfffe
#endif /* __PLAT_OMAP_DSP_MBCMD_H */
This diff is collapsed.
This diff is collapsed.
/*
* This file is part of OMAP DSP driver (DSP Gateway version 3.3.1)
*
* Copyright (C) 2002-2006 Nokia Corporation. All rights reserved.
*
* Contact: Toshihiro Kobayashi <toshihiro.kobayashi@nokia.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA
*
*/
#ifndef __OMAP_DSP_HARDWARE_DSP_H
#define __OMAP_DSP_HARDWARE_DSP_H
#ifdef CONFIG_ARCH_OMAP1
#include "omap1_dsp.h"
#endif
#if defined(CONFIG_ARCH_OMAP2) || defined(CONFIG_ARCH_OMAP3430)
#include "omap2_dsp.h"
#endif
#endif /* __OMAP_DSP_HARDWARE_DSP_H */
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment