1 #include "rs_core.rsh" 2 #include "rs_graphics.rsh" 3 /***************************************************************************** 4 * CAUTION 5 * 6 * The following structure layout provides a more efficient way to access 7 * internal members of the C++ class Allocation owned by librs. Unfortunately, 8 * since this class has virtual members, we can't simply use offsetof() or any 9 * other compiler trickery to dynamically get the appropriate values at 10 * build-time. This layout may need to be updated whenever 11 * frameworks/base/libs/rs/rsAllocation.h is modified. 12 * 13 * Having the layout information available in this file allows us to 14 * accelerate functionality like rsAllocationGetDimX(). Without this 15 * information, we would not be able to inline the bitcode, thus resulting in 16 * potential runtime performance penalties for tight loops operating on 17 * allocations. 18 * 19 *****************************************************************************/ 20 typedef struct Allocation { 21 char __pad[44]; 22 struct { 23 struct { 24 uint32_t dimensionX; 25 uint32_t dimensionY; 26 uint32_t dimensionZ; 27 uint32_t elementSizeBytes; 28 bool hasMipmaps; 29 bool hasFaces; 30 bool hasReferences; 31 } state; 32 33 struct DrvState { 34 void * mallocPtr; 35 } drvState; 36 } mHal; 37 } Allocation_t; 38 39 /* Declaration of 4 basic functions in libRS */ 40 extern void __attribute__((overloadable)) 41 rsDebug(const char *, float, float); 42 extern void __attribute__((overloadable)) 43 rsDebug(const char *, float, float, float); 44 extern void __attribute__((overloadable)) 45 rsDebug(const char *, float, float, float, float); 46 extern float4 __attribute__((overloadable)) convert_float4(uchar4 c); 47 48 /* Implementation of Core Runtime */ 49 50 extern void __attribute__((overloadable)) rsDebug(const char *s, float2 v) { 51 rsDebug(s, v.x, v.y); 52 } 53 54 extern void __attribute__((overloadable)) rsDebug(const char *s, float3 v) { 55 rsDebug(s, v.x, v.y, v.z); 56 } 57 58 extern void __attribute__((overloadable)) rsDebug(const char *s, float4 v) { 59 rsDebug(s, v.x, v.y, v.z, v.w); 60 } 61 62 extern uchar4 __attribute__((overloadable)) rsPackColorTo8888(float r, float g, float b) 63 { 64 uchar4 c; 65 c.x = (uchar)(r * 255.f + 0.5f); 66 c.y = (uchar)(g * 255.f + 0.5f); 67 c.z = (uchar)(b * 255.f + 0.5f); 68 c.w = 255; 69 return c; 70 } 71 72 extern uchar4 __attribute__((overloadable)) rsPackColorTo8888(float r, float g, float b, float a) 73 { 74 uchar4 c; 75 c.x = (uchar)(r * 255.f + 0.5f); 76 c.y = (uchar)(g * 255.f + 0.5f); 77 c.z = (uchar)(b * 255.f + 0.5f); 78 c.w = (uchar)(a * 255.f + 0.5f); 79 return c; 80 } 81 82 extern uchar4 __attribute__((overloadable)) rsPackColorTo8888(float3 color) 83 { 84 color *= 255.f; 85 color += 0.5f; 86 uchar4 c = {color.x, color.y, color.z, 255}; 87 return c; 88 } 89 90 extern uchar4 __attribute__((overloadable)) rsPackColorTo8888(float4 color) 91 { 92 color *= 255.f; 93 color += 0.5f; 94 uchar4 c = {color.x, color.y, color.z, color.w}; 95 return c; 96 } 97 98 extern float4 rsUnpackColor8888(uchar4 c) 99 { 100 float4 ret = (float4)0.003921569f; 101 ret *= convert_float4(c); 102 return ret; 103 } 104 105 ///////////////////////////////////////////////////// 106 // Matrix ops 107 ///////////////////////////////////////////////////// 108 109 extern void __attribute__((overloadable)) 110 rsMatrixSet(rs_matrix4x4 *m, uint32_t row, uint32_t col, float v) { 111 m->m[row * 4 + col] = v; 112 } 113 114 extern float __attribute__((overloadable)) 115 rsMatrixGet(const rs_matrix4x4 *m, uint32_t row, uint32_t col) { 116 return m->m[row * 4 + col]; 117 } 118 119 extern void __attribute__((overloadable)) 120 rsMatrixSet(rs_matrix3x3 *m, uint32_t row, uint32_t col, float v) { 121 m->m[row * 3 + col] = v; 122 } 123 124 extern float __attribute__((overloadable)) 125 rsMatrixGet(const rs_matrix3x3 *m, uint32_t row, uint32_t col) { 126 return m->m[row * 3 + col]; 127 } 128 129 extern void __attribute__((overloadable)) 130 rsMatrixSet(rs_matrix2x2 *m, uint32_t row, uint32_t col, float v) { 131 m->m[row * 2 + col] = v; 132 } 133 134 extern float __attribute__((overloadable)) 135 rsMatrixGet(const rs_matrix2x2 *m, uint32_t row, uint32_t col) { 136 return m->m[row * 2 + col]; 137 } 138 139 140 extern float4 __attribute__((overloadable)) 141 rsMatrixMultiply(const rs_matrix4x4 *m, float4 in) { 142 float4 ret; 143 ret.x = (m->m[0] * in.x) + (m->m[4] * in.y) + (m->m[8] * in.z) + (m->m[12] * in.w); 144 ret.y = (m->m[1] * in.x) + (m->m[5] * in.y) + (m->m[9] * in.z) + (m->m[13] * in.w); 145 ret.z = (m->m[2] * in.x) + (m->m[6] * in.y) + (m->m[10] * in.z) + (m->m[14] * in.w); 146 ret.w = (m->m[3] * in.x) + (m->m[7] * in.y) + (m->m[11] * in.z) + (m->m[15] * in.w); 147 return ret; 148 } 149 extern float4 __attribute__((overloadable)) 150 rsMatrixMultiply(rs_matrix4x4 *m, float4 in) { 151 return rsMatrixMultiply((const rs_matrix4x4 *)m, in); 152 } 153 154 extern float4 __attribute__((overloadable)) 155 rsMatrixMultiply(const rs_matrix4x4 *m, float3 in) { 156 float4 ret; 157 ret.x = (m->m[0] * in.x) + (m->m[4] * in.y) + (m->m[8] * in.z) + m->m[12]; 158 ret.y = (m->m[1] * in.x) + (m->m[5] * in.y) + (m->m[9] * in.z) + m->m[13]; 159 ret.z = (m->m[2] * in.x) + (m->m[6] * in.y) + (m->m[10] * in.z) + m->m[14]; 160 ret.w = (m->m[3] * in.x) + (m->m[7] * in.y) + (m->m[11] * in.z) + m->m[15]; 161 return ret; 162 } 163 extern float4 __attribute__((overloadable)) 164 rsMatrixMultiply(rs_matrix4x4 *m, float3 in) { 165 return rsMatrixMultiply((const rs_matrix4x4 *)m, in); 166 } 167 168 extern float4 __attribute__((overloadable)) 169 rsMatrixMultiply(const rs_matrix4x4 *m, float2 in) { 170 float4 ret; 171 ret.x = (m->m[0] * in.x) + (m->m[4] * in.y) + m->m[12]; 172 ret.y = (m->m[1] * in.x) + (m->m[5] * in.y) + m->m[13]; 173 ret.z = (m->m[2] * in.x) + (m->m[6] * in.y) + m->m[14]; 174 ret.w = (m->m[3] * in.x) + (m->m[7] * in.y) + m->m[15]; 175 return ret; 176 } 177 extern float4 __attribute__((overloadable)) 178 rsMatrixMultiply(rs_matrix4x4 *m, float2 in) { 179 return rsMatrixMultiply((const rs_matrix4x4 *)m, in); 180 } 181 182 extern float3 __attribute__((overloadable)) 183 rsMatrixMultiply(const rs_matrix3x3 *m, float3 in) { 184 float3 ret; 185 ret.x = (m->m[0] * in.x) + (m->m[3] * in.y) + (m->m[6] * in.z); 186 ret.y = (m->m[1] * in.x) + (m->m[4] * in.y) + (m->m[7] * in.z); 187 ret.z = (m->m[2] * in.x) + (m->m[5] * in.y) + (m->m[8] * in.z); 188 return ret; 189 } 190 extern float3 __attribute__((overloadable)) 191 rsMatrixMultiply(rs_matrix3x3 *m, float3 in) { 192 return rsMatrixMultiply((const rs_matrix3x3 *)m, in); 193 } 194 195 196 extern float3 __attribute__((overloadable)) 197 rsMatrixMultiply(const rs_matrix3x3 *m, float2 in) { 198 float3 ret; 199 ret.x = (m->m[0] * in.x) + (m->m[3] * in.y); 200 ret.y = (m->m[1] * in.x) + (m->m[4] * in.y); 201 ret.z = (m->m[2] * in.x) + (m->m[5] * in.y); 202 return ret; 203 } 204 extern float3 __attribute__((overloadable)) 205 rsMatrixMultiply(rs_matrix3x3 *m, float2 in) { 206 return rsMatrixMultiply((const rs_matrix3x3 *)m, in); 207 } 208 209 extern float2 __attribute__((overloadable)) 210 rsMatrixMultiply(const rs_matrix2x2 *m, float2 in) { 211 float2 ret; 212 ret.x = (m->m[0] * in.x) + (m->m[2] * in.y); 213 ret.y = (m->m[1] * in.x) + (m->m[3] * in.y); 214 return ret; 215 } 216 extern float2 __attribute__((overloadable)) 217 rsMatrixMultiply(rs_matrix2x2 *m, float2 in) { 218 return rsMatrixMultiply((const rs_matrix2x2 *)m, in); 219 } 220 221 ///////////////////////////////////////////////////// 222 // int ops 223 ///////////////////////////////////////////////////// 224 225 extern uint __attribute__((overloadable, always_inline)) rsClamp(uint amount, uint low, uint high) { 226 return amount < low ? low : (amount > high ? high : amount); 227 } 228 extern int __attribute__((overloadable, always_inline)) rsClamp(int amount, int low, int high) { 229 return amount < low ? low : (amount > high ? high : amount); 230 } 231 extern ushort __attribute__((overloadable, always_inline)) rsClamp(ushort amount, ushort low, ushort high) { 232 return amount < low ? low : (amount > high ? high : amount); 233 } 234 extern short __attribute__((overloadable, always_inline)) rsClamp(short amount, short low, short high) { 235 return amount < low ? low : (amount > high ? high : amount); 236 } 237 extern uchar __attribute__((overloadable, always_inline)) rsClamp(uchar amount, uchar low, uchar high) { 238 return amount < low ? low : (amount > high ? high : amount); 239 } 240 extern char __attribute__((overloadable, always_inline)) rsClamp(char amount, char low, char high) { 241 return amount < low ? low : (amount > high ? high : amount); 242 } 243 244 // Opaque Allocation type operations 245 extern uint32_t __attribute__((overloadable)) 246 rsAllocationGetDimX(rs_allocation a) { 247 Allocation_t *alloc = (Allocation_t *)a.p; 248 return alloc->mHal.state.dimensionX; 249 } 250 251 extern uint32_t __attribute__((overloadable)) 252 rsAllocationGetDimY(rs_allocation a) { 253 Allocation_t *alloc = (Allocation_t *)a.p; 254 return alloc->mHal.state.dimensionY; 255 } 256 257 extern uint32_t __attribute__((overloadable)) 258 rsAllocationGetDimZ(rs_allocation a) { 259 Allocation_t *alloc = (Allocation_t *)a.p; 260 return alloc->mHal.state.dimensionZ; 261 } 262 263 extern uint32_t __attribute__((overloadable)) 264 rsAllocationGetDimLOD(rs_allocation a) { 265 Allocation_t *alloc = (Allocation_t *)a.p; 266 return alloc->mHal.state.hasMipmaps; 267 } 268 269 extern uint32_t __attribute__((overloadable)) 270 rsAllocationGetDimFaces(rs_allocation a) { 271 Allocation_t *alloc = (Allocation_t *)a.p; 272 return alloc->mHal.state.hasFaces; 273 } 274 275 extern const void * __attribute__((overloadable)) 276 rsGetElementAt(rs_allocation a, uint32_t x) { 277 Allocation_t *alloc = (Allocation_t *)a.p; 278 const uint8_t *p = (const uint8_t *)alloc->mHal.drvState.mallocPtr; 279 const uint32_t eSize = alloc->mHal.state.elementSizeBytes; 280 return &p[eSize * x]; 281 } 282 283 extern const void * __attribute__((overloadable)) 284 rsGetElementAt(rs_allocation a, uint32_t x, uint32_t y) { 285 Allocation_t *alloc = (Allocation_t *)a.p; 286 const uint8_t *p = (const uint8_t *)alloc->mHal.drvState.mallocPtr; 287 const uint32_t eSize = alloc->mHal.state.elementSizeBytes; 288 const uint32_t dimX = alloc->mHal.state.dimensionX; 289 return &p[eSize * (x + y * dimX)]; 290 } 291 292 extern const void * __attribute__((overloadable)) 293 rsGetElementAt(rs_allocation a, uint32_t x, uint32_t y, uint32_t z) { 294 Allocation_t *alloc = (Allocation_t *)a.p; 295 const uint8_t *p = (const uint8_t *)alloc->mHal.drvState.mallocPtr; 296 const uint32_t eSize = alloc->mHal.state.elementSizeBytes; 297 const uint32_t dimX = alloc->mHal.state.dimensionX; 298 const uint32_t dimY = alloc->mHal.state.dimensionY; 299 return &p[eSize * (x + y * dimX + z * dimX * dimY)]; 300 } 301