Make python surface just a dumb (texture, face, level, zslice) tuple.
%rename(Device) st_device;
%rename(Context) st_context;
%rename(Texture) pipe_texture;
-%rename(Surface) pipe_surface;
+%rename(Surface) st_surface;
%rename(Buffer) pipe_buffer;
%rename(BlendColor) pipe_blend_color;
$self->pipe->set_constant_buffer($self->pipe, shader, index, &state);
}
- void set_framebuffer(const struct pipe_framebuffer_state *state ) {
+ void set_framebuffer(const struct pipe_framebuffer_state *state )
+ {
+ memcpy(&$self->framebuffer, state, sizeof *state);
cso_set_framebuffer($self->cso, state);
}
* Surface functions
*/
- void surface_copy(struct pipe_surface *dest,
+ void surface_copy(struct st_surface *dst,
unsigned destx, unsigned desty,
- struct pipe_surface *src,
+ struct st_surface *src,
unsigned srcx, unsigned srcy,
- unsigned width, unsigned height) {
- $self->pipe->surface_copy($self->pipe, dest, destx, desty, src, srcx, srcy, width, height);
+ unsigned width, unsigned height)
+ {
+ struct pipe_surface *_dst = NULL;
+ struct pipe_surface *_src = NULL;
+
+ _dst = st_pipe_surface(dst, PIPE_BUFFER_USAGE_GPU_WRITE);
+ if(!_dst)
+ SWIG_exception(SWIG_ValueError, "couldn't acquire destination surface for writing");
+
+ _src = st_pipe_surface(src, PIPE_BUFFER_USAGE_GPU_READ);
+ if(!_src)
+ SWIG_exception(SWIG_ValueError, "couldn't acquire source surface for reading");
+
+ $self->pipe->surface_copy($self->pipe, _dst, destx, desty, _src, srcx, srcy, width, height);
+
+ fail:
+ pipe_surface_reference(&_src, NULL);
+ pipe_surface_reference(&_dst, NULL);
}
- void surface_fill(struct pipe_surface *dst,
+ void surface_fill(struct st_surface *dst,
unsigned x, unsigned y,
unsigned width, unsigned height,
- unsigned value) {
- $self->pipe->surface_fill($self->pipe, dst, x, y, width, height, value);
+ unsigned value)
+ {
+ struct pipe_surface *_dst = NULL;
+
+ _dst = st_pipe_surface(dst, PIPE_BUFFER_USAGE_GPU_WRITE);
+ if(!_dst)
+ SWIG_exception(SWIG_ValueError, "couldn't acquire destination surface for writing");
+
+ $self->pipe->surface_fill($self->pipe, _dst, x, y, width, height, value);
+
+ fail:
+ pipe_surface_reference(&_dst, NULL);
}
- void surface_clear(struct pipe_surface *surface, unsigned value = 0) {
- $self->pipe->clear($self->pipe, surface, value);
+ void surface_clear(struct st_surface *surface, unsigned value = 0)
+ {
+ unsigned i;
+ struct pipe_surface *_surface = NULL;
+
+ if(!surface)
+ SWIG_exception(SWIG_TypeError, "surface must not be null");
+
+ for(i = 0; i < $self->framebuffer.nr_cbufs; ++i) {
+ struct pipe_surface *cbuf = $self->framebuffer.cbufs[i];
+ if(cbuf) {
+ if(cbuf->texture == surface->texture &&
+ cbuf->face == surface->face &&
+ cbuf->level == surface->level &&
+ cbuf->zslice == surface->zslice) {
+ _surface = cbuf;
+ break;
+ }
+ }
+ }
+
+ if(!_surface) {
+ struct pipe_surface *zsbuf = $self->framebuffer.zsbuf;
+ if(zsbuf) {
+ if(zsbuf->texture == surface->texture &&
+ zsbuf->face == surface->face &&
+ zsbuf->level == surface->level &&
+ zsbuf->zslice == surface->zslice) {
+ _surface = zsbuf;
+ }
+ }
+ }
+
+ if(!_surface)
+ SWIG_exception(SWIG_ValueError, "surface not bound");
+
+ $self->pipe->clear($self->pipe, _surface, value);
+ fail:
+ return;
}
};
}
void
- set_cbuf(unsigned index, struct pipe_surface *surface) {
- pipe_surface_reference(&$self->cbufs[index], surface);
+ set_cbuf(unsigned index, struct st_surface *surface)
+ {
+ struct pipe_surface *_surface = NULL;
+
+ if(index >= PIPE_MAX_COLOR_BUFS)
+ SWIG_exception(SWIG_ValueError, "index out of bounds");
+
+ _surface = st_pipe_surface(surface, PIPE_BUFFER_USAGE_GPU_WRITE);
+ if(!_surface)
+ SWIG_exception(SWIG_ValueError, "couldn't acquire surface for writing");
+
+ pipe_surface_reference(&$self->cbufs[index], _surface);
+
+ fail:
+ return;
}
void
- set_zsbuf(struct pipe_surface *surface) {
- pipe_surface_reference(&$self->zsbuf, surface);
+ set_zsbuf(struct st_surface *surface)
+ {
+ struct pipe_surface *_surface = NULL;
+
+ _surface = st_pipe_surface(surface, PIPE_BUFFER_USAGE_GPU_WRITE);
+ if(!_surface)
+ SWIG_exception(SWIG_ValueError, "couldn't acquire surface for writing");
+
+ pipe_surface_reference(&$self->zsbuf, _surface);
+
+ fail:
+ return;
}
};
%nodefaultctor pipe_texture;
-%nodefaultctor pipe_surface;
+%nodefaultctor st_surface;
%nodefaultctor pipe_buffer;
%nodefaultdtor pipe_texture;
-%nodefaultdtor pipe_surface;
+%nodefaultdtor st_surface;
%nodefaultdtor pipe_buffer;
%ignore pipe_texture::screen;
-%ignore pipe_surface::winsys;
-%immutable pipe_surface::texture;
-%immutable pipe_surface::buffer;
+%immutable st_surface::texture;
+%immutable st_surface::face;
+%immutable st_surface::level;
+%immutable st_surface::zslice;
%newobject pipe_texture::get_surface;
}
/** Get a surface which is a "view" into a texture */
- struct pipe_surface *
- get_surface(unsigned face=0, unsigned level=0, unsigned zslice=0 )
+ struct st_surface *
+ get_surface(unsigned face=0, unsigned level=0, unsigned zslice=0)
{
- const usage = PIPE_BUFFER_USAGE_GPU_READ_WRITE;
- struct pipe_screen *screen = $self->screen;
- return screen->get_tex_surface(screen, $self, face, level, zslice, usage);
+ struct st_surface *surface;
+
+ if(face >= ($self->target == PIPE_TEXTURE_CUBE ? 6 : 1))
+ SWIG_exception(SWIG_ValueError, "face out of bounds");
+ if(level > $self->last_level)
+ SWIG_exception(SWIG_ValueError, "level out of bounds");
+ if(zslice >= $self->depth[level])
+ SWIG_exception(SWIG_ValueError, "zslice out of bounds");
+
+ surface = CALLOC_STRUCT(st_surface);
+ if(!surface)
+ return NULL;
+
+ pipe_texture_reference(&surface->texture, $self);
+ surface->face = face;
+ surface->level = level;
+ surface->zslice = zslice;
+
+ return surface;
+
+ fail:
+ return NULL;
}
};
+struct st_surface
+{
+ %immutable;
+
+ struct pipe_texture *texture;
+ unsigned face;
+ unsigned level;
+ unsigned zslice;
+
+};
-%extend pipe_surface {
+%extend st_surface {
+
+ %immutable;
- ~pipe_surface() {
- struct pipe_surface *ptr = $self;
- pipe_surface_reference(&ptr, NULL);
+ unsigned format;
+ unsigned width;
+ unsigned height;
+
+ ~st_surface() {
+ pipe_texture_reference(&$self->texture, NULL);
+ FREE($self);
}
void
};
+%{
+ static enum pipe_format
+ st_surface_format_get(struct st_surface *surface)
+ {
+ return surface->texture->format;
+ }
+
+ static unsigned
+ st_surface_width_get(struct st_surface *surface)
+ {
+ return surface->texture->width[surface->level];
+ }
+
+ static unsigned
+ st_surface_height_get(struct st_surface *surface)
+ {
+ return surface->texture->height[surface->level];
+ }
+%}
+
/* Avoid naming conflict with p_inlines.h's pipe_buffer_read/write */
%rename(read) pipe_buffer_read_;
%rename(write) pipe_buffer_write_;
struct st_winsys;
+struct st_surface
+{
+ struct pipe_texture *texture;
+ unsigned face;
+ unsigned level;
+ unsigned zslice;
+};
+
+
struct st_context {
struct st_device *st_dev;
unsigned num_vertex_elements;
struct pipe_vertex_element vertex_elements[PIPE_MAX_ATTRIBS];
+
+ struct pipe_framebuffer_state framebuffer;
};
};
+static INLINE struct pipe_surface *
+st_pipe_surface(struct st_surface *surface, unsigned usage)
+{
+ struct pipe_texture *texture = surface->texture;
+ struct pipe_screen *screen = texture->screen;
+ return screen->get_tex_surface(screen, texture, surface->face, surface->level, surface->zslice, usage);
+}
+
struct st_context *
st_context_create(struct st_device *st_dev);
#include "util/u_math.h"
#include "util/u_memory.h"
+#include "st_device.h"
#include "st_sample.h"
void
-st_sample_surface(struct pipe_surface *surface, float *rgba)
+st_sample_surface(struct st_surface *surface, float *rgba)
{
- struct pipe_screen *screen = surface->texture->screen;
- uint rgba_stride = surface->width * 4;
+ struct pipe_texture *texture = surface->texture;
+ struct pipe_screen *screen = texture->screen;
+ unsigned width = texture->width[surface->level];
+ unsigned height = texture->height[surface->level];
+ uint rgba_stride = width * 4;
struct pipe_transfer *transfer;
void *raw;
surface->zslice,
PIPE_TRANSFER_READ,
0, 0,
- surface->width,
- surface->height);
+ width,
+ height);
if (!transfer)
return;
raw = screen->transfer_map(screen, transfer);
if (raw) {
- const struct pipe_format_block *block = &transfer->block;
+ const struct pipe_format_block *block = &texture->block;
uint x, y;
for (y = 0; y < transfer->nblocksy; ++y) {
for (x = 0; x < transfer->nblocksx; ++x) {
- st_sample_pixel_block(surface->format,
+ st_sample_pixel_block(texture->format,
block,
(uint8_t *) raw + y * transfer->stride + x * block->size,
rgba + y * block->height * rgba_stride + x * block->width * 4,
rgba_stride,
- MIN2(block->width, surface->width - x*block->width),
- MIN2(block->height, surface->height - y*block->height));
+ MIN2(block->width, width - x*block->width),
+ MIN2(block->height, height - y*block->height));
}
}
unsigned w, unsigned h);
void
-st_sample_surface(struct pipe_surface *surface, float *rgba);
+st_sample_surface(struct st_surface *surface, float *rgba);
#endif /* ST_SAMPLE_H_ */