i915: resize surface

git-svn-id: svn://kolibrios.org@3039 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
Sergey Semyonov (Serge) 2012-11-15 08:04:26 +00:00
parent aee4b03443
commit 8afe7310a7
8 changed files with 144 additions and 16 deletions

View File

@ -62,6 +62,7 @@
.global _TimerHs .global _TimerHs
.global _UserAlloc .global _UserAlloc
.global _UserFree
.global _WaitEvent .global _WaitEvent
@ -123,6 +124,7 @@
.def _TimerHs; .scl 2; .type 32; .endef .def _TimerHs; .scl 2; .type 32; .endef
.def _UserAlloc; .scl 2; .type 32; .endef .def _UserAlloc; .scl 2; .type 32; .endef
.def _UserFree; .scl 2; .type 32; .endef
.def _WaitEvent; .scl 2; .type 32; .endef .def _WaitEvent; .scl 2; .type 32; .endef
@ -185,6 +187,7 @@ _SysMsgBoardStr:
_TimerHs: _TimerHs:
_UserAlloc: _UserAlloc:
_UserFree:
_WaitEvent: _WaitEvent:
ret ret
@ -252,6 +255,7 @@ _WaitEvent:
.ascii " -export:TimerHs" # stdcall .ascii " -export:TimerHs" # stdcall
.ascii " -export:UserAlloc" # stdcall .ascii " -export:UserAlloc" # stdcall
.ascii " -export:UserFree" # stdcall
.ascii " -export:WaitEvent" # stdcall .ascii " -export:WaitEvent" # stdcall

View File

