mirror of
https://github.com/genesi/linux-legacy.git
synced 2026-07-09 02:06:28 +00:00
amd-gpu: Z160 context rework
* gsl_drawctxt_t -> kgsl_drawctxt (this touches some Z430 stuff too) * gsl_z1xx_t et al -> kgsl_z1xx * move some defines to includes * use symbolic values in addmarker/beginpacket * remove kgsl_context and opencode it's usage in ioctls etc. * rename context_* ftbl functions to device_context_* like Qualcomm .35 * add kgsl_g12_cmdstream.c and kgsl_g12_drawctxt.c like Qualcomms .32 but retain functionality from our versions of these functions behavior change: * under fbdev, tiger and es11ex work fine most of the time - es11ex will soft-lockup occasionally * under imxng, tiger locks occasionally when moving the mouse pointer - I thought this bug was fixed * under imxng, es11ex locks after good 30 seconds - but does NOT hang the system anymore (strange) Since some gsl_driver.lock usage was moved I wonder if this is the source of our race condition?
This commit is contained in:
@@ -1,11 +1,12 @@
|
||||
obj-$(CONFIG_MXC_KGSL) += mxc_kgsl.o
|
||||
mxc_kgsl-objs += kgsl_cmdstream.o \
|
||||
kgsl_cmdwindow.o \
|
||||
kgsl_context.o \
|
||||
kgsl_device.o \
|
||||
kgsl_drawctxt.o \
|
||||
kgsl_driver.o \
|
||||
kgsl_g12.o \
|
||||
kgsl_g12_cmdstream.o \
|
||||
kgsl_g12_drawctxt.o \
|
||||
kgsl_intrmgr.o \
|
||||
kgsl_memmgr.o \
|
||||
kgsl_mmu.o \
|
||||
|
||||
@@ -1,87 +0,0 @@
|
||||
/* Copyright (c) 2008-2010, Advanced Micro Devices. All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 and
|
||||
* only 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 Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*
|
||||
*/
|
||||
|
||||
#include "kgsl_types.h"
|
||||
#include "kgsl_mmu.h"
|
||||
#include "kgsl_buildconfig.h"
|
||||
#include "kgsl_hal.h"
|
||||
#include "kgsl_halconfig.h"
|
||||
#include "kgsl_memmgr.h"
|
||||
#include "kgsl_sharedmem.h"
|
||||
#include "kgsl_properties.h"
|
||||
#include "kgsl_intrmgr.h"
|
||||
#include "kgsl_ringbuffer.h"
|
||||
#include "kgsl_drawctxt.h"
|
||||
#include "kgsl_cmdwindow.h"
|
||||
#include "kgsl_device.h"
|
||||
#include "kgsl_driver.h"
|
||||
#include "kgsl_linux_map.h"
|
||||
#include "kgsl_hwaccess.h"
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
// functions
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
int
|
||||
kgsl_context_create(unsigned int device_id, unsigned int type, unsigned int *drawctxt_id, unsigned int flags)
|
||||
{
|
||||
struct kgsl_device* device = &gsl_driver.device[device_id-1];
|
||||
int status;
|
||||
|
||||
mutex_lock(&gsl_driver.lock);
|
||||
|
||||
if (device->ftbl.context_create)
|
||||
{
|
||||
status = device->ftbl.context_create(device, type, drawctxt_id, flags);
|
||||
}
|
||||
else
|
||||
{
|
||||
status = GSL_FAILURE;
|
||||
}
|
||||
|
||||
mutex_unlock(&gsl_driver.lock);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_context_destroy(unsigned int device_id, unsigned int drawctxt_id)
|
||||
{
|
||||
struct kgsl_device* device = &gsl_driver.device[device_id-1];
|
||||
int status;
|
||||
|
||||
mutex_lock(&gsl_driver.lock);
|
||||
|
||||
if (device->ftbl.context_destroy)
|
||||
{
|
||||
status = device->ftbl.context_destroy(device, drawctxt_id);
|
||||
}
|
||||
else
|
||||
{
|
||||
status = GSL_FAILURE;
|
||||
}
|
||||
|
||||
mutex_unlock(&gsl_driver.lock);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
@@ -70,8 +70,8 @@ struct kgsl_functable {
|
||||
int (*mmu_tlbinvalidate) (struct kgsl_device *device, unsigned int reg_invalidate, unsigned int pid);
|
||||
int (*mmu_setpagetable) (struct kgsl_device *device, unsigned int reg_ptbase, uint32_t ptbase, unsigned int pid);
|
||||
int (*cmdstream_issueibcmds) (struct kgsl_device *device, int drawctxt_index, uint32_t ibaddr, int sizedwords, unsigned int *timestamp, unsigned int flags);
|
||||
int (*context_create) (struct kgsl_device *device, unsigned int type, unsigned int *drawctxt_id, unsigned int flags);
|
||||
int (*context_destroy) (struct kgsl_device *device_id, unsigned int drawctxt_id);
|
||||
int (*device_drawctxt_create) (struct kgsl_device *device, unsigned int type, unsigned int *drawctxt_id, unsigned int flags);
|
||||
int (*device_drawctxt_destroy) (struct kgsl_device *device_id, unsigned int drawctxt_id);
|
||||
};
|
||||
|
||||
#define GSL_CALLER_PROCESS_MAX 64
|
||||
|
||||
@@ -119,8 +119,4 @@ int kgsl_drawctxt_destroy(struct kgsl_device* device, unsigned int drawctxt_
|
||||
|
||||
int kgsl_drawctxt_bind_gmem_shadow(unsigned int device_id, unsigned int drawctxt_id, const struct kgsl_gmem_desc* gmem_rect, unsigned int shadow_x, unsigned int shadow_y, const struct kgsl_buffer_desc* shadow_buffer, unsigned int buffer_id);
|
||||
|
||||
/* these are in the wrong place..! */
|
||||
int kgsl_context_create(unsigned int device_id, unsigned int type, unsigned int *drawctxt_id, unsigned int flags);
|
||||
int kgsl_context_destroy(unsigned int device_id, unsigned int drawctxt_id);
|
||||
|
||||
#endif // __GSL_DRAWCTXT_H
|
||||
|
||||
@@ -26,6 +26,8 @@
|
||||
#include "kgsl_sharedmem.h"
|
||||
#include "kgsl_driver.h"
|
||||
#include "kgsl_ioctl.h"
|
||||
#include "kgsl_g12_drawctxt.h"
|
||||
#include "kgsl_g12_cmdstream.h"
|
||||
|
||||
#include "g12_reg.h"
|
||||
#include "kgsl_g12_vgv3types.h"
|
||||
@@ -36,15 +38,9 @@
|
||||
|
||||
#define GSL_IRQ_TIMEOUT 200
|
||||
|
||||
|
||||
int kgsl_g12_regread(struct kgsl_device *device, unsigned int offsetwords, unsigned int *value);
|
||||
int kgsl_g12_regwrite(struct kgsl_device *device, unsigned int offsetwords, unsigned int value);
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
#define GSL_HAL_NUMCMDBUFFERS 5
|
||||
#define GSL_HAL_CMDBUFFERSIZE (1024 + 13) * sizeof(unsigned int)
|
||||
|
||||
/* G12 MH arbiter config*/
|
||||
#define KGSL_G12_CFG_G12_MHARB \
|
||||
(0x10 \
|
||||
@@ -63,82 +59,9 @@ int kgsl_g12_regwrite(struct kgsl_device *device, unsigned int offsetwords, unsi
|
||||
| (1 << MH_ARBITER_CONFIG__RB_CLNT_ENABLE__SHIFT) \
|
||||
| (1 << MH_ARBITER_CONFIG__PA_CLNT_ENABLE__SHIFT))
|
||||
|
||||
#define ALIGN_IN_BYTES( dim, alignment ) ( ( (dim) + (alignment-1) ) & ~(alignment-1) )
|
||||
|
||||
|
||||
#ifdef _Z180
|
||||
#define NUMTEXUNITS 4
|
||||
#define TEXUNITREGCOUNT 25
|
||||
#define VG_REGCOUNT 0x39
|
||||
#define GSL_HAL_EDGE0BUFSIZE 0x3E8+64
|
||||
#define GSL_HAL_EDGE1BUFSIZE 0x8000+64
|
||||
#define GSL_HAL_EDGE2BUFSIZE 0x80020+64
|
||||
#define GSL_HAL_EDGE0REG ADDR_VGV1_CBUF
|
||||
#define GSL_HAL_EDGE1REG ADDR_VGV1_BBUF
|
||||
#define GSL_HAL_EDGE2REG ADDR_VGV1_EBUF
|
||||
#else
|
||||
#define NUMTEXUNITS 2
|
||||
#define TEXUNITREGCOUNT 24
|
||||
#define VG_REGCOUNT 0x3A
|
||||
#define L1TILESIZE 64
|
||||
#define GSL_HAL_EDGE0BUFSIZE L1TILESIZE*L1TILESIZE*4+64
|
||||
#define GSL_HAL_EDGE1BUFSIZE L1TILESIZE*L1TILESIZE*16+64
|
||||
#define GSL_HAL_EDGE0REG ADDR_VGV1_CBASE1
|
||||
#define GSL_HAL_EDGE1REG ADDR_VGV1_UBASE2
|
||||
#endif
|
||||
|
||||
#define PACKETSIZE_BEGIN 3
|
||||
#define PACKETSIZE_G2DCOLOR 2
|
||||
#define PACKETSIZE_TEXUNIT (TEXUNITREGCOUNT*2)
|
||||
#define PACKETSIZE_REG (VG_REGCOUNT*2)
|
||||
#define PACKETSIZE_STATE (PACKETSIZE_TEXUNIT*NUMTEXUNITS + PACKETSIZE_REG + PACKETSIZE_BEGIN + PACKETSIZE_G2DCOLOR)
|
||||
#define PACKETSIZE_STATESTREAM ALIGN_IN_BYTES((PACKETSIZE_STATE*sizeof(unsigned int)), 32) / sizeof(unsigned int)
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned int id;
|
||||
// unsigned int regs[];
|
||||
}gsl_hal_z1xxdrawctx_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned int offs;
|
||||
unsigned int curr;
|
||||
unsigned int prevctx;
|
||||
|
||||
struct kgsl_memdesc e0;
|
||||
struct kgsl_memdesc e1;
|
||||
struct kgsl_memdesc e2;
|
||||
unsigned int* cmdbuf[GSL_HAL_NUMCMDBUFFERS];
|
||||
struct kgsl_memdesc cmdbufdesc[GSL_HAL_NUMCMDBUFFERS];
|
||||
unsigned int timestamp[GSL_HAL_NUMCMDBUFFERS];
|
||||
|
||||
unsigned int numcontext;
|
||||
unsigned int nextUniqueContextID;
|
||||
}gsl_z1xx_t;
|
||||
|
||||
static gsl_z1xx_t g_z1xx = {0};
|
||||
|
||||
extern int z160_version;
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
// functions
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static int kgsl_g12_addtimestamp(struct kgsl_device* device, unsigned int *timestamp);
|
||||
static int kgsl_g12_issueibcmds(struct kgsl_device* device, int drawctxt_index, uint32_t ibaddr, int sizedwords, unsigned int *timestamp, unsigned int flags);
|
||||
static int kgsl_g12_context_create(struct kgsl_device* device, unsigned int type, unsigned int *drawctxt_id, unsigned int flags);
|
||||
static int kgsl_g12_context_destroy(struct kgsl_device* device, unsigned int drawctxt_id);
|
||||
static unsigned int drawctx_id = 0;
|
||||
static int kgsl_g12_idle(struct kgsl_device *device, unsigned int timeout);
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
void
|
||||
kgsl_g12_intrcallback(gsl_intrid_t id, void *cookie)
|
||||
{
|
||||
@@ -172,8 +95,6 @@ kgsl_g12_intrcallback(gsl_intrid_t id, void *cookie)
|
||||
}
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_isr(struct kgsl_device *device)
|
||||
{
|
||||
@@ -206,8 +127,6 @@ kgsl_g12_isr(struct kgsl_device *device)
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_tlbinvalidate(struct kgsl_device *device, unsigned int reg_invalidate, unsigned int pid)
|
||||
{
|
||||
@@ -225,8 +144,6 @@ kgsl_g12_tlbinvalidate(struct kgsl_device *device, unsigned int reg_invalidate,
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_setpagetable(struct kgsl_device *device, unsigned int reg_ptbase, uint32_t ptbase, unsigned int pid)
|
||||
{
|
||||
@@ -243,8 +160,6 @@ kgsl_g12_setpagetable(struct kgsl_device *device, unsigned int reg_ptbase, uint3
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static void kgsl_g12_updatetimestamp(struct kgsl_device *device)
|
||||
{
|
||||
unsigned int count = 0;
|
||||
@@ -262,8 +177,6 @@ static void kgsl_g12_updatetimestamp(struct kgsl_device *device)
|
||||
kgsl_sharedmem_write0(&device->memstore, KGSL_DEVICE_MEMSTORE_OFFSET(eoptimestamp), &device->timestamp, 4, 0);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static void kgsl_g12_irqtask(struct work_struct *work)
|
||||
{
|
||||
struct kgsl_device *device = &gsl_driver.device[KGSL_DEVICE_G12-1];
|
||||
@@ -278,8 +191,6 @@ static void kgsl_g12_irqerr(struct work_struct *work)
|
||||
}
|
||||
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_init(struct kgsl_device *device)
|
||||
{
|
||||
@@ -336,8 +247,6 @@ kgsl_g12_init(struct kgsl_device *device)
|
||||
return (status);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_close(struct kgsl_device *device)
|
||||
{
|
||||
@@ -379,14 +288,12 @@ kgsl_g12_close(struct kgsl_device *device)
|
||||
|
||||
DEBUG_ASSERT(g_z1xx.numcontext == 0);
|
||||
|
||||
memset(&g_z1xx, 0, sizeof(gsl_z1xx_t));
|
||||
memset(&g_z1xx, 0, sizeof(struct kgsl_g12_z1xx));
|
||||
}
|
||||
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_destroy(struct kgsl_device *device)
|
||||
{
|
||||
@@ -415,8 +322,6 @@ kgsl_g12_destroy(struct kgsl_device *device)
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_start(struct kgsl_device *device, unsigned int flags)
|
||||
{
|
||||
@@ -441,8 +346,6 @@ kgsl_g12_start(struct kgsl_device *device, unsigned int flags)
|
||||
return (status);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_stop(struct kgsl_device *device)
|
||||
{
|
||||
@@ -460,8 +363,6 @@ kgsl_g12_stop(struct kgsl_device *device)
|
||||
return (status);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_getproperty(struct kgsl_device *device, gsl_property_type_t type, void *value, unsigned int sizebytes)
|
||||
{
|
||||
@@ -491,8 +392,6 @@ kgsl_g12_getproperty(struct kgsl_device *device, gsl_property_type_t type, void
|
||||
return (status);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_setproperty(struct kgsl_device *device, gsl_property_type_t type, void *value, unsigned int sizebytes)
|
||||
{
|
||||
@@ -517,8 +416,6 @@ kgsl_g12_setproperty(struct kgsl_device *device, gsl_property_type_t type, void
|
||||
return (status);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_idle(struct kgsl_device *device, unsigned int timeout)
|
||||
{
|
||||
@@ -537,8 +434,6 @@ kgsl_g12_idle(struct kgsl_device *device, unsigned int timeout)
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int kgsl_g12_regread(struct kgsl_device *device, unsigned int offsetwords, unsigned int *value)
|
||||
{
|
||||
unsigned int *reg;
|
||||
@@ -600,9 +495,6 @@ int kgsl_g12_regwrite(struct kgsl_device *device, unsigned int offsetwords, unsi
|
||||
return GSL_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_waitirq(struct kgsl_device *device, gsl_intrid_t intr_id, unsigned int *count, unsigned int timeout)
|
||||
{
|
||||
@@ -670,8 +562,6 @@ kgsl_g12_waitirq(struct kgsl_device *device, gsl_intrid_t intr_id, unsigned int
|
||||
return (status);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
int
|
||||
kgsl_g12_waittimestamp(struct kgsl_device *device, unsigned int timestamp, unsigned int timeout)
|
||||
{
|
||||
@@ -687,255 +577,26 @@ kgsl_g12_waittimestamp(struct kgsl_device *device, unsigned int timestamp, unsig
|
||||
int
|
||||
kgsl_g12_getfunctable(struct kgsl_functable *ftbl)
|
||||
{
|
||||
ftbl->init = kgsl_g12_init;
|
||||
ftbl->close = kgsl_g12_close;
|
||||
ftbl->destroy = kgsl_g12_destroy;
|
||||
ftbl->start = kgsl_g12_start;
|
||||
ftbl->stop = kgsl_g12_stop;
|
||||
ftbl->getproperty = kgsl_g12_getproperty;
|
||||
ftbl->setproperty = kgsl_g12_setproperty;
|
||||
ftbl->idle = kgsl_g12_idle;
|
||||
ftbl->regread = kgsl_g12_regread;
|
||||
ftbl->regwrite = kgsl_g12_regwrite;
|
||||
ftbl->waitirq = kgsl_g12_waitirq;
|
||||
ftbl->waittimestamp = kgsl_g12_waittimestamp;
|
||||
ftbl->runpending = NULL;
|
||||
ftbl->addtimestamp = kgsl_g12_addtimestamp;
|
||||
ftbl->intr_isr = kgsl_g12_isr;
|
||||
ftbl->mmu_tlbinvalidate = kgsl_g12_tlbinvalidate;
|
||||
ftbl->mmu_setpagetable = kgsl_g12_setpagetable;
|
||||
ftbl->cmdstream_issueibcmds = kgsl_g12_issueibcmds;
|
||||
ftbl->context_create = kgsl_g12_context_create;
|
||||
ftbl->context_destroy = kgsl_g12_context_destroy;
|
||||
ftbl->init = kgsl_g12_init;
|
||||
ftbl->close = kgsl_g12_close;
|
||||
ftbl->destroy = kgsl_g12_destroy;
|
||||
ftbl->start = kgsl_g12_start;
|
||||
ftbl->stop = kgsl_g12_stop;
|
||||
ftbl->getproperty = kgsl_g12_getproperty;
|
||||
ftbl->setproperty = kgsl_g12_setproperty;
|
||||
ftbl->idle = kgsl_g12_idle;
|
||||
ftbl->regread = kgsl_g12_regread;
|
||||
ftbl->regwrite = kgsl_g12_regwrite;
|
||||
ftbl->waitirq = kgsl_g12_waitirq;
|
||||
ftbl->waittimestamp = kgsl_g12_waittimestamp;
|
||||
ftbl->runpending = NULL;
|
||||
ftbl->addtimestamp = kgsl_g12_addtimestamp;
|
||||
ftbl->intr_isr = kgsl_g12_isr;
|
||||
ftbl->mmu_tlbinvalidate = kgsl_g12_tlbinvalidate;
|
||||
ftbl->mmu_setpagetable = kgsl_g12_setpagetable;
|
||||
ftbl->cmdstream_issueibcmds = kgsl_g12_issueibcmds;
|
||||
ftbl->device_drawctxt_create = kgsl_g12_drawctxt_create;
|
||||
ftbl->device_drawctxt_destroy = kgsl_g12_drawctxt_destroy;
|
||||
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static void addmarker(gsl_z1xx_t* z1xx)
|
||||
{
|
||||
DEBUG_ASSERT(z1xx);
|
||||
{
|
||||
unsigned int *p = z1xx->cmdbuf[z1xx->curr];
|
||||
/* todo: use symbolic values */
|
||||
p[z1xx->offs++] = 0x7C000176;
|
||||
p[z1xx->offs++] = (0x8000|5);
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = 0x7C000176;
|
||||
p[z1xx->offs++] = 5;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
}
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
static void beginpacket(gsl_z1xx_t* z1xx, uint32_t cmd, unsigned int nextcnt)
|
||||
{
|
||||
unsigned int *p = z1xx->cmdbuf[z1xx->curr];
|
||||
|
||||
p[z1xx->offs++] = 0x7C000176;
|
||||
p[z1xx->offs++] = 5;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = 0x7C000275;
|
||||
p[z1xx->offs++] = cmd;
|
||||
p[z1xx->offs++] = 0x1000|nextcnt; // nextcount
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST<<24;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static int
|
||||
kgsl_g12_issueibcmds(struct kgsl_device* device, int drawctxt_index, uint32_t ibaddr, int sizedwords, unsigned int *timestamp, unsigned int flags)
|
||||
{
|
||||
unsigned int ofs = PACKETSIZE_STATESTREAM*sizeof(unsigned int);
|
||||
unsigned int cnt = 5;
|
||||
unsigned int cmd = ibaddr;
|
||||
unsigned int nextbuf = (g_z1xx.curr+1)%GSL_HAL_NUMCMDBUFFERS;
|
||||
unsigned int nextaddr = g_z1xx.cmdbufdesc[nextbuf].gpuaddr;
|
||||
unsigned int nextcnt = 0x9000|5;
|
||||
struct kgsl_memdesc tmp = {0};
|
||||
unsigned int processed_timestamp;
|
||||
|
||||
(void) flags;
|
||||
|
||||
// read what is the latest timestamp device have processed
|
||||
KGSL_CMDSTREAM_GET_EOP_TIMESTAMP(device, (int *)&processed_timestamp);
|
||||
|
||||
/* wait for the next buffer's timestamp to occur */
|
||||
while(processed_timestamp < g_z1xx.timestamp[nextbuf])
|
||||
{
|
||||
kgsl_cmdstream_waittimestamp(device->id, g_z1xx.timestamp[nextbuf], 1000);
|
||||
KGSL_CMDSTREAM_GET_EOP_TIMESTAMP(device, (int *)&processed_timestamp);
|
||||
}
|
||||
|
||||
*timestamp = g_z1xx.timestamp[nextbuf] = device->current_timestamp + 1;
|
||||
|
||||
/* context switch */
|
||||
if (drawctxt_index != (int)g_z1xx.prevctx)
|
||||
{
|
||||
cnt = PACKETSIZE_STATESTREAM;
|
||||
ofs = 0;
|
||||
}
|
||||
g_z1xx.prevctx = drawctxt_index;
|
||||
|
||||
g_z1xx.offs = 10;
|
||||
beginpacket(&g_z1xx, cmd+ofs, cnt);
|
||||
|
||||
tmp.gpuaddr=ibaddr+(sizedwords*sizeof(unsigned int));
|
||||
kgsl_sharedmem_write0(&tmp, 4, &nextaddr, 4, false);
|
||||
kgsl_sharedmem_write0(&tmp, 8, &nextcnt, 4, false);
|
||||
|
||||
/* sync mem */
|
||||
kgsl_sharedmem_write0((const struct kgsl_memdesc *)&g_z1xx.cmdbufdesc[g_z1xx.curr], 0, g_z1xx.cmdbuf[g_z1xx.curr], (512 + 13) * sizeof(unsigned int), false);
|
||||
|
||||
g_z1xx.offs = 0;
|
||||
g_z1xx.curr = nextbuf;
|
||||
|
||||
/* increment mark counter */
|
||||
#ifdef V3_SYNC
|
||||
if (device->timestamp == device->current_timestamp)
|
||||
{
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, flags);
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, 0);
|
||||
}
|
||||
#else
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, flags);
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, 0);
|
||||
#endif
|
||||
|
||||
/* increment consumed timestamp */
|
||||
device->current_timestamp++;
|
||||
kgsl_sharedmem_write0(&device->memstore, KGSL_DEVICE_MEMSTORE_OFFSET(soptimestamp), &device->current_timestamp, 4, 0);
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static int
|
||||
kgsl_g12_context_create(struct kgsl_device* device, unsigned int type, unsigned int *drawctxt_id, unsigned int flags)
|
||||
{
|
||||
int status = 0;
|
||||
int i;
|
||||
int cmd;
|
||||
unsigned int gslflags = (GSL_MEMFLAGS_CONPHYS | GSL_MEMFLAGS_ALIGNPAGE);
|
||||
|
||||
// unreferenced formal parameters
|
||||
(void) device;
|
||||
(void) type;
|
||||
//(void) drawctxt_id;
|
||||
(void) flags;
|
||||
|
||||
kgsl_device_active(device);
|
||||
|
||||
if (g_z1xx.numcontext==0)
|
||||
{
|
||||
g_z1xx.nextUniqueContextID = 0;
|
||||
/* todo: move this to device create or start. Error checking!! */
|
||||
for (i=0;i<GSL_HAL_NUMCMDBUFFERS;i++)
|
||||
{
|
||||
status = kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_CMDBUFFERSIZE, &g_z1xx.cmdbufdesc[i]);
|
||||
DEBUG_ASSERT(status == GSL_SUCCESS);
|
||||
g_z1xx.cmdbuf[i]=kmalloc(GSL_HAL_CMDBUFFERSIZE, GFP_KERNEL);
|
||||
DEBUG_ASSERT(g_z1xx.cmdbuf[i]);
|
||||
memset((void*)g_z1xx.cmdbuf[i], 0, GSL_HAL_CMDBUFFERSIZE);
|
||||
|
||||
g_z1xx.curr = i;
|
||||
g_z1xx.offs = 0;
|
||||
addmarker(&g_z1xx);
|
||||
status = kgsl_sharedmem_write0(&g_z1xx.cmdbufdesc[i],0, g_z1xx.cmdbuf[i], (512 + 13) * sizeof(unsigned int), false);
|
||||
DEBUG_ASSERT(status == GSL_SUCCESS);
|
||||
}
|
||||
g_z1xx.curr = 0;
|
||||
cmd = VGV3_NEXTCMD_JUMP << VGV3_NEXTCMD_NEXTCMD_FSHIFT;
|
||||
|
||||
/* set cmd stream buffer to hw */
|
||||
status |= kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, ADDR_VGV3_MODE, 4);
|
||||
status |= kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, ADDR_VGV3_NEXTADDR, g_z1xx.cmdbufdesc[0].gpuaddr );
|
||||
status |= kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, ADDR_VGV3_NEXTCMD, cmd | 5);
|
||||
|
||||
DEBUG_ASSERT(status == GSL_SUCCESS);
|
||||
|
||||
/* Edge buffer setup todo: move register setup to own function.
|
||||
This function can be then called, if power managemnet is used and clocks are turned off and then on.
|
||||
*/
|
||||
status |= kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_EDGE0BUFSIZE, &g_z1xx.e0);
|
||||
status |= kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_EDGE1BUFSIZE, &g_z1xx.e1);
|
||||
status |= kgsl_sharedmem_set0(&g_z1xx.e0, 0, 0, GSL_HAL_EDGE0BUFSIZE);
|
||||
status |= kgsl_sharedmem_set0(&g_z1xx.e1, 0, 0, GSL_HAL_EDGE1BUFSIZE);
|
||||
|
||||
status |= kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, GSL_HAL_EDGE0REG, g_z1xx.e0.gpuaddr);
|
||||
status |= kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, GSL_HAL_EDGE1REG, g_z1xx.e1.gpuaddr);
|
||||
#ifdef _Z180
|
||||
kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_EDGE2BUFSIZE, &g_z1xx.e2);
|
||||
kgsl_sharedmem_set0(&g_z1xx.e2, 0, 0, GSL_HAL_EDGE2BUFSIZE);
|
||||
kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, GSL_HAL_EDGE2REG, g_z1xx.e2.gpuaddr);
|
||||
#endif
|
||||
DEBUG_ASSERT(status == GSL_SUCCESS);
|
||||
}
|
||||
|
||||
if(g_z1xx.numcontext < GSL_CONTEXT_MAX)
|
||||
{
|
||||
g_z1xx.numcontext++;
|
||||
g_z1xx.nextUniqueContextID++;
|
||||
*drawctxt_id=g_z1xx.nextUniqueContextID;
|
||||
status = GSL_SUCCESS;
|
||||
}
|
||||
else
|
||||
{
|
||||
status = GSL_FAILURE;
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static int
|
||||
kgsl_g12_context_destroy(struct kgsl_device* device, unsigned int drawctxt_id)
|
||||
{
|
||||
|
||||
// unreferenced formal parameters
|
||||
(void) device;
|
||||
(void) drawctxt_id;
|
||||
|
||||
g_z1xx.numcontext--;
|
||||
if (g_z1xx.numcontext<0)
|
||||
{
|
||||
g_z1xx.numcontext=0;
|
||||
return (GSL_FAILURE);
|
||||
}
|
||||
|
||||
if (g_z1xx.numcontext==0)
|
||||
{
|
||||
int i;
|
||||
for (i=0;i<GSL_HAL_NUMCMDBUFFERS;i++)
|
||||
{
|
||||
kgsl_sharedmem_free0(&g_z1xx.cmdbufdesc[i], current->tgid);
|
||||
kfree(g_z1xx.cmdbuf[i]);
|
||||
}
|
||||
kgsl_sharedmem_free0(&g_z1xx.e0, current->tgid);
|
||||
kgsl_sharedmem_free0(&g_z1xx.e1, current->tgid);
|
||||
#ifdef _Z180
|
||||
kgsl_sharedmem_free0(&g_z1xx.e2, current->tgid);
|
||||
#endif
|
||||
}
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
static int
|
||||
kgsl_g12_addtimestamp(struct kgsl_device* device, unsigned int *timestamp)
|
||||
{
|
||||
device->current_timestamp++;
|
||||
*timestamp = device->current_timestamp;
|
||||
|
||||
return (GSL_SUCCESS);
|
||||
return GSL_SUCCESS;
|
||||
}
|
||||
|
||||
139
drivers/mxc/amd-gpu/kgsl_g12_cmdstream.c
Normal file
139
drivers/mxc/amd-gpu/kgsl_g12_cmdstream.c
Normal file
@@ -0,0 +1,139 @@
|
||||
/* Copyright (c) 2002,2007-2010, Code Aurora Forum. All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 and
|
||||
* only 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 Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <linux/delay.h>
|
||||
#include <linux/sched.h>
|
||||
#include <linux/io.h>
|
||||
|
||||
#include "kgsl_types.h"
|
||||
#include "kgsl_hal.h"
|
||||
#include "kgsl_cmdstream.h"
|
||||
#include "kgsl_sharedmem.h"
|
||||
#include "kgsl_driver.h"
|
||||
#include "kgsl_ioctl.h"
|
||||
#include "kgsl_g12_drawctxt.h"
|
||||
|
||||
#include "g12_reg.h"
|
||||
#include "kgsl_g12_vgv3types.h"
|
||||
|
||||
#ifdef CONFIG_ARCH_MX35
|
||||
#define V3_SYNC
|
||||
#endif
|
||||
|
||||
static void beginpacket(struct kgsl_g12_z1xx* z1xx, uint32_t cmd, unsigned int nextcount)
|
||||
{
|
||||
unsigned int *p = z1xx->cmdbuf[z1xx->curr];
|
||||
|
||||
p[z1xx->offs++] = KGSL_G12_STREAM_PACKET;
|
||||
p[z1xx->offs++] = 5;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = KGSL_G12_STREAM_PACKET_CALL;
|
||||
p[z1xx->offs++] = cmd;
|
||||
p[z1xx->offs++] = KGSL_G12_CALL_CMD | nextcount;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
}
|
||||
|
||||
|
||||
int kgsl_g12_issueibcmds(struct kgsl_device* device, int drawctxt_index, uint32_t ibaddr,
|
||||
int sizedwords, unsigned int *timestamp, unsigned int flags)
|
||||
{
|
||||
unsigned int ofs = PACKETSIZE_STATESTREAM * sizeof(unsigned int);
|
||||
unsigned int cnt = 5;
|
||||
unsigned int cmd = ibaddr;
|
||||
unsigned int nextbuf = (g_z1xx.curr+1) % GSL_HAL_NUMCMDBUFFERS;
|
||||
unsigned int nextaddr = g_z1xx.cmdbufdesc[nextbuf].gpuaddr;
|
||||
unsigned int nextcnt = KGSL_G12_STREAM_END_CMD | 5;
|
||||
struct kgsl_memdesc tmp = {0};
|
||||
unsigned int processed_timestamp;
|
||||
|
||||
(void) flags;
|
||||
|
||||
/* read what is the latest timestamp device have processed */
|
||||
/* note: diverge from qcom */
|
||||
KGSL_CMDSTREAM_GET_EOP_TIMESTAMP(device, (int *)&processed_timestamp);
|
||||
|
||||
/* wait for the next buffer's timestamp to occur - note: diverge */
|
||||
while(processed_timestamp < g_z1xx.timestamp[nextbuf]) {
|
||||
kgsl_cmdstream_waittimestamp(device->id, g_z1xx.timestamp[nextbuf], 1000);
|
||||
KGSL_CMDSTREAM_GET_EOP_TIMESTAMP(device, (int *)&processed_timestamp);
|
||||
}
|
||||
|
||||
// QCOM
|
||||
// tmp.hostptr = (void *) *timestamp;
|
||||
// device->current_timestamp++;
|
||||
// *timestamp = device->current_timestamp;
|
||||
|
||||
*timestamp = g_z1xx.timestamp[nextbuf] = device->current_timestamp + 1;
|
||||
|
||||
/* context switch */
|
||||
if (drawctxt_index != (int) g_z1xx.prevctx) {
|
||||
cnt = PACKETSIZE_STATESTREAM;
|
||||
ofs = 0;
|
||||
}
|
||||
|
||||
g_z1xx.prevctx = drawctxt_index;
|
||||
|
||||
g_z1xx.offs = 10;
|
||||
beginpacket(&g_z1xx, cmd + ofs, cnt);
|
||||
|
||||
// tmp.hostptr = (void*)(tmp.hostptr + (sizedwords * sizeof(unsigned int)));
|
||||
// tmp.size = 12;
|
||||
tmp.gpuaddr = ibaddr + (sizedwords * sizeof(unsigned int));
|
||||
|
||||
kgsl_sharedmem_write0(&tmp, 4, &nextaddr, 4, false);
|
||||
kgsl_sharedmem_write0(&tmp, 8, &nextcnt, 4, false);
|
||||
|
||||
/* sync mem */
|
||||
kgsl_sharedmem_write0((const struct kgsl_memdesc *)
|
||||
&g_z1xx.cmdbufdesc[g_z1xx.curr], 0,
|
||||
g_z1xx.cmdbuf[g_z1xx.curr],
|
||||
(512 + 13) * sizeof(unsigned int), false);
|
||||
|
||||
g_z1xx.offs = 0;
|
||||
g_z1xx.curr = nextbuf;
|
||||
|
||||
/* this is Freescale code but it matches a .35 msm kernel too */
|
||||
/* increment mark counter */
|
||||
#ifdef V3_SYNC
|
||||
if (device->timestamp == device->current_timestamp) {
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, flags);
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, 0);
|
||||
}
|
||||
#else
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, flags);
|
||||
kgsl_cmdwindow_write0(2, GSL_CMDWINDOW_2D, ADDR_VGV3_CONTROL, 0);
|
||||
#endif
|
||||
|
||||
/* increment consumed timestamp */
|
||||
device->current_timestamp++;
|
||||
kgsl_sharedmem_write0(&device->memstore, KGSL_DEVICE_MEMSTORE_OFFSET(soptimestamp), &device->current_timestamp, 4, 0);
|
||||
/* end FSL code */
|
||||
|
||||
return GSL_SUCCESS;
|
||||
}
|
||||
|
||||
int kgsl_g12_addtimestamp(struct kgsl_device* device, unsigned int *timestamp)
|
||||
{
|
||||
device->current_timestamp++;
|
||||
*timestamp = device->current_timestamp;
|
||||
|
||||
return GSL_SUCCESS;
|
||||
}
|
||||
50
drivers/mxc/amd-gpu/kgsl_g12_cmdstream.h
Normal file
50
drivers/mxc/amd-gpu/kgsl_g12_cmdstream.h
Normal file
@@ -0,0 +1,50 @@
|
||||
/* Copyright (c) 2002,2007-2010, Code Aurora Forum. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are
|
||||
* met:
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* * Redistributions in binary form must reproduce the above
|
||||
* copyright notice, this list of conditions and the following
|
||||
* disclaimer in the documentation and/or other materials provided
|
||||
* with the distribution.
|
||||
* * Neither the name of Code Aurora Forum, Inc. nor the names of its
|
||||
* contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
|
||||
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
|
||||
* BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
||||
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
#ifndef _GSL_CMDSTREAM_H
|
||||
#define _GSL_CMDSTREAM_H
|
||||
|
||||
#include <linux/types.h>
|
||||
#include <linux/mutex.h>
|
||||
|
||||
#include "kgsl_device.h"
|
||||
#include "kgsl_sharedmem.h"
|
||||
|
||||
struct kgsl_device;
|
||||
|
||||
int kgsl_g12_cmdstream_check_timestamp(struct kgsl_device *device,
|
||||
unsigned int timestamp);
|
||||
int kgsl_g12_cmdstream_issueibcmds(struct kgsl_device *device,
|
||||
int drawctxt_index,
|
||||
uint32_t ibaddr,
|
||||
int sizedwords,
|
||||
int *timestamp,
|
||||
unsigned int flags);
|
||||
int kgsl_g12_cmdstream_addtimestamp(struct kgsl_device *device,
|
||||
int *timestamp);
|
||||
#endif /* _GSL_CMDSTREAM_H */
|
||||
178
drivers/mxc/amd-gpu/kgsl_g12_drawctxt.c
Normal file
178
drivers/mxc/amd-gpu/kgsl_g12_drawctxt.c
Normal file
@@ -0,0 +1,178 @@
|
||||
/* Copyright (c) 2002,2007-2010, Code Aurora Forum. All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 and
|
||||
* only 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 Street, Fifth Floor, Boston, MA
|
||||
* 02110-1301, USA.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <linux/delay.h>
|
||||
#include <linux/sched.h>
|
||||
#include <linux/io.h>
|
||||
|
||||
#include "kgsl_g12_drawctxt.h"
|
||||
#include "kgsl_types.h"
|
||||
#include "kgsl_hal.h"
|
||||
#include "kgsl_cmdstream.h"
|
||||
#include "kgsl_sharedmem.h"
|
||||
#include "kgsl_driver.h"
|
||||
#include "kgsl_ioctl.h"
|
||||
|
||||
#include "kgsl_g12_vgv3types.h"
|
||||
#include "g12_reg.h"
|
||||
|
||||
struct kgsl_g12_z1xx g_z1xx = {0};
|
||||
|
||||
static void addmarker(struct kgsl_g12_z1xx *z1xx)
|
||||
{
|
||||
if (z1xx) {
|
||||
unsigned int *p = z1xx->cmdbuf[z1xx->curr];
|
||||
p[z1xx->offs++] = KGSL_G12_STREAM_PACKET;
|
||||
p[z1xx->offs++] = (KGSL_G12_MARKER_CMD | 5);
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = KGSL_G12_STREAM_PACKET;
|
||||
p[z1xx->offs++] = 5;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
p[z1xx->offs++] = ADDR_VGV3_LAST << 24;
|
||||
}
|
||||
}
|
||||
|
||||
int kgsl_g12_drawctxt_create(struct kgsl_device* device, unsigned int type, unsigned int *drawctxt_id, unsigned int flags)
|
||||
{
|
||||
int i;
|
||||
int cmd;
|
||||
int result;
|
||||
unsigned int gslflags = (GSL_MEMFLAGS_CONPHYS | GSL_MEMFLAGS_ALIGNPAGE);
|
||||
|
||||
// unreferenced formal parameters
|
||||
(void) device;
|
||||
(void) type;
|
||||
(void) flags;
|
||||
|
||||
kgsl_device_active(device);
|
||||
|
||||
if (g_z1xx.numcontext == 0) {
|
||||
g_z1xx.nextUniqueContextID = 0;
|
||||
|
||||
/* todo: move this to device create or start. Error checking!! */
|
||||
for (i = 0; i < GSL_HAL_NUMCMDBUFFERS; i++) {
|
||||
if (kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags,
|
||||
GSL_HAL_CMDBUFFERSIZE, &g_z1xx.cmdbufdesc[i]) != GSL_SUCCESS)
|
||||
return GSL_FAILURE;
|
||||
|
||||
g_z1xx.cmdbuf[i] = kzalloc(GSL_HAL_CMDBUFFERSIZE, GFP_KERNEL);
|
||||
|
||||
g_z1xx.curr = i;
|
||||
g_z1xx.offs = 0;
|
||||
addmarker(&g_z1xx);
|
||||
kgsl_sharedmem_write0(&g_z1xx.cmdbufdesc[i], 0, g_z1xx.cmdbuf[i],
|
||||
(512 + 13) * sizeof(unsigned int), false);
|
||||
}
|
||||
|
||||
g_z1xx.curr = 0;
|
||||
cmd = VGV3_NEXTCMD_JUMP << VGV3_NEXTCMD_NEXTCMD_FSHIFT;
|
||||
|
||||
/* set cmd stream buffer to hw */
|
||||
result = kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D,
|
||||
ADDR_VGV3_MODE, 4);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
result = kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D,
|
||||
ADDR_VGV3_NEXTADDR,
|
||||
g_z1xx.cmdbufdesc[0].gpuaddr );
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
result = kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D,
|
||||
ADDR_VGV3_NEXTCMD, cmd | 5);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
/*
|
||||
* NOTE: diverges from upstream Qualcomm code...!!!
|
||||
* there are some cmdwindow writes to VGV3_CONTROL to add markers?
|
||||
*/
|
||||
|
||||
|
||||
/* NOTE: this may be done in Qualcomm's userspace...
|
||||
*
|
||||
* Edge buffer setup todo: move register setup to own function.
|
||||
* This function can be then called, if power managemnet is used and clocks are turned off and then on.
|
||||
*/
|
||||
result = kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_EDGE0BUFSIZE, &g_z1xx.e0);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
result = kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_EDGE1BUFSIZE, &g_z1xx.e1);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
result = kgsl_sharedmem_set0(&g_z1xx.e0, 0, 0, GSL_HAL_EDGE0BUFSIZE);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
result = kgsl_sharedmem_set0(&g_z1xx.e1, 0, 0, GSL_HAL_EDGE1BUFSIZE);
|
||||
|
||||
result = kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, GSL_HAL_EDGE0REG, g_z1xx.e0.gpuaddr);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
result = kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, GSL_HAL_EDGE1REG, g_z1xx.e1.gpuaddr);
|
||||
if (result != GSL_SUCCESS)
|
||||
return result;
|
||||
|
||||
#ifdef _Z180
|
||||
kgsl_sharedmem_alloc0(KGSL_DEVICE_ANY, gslflags, GSL_HAL_EDGE2BUFSIZE, &g_z1xx.e2);
|
||||
kgsl_sharedmem_set0(&g_z1xx.e2, 0, 0, GSL_HAL_EDGE2BUFSIZE);
|
||||
kgsl_cmdwindow_write0(KGSL_DEVICE_G12, GSL_CMDWINDOW_2D, GSL_HAL_EDGE2REG, g_z1xx.e2.gpuaddr);
|
||||
#endif
|
||||
}
|
||||
|
||||
/* diverge from qualcomm - it returns numcontext */
|
||||
g_z1xx.numcontext++;
|
||||
g_z1xx.nextUniqueContextID++;
|
||||
*drawctxt_id = g_z1xx.nextUniqueContextID;
|
||||
|
||||
return GSL_SUCCESS;
|
||||
}
|
||||
|
||||
int kgsl_g12_drawctxt_destroy(struct kgsl_device* device, unsigned int drawctxt_id)
|
||||
{
|
||||
(void) device;
|
||||
(void) drawctxt_id;
|
||||
|
||||
g_z1xx.numcontext--;
|
||||
if (g_z1xx.numcontext < 0) {
|
||||
g_z1xx.numcontext=0;
|
||||
return GSL_FAILURE;
|
||||
}
|
||||
|
||||
if (g_z1xx.numcontext == 0) {
|
||||
int i;
|
||||
for (i = 0; i < GSL_HAL_NUMCMDBUFFERS; i++) {
|
||||
kgsl_sharedmem_free0(&g_z1xx.cmdbufdesc[i], current->tgid);
|
||||
kfree(g_z1xx.cmdbuf[i]);
|
||||
}
|
||||
/* remember, qualcomm's code doesn't have these edge buffers? */
|
||||
kgsl_sharedmem_free0(&g_z1xx.e0, current->tgid);
|
||||
kgsl_sharedmem_free0(&g_z1xx.e1, current->tgid);
|
||||
#ifdef _Z180
|
||||
kgsl_sharedmem_free0(&g_z1xx.e2, current->tgid);
|
||||
#endif
|
||||
}
|
||||
return GSL_SUCCESS;
|
||||
}
|
||||
129
drivers/mxc/amd-gpu/kgsl_g12_drawctxt.h
Normal file
129
drivers/mxc/amd-gpu/kgsl_g12_drawctxt.h
Normal file
@@ -0,0 +1,129 @@
|
||||
/* Copyright (c) 2002,2007-2010, Code Aurora Forum. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are
|
||||
* met:
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* * Redistributions in binary form must reproduce the above
|
||||
* copyright notice, this list of conditions and the following
|
||||
* disclaimer in the documentation and/or other materials provided
|
||||
* with the distribution.
|
||||
* * Neither the name of Code Aurora Forum, Inc. nor the names of its
|
||||
* contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
|
||||
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
|
||||
* BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
||||
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
#ifndef __GSL_DRAWCTXT_G12_H
|
||||
#define __GSL_DRAWCTXT_G12_H
|
||||
|
||||
#include "kgsl_sharedmem.h"
|
||||
|
||||
struct kgsl_device;
|
||||
|
||||
#define GSL_HAL_NUMCMDBUFFERS 5
|
||||
#define GSL_HAL_CMDBUFFERSIZE ((1024 + 13) * sizeof(unsigned int))
|
||||
|
||||
#define ALIGN_IN_BYTES(dim, alignment) (((dim) + (alignment - 1)) & \
|
||||
~(alignment - 1))
|
||||
|
||||
|
||||
|
||||
#define PACKETSIZE_BEGIN 3
|
||||
#define PACKETSIZE_G2DCOLOR 2
|
||||
#define PACKETSIZE_TEXUNIT (TEXUNITREGCOUNT * 2)
|
||||
#define PACKETSIZE_REG (VG_REGCOUNT * 2)
|
||||
#define PACKETSIZE_STATE (PACKETSIZE_TEXUNIT * NUMTEXUNITS + \
|
||||
PACKETSIZE_REG + PACKETSIZE_BEGIN + \
|
||||
PACKETSIZE_G2DCOLOR)
|
||||
#define PACKETSIZE_STATESTREAM (ALIGN_IN_BYTES((PACKETSIZE_STATE * \
|
||||
sizeof(unsigned int)), 32) / \
|
||||
sizeof(unsigned int))
|
||||
|
||||
|
||||
#define KGSL_G12_PACKET_SIZE 15
|
||||
#define KGSL_G12_MARKER_SIZE 10
|
||||
#define KGSL_G12_CALL_CMD 0x1000
|
||||
#define KGSL_G12_MARKER_CMD 0x8000
|
||||
#define KGSL_G12_STREAM_END_CMD 0x9000
|
||||
#define KGSL_G12_STREAM_PACKET 0x7C000176
|
||||
#define KGSL_G12_STREAM_PACKET_CALL 0x7C000275
|
||||
|
||||
struct kgsl_g12_hal_z1xxdrawctx_t {
|
||||
unsigned int id;
|
||||
};
|
||||
|
||||
struct kgsl_g12_z1xx {
|
||||
unsigned int offs;
|
||||
unsigned int curr;
|
||||
unsigned int prevctx;
|
||||
|
||||
struct kgsl_memdesc e0;
|
||||
struct kgsl_memdesc e1;
|
||||
#ifdef _Z180
|
||||
struct kgsl_memdesc e2;
|
||||
#endif
|
||||
unsigned int *cmdbuf[GSL_HAL_NUMCMDBUFFERS];
|
||||
struct kgsl_memdesc cmdbufdesc[GSL_HAL_NUMCMDBUFFERS];
|
||||
unsigned int timestamp[GSL_HAL_NUMCMDBUFFERS];
|
||||
|
||||
unsigned int numcontext;
|
||||
unsigned int nextUniqueContextID;
|
||||
};
|
||||
|
||||
extern struct kgsl_g12_z1xx g_z1xx;
|
||||
extern int z160_version;
|
||||
|
||||
int
|
||||
kgsl_g12_drawctxt_create(struct kgsl_device *device,
|
||||
unsigned int type,
|
||||
unsigned int *drawctxt_id,
|
||||
unsigned int flags);
|
||||
|
||||
int
|
||||
kgsl_g12_drawctxt_destroy(struct kgsl_device *device,
|
||||
unsigned int drawctxt_id);
|
||||
|
||||
|
||||
#ifdef _Z180
|
||||
#define NUMTEXUNITS 4
|
||||
#define TEXUNITREGCOUNT 25
|
||||
#define VG_REGCOUNT 0x39
|
||||
#define GSL_HAL_EDGE0BUFSIZE 0x3E8 + 64
|
||||
#define GSL_HAL_EDGE1BUFSIZE 0x8000 + 64
|
||||
#define GSL_HAL_EDGE2BUFSIZE 0x80020 + 64
|
||||
#define GSL_HAL_EDGE0REG ADDR_VGV1_CBUF
|
||||
#define GSL_HAL_EDGE1REG ADDR_VGV1_BBUF
|
||||
#define GSL_HAL_EDGE2REG ADDR_VGV1_EBUF
|
||||
#else
|
||||
#define NUMTEXUNITS 2
|
||||
#define TEXUNITREGCOUNT 24
|
||||
#define VG_REGCOUNT 0x3A
|
||||
#define L1TILESIZE 64
|
||||
#define GSL_HAL_EDGE0BUFSIZE L1TILESIZE * L1TILESIZE * 4 + 64
|
||||
#define GSL_HAL_EDGE1BUFSIZE L1TILESIZE * L1TILESIZE * 16 + 64
|
||||
#define GSL_HAL_EDGE0REG ADDR_VGV1_CBASE1
|
||||
#define GSL_HAL_EDGE1REG ADDR_VGV1_UBASE2
|
||||
#endif
|
||||
|
||||
/* should be in kgsl_g12_drawctxt.h? */
|
||||
int kgsl_g12_addtimestamp(struct kgsl_device* device, unsigned int *timestamp);
|
||||
int kgsl_g12_issueibcmds(struct kgsl_device* device, int drawctxt_index, uint32_t ibaddr, int sizedwords, unsigned int *timestamp, unsigned int flags);
|
||||
int kgsl_g12_drawctxt_create(struct kgsl_device* device, unsigned int type, unsigned int *drawctxt_id, unsigned int flags);
|
||||
int kgsl_g12_drawctxt_destroy(struct kgsl_device* device, unsigned int drawctxt_id);
|
||||
|
||||
|
||||
|
||||
#endif /* __GSL_DRAWCTXT_H */
|
||||
@@ -409,6 +409,7 @@ static int gsl_kmod_ioctl(struct inode *inode, struct file *fd, unsigned int cmd
|
||||
kgsl_context_create_t param;
|
||||
unsigned int tmp;
|
||||
int tmpStatus;
|
||||
struct kgsl_device *device;
|
||||
|
||||
#if defined(GSL_IOCTL_DEBUG)
|
||||
printk(KERN_INFO "--> %s: IOCTL_KGSL_CONTEXT_CREATE\n", __func__);
|
||||
@@ -420,14 +421,20 @@ static int gsl_kmod_ioctl(struct inode *inode, struct file *fd, unsigned int cmd
|
||||
kgslStatus = GSL_FAILURE;
|
||||
break;
|
||||
}
|
||||
kgslStatus = kgsl_context_create(param.device_id, param.type, &tmp, param.flags);
|
||||
device = &gsl_driver.device[param.device_id-1];
|
||||
mutex_lock(&gsl_driver.lock);
|
||||
kgslStatus = device->ftbl.device_drawctxt_create(device, param.type, &tmp, param.flags);
|
||||
mutex_unlock(&gsl_driver.lock);
|
||||
|
||||
if (kgslStatus == GSL_SUCCESS)
|
||||
{
|
||||
if (copy_to_user(param.drawctxt_id, &tmp, sizeof(unsigned int)))
|
||||
{
|
||||
tmpStatus = kgsl_context_destroy(param.device_id, tmp);
|
||||
mutex_lock(&gsl_driver.lock);
|
||||
tmpStatus = device->ftbl.device_drawctxt_destroy(device, *param.drawctxt_id);
|
||||
mutex_unlock(&gsl_driver.lock);
|
||||
/* is asserting ok? Basicly we should return the error from copy_to_user
|
||||
* but will the user space interpret it correctly? Will the user space
|
||||
* but will the user space interpret it correctly? Will the user space
|
||||
* always check against GSL_SUCCESS or GSL_FAILURE as they are not the only
|
||||
* return values.
|
||||
*/
|
||||
@@ -446,6 +453,7 @@ static int gsl_kmod_ioctl(struct inode *inode, struct file *fd, unsigned int cmd
|
||||
case IOCTL_KGSL_CONTEXT_DESTROY:
|
||||
{
|
||||
kgsl_context_destroy_t param;
|
||||
struct kgsl_device *device;
|
||||
#if defined(GSL_IOCTL_DEBUG)
|
||||
printk(KERN_INFO "--> %s: IOCTL_KGSL_CONTEXT_DESTROY\n", __func__);
|
||||
#endif
|
||||
@@ -455,7 +463,12 @@ static int gsl_kmod_ioctl(struct inode *inode, struct file *fd, unsigned int cmd
|
||||
kgslStatus = GSL_FAILURE;
|
||||
break;
|
||||
}
|
||||
kgslStatus = kgsl_context_destroy(param.device_id, param.drawctxt_id);
|
||||
device = &gsl_driver.device[param.device_id-1];
|
||||
|
||||
mutex_lock(&gsl_driver.lock);
|
||||
kgslStatus = device->ftbl.device_drawctxt_destroy(device, param.drawctxt_id);
|
||||
mutex_unlock(&gsl_driver.lock);
|
||||
|
||||
del_device_context_from_array(fd, param.device_id, param.drawctxt_id);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/fs.h>
|
||||
|
||||
#include "kgsl_driver.h"
|
||||
#include "kgsl_kmod_cleanup.h"
|
||||
#include "kgsl_device.h"
|
||||
#include "kgsl_drawctxt.h"
|
||||
@@ -243,7 +244,7 @@ void del_all_devices_contexts(struct file *fd)
|
||||
u32 ctx_array_index;
|
||||
s8 ctx;
|
||||
int err;
|
||||
|
||||
|
||||
datp = get_fd_private_data(fd);
|
||||
|
||||
/* device_id is 1 based */
|
||||
@@ -255,7 +256,15 @@ void del_all_devices_contexts(struct file *fd)
|
||||
ctx = datp->created_contexts_array[device_index][ctx_array_index];
|
||||
if(ctx != EMPTY_ENTRY)
|
||||
{
|
||||
err = kgsl_context_destroy(id, ctx);
|
||||
struct kgsl_device *device = &gsl_driver.device[id];
|
||||
|
||||
if (device && device->ftbl.device_drawctxt_destroy) {
|
||||
mutex_lock(&gsl_driver.lock);
|
||||
err = device->ftbl.device_drawctxt_destroy(device, ctx);
|
||||
mutex_unlock(&gsl_driver.lock);
|
||||
} else
|
||||
err = GSL_FAILURE;
|
||||
|
||||
if(err != GSL_SUCCESS)
|
||||
{
|
||||
printk(KERN_ERR "%s: could not destroy context %d on device id = %u\n", __func__, ctx, id);
|
||||
|
||||
@@ -929,8 +929,8 @@ kgsl_yamato_getfunctable(struct kgsl_functable *ftbl)
|
||||
ftbl->mmu_tlbinvalidate = kgsl_yamato_tlbinvalidate;
|
||||
ftbl->mmu_setpagetable = kgsl_yamato_setpagetable;
|
||||
ftbl->cmdstream_issueibcmds = kgsl_ringbuffer_issueibcmds;
|
||||
ftbl->context_create = kgsl_drawctxt_create;
|
||||
ftbl->context_destroy = kgsl_drawctxt_destroy;
|
||||
ftbl->device_drawctxt_create = kgsl_drawctxt_create;
|
||||
ftbl->device_drawctxt_destroy = kgsl_drawctxt_destroy;
|
||||
|
||||
return (GSL_SUCCESS);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user