1326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams/* 2326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * Copyright (C) 2009 The Android Open Source Project 3326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * 4326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * Licensed under the Apache License, Version 2.0 (the "License"); 5326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * you may not use this file except in compliance with the License. 6326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * You may obtain a copy of the License at 7326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * 8326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * http://www.apache.org/licenses/LICENSE-2.0 9326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * 10326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * Unless required by applicable law or agreed to in writing, software 11326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * distributed under the License is distributed on an "AS IS" BASIS, 12326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * See the License for the specific language governing permissions and 14326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams * limitations under the License. 15326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams */ 16326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 17326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams#include "rsContext.h" 18fb6b614bcea88a587a7ea4530be45ff0ffa0210eAlex Sakhartchouk#include "rsProgramFragment.h" 191aa5a4eb81b8b88aeb5d2b6f4c47356fd0a62923Jason Sams 20326e0ddf89e8df2837752fbfd7a014814b32082cJason Samsusing namespace android; 21326e0ddf89e8df2837752fbfd7a014814b32082cJason Samsusing namespace android::renderscript; 22326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 23748eb07e805b93c2bf79340d4937963ab739d17cAlex SakhartchoukProgramFragment::ProgramFragment(Context *rsc, const char * shaderText, size_t shaderLength, 24748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk const char** textureNames, size_t textureNamesCount, const size_t *textureNamesLength, 25748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk 26748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk const uint32_t * params, size_t paramLength) 27afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk : Program(rsc, shaderText, shaderLength, params, paramLength) { 286445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[0] = 1.f; 296445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[1] = 1.f; 306445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[2] = 1.f; 316445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[3] = 1.f; 326445e5210c6d7f8689e94be9026153d017c9545bJason Sams 33748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk mRSC->mHal.funcs.fragment.init(mRSC, this, mUserShader.string(), mUserShader.length(), 34748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk textureNames, textureNamesCount, textureNamesLength); 35f2e4fa215c420cf0f8d226e9a59acb1f312e5e40Jason Sams} 36f2e4fa215c420cf0f8d226e9a59acb1f312e5e40Jason Sams 37afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex SakhartchoukProgramFragment::~ProgramFragment() { 38a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk mRSC->mHal.funcs.fragment.destroy(mRSC, this); 39326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams} 40326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 41afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchoukvoid ProgramFragment::setConstantColor(Context *rsc, float r, float g, float b, float a) { 42afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchouk if (isUserProgram()) { 43af12ac6a08651464f8d823add667c706f993b587Steve Block ALOGE("Attempting to set fixed function emulation color on user program"); 44383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk rsc->setError(RS_ERROR_BAD_SHADER, "Cannot set fixed function emulation color on user program"); 45383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk return; 46383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk } 47064aa7ed76db9564b041afcd4b75da5b3d12fabaAlex Sakhartchouk if (mHal.state.constants[0] == NULL) { 48af12ac6a08651464f8d823add667c706f993b587Steve Block ALOGE("Unable to set fixed function emulation color because allocation is missing"); 49383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk rsc->setError(RS_ERROR_BAD_SHADER, "Unable to set fixed function emulation color because allocation is missing"); 50e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk return; 51e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk } 526445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[0] = r; 536445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[1] = g; 546445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[2] = b; 556445e5210c6d7f8689e94be9026153d017c9545bJason Sams mConstantColor[3] = a; 56807fdc4b6f3fb893015ee136565d6151bb2332d3Jason Sams void *p = rsc->mHal.funcs.allocation.lock1D(rsc, mHal.state.constants[0]); 57807fdc4b6f3fb893015ee136565d6151bb2332d3Jason Sams memcpy(p, mConstantColor, 4*sizeof(float)); 586445e5210c6d7f8689e94be9026153d017c9545bJason Sams mDirty = true; 59807fdc4b6f3fb893015ee136565d6151bb2332d3Jason Sams rsc->mHal.funcs.allocation.unlock1D(rsc, mHal.state.constants[0]); 606445e5210c6d7f8689e94be9026153d017c9545bJason Sams} 61334fd9aeacd4221fc8cd1333b2a34fb3b26b3a0dJason Sams 62c19ff0177a7a0dadfc01b1990f822354fdc95991Alex Sakhartchoukvoid ProgramFragment::setup(Context *rsc, ProgramFragmentState *state) { 63c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams if ((state->mLast.get() == this) && !mDirty) { 64e64c2f172516972abe581ca1b762302dd2ba1199Jason Sams return; 65c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams } 66c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams state->mLast.set(this); 67c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams 68a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk for (uint32_t ct=0; ct < mHal.state.texturesCount; ct++) { 69064aa7ed76db9564b041afcd4b75da5b3d12fabaAlex Sakhartchouk if (!mHal.state.textures[ct]) { 70af12ac6a08651464f8d823add667c706f993b587Steve Block ALOGE("No texture bound for shader id %u, texture unit %u", (uint)this, ct); 71383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk rsc->setError(RS_ERROR_BAD_SHADER, "No texture bound"); 72c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams continue; 73c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams } 74383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk } 756e9342199959dc9beb5299fefc9775fe8c32620eAlex Sakhartchouk 76a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk rsc->mHal.funcs.fragment.setActive(rsc, this); 77c460e55d78cbe8bee95c5c947dfe541218142a5bJason Sams} 78326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 79e3150cfb3edb028407669e4a65e087eae77e718cJason Samsvoid ProgramFragment::serialize(Context *rsc, OStream *stream) const { 80fb6b614bcea88a587a7ea4530be45ff0ffa0210eAlex Sakhartchouk} 81fb6b614bcea88a587a7ea4530be45ff0ffa0210eAlex Sakhartchouk 82afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex SakhartchoukProgramFragment *ProgramFragment::createFromStream(Context *rsc, IStream *stream) { 83fb6b614bcea88a587a7ea4530be45ff0ffa0210eAlex Sakhartchouk return NULL; 84fb6b614bcea88a587a7ea4530be45ff0ffa0210eAlex Sakhartchouk} 85fb6b614bcea88a587a7ea4530be45ff0ffa0210eAlex Sakhartchouk 86afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex SakhartchoukProgramFragmentState::ProgramFragmentState() { 87326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams mPF = NULL; 88326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams} 89326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 90afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex SakhartchoukProgramFragmentState::~ProgramFragmentState() { 91225afd317e101a7be5fe02c0a86361146ea89f05Jason Sams ObjectBase::checkDelete(mPF); 92225afd317e101a7be5fe02c0a86361146ea89f05Jason Sams mPF = NULL; 93326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams} 94326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 95afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchoukvoid ProgramFragmentState::init(Context *rsc) { 96e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk String8 shaderString(RS_SHADER_INTERNAL); 97e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk shaderString.append("varying lowp vec4 varColor;\n"); 987ffcaf20cbb115326f3d72a983835d6c314a4cefAlex Sakhartchouk shaderString.append("varying vec2 varTex0;\n"); 99e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk shaderString.append("void main() {\n"); 100e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk shaderString.append(" lowp vec4 col = UNI_Color;\n"); 101e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk shaderString.append(" gl_FragColor = col;\n"); 102e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk shaderString.append("}\n"); 103e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk 104c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk ObjectBaseRef<const Element> colorElem = Element::createRef(rsc, RS_TYPE_FLOAT_32, RS_KIND_USER, false, 4); 105c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk Element::Builder builder; 106c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk builder.add(colorElem.get(), "Color", 1); 107c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk ObjectBaseRef<const Element> constInput = builder.create(rsc); 108e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk 109c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk ObjectBaseRef<Type> inputType = Type::getTypeRef(rsc, constInput.get(), 1, 0, 0, false, false); 110e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk 11184e4027f83b20af59f5b1fc52be6e45f159d3970Alex Sakhartchouk uint32_t tmp[2]; 112e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk tmp[0] = RS_PROGRAM_PARAM_CONSTANT; 113c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk tmp[1] = (uint32_t)inputType.get(); 114e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk 115c700e649ca44d0dcff8b271e42d949ea72fe3c63Alex Sakhartchouk Allocation *constAlloc = Allocation::createAllocation(rsc, inputType.get(), 116eb4fe18dd88634330f9566cbb9e785d8c7ec5813Jason Sams RS_ALLOCATION_USAGE_SCRIPT | RS_ALLOCATION_USAGE_GRAPHICS_CONSTANTS); 117748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk ProgramFragment *pf = new ProgramFragment(rsc, shaderString.string(), shaderString.length(), 118748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk NULL, 0, NULL, tmp, 2); 119383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk pf->bindAllocation(rsc, constAlloc, 0); 120383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex Sakhartchouk pf->setConstantColor(rsc, 1.0f, 1.0f, 1.0f, 1.0f); 121e7ae69f4a70f1813cf8086ebd9714192c635300aAlex Sakhartchouk 1228ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams mDefault.set(pf); 1238ce125be69531dbf3a7e856d5e59d1b8e2789db0Jason Sams} 124326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 125afb743aca56c18beb7ab924e75cb6e070ef3e55aAlex Sakhartchoukvoid ProgramFragmentState::deinit(Context *rsc) { 126f2649a961db2995e9e24a6c98f8a419f1496c1b7Jason Sams mDefault.clear(); 127f2649a961db2995e9e24a6c98f8a419f1496c1b7Jason Sams mLast.clear(); 128f2649a961db2995e9e24a6c98f8a419f1496c1b7Jason Sams} 129f2649a961db2995e9e24a6c98f8a419f1496c1b7Jason Sams 130326e0ddf89e8df2837752fbfd7a014814b32082cJason Samsnamespace android { 131326e0ddf89e8df2837752fbfd7a014814b32082cJason Samsnamespace renderscript { 132326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 133383e5b1f68c321a77bfd7466fa1171a9bfab4a6fAlex SakhartchoukRsProgramFragment rsi_ProgramFragmentCreate(Context *rsc, const char * shaderText, 134748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk size_t shaderLength, 135748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk const char** textureNames, 136748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk size_t textureNamesCount, 137748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk const size_t *textureNamesLength, 138748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk const uint32_t * params, size_t paramLength) { 139748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk ProgramFragment *pf = new ProgramFragment(rsc, shaderText, shaderLength, 140748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk textureNames, textureNamesCount, textureNamesLength, 141748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk params, paramLength); 142f2e4fa215c420cf0f8d226e9a59acb1f312e5e40Jason Sams pf->incUserRef(); 143af12ac6a08651464f8d823add667c706f993b587Steve Block //ALOGE("rsi_ProgramFragmentCreate %p", pf); 144f2e4fa215c420cf0f8d226e9a59acb1f312e5e40Jason Sams return pf; 145f2e4fa215c420cf0f8d226e9a59acb1f312e5e40Jason Sams} 146326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 147326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams} 148326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams} 149326e0ddf89e8df2837752fbfd7a014814b32082cJason Sams 150