Commit 472f7a03 authored by julbouln's avatar julbouln
Browse files

trapezoids & triangles optimization

parent fee6e7c9
......@@ -97,7 +97,7 @@ ARMSOCPixmapExchange(PixmapPtr a, PixmapPtr b)
static void *
CreateExaPixmap(struct ARMSOCPixmapPrivRec *priv, ScreenPtr pScreen, int width, int height,
int depth, int bitsPerPixel,
int depth, int usage_hint, int bitsPerPixel,
int *new_fb_pitch)
{
ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen);
......@@ -107,7 +107,7 @@ CreateExaPixmap(struct ARMSOCPixmapPrivRec *priv, ScreenPtr pScreen, int width,
#ifdef ARMSOC_EXA_DEBUG
INFO_MSG("CreateExaPixmap %dx%d %d %d", width, height, depth, bitsPerPixel);
#endif
pARMSOC->pARMSOCEXA->AllocBuf(pARMSOC->pARMSOCEXA, width, height, depth, bitsPerPixel, &priv->buf);
pARMSOC->pARMSOCEXA->AllocBuf(pARMSOC->pARMSOCEXA, width, height, depth, bitsPerPixel, usage_hint, &priv->buf);
if (!priv->buf.buf) {
ERROR_MSG("failed to allocate %dx%d mem", width, height);
......@@ -122,7 +122,7 @@ CreateExaPixmap(struct ARMSOCPixmapPrivRec *priv, ScreenPtr pScreen, int width,
static void *
CreateDumbPixmap(struct ARMSOCPixmapPrivRec *priv, ScreenPtr pScreen, int width, int height,
int depth, int bitsPerPixel,
int depth, int usage_hint, int bitsPerPixel,
int *new_fb_pitch)
{
ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen);
......@@ -195,9 +195,9 @@ ARMSOCCreatePixmap2(ScreenPtr pScreen, int width, int height,
#endif
if (IsDumbPixmap(priv, width * height * (bitsPerPixel / 8)))
return CreateDumbPixmap(priv, pScreen, width, height, depth, bitsPerPixel, new_fb_pitch);
return CreateDumbPixmap(priv, pScreen, width, height, depth, usage_hint, bitsPerPixel, new_fb_pitch);
else
return CreateExaPixmap(priv, pScreen, width, height, depth, bitsPerPixel, new_fb_pitch);
return CreateExaPixmap(priv, pScreen, width, height, depth, usage_hint, bitsPerPixel, new_fb_pitch);
}
_X_EXPORT void
......@@ -329,7 +329,7 @@ ModifyExaPixmapHeader(struct ARMSOCPixmapPrivRec *priv, PixmapPtr pPixmap, int w
}
// INFO_MSG("AllocBuf modify %p",&priv->buf);
pARMSOC->pARMSOCEXA->AllocBuf(pARMSOC->pARMSOCEXA, pPixmap->drawable.width, pPixmap->drawable.height, pPixmap->drawable.depth, pPixmap->drawable.bitsPerPixel, &priv->buf);
pARMSOC->pARMSOCEXA->AllocBuf(pARMSOC->pARMSOCEXA, pPixmap->drawable.width, pPixmap->drawable.height, pPixmap->drawable.depth, pPixmap->drawable.bitsPerPixel, 0, &priv->buf);
if (!priv->buf.buf) {
INFO_MSG("ModifyExaPixmapHeader failed to allocate buffer");
......
......@@ -72,7 +72,7 @@ struct ARMSOCEXARec {
void (*Reattach)(PixmapPtr pixmap, int width, int height, int stride);
// EXA driver buffer allocation, typically let the render DRI card create buffers
void (*AllocBuf)(struct ARMSOCEXARec *exa, int width, int height, int depth, int bpp, struct ARMSOCEXABuf *buf);
void (*AllocBuf)(struct ARMSOCEXARec *exa, int width, int height, int depth, int bpp, int usage_hint, struct ARMSOCEXABuf *buf);
// EXA driver buffer freeing
void (*FreeBuf)(struct ARMSOCEXARec *exa, struct ARMSOCEXABuf *buf);
......
......@@ -53,7 +53,7 @@ struct ARMSOCNullEXARec {
/* add any other driver private data here.. */
};
static void AllocBuf(struct ARMSOCEXARec *exa, int width, int height, int depth, int bpp, struct ARMSOCEXABuf *buf) {
static void AllocBuf(struct ARMSOCEXARec *exa, int width, int height, int depth, int bpp, int usage_hint, struct ARMSOCEXABuf *buf) {
int pitch = ((width * bpp + FB_MASK) >> FB_SHIFT) * sizeof(FbBits);
size_t size = pitch * height;
buf->buf = malloc(size);
......
......@@ -94,7 +94,7 @@ void etna_bo_cache_init(struct etna_device *dev) {
#endif
}
struct etna_bo *etna_bo_cache_new(struct etna_device *dev, size_t size) {
struct etna_bo *etna_bo_cache_new(struct etna_device *dev, size_t size, int flags) {
#ifdef ETNAVIV_CUSTOM
struct etna_bo_cache *cache = dev->cache;
size_t aligned_size = ALIGN(size, ETNA_BO_CACHE_PAGE_SIZE);
......@@ -138,7 +138,8 @@ struct etna_bo *etna_bo_cache_new(struct etna_device *dev, size_t size) {
return NULL;
#else
struct etna_bo *bo = etna_bo_new(dev, size, ETNA_BO_WC);
struct etna_bo *bo;
bo = etna_bo_new(dev, size, flags);
CACHE_DEBUG_MSG("etna_bo_new: new bo:%p", bo);
return bo;
#endif
......@@ -278,11 +279,19 @@ void etna_nop(struct etna_cmd_stream *stream) {
etna_cmd_stream_emit(stream, 0x18000000);
}
void etna_bo_unmap(struct etna_bo *bo) {
if (bo->map) {
munmap(bo->map, bo->size);
bo->map = NULL;
}
}
int etna_bo_ready(struct etna_bo *bo) {
#ifdef ETNAVIV_CUSTOM
return (bo->state == ETNA_BO_READY);
#else
return 1;
return (bo->current_stream == NULL);
#endif
}
......
......@@ -40,7 +40,7 @@ struct etna_bo_cache {
// cache
void etna_bo_cache_destroy(struct etna_device *dev);
void etna_bo_cache_init(struct etna_device *dev);
struct etna_bo *etna_bo_cache_new(struct etna_device *dev, size_t size);
struct etna_bo *etna_bo_cache_new(struct etna_device *dev, size_t size, int flags);
void etna_bo_cache_del(struct etna_device *dev, struct etna_bo *bo);
void etna_bo_cache_clean(struct etna_device *dev);
void etna_bo_cache_usermem_del(struct etna_device *dev, struct etna_bo *bo);
......
......@@ -23,7 +23,7 @@
#define VIV2D_SUPPORT_A8_MASK 1
// EXPERIMENTAL
//#define VIV2D_PREPARE_SET_FORMAT 1
#define VIV2D_PREPARE_SET_FORMAT 1
//#define VIV2D_FILL_BRUSH 1
//#define VIV2D_SUPPORT_A8_DST 1
//#define VIV2D_SUPPORT_MONO 1
......@@ -34,6 +34,7 @@
#define VIV2D_MASK_COMPONENT_SUPPORT 1
#define VIV2D_FLUSH_CALLBACK 1
#define VIV2D_CACHE_FLUSH_OPS 1
#define VIV2D_EXA_HACK 1
// CPU only for surface < VIV2D_MIN_SIZE and > VIV2D_MAX_SIZE
#define VIV2D_MAX_SIZE 2048*2048*4 // 16Mbytes
......
......@@ -144,7 +144,7 @@ static void Viv2DFlush(struct ARMSOCEXARec *exa) {
}
static void Viv2DAllocBuf(struct ARMSOCEXARec *exa, int width, int height, int depth, int bpp, struct ARMSOCEXABuf *buf) {
static void Viv2DAllocBuf(struct ARMSOCEXARec *exa, int width, int height, int depth, int bpp, int usage_hint, struct ARMSOCEXABuf *buf) {
Viv2DEXAPtr v2d_exa = (Viv2DEXAPtr)(exa);
Viv2DRec *v2d = v2d_exa->v2d;
......@@ -155,10 +155,10 @@ static void Viv2DAllocBuf(struct ARMSOCEXARec *exa, int width, int height, int d
Viv2DFormat fmt;
// do not create etna bo if too small or unsupported format
if (size > VIV2D_MIN_SIZE && size < VIV2D_MAX_SIZE && _Viv2DSetFormat(depth, bpp, &fmt)) {
if (size > VIV2D_MIN_SIZE && size < VIV2D_MAX_SIZE) { // && _Viv2DSetFormat(depth, bpp, &fmt)) {
struct etna_bo *bo;
// VIV2D_INFO_MSG("Viv2DAllocBuf size:%d pitch:%d", pitch * height, pitch);
bo = etna_bo_cache_new(v2d->dev, size);
bo = etna_bo_cache_new(v2d->dev, size, ETNA_BO_WC);
buf->priv = (void *)bo;
buf->buf = etna_bo_map(bo);
} else {
......@@ -304,6 +304,7 @@ static void Viv2DReattach(PixmapPtr pPixmap, int width, int height, int pitch) {
Viv2DAttachBo(pARMSOC, armsocPix);
}
// from libyuv
static inline void ARGBExtractAlphaRow_NEON(const uint8_t* src_argb,
uint8_t* dst_a,
......@@ -407,6 +408,25 @@ static inline uint32_t idx2op(int index)
}
}
static PixmapPtr
GetDrawablePixmap(DrawablePtr pDrawable) {
/* Make sure there is a drawable. */
if (NULL == pDrawable) {
return NULL;
}
/* Check for a backing pixmap. */
if (DRAWABLE_WINDOW == pDrawable->type) {
WindowPtr pWindow = (WindowPtr) pDrawable;
return pDrawable->pScreen->GetWindowPixmap(pWindow);
}
/* Otherwise, it's a regular pixmap. */
return (PixmapPtr) pDrawable;
}
#ifdef VIV2D_FLUSH_CALLBACK
static void Viv2DFlushCallback(CallbackListPtr *list, pointer user_data,
pointer call_data)
......@@ -481,7 +501,9 @@ Viv2DPrepareAccess(PixmapPtr pPixmap, int index) {
_Viv2DStreamCommit(v2d, TRUE);
_Viv2DStreamWait(v2d);
}
etna_bo_cpu_prep(pix->bo, idx2op(index));
#ifdef VIV2D_TRACE
_Viv2DPixTrace(pix, "prep");
#endif
......@@ -515,10 +537,75 @@ Viv2DFinishAccess(PixmapPtr pPixmap, int index)
etna_bo_cpu_fini(pix->bo);
VIV2D_DBG_MSG("Viv2DFinishAccess pix:%p/%p(%dx%d) bo:%p index:%d refcnt:(%d)", pPixmap, pix, pix->width, pix->height, pix->bo, index, pix->refcnt);
}
pix->refcnt = 0;
}
}
#ifdef VIV2D_EXA_HACK
#include "fb.h"
#include "fbpict.h"
// Trapezoids hack
void Viv2DTrapezoids(CARD8 op, PicturePtr pSrcPicture, PicturePtr pDstPicture,
PictFormatPtr maskFormat, INT16 xSrc, INT16 ySrc, int ntrap,
xTrapezoid * traps)
{
PixmapPtr pSrc = GetDrawablePixmap(pSrcPicture->pDrawable);
PixmapPtr pDst = GetDrawablePixmap(pDstPicture->pDrawable);
if (pSrc)
Viv2DPrepareAccess(pSrc, EXA_PREPARE_SRC);
if (pDst)
Viv2DPrepareAccess(pDst, EXA_PREPARE_DEST);
fbTrapezoids(op, pSrcPicture, pDstPicture, maskFormat, xSrc, ySrc, ntrap, traps);
if (pDst)
Viv2DFinishAccess(pDst, EXA_PREPARE_DEST);
if (pSrc)
Viv2DFinishAccess(pSrc, EXA_PREPARE_SRC);
}
void Viv2DAddTraps(PicturePtr pPicture, INT16 x_off, INT16 y_off,
int ntrap, xTrap *traps)
{
PixmapPtr pPix = GetDrawablePixmap(pPicture->pDrawable);
Viv2DPrepareAccess(pPix, EXA_PREPARE_DEST);
fbAddTraps(pPicture, x_off, y_off, ntrap, traps);
Viv2DFinishAccess(pPix, EXA_PREPARE_DEST);
}
void Viv2DTriangles(CARD8 op, PicturePtr pSrcPicture, PicturePtr pDstPicture,
PictFormatPtr maskFormat, INT16 xSrc, INT16 ySrc, int ntri, xTriangle *tri)
{
PixmapPtr pSrc = GetDrawablePixmap(pSrcPicture->pDrawable);
PixmapPtr pDst = GetDrawablePixmap(pDstPicture->pDrawable);
if (pSrc)
Viv2DPrepareAccess(pSrc, EXA_PREPARE_SRC);
if (pDst)
Viv2DPrepareAccess(pDst, EXA_PREPARE_DEST);
fbTriangles(op, pSrcPicture, pDstPicture, maskFormat, xSrc, ySrc, ntri, tri);
if (pDst)
Viv2DFinishAccess(pDst, EXA_PREPARE_DEST);
if (pSrc)
Viv2DFinishAccess(pSrc, EXA_PREPARE_SRC);
}
void Viv2DAddTriangles(PicturePtr pPicture, INT16 x_off, INT16 y_off,
int ntri, xTriangle *tris)
{
PixmapPtr pPix = GetDrawablePixmap(pPicture->pDrawable);
Viv2DPrepareAccess(pPix, EXA_PREPARE_DEST);
fbAddTriangles(pPicture, x_off, y_off, ntri, tris);
Viv2DFinishAccess(pPix, EXA_PREPARE_DEST);
}
#endif
/**
* PixmapIsOffscreen() is an optional driver replacement to
* exaPixmapHasGpuCopy(). Set to NULL if you want the standard behaviour
......@@ -555,14 +642,15 @@ Viv2DCreatePixmap2 (ScreenPtr pScreen, int width, int height,
{
struct ARMSOCPixmapPrivRec *armsocPix = ARMSOCCreatePixmap2(pScreen, width, height, depth,
usage_hint, bitsPerPixel, new_fb_pitch);
Viv2DPixmapPrivPtr pix = calloc(sizeof(Viv2DPixmapPrivRec), 1);
VIV2D_DBG_MSG("Viv2DCreatePixmap pix %p", pix);
_Viv2DSetFormat(32, 32, &pix->format);
if (armsocPix) {
Viv2DPixmapPrivPtr pix = calloc(sizeof(Viv2DPixmapPrivRec), 1);
VIV2D_DBG_MSG("Viv2DCreatePixmap pix %p", pix);
armsocPix->priv = pix;
pix->armsocPix = armsocPix;
_Viv2DSetFormat(32, 32, &pix->format);
armsocPix->priv = pix;
pix->armsocPix = armsocPix;
}
return armsocPix;
}
......@@ -797,11 +885,11 @@ static Bool Viv2DUploadToScreen(PixmapPtr pDst,
_Viv2DStreamCacheFlush(v2d);
VIV2D_DBG_MSG("Viv2DUploadToScreen blit done dst:%p/%p bo:%p buf:%p src_buf:%p(%d/%d) %dx%d(%dx%d) %dx%d %d/%d",
pDst, dst, dst->bo, etna_bo_map(dst->bo),
src, src_pitch, tmp->pitch, x, y, w, h,
pDst->drawable.width, pDst->drawable.height,
pDst->drawable.depth, pDst->drawable.bitsPerPixel);
VIV2D_INFO_MSG("Viv2DUploadToScreen blit done dst:%p/%p bo:%p buf:%p src_buf:%p(%d/%d) %dx%d(%dx%d) %dx%d %d/%d",
pDst, dst, dst->bo, etna_bo_map(dst->bo),
src, src_pitch, tmp->pitch, x, y, w, h,
pDst->drawable.width, pDst->drawable.height,
pDst->drawable.depth, pDst->drawable.bitsPerPixel);
#ifdef VIV2D_USERPTR
if (use_usermem) {
......@@ -916,8 +1004,6 @@ static Bool Viv2DDownloadFromScreen(PixmapPtr pSrc,
etna_bo_cpu_fini(tmp->bo);
// munmap(src_buf, etna_bo_size(tmp->bo));
VIV2D_INFO_MSG("Viv2DDownloadFromScreen blit done %p %p %p(%d/%d) %dx%d(%dx%d) %dx%d %d/%d", pSrc, etna_bo_map(src->bo), src, pitch, tmp->pitch, x, y, w, h,
pSrc->drawable.width, pSrc->drawable.height,
pSrc->drawable.depth, pSrc->drawable.bitsPerPixel);
......@@ -1296,24 +1382,6 @@ PrepareCopyFail(PixmapPtr pSrc, PixmapPtr pDst, int xdir, int ydir,
#ifdef VIV2D_COMPOSITE
static PixmapPtr
GetDrawablePixmap(DrawablePtr pDrawable) {
/* Make sure there is a drawable. */
if (NULL == pDrawable) {
return NULL;
}
/* Check for a backing pixmap. */
if (DRAWABLE_WINDOW == pDrawable->type) {
WindowPtr pWindow = (WindowPtr) pDrawable;
return pDrawable->pScreen->GetWindowPixmap(pWindow);
}
/* Otherwise, it's a regular pixmap. */
return (PixmapPtr) pDrawable;
}
static Bool Viv2DGetPictureFormat(int exa_fmt, Viv2DFormat * fmt) {
int i;
Bool isFound = FALSE;
......@@ -1887,9 +1955,9 @@ Viv2DComposite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
_Viv2DSetFormat(32, 32, &tmp->format); // A8R8G8B8
// do not need to to alpha blend for solid src
// if (v2d->op.src_type == viv2d_src_solid) {
if (v2d->op.src_type == viv2d_src_solid) {
// cpy_op = NULL;
// }
}
_Viv2DStreamCompAlpha(v2d, v2d->op.src_type, v2d->op.src, &v2d->op.src_fmt, v2d->op.fg, tmp, cpy_op,
v2d->op.src_alpha_mode_global, v2d->op.src_alpha,
......@@ -1900,7 +1968,6 @@ Viv2DComposite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY,
v2d->op.msk_alpha_mode_global, v2d->op.msk_alpha,
FALSE, 0,
maskX, maskY, width, height, mrect, 1);
// }
_Viv2DStreamCompAlpha(v2d, viv2d_src_pix, tmp, &tmp->format, 0, v2d->op.dst, v2d->op.blend_op,
FALSE, 0,
......@@ -2447,6 +2514,15 @@ InitViv2DEXA(ScreenPtr pScreen, ScrnInfoPtr pScrn, int fd)
goto fail;
}
#ifdef VIV2D_EXA_HACK
// Trapezoids hack
PictureScreenPtr ps = GetPictureScreenIfSet(pScreen);
ps->Trapezoids = Viv2DTrapezoids;
ps->AddTraps = Viv2DAddTraps;
ps->Triangles = Viv2DTriangles;
ps->AddTriangles = Viv2DAddTriangles;
#endif
armsoc_exa->CloseScreen = CloseScreen;
armsoc_exa->FreeScreen = FreeScreen;
......
......@@ -594,7 +594,7 @@ static inline Viv2DPixmapPrivPtr _Viv2DOpCreateTmpPix(Viv2DPtr v2d, int width, i
tmp = calloc(sizeof(*tmp), 1);
pitch = ALIGN(width * ((bpp + 7) / 8), VIV2D_PITCH_ALIGN);
tmp->bo = etna_bo_cache_new(v2d->dev, pitch * height);
tmp->bo = etna_bo_cache_new(v2d->dev, pitch * height, ETNA_BO_WC);
VIV2D_OP_DBG_MSG("_Viv2DOpCreateTmpPix bo:%p %dx%d %d", tmp->bo, width, height, pitch * height);
tmp->width = width;
......
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