@ -89,9 +89,9 @@ typedef unsigned int flag_t; /* The type of various bit flag sets */
#define NO_SEGMENT_TRAVERSAL 1 #define NO_SEGMENT_TRAVERSAL 1
#define MALLOC_ALIGNMENT ((size_t)8U) #define MALLOC_ALIGNMENT ((size_t)8U)
#define CHUNK_OVERHEAD (SIZE_T_SIZE) #define CHUNK_OVERHEAD (SIZE_T_SIZE)
#define DEFAULT_GRANULARITY ((size_t)64U * (size_t)1024U) #define DEFAULT_GRANULARITY ((size_t)128U * (size_t)1024U)
#define DEFAULT_MMAP_THRESHOLD ((size_t)256U * (size_t)1024U) #define DEFAULT_MMAP_THRESHOLD ((size_t)512U * (size_t)1024U)
#define DEFAULT_TRIM_THRESHOLD ((size_t)512U * (size_t)1024U) #define DEFAULT_TRIM_THRESHOLD ((size_t)1024U * (size_t)1024U)
/* The bit mask value corresponding to MALLOC_ALIGNMENT */ /* The bit mask value corresponding to MALLOC_ALIGNMENT */
#define CHUNK_ALIGN_MASK (MALLOC_ALIGNMENT - SIZE_T_ONE) #define CHUNK_ALIGN_MASK (MALLOC_ALIGNMENT - SIZE_T_ONE)
@ -835,6 +835,7 @@ static int has_segment_link(mstate m, msegmentptr ss)
static inline void* os_mmap(size_t size) static inline void* os_mmap(size_t size)
{ {
void* ptr = KernelAlloc(size); void* ptr = KernelAlloc(size);
printf("%s %x %d bytes\n",__FUNCTION__, ptr, size);
return (ptr != 0)? ptr: MFAIL; return (ptr != 0)? ptr: MFAIL;
} }
@ -1110,6 +1111,8 @@ static void* sys_alloc(mstate m, size_t nb)
ensure_initialization(); ensure_initialization();
printf("%s %d bytes\n", __FUNCTION__, nb);
/* Directly map large chunks, but only if already initialized */ /* Directly map large chunks, but only if already initialized */
if (use_mmap(m) && nb >= mparams.mmap_threshold && m->topsize != 0) if (use_mmap(m) && nb >= mparams.mmap_threshold && m->topsize != 0)
{ {

View File

@ -36,7 +36,13 @@
#define PTR_ALIGN(p, a) ((typeof(p))ALIGN((unsigned long)(p), (a))) #define PTR_ALIGN(p, a) ((typeof(p))ALIGN((unsigned long)(p), (a)))
#define IS_ALIGNED(x, a) (((x) & ((typeof(x))(a) - 1)) == 0) #define IS_ALIGNED(x, a) (((x) & ((typeof(x))(a) - 1)) == 0)
#define roundup(x, y) ((((x) + ((y) - 1)) / (y)) * (y)) /* The `const' in roundup() prevents gcc-3.3 from calling __divdi3 */
#define roundup(x, y) ( \
{ \
const typeof(y) __y = y; \
(((x) + (__y - 1)) / __y) * __y; \
} \
)
#define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d)) #define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
#define DIV_ROUND_CLOSEST(x, divisor)( \ #define DIV_ROUND_CLOSEST(x, divisor)( \

View File

@ -36,7 +36,7 @@ void __attribute__((regparm(1))) destroy_bitmap(bitmap_t *bitmap)
for (i = 0; i < bitmap->page_count; i++) for (i = 0; i < bitmap->page_count; i++)
FreePage(pages[i]); FreePage(pages[i]);
DRM_DEBUG("%s freec %d pages\n", __FUNCTION__, bitmap->page_count); DRM_DEBUG("%s release %d pages\n", __FUNCTION__, bitmap->page_count);
free(pages); free(pages);
}; };
@ -52,6 +52,7 @@ static int bitmap_get_pages_gtt(struct drm_i915_gem_object *obj)
/* Get the list of pages out of our struct file. They'll be pinned /* Get the list of pages out of our struct file. They'll be pinned
* at this point until we release them. * at this point until we release them.
*/ */
page_count = obj->base.size / PAGE_SIZE; page_count = obj->base.size / PAGE_SIZE;
BUG_ON(obj->allocated_pages == NULL); BUG_ON(obj->allocated_pages == NULL);
BUG_ON(obj->pages.page != NULL); BUG_ON(obj->pages.page != NULL);
@ -305,6 +306,105 @@ int lock_surface(struct io_call_12 *pbitmap)
}; };
int resize_surface(struct io_call_14 *pbitmap)
{
bitmap_t *bitmap;
dma_addr_t page, *pages;
u32 size, page_count;
u32 width, height;
u32 pitch;
int i;
int ret = 0;
if(unlikely(pbitmap->handle == 0))
return -1;
bitmap = (bitmap_t*)hmm_get_data(&bm_mm, pbitmap->handle);
if(unlikely(bitmap==NULL))
return -1;
if( pbitmap->new_width > bitmap->max_width ||
pbitmap->new_height > bitmap->max_height)
return -1;
width = pbitmap->new_width;
height = pbitmap->new_height;
pitch = ALIGN(width*4,64);
size = roundup(pitch * height, PAGE_SIZE);
page_count = size/PAGE_SIZE;
DRM_DEBUG("new width %d height %d pitch %d size %d\n",
width, height, pitch, size);
if( page_count == bitmap->page_count )
{
bitmap->width = width;
bitmap->height = height;
bitmap->pitch = pitch;
}
else if(page_count > bitmap->page_count)
{
char *vaddr = bitmap->uaddr + PAGE_SIZE * bitmap->page_count;
pages = bitmap->obj->allocated_pages;
DRM_DEBUG("old pages %d new_pages %d vaddr %x\n",
bitmap->page_count, page_count, vaddr);
for(i = bitmap->page_count; i < page_count; i++, vaddr+= PAGE_SIZE)
{
page = AllocPage();
if ( page == 0 )
goto err4;
pages[i] = page;
MapPage(vaddr, page, 0x207); //map as shared page
};
DRM_DEBUG("%s alloc %d pages\n", __FUNCTION__,
page_count - bitmap->page_count);
// mutex_lock(&main_device->struct_mutex);
i915_gem_object_unpin(bitmap->obj);
i915_gem_object_unbind(bitmap->obj);
bitmap->obj->base.size = size;
bitmap->obj->pages.nents = page_count;
ret = i915_gem_object_pin(bitmap->obj, PAGE_SIZE, true,true);
if (ret)
goto err4;
// mutex_unlock(&main_device->struct_mutex);
bitmap->page_count = page_count;
bitmap->width = width;
bitmap->height = height;
bitmap->pitch = pitch;
bitmap->gaddr = bitmap->obj->gtt_offset;
};
if(ret != 0 )
{
pbitmap->data = NULL;
pbitmap->pitch = 0;
dbgprintf("%s fail\n", __FUNCTION__);
return ret;
};
pbitmap->data = bitmap->uaddr;
pbitmap->pitch = bitmap->pitch;
return 0;
err4:
while (i-- > bitmap->page_count)
FreePage(pages[i]);
return -1;
};
int init_bitmaps() int init_bitmaps()

View File

