16173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark/* -*- mode: C; c-file-style: "k&r"; tab-width 4; indent-tabs-mode: t; -*- */ 26173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 36173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark/* 46173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * Copyright (C) 2012 Rob Clark <robclark@freedesktop.org> 56173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * 66173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * Permission is hereby granted, free of charge, to any person obtaining a 76173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * copy of this software and associated documentation files (the "Software"), 86173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * to deal in the Software without restriction, including without limitation 96173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * the rights to use, copy, modify, merge, publish, distribute, sublicense, 106173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * and/or sell copies of the Software, and to permit persons to whom the 116173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * Software is furnished to do so, subject to the following conditions: 126173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * 136173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * The above copyright notice and this permission notice (including the next 146173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * paragraph) shall be included in all copies or substantial portions of the 156173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * Software. 166173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * 176173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 186173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 196173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 206173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 216173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 226173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 236173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * SOFTWARE. 246173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * 256173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * Authors: 266173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark * Rob Clark <robclark@freedesktop.org> 276173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark */ 286173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 296173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark#include "pipe/p_state.h" 306173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark#include "util/u_string.h" 316173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark#include "util/u_memory.h" 326173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark#include "util/u_inlines.h" 336173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 346173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark#include "freedreno_texture.h" 3518c317b21ddc2ec4538544f9dd69dc568dcf821fRob Clark#include "freedreno_context.h" 366173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark#include "freedreno_util.h" 376173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 386173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clarkstatic void 396173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clarkfd_sampler_state_delete(struct pipe_context *pctx, void *hwcso) 406173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 416173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark FREE(hwcso); 426173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark} 436173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 446173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clarkstatic void 456173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clarkfd_sampler_view_destroy(struct pipe_context *pctx, 466173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark struct pipe_sampler_view *view) 476173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 486173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark pipe_resource_reference(&view->texture, NULL); 496173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark FREE(view); 506173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark} 516173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 52a6746d11247cdd6f795c7e857019c3a4bd71e26aRob Clarkstatic void bind_sampler_states(struct fd_texture_stateobj *tex, 53243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark unsigned start, unsigned nr, void **hwcso) 546173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 556173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark unsigned i; 566173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 576173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark for (i = 0; i < nr; i++) { 58243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark unsigned p = i + start; 59243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->samplers[p] = hwcso[i]; 60243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark if (tex->samplers[p]) 61243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->valid_samplers |= (1 << p); 62243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark else 63243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->valid_samplers &= ~(1 << p); 646173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark } 656173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 66243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->num_samplers = util_last_bit(tex->valid_samplers); 676173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark} 686173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 69a6746d11247cdd6f795c7e857019c3a4bd71e26aRob Clarkstatic void set_sampler_views(struct fd_texture_stateobj *tex, 70243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark unsigned start, unsigned nr, struct pipe_sampler_view **views) 716173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 726173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark unsigned i; 736173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 746173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark for (i = 0; i < nr; i++) { 75243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark struct pipe_sampler_view *view = views ? views[i] : NULL; 76243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark unsigned p = i + start; 77243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark pipe_sampler_view_reference(&tex->textures[p], view); 78243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark if (tex->textures[p]) 79243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->valid_textures |= (1 << p); 80243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark else 81243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->valid_textures &= ~(1 << p); 826173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark } 836173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 84243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark tex->num_textures = util_last_bit(tex->valid_textures); 856173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark} 866173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 87a6746d11247cdd6f795c7e857019c3a4bd71e26aRob Clarkvoid 887d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paulfd_sampler_states_bind(struct pipe_context *pctx, 897413625ad357c87f409cd1673b40f8dffbc43259Kai Wasserbäch enum pipe_shader_type shader, unsigned start, 906173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark unsigned nr, void **hwcso) 916173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 926173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark struct fd_context *ctx = fd_context(pctx); 93f706d4d340f0778de23062ef13c54b07bfac7967Rob Clark 947d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paul if (shader == PIPE_SHADER_FRAGMENT) { 95243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark bind_sampler_states(&ctx->fragtex, start, nr, hwcso); 967d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paul ctx->dirty |= FD_DIRTY_FRAGTEX; 977d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paul } 987d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paul else if (shader == PIPE_SHADER_VERTEX) { 99243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark bind_sampler_states(&ctx->verttex, start, nr, hwcso); 1007d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paul ctx->dirty |= FD_DIRTY_VERTTEX; 1017d7a9714d2f6cdceb9e9e6f6b43004008b56c8d2Brian Paul } 1026173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark} 1036173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 104d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clarkvoid 105532db3b7881f3dfcd299320cbf44443d06b88373Kai Wasserbächfd_set_sampler_views(struct pipe_context *pctx, enum pipe_shader_type shader, 106d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark unsigned start, unsigned nr, 1076173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark struct pipe_sampler_view **views) 1086173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 1096173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark struct fd_context *ctx = fd_context(pctx); 110f706d4d340f0778de23062ef13c54b07bfac7967Rob Clark 111d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark switch (shader) { 112d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark case PIPE_SHADER_FRAGMENT: 113d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark /* on a2xx, since there is a flat address space for textures/samplers, 114d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark * a change in # of fragment textures/samplers will trigger patching 115d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark * and re-emitting the vertex shader: 116d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark * 117d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark * (note: later gen's ignore FD_DIRTY_TEXSTATE so fine to set it) 118d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark */ 119d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark if (nr != ctx->fragtex.num_textures) 120d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark ctx->dirty |= FD_DIRTY_TEXSTATE; 121d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark 122243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark set_sampler_views(&ctx->fragtex, start, nr, views); 123d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark ctx->dirty |= FD_DIRTY_FRAGTEX; 124d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark break; 125d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark case PIPE_SHADER_VERTEX: 126243417810bce6b4e0c466a8b1dbe3873b4f5562bRob Clark set_sampler_views(&ctx->verttex, start, nr, views); 127d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark ctx->dirty |= FD_DIRTY_VERTTEX; 128d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark break; 129d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark default: 130d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark break; 131d4ff42bd0a80acfac080507e4e14f33f0b3bffbbRob Clark } 132a3ed98f7aa85636579a5696bf036ec13e5c9104aBrian Paul} 133a3ed98f7aa85636579a5696bf036ec13e5c9104aBrian Paul 1346173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clarkvoid 1356173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clarkfd_texture_init(struct pipe_context *pctx) 1366173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark{ 1376173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark pctx->delete_sampler_state = fd_sampler_state_delete; 1386173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark 1396173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark pctx->sampler_view_destroy = fd_sampler_view_destroy; 1406173cc19c45d92ef0b7bc6aa008aa89bb29abbdaRob Clark} 1419124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark 1429124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark/* helper for setting up border-color buffer for a3xx/a4xx: */ 1439124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clarkvoid 1449124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clarkfd_setup_border_colors(struct fd_texture_stateobj *tex, void *ptr, 1459124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark unsigned offset) 1469124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark{ 1479124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark unsigned i, j; 1489124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark 1499124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark for (i = 0; i < tex->num_samplers; i++) { 1509124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark struct pipe_sampler_state *sampler = tex->samplers[i]; 1519124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark uint16_t *bcolor = (uint16_t *)((uint8_t *)ptr + 1529124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark (BORDERCOLOR_SIZE * offset) + 1539124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark (BORDERCOLOR_SIZE * i)); 1549124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark uint32_t *bcolor32 = (uint32_t *)&bcolor[16]; 1559124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark 1569124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark if (!sampler) 1579124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark continue; 1589124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark 1599124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark /* 1609124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * XXX HACK ALERT XXX 1619124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * 1629124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * The border colors need to be swizzled in a particular 1639124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * format-dependent order. Even though samplers don't know about 1649124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * formats, we can assume that with a GL state tracker, there's a 1659124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * 1:1 correspondence between sampler and texture. Take advantage 1669124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark * of that knowledge. 1679124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark */ 1689124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark if (i < tex->num_textures && tex->textures[i]) { 1699124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark const struct util_format_description *desc = 1709124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark util_format_description(tex->textures[i]->format); 1719124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark for (j = 0; j < 4; j++) { 1729124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark if (desc->swizzle[j] >= 4) 1739124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark continue; 1749124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark 1759124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark const struct util_format_channel_description *chan = 176c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin &desc->channel[desc->swizzle[j]]; 177c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin if (chan->pure_integer) { 178c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin bcolor32[desc->swizzle[j] + 4] = sampler->border_color.i[j]; 179c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin bcolor[desc->swizzle[j] + 8] = sampler->border_color.i[j]; 180c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin } else { 181c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin bcolor32[desc->swizzle[j]] = fui(sampler->border_color.f[j]); 1829124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark bcolor[desc->swizzle[j]] = 183c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin util_float_to_half(sampler->border_color.f[j]); 184c1babbd85c4069d9d9b319d5ca95a614039ba609Ilia Mirkin } 1859124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark } 1869124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark } 1879124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark } 1889124a49d54af5d7bd8230af4ba3eebfb167a7655Rob Clark} 189