rsScriptC_Lib.cpp revision 584a375df68ed7d62b38389078c6804edf228f9c
1/* 2 * Copyright (C) 2009 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17#include "rsContext.h" 18#include "rsScriptC.h" 19#include "rsMatrix.h" 20 21#include "acc/acc.h" 22#include "utils/String8.h" 23 24#include <GLES/gl.h> 25#include <GLES/glext.h> 26 27#include <time.h> 28#include <cutils/tztime.h> 29 30using namespace android; 31using namespace android::renderscript; 32 33#define GET_TLS() Context::ScriptTLSStruct * tls = \ 34 (Context::ScriptTLSStruct *)pthread_getspecific(Context::gThreadTLSKey); \ 35 Context * rsc = tls->mContext; \ 36 ScriptC * sc = (ScriptC *) tls->mScript 37 38 39////////////////////////////////////////////////////////////////////////////// 40// IO routines 41////////////////////////////////////////////////////////////////////////////// 42 43static float SC_loadF(uint32_t bank, uint32_t offset) 44{ 45 GET_TLS(); 46 const void *vp = sc->mSlots[bank]->getPtr(); 47 const float *f = static_cast<const float *>(vp); 48 //LOGE("loadF %i %i = %f %x", bank, offset, f, ((int *)&f)[0]); 49 return f[offset]; 50} 51 52static int32_t SC_loadI32(uint32_t bank, uint32_t offset) 53{ 54 GET_TLS(); 55 const void *vp = sc->mSlots[bank]->getPtr(); 56 const int32_t *i = static_cast<const int32_t *>(vp); 57 //LOGE("loadI32 %i %i = %i", bank, offset, t); 58 return i[offset]; 59} 60 61static uint32_t SC_loadU32(uint32_t bank, uint32_t offset) 62{ 63 GET_TLS(); 64 const void *vp = sc->mSlots[bank]->getPtr(); 65 const uint32_t *i = static_cast<const uint32_t *>(vp); 66 return i[offset]; 67} 68 69static void SC_loadVec4(uint32_t bank, uint32_t offset, rsc_Vector4 *v) 70{ 71 GET_TLS(); 72 const void *vp = sc->mSlots[bank]->getPtr(); 73 const float *f = static_cast<const float *>(vp); 74 memcpy(v, &f[offset], sizeof(rsc_Vector4)); 75} 76 77static void SC_loadMatrix(uint32_t bank, uint32_t offset, rsc_Matrix *m) 78{ 79 GET_TLS(); 80 const void *vp = sc->mSlots[bank]->getPtr(); 81 const float *f = static_cast<const float *>(vp); 82 memcpy(m, &f[offset], sizeof(rsc_Matrix)); 83} 84 85 86static void SC_storeF(uint32_t bank, uint32_t offset, float v) 87{ 88 //LOGE("storeF %i %i %f", bank, offset, v); 89 GET_TLS(); 90 void *vp = sc->mSlots[bank]->getPtr(); 91 float *f = static_cast<float *>(vp); 92 f[offset] = v; 93} 94 95static void SC_storeI32(uint32_t bank, uint32_t offset, int32_t v) 96{ 97 GET_TLS(); 98 void *vp = sc->mSlots[bank]->getPtr(); 99 int32_t *f = static_cast<int32_t *>(vp); 100 static_cast<int32_t *>(sc->mSlots[bank]->getPtr())[offset] = v; 101} 102 103static void SC_storeU32(uint32_t bank, uint32_t offset, uint32_t v) 104{ 105 GET_TLS(); 106 void *vp = sc->mSlots[bank]->getPtr(); 107 uint32_t *f = static_cast<uint32_t *>(vp); 108 static_cast<uint32_t *>(sc->mSlots[bank]->getPtr())[offset] = v; 109} 110 111static void SC_storeVec4(uint32_t bank, uint32_t offset, const rsc_Vector4 *v) 112{ 113 GET_TLS(); 114 void *vp = sc->mSlots[bank]->getPtr(); 115 float *f = static_cast<float *>(vp); 116 memcpy(&f[offset], v, sizeof(rsc_Vector4)); 117} 118 119static void SC_storeMatrix(uint32_t bank, uint32_t offset, const rsc_Matrix *m) 120{ 121 GET_TLS(); 122 void *vp = sc->mSlots[bank]->getPtr(); 123 float *f = static_cast<float *>(vp); 124 memcpy(&f[offset], m, sizeof(rsc_Matrix)); 125} 126 127 128////////////////////////////////////////////////////////////////////////////// 129// Math routines 130////////////////////////////////////////////////////////////////////////////// 131 132static float SC_randf(float max) 133{ 134 float r = (float)rand(); 135 return r / RAND_MAX * max; 136} 137 138 139////////////////////////////////////////////////////////////////////////////// 140// Time routines 141////////////////////////////////////////////////////////////////////////////// 142 143static uint32_t SC_second() 144{ 145 GET_TLS(); 146 147 time_t rawtime; 148 time(&rawtime); 149 150 if (sc->mEnviroment.mTimeZone) { 151 struct tm timeinfo; 152 localtime_tz(&rawtime, &timeinfo, sc->mEnviroment.mTimeZone); 153 return timeinfo.tm_sec; 154 } else { 155 struct tm *timeinfo; 156 timeinfo = localtime(&rawtime); 157 return timeinfo->tm_sec; 158 } 159} 160 161static uint32_t SC_minute() 162{ 163 GET_TLS(); 164 165 time_t rawtime; 166 time(&rawtime); 167 168 if (sc->mEnviroment.mTimeZone) { 169 struct tm timeinfo; 170 localtime_tz(&rawtime, &timeinfo, sc->mEnviroment.mTimeZone); 171 return timeinfo.tm_min; 172 } else { 173 struct tm *timeinfo; 174 timeinfo = localtime(&rawtime); 175 return timeinfo->tm_min; 176 } 177} 178 179static uint32_t SC_hour() 180{ 181 GET_TLS(); 182 183 time_t rawtime; 184 time(&rawtime); 185 186 if (sc->mEnviroment.mTimeZone) { 187 struct tm timeinfo; 188 localtime_tz(&rawtime, &timeinfo, sc->mEnviroment.mTimeZone); 189 return timeinfo.tm_hour; 190 } else { 191 struct tm *timeinfo; 192 timeinfo = localtime(&rawtime); 193 return timeinfo->tm_hour; 194 } 195} 196 197////////////////////////////////////////////////////////////////////////////// 198// Matrix routines 199////////////////////////////////////////////////////////////////////////////// 200 201 202static void SC_matrixLoadIdentity(rsc_Matrix *mat) 203{ 204 Matrix *m = reinterpret_cast<Matrix *>(mat); 205 m->loadIdentity(); 206} 207 208static void SC_matrixLoadFloat(rsc_Matrix *mat, const float *f) 209{ 210 Matrix *m = reinterpret_cast<Matrix *>(mat); 211 m->load(f); 212} 213 214static void SC_matrixLoadMat(rsc_Matrix *mat, const rsc_Matrix *newmat) 215{ 216 Matrix *m = reinterpret_cast<Matrix *>(mat); 217 m->load(reinterpret_cast<const Matrix *>(newmat)); 218} 219 220static void SC_matrixLoadRotate(rsc_Matrix *mat, float rot, float x, float y, float z) 221{ 222 Matrix *m = reinterpret_cast<Matrix *>(mat); 223 m->loadRotate(rot, x, y, z); 224} 225 226static void SC_matrixLoadScale(rsc_Matrix *mat, float x, float y, float z) 227{ 228 Matrix *m = reinterpret_cast<Matrix *>(mat); 229 m->loadScale(x, y, z); 230} 231 232static void SC_matrixLoadTranslate(rsc_Matrix *mat, float x, float y, float z) 233{ 234 Matrix *m = reinterpret_cast<Matrix *>(mat); 235 m->loadTranslate(x, y, z); 236} 237 238static void SC_matrixLoadMultiply(rsc_Matrix *mat, const rsc_Matrix *lhs, const rsc_Matrix *rhs) 239{ 240 Matrix *m = reinterpret_cast<Matrix *>(mat); 241 m->loadMultiply(reinterpret_cast<const Matrix *>(lhs), 242 reinterpret_cast<const Matrix *>(rhs)); 243} 244 245static void SC_matrixMultiply(rsc_Matrix *mat, const rsc_Matrix *rhs) 246{ 247 Matrix *m = reinterpret_cast<Matrix *>(mat); 248 m->multiply(reinterpret_cast<const Matrix *>(rhs)); 249} 250 251static void SC_matrixRotate(rsc_Matrix *mat, float rot, float x, float y, float z) 252{ 253 Matrix *m = reinterpret_cast<Matrix *>(mat); 254 m->rotate(rot, x, y, z); 255} 256 257static void SC_matrixScale(rsc_Matrix *mat, float x, float y, float z) 258{ 259 Matrix *m = reinterpret_cast<Matrix *>(mat); 260 m->scale(x, y, z); 261} 262 263static void SC_matrixTranslate(rsc_Matrix *mat, float x, float y, float z) 264{ 265 Matrix *m = reinterpret_cast<Matrix *>(mat); 266 m->translate(x, y, z); 267} 268 269 270 271 272////////////////////////////////////////////////////////////////////////////// 273// Context 274////////////////////////////////////////////////////////////////////////////// 275 276static void SC_bindTexture(RsProgramFragment vpf, uint32_t slot, RsAllocation va) 277{ 278 GET_TLS(); 279 rsi_ProgramFragmentBindTexture(rsc, 280 static_cast<ProgramFragment *>(vpf), 281 slot, 282 static_cast<Allocation *>(va)); 283 284} 285 286static void SC_bindSampler(RsProgramFragment vpf, uint32_t slot, RsSampler vs) 287{ 288 GET_TLS(); 289 rsi_ProgramFragmentBindSampler(rsc, 290 static_cast<ProgramFragment *>(vpf), 291 slot, 292 static_cast<Sampler *>(vs)); 293 294} 295 296static void SC_bindProgramFragmentStore(RsProgramFragmentStore pfs) 297{ 298 GET_TLS(); 299 rsi_ContextBindProgramFragmentStore(rsc, pfs); 300 301} 302 303static void SC_bindProgramFragment(RsProgramFragment pf) 304{ 305 GET_TLS(); 306 rsi_ContextBindProgramFragment(rsc, pf); 307 308} 309 310static void SC_bindProgramVertex(RsProgramVertex pv) 311{ 312 GET_TLS(); 313 rsi_ContextBindProgramVertex(rsc, pv); 314 315} 316 317////////////////////////////////////////////////////////////////////////////// 318// VP 319////////////////////////////////////////////////////////////////////////////// 320 321static void SC_vpLoadModelMatrix(const rsc_Matrix *m) 322{ 323 GET_TLS(); 324 rsc->getVertex()->setModelviewMatrix(m); 325} 326 327static void SC_vpLoadTextureMatrix(const rsc_Matrix *m) 328{ 329 GET_TLS(); 330 rsc->getVertex()->setTextureMatrix(m); 331} 332 333 334 335////////////////////////////////////////////////////////////////////////////// 336// Drawing 337////////////////////////////////////////////////////////////////////////////// 338 339static void SC_drawTriangleMesh(RsTriangleMesh mesh) 340{ 341 GET_TLS(); 342 rsi_TriangleMeshRender(rsc, mesh); 343} 344 345static void SC_drawTriangleMeshRange(RsTriangleMesh mesh, uint32_t start, uint32_t count) 346{ 347 GET_TLS(); 348 rsi_TriangleMeshRenderRange(rsc, mesh, start, count); 349} 350 351// Assumes (GL_FIXED) x,y,z (GL_UNSIGNED_BYTE)r,g,b,a 352static void SC_drawTriangleArray(int ialloc, uint32_t count) 353{ 354 GET_TLS(); 355 RsAllocation alloc = (RsAllocation)ialloc; 356 357 const Allocation *a = (const Allocation *)alloc; 358 const uint32_t *ptr = (const uint32_t *)a->getPtr(); 359 360 rsc->setupCheck(); 361 362 glBindBuffer(GL_ARRAY_BUFFER, 0); 363 //glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, tm->mBufferObjects[1]); 364 365 glEnableClientState(GL_VERTEX_ARRAY); 366 glDisableClientState(GL_NORMAL_ARRAY); 367 glDisableClientState(GL_TEXTURE_COORD_ARRAY); 368 glEnableClientState(GL_COLOR_ARRAY); 369 370 glVertexPointer(2, GL_FIXED, 12, ptr + 1); 371 //glTexCoordPointer(2, GL_FIXED, 24, ptr + 1); 372 glColorPointer(4, GL_UNSIGNED_BYTE, 12, ptr); 373 374 glDrawArrays(GL_TRIANGLES, 0, count * 3); 375} 376 377static void SC_drawQuad(float x1, float y1, float z1, 378 float x2, float y2, float z2, 379 float x3, float y3, float z3, 380 float x4, float y4, float z4) 381{ 382 GET_TLS(); 383 384 //LOGE("Quad"); 385 //LOGE("%4.2f, %4.2f, %4.2f", x1, y1, z1); 386 //LOGE("%4.2f, %4.2f, %4.2f", x2, y2, z2); 387 //LOGE("%4.2f, %4.2f, %4.2f", x3, y3, z3); 388 //LOGE("%4.2f, %4.2f, %4.2f", x4, y4, z4); 389 390 float vtx[] = {x1,y1,z1, x2,y2,z2, x3,y3,z3, x4,y4,z4}; 391 static const float tex[] = {0,1, 1,1, 1,0, 0,0}; 392 393 394 rsc->setupCheck(); 395 396 glBindBuffer(GL_ARRAY_BUFFER, 0); 397 //glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, tm->mBufferObjects[1]); 398 399 glEnableClientState(GL_VERTEX_ARRAY); 400 glVertexPointer(3, GL_FLOAT, 0, vtx); 401 402 glClientActiveTexture(GL_TEXTURE0); 403 glEnableClientState(GL_TEXTURE_COORD_ARRAY); 404 glTexCoordPointer(2, GL_FLOAT, 0, tex); 405 glClientActiveTexture(GL_TEXTURE1); 406 glEnableClientState(GL_TEXTURE_COORD_ARRAY); 407 glTexCoordPointer(2, GL_FLOAT, 0, tex); 408 glClientActiveTexture(GL_TEXTURE0); 409 410 glDisableClientState(GL_NORMAL_ARRAY); 411 glDisableClientState(GL_COLOR_ARRAY); 412 413 //glColorPointer(4, GL_UNSIGNED_BYTE, 12, ptr); 414 415 glDrawArrays(GL_TRIANGLE_FAN, 0, 4); 416} 417 418static void SC_drawRect(float x1, float y1, 419 float x2, float y2, float z) 420{ 421 SC_drawQuad(x1, y2, z, 422 x2, y2, z, 423 x2, y1, z, 424 x1, y1, z); 425} 426 427////////////////////////////////////////////////////////////////////////////// 428// 429////////////////////////////////////////////////////////////////////////////// 430 431static void SC_color(float r, float g, float b, float a) 432{ 433 glColor4f(r, g, b, a); 434} 435 436/* 437extern "C" void materialDiffuse(float r, float g, float b, float a) 438{ 439 float v[] = {r, g, b, a}; 440 glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, v); 441} 442 443extern "C" void materialSpecular(float r, float g, float b, float a) 444{ 445 float v[] = {r, g, b, a}; 446 glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, v); 447} 448 449extern "C" void materialShininess(float s) 450{ 451 glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, &s); 452} 453*/ 454 455static void SC_uploadToTexture(RsAllocation va, uint32_t baseMipLevel) 456{ 457 GET_TLS(); 458 rsi_AllocationUploadToTexture(rsc, va, baseMipLevel); 459} 460 461static void SC_ClearColor(float r, float g, float b, float a) 462{ 463 //LOGE("c %f %f %f %f", r, g, b, a); 464 GET_TLS(); 465 sc->mEnviroment.mClearColor[0] = r; 466 sc->mEnviroment.mClearColor[1] = g; 467 sc->mEnviroment.mClearColor[2] = b; 468 sc->mEnviroment.mClearColor[3] = a; 469} 470 471static void SC_debugF(const char *s, float f) 472{ 473 LOGE("%s %f", s, f); 474} 475 476static void SC_debugI32(const char *s, int32_t i) 477{ 478 LOGE("%s %i", s, i); 479} 480 481 482 483////////////////////////////////////////////////////////////////////////////// 484// Class implementation 485////////////////////////////////////////////////////////////////////////////// 486 487ScriptCState::SymbolTable_t ScriptCState::gSyms[] = { 488 // IO 489 { "loadI32", (void *)&SC_loadI32, 490 "int", "(int, int)" }, 491 //{ "loadU32", (void *)&SC_loadU32, "unsigned int", "(int, int)" }, 492 { "loadF", (void *)&SC_loadF, 493 "float", "(int, int)" }, 494 { "loadVec4", (void *)&SC_loadVec4, 495 "void", "(int, int, float *)" }, 496 { "loadMatrix", (void *)&SC_loadMatrix, 497 "void", "(int, int, float *)" }, 498 { "storeI32", (void *)&SC_storeI32, 499 "void", "(int, int, int)" }, 500 //{ "storeU32", (void *)&SC_storeU32, "void", "(int, int, unsigned int)" }, 501 { "storeF", (void *)&SC_storeF, 502 "void", "(int, int, float)" }, 503 { "storeVec4", (void *)&SC_storeVec4, 504 "void", "(int, int, float *)" }, 505 { "storeMatrix", (void *)&SC_storeMatrix, 506 "void", "(int, int, float *)" }, 507 508 // math 509 { "sinf", (void *)&sinf, 510 "float", "(float)" }, 511 { "cosf", (void *)&cosf, 512 "float", "(float)" }, 513 { "fabsf", (void *)&fabsf, 514 "float", "(float)" }, 515 { "randf", (void *)&SC_randf, 516 "float", "(float)" }, 517 { "floorf", (void *)&floorf, 518 "float", "(float)" }, 519 { "ceilf", (void *)&ceilf, 520 "float", "(float)" }, 521 522 // time 523 { "second", (void *)&SC_second, 524 "int", "()" }, 525 { "minute", (void *)&SC_minute, 526 "int", "()" }, 527 { "hour", (void *)&SC_hour, 528 "int", "()" }, 529 530 // matrix 531 { "matrixLoadIdentity", (void *)&SC_matrixLoadIdentity, 532 "void", "(float *mat)" }, 533 { "matrixLoadFloat", (void *)&SC_matrixLoadFloat, 534 "void", "(float *mat, float *f)" }, 535 { "matrixLoadMat", (void *)&SC_matrixLoadMat, 536 "void", "(float *mat, float *newmat)" }, 537 { "matrixLoadRotate", (void *)&SC_matrixLoadRotate, 538 "void", "(float *mat, float rot, float x, float y, float z)" }, 539 { "matrixLoadScale", (void *)&SC_matrixLoadScale, 540 "void", "(float *mat, float x, float y, float z)" }, 541 { "matrixLoadTranslate", (void *)&SC_matrixLoadTranslate, 542 "void", "(float *mat, float x, float y, float z)" }, 543 { "matrixLoadMultiply", (void *)&SC_matrixLoadMultiply, 544 "void", "(float *mat, float *lhs, float *rhs)" }, 545 { "matrixMultiply", (void *)&SC_matrixMultiply, 546 "void", "(float *mat, float *rhs)" }, 547 { "matrixRotate", (void *)&SC_matrixRotate, 548 "void", "(float *mat, float rot, float x, float y, float z)" }, 549 { "matrixScale", (void *)&SC_matrixScale, 550 "void", "(float *mat, float x, float y, float z)" }, 551 { "matrixTranslate", (void *)&SC_matrixTranslate, 552 "void", "(float *mat, float x, float y, float z)" }, 553 554 // context 555 { "bindProgramFragment", (void *)&SC_bindProgramFragment, 556 "void", "(int)" }, 557 { "bindProgramFragmentStore", (void *)&SC_bindProgramFragmentStore, 558 "void", "(int)" }, 559 { "bindProgramVertex", (void *)&SC_bindProgramVertex, 560 "void", "(int)" }, 561 { "bindSampler", (void *)&SC_bindSampler, 562 "void", "(int, int, int)" }, 563 { "bindTexture", (void *)&SC_bindTexture, 564 "void", "(int, int, int)" }, 565 566 // vp 567 { "vpLoadModelMatrix", (void *)&SC_vpLoadModelMatrix, 568 "void", "(void *)" }, 569 { "vpLoadTextureMatrix", (void *)&SC_vpLoadTextureMatrix, 570 "void", "(void *)" }, 571 572 573 574 // drawing 575 { "drawRect", (void *)&SC_drawRect, 576 "void", "(float x1, float y1, float x2, float y2, float z)" }, 577 { "drawQuad", (void *)&SC_drawQuad, 578 "void", "(float x1, float y1, float z1, float x2, float y2, float z2, float x3, float y3, float z3, float x4, float y4, float z4)" }, 579 { "drawTriangleArray", (void *)&SC_drawTriangleArray, 580 "void", "(int ialloc, int count)" }, 581 { "drawTriangleMesh", (void *)&SC_drawTriangleMesh, 582 "void", "(int mesh)" }, 583 { "drawTriangleMeshRange", (void *)&SC_drawTriangleMeshRange, 584 "void", "(int mesh, int start, int count)" }, 585 586 587 // misc 588 { "pfClearColor", (void *)&SC_ClearColor, 589 "void", "(float, float, float, float)" }, 590 { "color", (void *)&SC_color, 591 "void", "(float, float, float, float)" }, 592 593 { "uploadToTexture", (void *)&SC_uploadToTexture, 594 "void", "(int, int)" }, 595 596 597 { "debugF", (void *)&SC_debugF, 598 "void", "(void *, float)" }, 599 { "debugI32", (void *)&SC_debugI32, 600 "void", "(void *, int)" }, 601 602 603 { NULL, NULL, NULL, NULL } 604}; 605 606const ScriptCState::SymbolTable_t * ScriptCState::lookupSymbol(const char *sym) 607{ 608 ScriptCState::SymbolTable_t *syms = gSyms; 609 610 while (syms->mPtr) { 611 if (!strcmp(syms->mName, sym)) { 612 return syms; 613 } 614 syms++; 615 } 616 return NULL; 617} 618 619void ScriptCState::appendDecls(String8 *str) 620{ 621 ScriptCState::SymbolTable_t *syms = gSyms; 622 while (syms->mPtr) { 623 str->append(syms->mRet); 624 str->append(" "); 625 str->append(syms->mName); 626 str->append(syms->mParam); 627 str->append(";\n"); 628 syms++; 629 } 630} 631 632 633