@ -17,7 +17,7 @@ typedef struct
kobj_t header; kobj_t header;
u32 handle; u32 handle;
void *uaddr; char *uaddr;
u32 pitch; u32 pitch;
u32 gaddr; u32 gaddr;
@ -50,14 +50,19 @@ struct io_call_10 /* SRV_CREATE_SURFACE */
struct io_call_12 /* SRV_LOCK_SURFACE */ struct io_call_12 /* SRV_LOCK_SURFACE */
{ {
u32 handle; // ignored u32 handle;
void *data; // ignored void *data;
u32 pitch;
u32 width;
u32 height;
u32 pitch; // ignored
}; };
struct io_call_14 /* SRV_RESIZE_SURFACE */
{
u32 handle;
void *data;
u32 new_width;
u32 new_height;
u32 pitch;
};
typedef struct typedef struct
{ {
@ -93,6 +98,7 @@ struct context
int get_driver_caps(hwcaps_t *caps); int get_driver_caps(hwcaps_t *caps);
int create_surface(struct drm_device *dev, struct io_call_10 *pbitmap); int create_surface(struct drm_device *dev, struct io_call_10 *pbitmap);
int lock_surface(struct io_call_12 *pbitmap); int lock_surface(struct io_call_12 *pbitmap);
int resize_surface(struct io_call_14 *pbitmap);
struct context *get_context(struct drm_device *dev); struct context *get_context(struct drm_device *dev);

View File

@ -1409,7 +1409,7 @@ i915_gem_object_put_pages_gtt(struct drm_i915_gem_object *obj)
for (i = 0; i < obj->pages.nents; i++) for (i = 0; i < obj->pages.nents; i++)
FreePage(obj->pages.page[i]); FreePage(obj->pages.page[i]);
DRM_DEBUG_KMS("%s free %d pages\n", __FUNCTION__, obj->pages.nents); DRM_DEBUG_KMS("%s release %d pages\n", __FUNCTION__, obj->pages.nents);
obj->dirty = 0; obj->dirty = 0;
kfree(obj->pages.page); kfree(obj->pages.page);
} }
@ -1419,6 +1419,9 @@ i915_gem_object_put_pages(struct drm_i915_gem_object *obj)
{ {
const struct drm_i915_gem_object_ops *ops = obj->ops; const struct drm_i915_gem_object_ops *ops = obj->ops;
// printf("page %x pin count %d\n",
// obj->pages.page, obj->pages_pin_count );
if (obj->pages.page == NULL) if (obj->pages.page == NULL)
return 0; return 0;

View File

@ -716,8 +716,8 @@ int blit_video(u32 hbitmap, int dst_x, int dst_y,
dst_clip.xmin = 0; dst_clip.xmin = 0;
dst_clip.ymin = 0; dst_clip.ymin = 0;
dst_clip.xmax = winrc.right-winrc.left-1; dst_clip.xmax = winrc.right-winrc.left;
dst_clip.ymax = winrc.bottom -winrc.top-1; dst_clip.ymax = winrc.bottom -winrc.top;
src_clip.xmin = 0; src_clip.xmin = 0;
src_clip.ymin = 0; src_clip.ymin = 0;
@ -869,7 +869,7 @@ int blit_video(u32 hbitmap, int dst_x, int dst_y,
b[n++] = cmd; b[n++] = cmd;
b[n++] = br13; b[n++] = br13;
b[n++] = (dst_y << 16) | dst_x; // left, top b[n++] = (dst_y << 16) | dst_x; // left, top
b[n++] = ((dst_y+height-1)<< 16)|(dst_x+width-1); // bottom, right b[n++] = ((dst_y+height)<< 16)|(dst_x+width); // bottom, right
b[n++] = 0; // destination b[n++] = 0; // destination
b[n++] = (src_y << 16) | src_x; // source left & top b[n++] = (src_y << 16) | src_x; // source left & top
b[n++] = bitmap->pitch; // source pitch b[n++] = bitmap->pitch; // source pitch

View File

@ -100,6 +100,8 @@ u32_t drvEntry(int action, char *cmdline)
#define SRV_DESTROY_SURFACE 11 #define SRV_DESTROY_SURFACE 11
#define SRV_LOCK_SURFACE 12 #define SRV_LOCK_SURFACE 12
#define SRV_UNLOCK_SURFACE 13 #define SRV_UNLOCK_SURFACE 13
#define SRV_RESIZE_SURFACE 14
#define SRV_BLIT_VIDEO 20 #define SRV_BLIT_VIDEO 20
@ -158,6 +160,10 @@ int _stdcall display_handler(ioctl_t *io)
retval = lock_surface((struct io_call_12*)inp); retval = lock_surface((struct io_call_12*)inp);
break; break;
case SRV_RESIZE_SURFACE:
retval = resize_surface((struct io_call_14*)inp);
break;
case SRV_BLIT_VIDEO: case SRV_BLIT_VIDEO:
blit_video( inp[0], inp[1], inp[2], blit_video( inp[0], inp[1], inp[2],
inp[3], inp[4], inp[5], inp[6]); inp[3], inp[4], inp[5], inp[6]);