1 /************************************************************************** 2 * 3 * Copyright 2009 Artur Wyszynski <harakash (at) gmail.com> 4 * Copyright 2013-2014 Alexander von Gluck IV <kallisti5 (at) unixzen.com> 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a 7 * copy of this software and associated documentation files (the 8 * "Software"), to deal in the Software without restriction, including 9 * without limitation the rights to use, copy, modify, merge, publish, 10 * distribute, sub license, and/or sell copies of the Software, and to 11 * permit persons to whom the Software is furnished to do so, subject to 12 * the following conditions: 13 * 14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 16 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL 17 * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, 18 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 19 * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE 20 * USE OR OTHER DEALINGS IN THE SOFTWARE. 21 * 22 * The above copyright notice and this permission notice (including the 23 * next paragraph) shall be included in all copies or substantial portions 24 * of the Software. 25 * 26 **************************************************************************/ 27 28 #include <stdio.h> 29 30 #include "pipe/p_compiler.h" 31 #include "pipe/p_defines.h" 32 #include "pipe/p_format.h" 33 #include "util/u_inlines.h" 34 #include "util/u_format.h" 35 #include "util/u_math.h" 36 #include "util/u_memory.h" 37 #include "state_tracker/st_api.h" 38 #include "state_tracker/sw_winsys.h" 39 40 #include "bitmap_wrapper.h" 41 #include "hgl_sw_winsys.h" 42 43 44 #ifdef DEBUG 45 # define TRACE(x...) printf("hgl:winsys: " x) 46 # define CALLED() TRACE("CALLED: %s\n", __PRETTY_FUNCTION__) 47 #else 48 # define TRACE(x...) 49 # define CALLED() 50 #endif 51 #define ERROR(x...) printf("hgl:winsys: " x) 52 53 54 struct haiku_displaytarget 55 { 56 enum pipe_format format; 57 color_space colorSpace; 58 59 unsigned width; 60 unsigned height; 61 unsigned stride; 62 63 unsigned size; 64 65 void* data; 66 }; 67 68 69 // Cast 70 static inline struct haiku_displaytarget* 71 hgl_sw_displaytarget(struct sw_displaytarget* target) 72 { 73 return (struct haiku_displaytarget *)target; 74 } 75 76 77 static void 78 hgl_winsys_destroy(struct sw_winsys* winsys) 79 { 80 FREE(winsys); 81 } 82 83 84 static boolean 85 hgl_winsys_is_displaytarget_format_supported(struct sw_winsys* winsys, 86 unsigned textureUsage, enum pipe_format format) 87 { 88 // TODO STUB 89 return TRUE; 90 } 91 92 static color_space 93 hgl_winsys_convert_cs(enum pipe_format format) 94 { 95 // TODO: B_RGB24, B_RGB16, B_RGB15? 96 switch(format) { 97 case PIPE_FORMAT_B5G6R5_UNORM: 98 return B_CMAP8; 99 case PIPE_FORMAT_A8B8G8R8_UNORM: 100 case PIPE_FORMAT_X8B8G8R8_UNORM: 101 default: 102 return B_RGB32; 103 } 104 } 105 106 static struct sw_displaytarget* 107 hgl_winsys_displaytarget_create(struct sw_winsys* winsys, 108 unsigned textureUsage, enum pipe_format format, unsigned width, 109 unsigned height, unsigned alignment, const void *front_private, 110 unsigned* stride) 111 { 112 struct haiku_displaytarget* haikuDisplayTarget 113 = CALLOC_STRUCT(haiku_displaytarget); 114 assert(haikuDisplayTarget); 115 116 TRACE("%s: %d x %d\n", __func__, width, height); 117 118 haikuDisplayTarget->colorSpace = hgl_winsys_convert_cs(format); 119 haikuDisplayTarget->format = format; 120 haikuDisplayTarget->width = width; 121 haikuDisplayTarget->height = height; 122 123 size_t formatStride = util_format_get_stride(format, width); 124 unsigned blockSize = util_format_get_nblocksy(format, height); 125 126 haikuDisplayTarget->stride = align(formatStride, alignment); 127 haikuDisplayTarget->size = haikuDisplayTarget->stride * blockSize; 128 129 haikuDisplayTarget->data 130 = align_malloc(haikuDisplayTarget->size, alignment); 131 132 assert(haikuDisplayTarget->data); 133 134 *stride = haikuDisplayTarget->stride; 135 136 // Cast to ghost sw_displaytarget type 137 return (struct sw_displaytarget*)haikuDisplayTarget; 138 } 139 140 141 static void 142 hgl_winsys_displaytarget_destroy(struct sw_winsys* winsys, 143 struct sw_displaytarget* displayTarget) 144 { 145 struct haiku_displaytarget* haikuDisplayTarget 146 = hgl_sw_displaytarget(displayTarget); 147 148 if (!haikuDisplayTarget) 149 return; 150 151 if (haikuDisplayTarget->data != NULL) 152 align_free(haikuDisplayTarget->data); 153 154 FREE(haikuDisplayTarget); 155 } 156 157 158 static struct sw_displaytarget* 159 hgl_winsys_displaytarget_from_handle(struct sw_winsys* winsys, 160 const struct pipe_resource* templat, struct winsys_handle* whandle, 161 unsigned* stride) 162 { 163 return NULL; 164 } 165 166 167 static boolean 168 hgl_winsys_displaytarget_get_handle(struct sw_winsys* winsys, 169 struct sw_displaytarget* displayTarget, struct winsys_handle* whandle) 170 { 171 return FALSE; 172 } 173 174 175 static void* 176 hgl_winsys_displaytarget_map(struct sw_winsys* winsys, 177 struct sw_displaytarget* displayTarget, unsigned flags) 178 { 179 struct haiku_displaytarget* haikuDisplayTarget 180 = hgl_sw_displaytarget(displayTarget); 181 182 return haikuDisplayTarget->data; 183 } 184 185 186 static void 187 hgl_winsys_displaytarget_unmap(struct sw_winsys* winsys, 188 struct sw_displaytarget* disptarget) 189 { 190 return; 191 } 192 193 194 static void 195 hgl_winsys_displaytarget_display(struct sw_winsys* winsys, 196 struct sw_displaytarget* displayTarget, void* contextPrivate, 197 struct pipe_box *box) 198 { 199 assert(contextPrivate); 200 201 Bitmap* bitmap = (Bitmap*)contextPrivate; 202 203 struct haiku_displaytarget* haikuDisplayTarget 204 = hgl_sw_displaytarget(displayTarget); 205 206 import_bitmap_bits(bitmap, haikuDisplayTarget->data, 207 haikuDisplayTarget->size, haikuDisplayTarget->stride, 208 haikuDisplayTarget->colorSpace); 209 210 // Dump the rendered bitmap to disk for debugging 211 //dump_bitmap(bitmap); 212 213 return; 214 } 215 216 217 struct sw_winsys* 218 hgl_create_sw_winsys() 219 { 220 struct sw_winsys* winsys = CALLOC_STRUCT(sw_winsys); 221 222 if (!winsys) 223 return NULL; 224 225 // Attach winsys hooks for Haiku 226 winsys->destroy = hgl_winsys_destroy; 227 winsys->is_displaytarget_format_supported 228 = hgl_winsys_is_displaytarget_format_supported; 229 winsys->displaytarget_create = hgl_winsys_displaytarget_create; 230 winsys->displaytarget_from_handle = hgl_winsys_displaytarget_from_handle; 231 winsys->displaytarget_get_handle = hgl_winsys_displaytarget_get_handle; 232 winsys->displaytarget_map = hgl_winsys_displaytarget_map; 233 winsys->displaytarget_unmap = hgl_winsys_displaytarget_unmap; 234 winsys->displaytarget_display = hgl_winsys_displaytarget_display; 235 winsys->displaytarget_destroy = hgl_winsys_displaytarget_destroy; 236 237 return winsys; 238 } 239