This is needed to instantiate `std::streampos`. It currently relies on transitive header inclusion to get that, which is going away for libc++ in ebcf1bf2ec.
The parser object was accessed to generate a key after being passed to
the lambda using std::move(). This led to a crash on certain platforms
(at least on Windows).
This change fixes it by creating key first before moving the parser
object into the lambda.
This new method, intended for the vertex shader, returns a matrix that
transforms vertices from view space (also known as head space) to the
current eye space.
BUGS=[441127971]
In ZstdHelper::isCompressed call, `src` may not be aligned to 4 bytes,
which is violating the alignment requirement of
`UndefinedBehaviorSanitizer: misaligned-pointer-use`, thereby resuling
in a runtime failure with UBSan enabled. So reconstruct the 32-bit
integer as a workaround.
In EGLAndroid, external textures imported from an AHB
that dont use a SAMPLER_EXTERNAL are not properly destroyed,
causing a memory leak that eventually leads to an OOM.
- add conveniences function to make LineDictionary look like a vector
- a pattern must start on a word boundary but "_" wasn't treated as one
- getIndices() must return the empty vector when any of the substring
is not found
We link the behavior of certain precondition/postcondition checks to feature flag states.
- If provided *flag* is true, then this macro will assert when the *condition* is false.
- If provided *flag* is fase, then this macro will output a warning when the condition is false.
- If the condition is true, then neither of the above will happen
These two macros will enable us to provide less restrictive behavior for certain correctness assertions, allowing clients to modify their before enabling these assertions by default.
* gl: Enhance error reporting for asynchronous shader operations
When ShaderCompilerService asynchronously compiles and links shaders,
unexpected errors (e.g., GL_CONTEXT_LOST) can occur after the initial GL
call, complicating diagnostics.
This change improves error context by collecting the GL error status
when querying shader compilation and program link statuses. This
provides a more detailed understanding of error origins.
BUGS=[373396840]
* feedback
When a program was created directly from a cached blob in
`ShaderCompilerService`, its associated token was not signaled as ready
in the THREAD_POOL mode. This oversight caused a deadlock at the
`token->wait()` call during program destruction.
This commit resolves the issue by skipping the token's readiness check
upon destruction if the program was created from the cache blob.
BUGS=[423221474]
This reverts a behavioral regression introduced in commit c3542b135e,
which deferred callback submission until the program was first used.
This commit restores the correct behavior by submitting the callback
handle as soon as the token's work is complete. This occurs either upon
successful `gl.program` population or via cancellation, ensuring the
caller is properly notified that the resource loading operation has
concluded.
The addition JobSystem.cpp allows for defining
FILAMENT_TRACING_ENABLED across targets.
Addingin FILAMENT_TRACING_ENABLED to the #if in Tracing.h prevents
perfetto from being included.
There was several issues:
1) when we're switching contexts (e.g. between protect and regular) we
needed up reattach all SurfaceView (i.e. streams), because they need
to be attached on currently active context.
2) reattaching, because it's implemented as detach + attach, would
destroy the current gl texture id and create a new one. However,
because of the way descriptor-sets were implemented, that GL
texture id was kept inside the descriptor, later leading to using
a destroyed texture id.
The fix here is to store texture handles in descriptors, so that
we can update the id independently.
3) we also needed to invalidate all bound descriptor sets because it's
now possible for descriptor sets to have outdated descriptors
- Some tests require textures larger than 2048. Change the minimum
to 4096 for now, and file proper bugs for tests.
- The introduction of uint8_t to DescriptorSetLayoutBinding
caused unintended padding with using this struct as a hash key.
We comment out the relevent code for now.
Just like mCulling, mShadowCulling needs to be inherited from the
material.
Fix breakage introduced in #8422 with attempted fix in #8475 and
caused by an uninitialized variable (mShadowCulling).
BUGS=[391679058]
If FXAA is the last post process effect (i.e. no upscaling), and
color grading produced a luma channel, then FXAA needs to reset the
alpha channel to 1.
This will allow a more lenient rollout of the assertion, which
otherwise will increase crashes for current clients.
We also disable features.engine.debug.assert_material_instance_in_use
by default (it was enabled for debug builds).
If the shared osmesa lib is not found, then we assume that the
library has been compile-time linked via the linker. This is to
accommodate build frameworks where compile-time linking is
preferred.
This restores the old behavior with depth variant caching. We pay the
price at engine init time, instead of when the variant is needed the
first time. We can revisit this later.
Note that the default material doesn't have all possible depth variants
(e.g. VSM), but that pre-caches the most popular ones.
BUGS=[381946222]
On ES2 devices (or in forceES2 mode), we emulate the sRGB swapchain
in the shader if the h/w doesn't support it. In that case, the emulation
is controlled by a uniform that technically lives in the frameUniforms
block. However, the frameUniforms buffer is not updated, instead,
the uniform is manually set. Unfortunately, the UBO emulation
overrides it with the uninitialized variable.
BUGS=[377913730]
Mesa always clears the generic binding if the buffer deleted
is bound to an indexed binding, even if it's not bound to the
generic binding.
BUGS=[371324321]
- We change GLDescriptorSet::Buffer default constructor to
workaround a client's compiler set up issue.
- We removed the assert_invariant that checks that ubo/samplers
are not changed after committed in DescriptorSet. This caused
an existing client's build to crash.
Found through testing that renderStandaloneView+vk+swiftshader
seems to cause synchronization issues, which results in incorrect
rendering. Here we workaround the issue by forcibly flush and
wait per renderStandaloneView call.
BUG=361822355
`DebugRegistry::setProperty` is no longer just applicable to debug
builds.
This change was previously added in 6c0bd36 but then reverted
in a7317e7. We re-enable it and separate it from the shadow
changes in this commit.
This fixes a crash introduced by a8ace2891d
The refactored FrameInfoManager can cause a crash when IBL resource loading
happens because now the getLastFrameInfo() references an invalid value via the
`front` method. Return the default FrameInfo to resolve this.
Also fix a null pointer reference bug for OpenGLTimer::State, which
happenes when the renderer for IBLPrefilterContext is destroyed.
- remove deprecated morphing APIs
- repair gltfio, samples and tests
The new API doesn't allow a MorphTargetBuffer per RenderPrimitive,
instead the MorphTargetBuffer is specified per Renderable.
gltfio separates RenderPrimitives from Renderables, in particular all
RenderPrimitives are created before their Renderable; this was
problematic for this change because all primitives must share
a single MorphTargetBuffer living in the Renderable.
To fix this, we're no longer initializing the morphing paramters
at RenderPrimitive creation, instead we store a reference to the
BufferSlot in the Primtive structure, so that later, when the Renderable
is created we can finally retrieve the BufferSlot and initialize its
morphing paramters, which are not available. The "morphing parameters"
are now expanded to contain the MorphTargetBuffer as before (except now
it's always the same for all the primitives of a Rendrable), as well
as the offset within the buffer and the vertex count.
If a user is using `setFrameScheduledCallback()`, managing the provided PresentCallable during engine shutdown is tricky -- we'll likely get a final frame scheduled when we flush the engine's work queue, but the PresentCallable will schedule the final CAMetalDrawable to be released on main thread afterwards, even if we call `present(false)` to skip it. If the swap chain is destroyed before that main queue block gets executed, the mutex presenting that drawable will no longer exist, causing a crash.
To make things easier, store the std::mutex in a shared_ptr, so that a PresentCallable can safely outlive the FSwapChain instance that created it and clean itself up afterwards.
Alternatives considered, all of which seem unfortunate:
* Require users to clear out the callback before shutting down the engine, so that any final drawables are immediately discarded instead of using PresentCallable
* Require users to split up the engine teardown across two main queue blocks, ensuring that the PresentCallable cleanup executes before swapchains are destroyed
* Drop the PresentCallable on the ground and leak the memory
PresentDrawable was moved to main thread by default in google#7535 and stopped
most crashes when a drawable is released. But there still appears to be crashes
if a drawable is released on main thread at the same time that -nextDrawable is
called from the Filament render thread. (It's likely that the drawable pool in
CAMetalLayer is completely non-thread-safe.)
So, add a mutex to the swapchain and always acquire it before creating or
releasing a CAMetalDrawable.
Users can opt out of this behavior by passing
-DFILAMENT_LOCK_METAL_DRAWABLE_POOL=0.
Currently, if this fails we log the error message to stderr (which
doesn't get captured by most crash reporting systems) and then crash in
a postcondition assert. By including the error message in an exception
reason and throwing an ObjC exception, we get better discoverability of
error causes.
(Building a render pipeline state from shaders is usually when a shader
actually gets JITted from LLVM IR to GPU-specific code, so if we
accidentally used a feature that's not available on the local GPU, we'll
find out about it here.)
The current API allowed to have a buffer for each primitive in a
renderable. We instead restrict the API so that there is a single
MorphTargetBuffer for the whole renderable, shared by all primitives.
The buffer can be shared thanks to the "offset" parameter on
setMorphTargetBufferAt().
Also
- fix FMorphTargetBuffer::updateDataAt()
- add support for the "offset" parameter of setMorphTargetBufferAt()
If a .metallib was compiled with a target iOS version that's newer than
the current device, loading the .metallib may succeed, but finding main0
(or any other function in it) will fail. Currently, this causes a crash
due to an assert. Logging the error and returning
MetalFunctionBundle::error() makes the crash slightly easier to
diagnose.
(Note that in practice, this will probably be a useless "Compiler
encountered an internal error" message -- the GPU backend is crashing,
and the Metal stub library sees XPC_ERROR_CONNECTION_INTERRUPTED. It
retries up to 3 times (crashing each time) and then gives up.)
I was unfortunately naive about the way that Filament handled external textures
on non-GLES platforms. This fix restricts the changes to Android (which is the
only place this change is required in the first place). Long story short, the
change broke WebGL. Desktop seems to be unaffected.
the gl backend did some of its cleanup in the its destructor,
including calling into OpenGL, however, the destructor is called from
the main thread, not the GL thread, so these calls would be no-ops at
best, and crashes in the worst case.
This PR adds a new `pause()` option to the `Engine` `Builder` and a new function
`setPaused()` to the `Engine`. While paused, the rendering thread will pause
indefinitely for commands as if none are available. As soon as the rendering
thread is unpaused, the commands are immediately executed.
in case the swapchain creation fails, it will now return a swapchain
with an EGL_NO_SURFACE handle. this will avoid having to nullptr check
the pointer in various places and will revert to the previous behavior
on failure.
FIXES=[329659681]
Previous commit [1] changed the semantic of the index to
mBufferObjects. Here we just make sure that if a buffer has been
allocated, we don't allocate another (otherwise, we'd leak).
Also cleaned up `updateBoneIndicesAndWeights` indexing
[1]: a3131a64b6
The OOB would happen is the scene never had any renderables, in that
case the scene's SoA would stay unallocated, but the summedAreaTable
code relies on it have at least a capacity of 1.
It was incorrect to skip the RenderPass entirely because it might have
had some custom commands that needed to be executed (e.g. for applying
post-processing in subpass mode).
This has caused issues and over time we have reduced the use of
spinlocks, it was only used in few places and we still have evidence
that it's causing ANRs.
We use utils::Mutex instead which is a low overhead mutex implementation
on Linux systems.
FIXES=[321101014]
See #7415 for a more detailed description of why this change is necessary.
The remaining variants which are filtered from FL0 materials are all related to
lighting, so further hacks like this won't be necessary.
Future work involves properly supporting differing sets of variants based on
shader language.
Even if skinning is not fully implemented on FL0, we have clients which depend
on materials with skinning variants that otherwise could easily be converted to
FL0 materials. There are two proper ways to deal with this:
1. Support skinning/morphing in Feature Level 0.
2. Allow ESSL 1.0 code and ESSL 3.0 code to support different sets of variants.
However, the simplest solution is to just include skinning/morphing variants,
but disable codegen for ESSL 1.0 code, making them identical to the base
variants. This shouldn't increase the file size much due to the dictionary
deflation. Of course, skinning will not work correctly on FL0, but this has
always been the case. Future work here would be to properly implement one of the
two solutions described above.
Swiftshader runs spirv validation before compilation. However,
the validation does not like having Nop (no-op) in the input.
So we skip instructions instead of writing no-op for the
output of `workaroundSpecConstant`.
Also, fix issue to keep the value in the original shader if a
specialization wasn't provided.
The CL introducing the ESSL 1.0 chunk in materials inadvertently disabled
optimizations for said code. This commit reintroduces those optimizations and
fixes associated bugs which manifested. In particular, spirv-cross was
generating uints for bools; this has been fixed with a hack. Additionally,
spirv-cross is now compiled with exceptions enabled so that matc can gracefully
fail and show the code which failed to compile rather than abruptly aborting.
Since #7358 is blocked by an upstream spirv-cross issue, we can at least do a
bit of preprocessor optimization for ESSL 1.0 code in the meantime and introduce
the FILAMENT_EFFECTIVE_VERSION preprocessor definitions.
This change in glslang removes the include of "intermediate.h" from
GlslangToSpv.h:
62de186c33
As a result, the definition of "class TIntermediate" is removed, and
will fail compilation of MaterialCompiler.cpp when glslang is updated to
a version including the aforementioned change. We fix this by adding an
explicit include to this header in MaterialCompiler.cpp.
Co-authored-by: Powei Feng <powei@google.com>
- gltfio: Enable -Wall -Werror for gltfio_core
- gltfio: Fix various errors that were missed warnings
- matdbg: switch from std::atomic_uint64_t to
std::atomic<uint64_t> for older clang
- we were not using the correct field in ShadowMapManager
- we were not computing the transform correctly, it should applied
after the local transform, not before.
FIXES=[299310624]
We've seen hangs/ANR that are not well understood on that spinlock, so
for now we're going back to mutexes, which, on android, are very
efficient under low contention (no syscall).
FIXES=[308029108]
* prevent public classes from being created on the stack
- we used to to this by deleting operator delete, but this prevented
the internal "F" classes from being virtual; which can be useful
when using EntityManger::Listener.
now we just make the destructor protected in each class.
- EntityManger::Listener now has a virtual destructor so that
objects could be correctly destroyed from Listener*
* improve EntityManger and Component managers
- all component managers now have the same "base" API
- getComponentCount()
- empty()
- getEntity()
- getEntities()
- Scene now has getEntityCount()
- EntityManager now has getEntityCount()
- all component manager implement gc() the same way, by calling destroy()
- SingleInstanceComponentManager::gc() that calls removeComponent() has
been removed because it's dangerous. removeComponent() is often
not enough, some additional cleanup might be needed.
CameraManager creates a Transform component for each Camera component
is not already present. However, it didn't destroy the transform
component when it's itself destroyed. the leaked transform component
would eventually be garbage collected, but caused significant
slow down and memory pressure. This is because camera components are
created every frame for the shadow maps.
FIXES=[303914944]
- the insert and retrieve handlers can now be set/unset independently.
this could be useful for debugging.
- program caching is disabled if the GL implementation doesn't support it.
- removed unused code
FIXES=[307549547]
This reverts most of commit 9a6b8bf24e. The hello
triangle sample remains unreverted.
The original commit inadvertently broke screen space reflections, and perhaps
other features when the default material was used. The source of the issue is
that MaterialBuilder.cpp (correctly) filters out variants that aren't supported
in feature level 0 materials, including screen space reflections.
Unfortunately, while the "feature level 0 compatibility" feature itself was
intended to make creating duplicate materials like this redundant in client
code, unfortunately, it seems the best solution for resolving this issue is to
simply keep these redundant materials in the core.
To elaborate: clients should expect that feature level 0 materials that they
create work on /all/ feature levels /exactly/ or /close to exactly/ identically.
This includes restricting more advanced features that theoretically could be
available on a higher feature level, like SSR. It's already true that if a user
would like to optionally opt-in to a more advanced material which takes
advantage of more advanced features, they would have to maintain two separate
versions of that material: one for feature level 3 and one for feature level 1.
It should be no different in this case.
However, the materials built into the engine core are an exception to this
expectation. Given that feature level 0 was tacked on after the fact with fewer
features, there must /by necessity/ have been a new material introduced for both
the default material and the default skybox specifically for feature level 0
with fewer features than extant client apps expected to be included by default.
I imagine if filament were to be rebuilt from the ground up, this exception
wouldn't exist. However, the end result is this somewhat messy redundancy.
We wrote a bool directly into 4 bytes (as the first byte). This has two issues:
- the other 3 bytes are not initialized
- should be writing VK_TRUE/FALSE instead
This reverts commit 58f96be2c4.
This caused material files to increase in size significantly. It turns
out that glslang has to generate a copy for each parameter that is
passed to a function as a non-const parameter.
This revert will break IMG devices again, but that should be the case
only on debug builds. Release builds lose the const qualifier by
virtue of going through spirv. We'll try to address this some other
way later.
This reverts commit 58f96be2c4.
This caused material files to increase in size significantly. It turns
out that glslang has to generate a copy for each parameter that is
passed to a function as a non-const parameter.
This revert will break IMG devices again, but that should be the case
only on debug builds. Release builds lose the const qualifier by
virtue of going through spirv. We'll try to address this some other
way later.
Previously, we have a VulkanSync with a default constructor that
allows us to have sync objects that returns error when
actual fences are not yet present. We need to replicate that
with VulkanFence since sync objects have been removed from the
API.
Fixes#7034
this is needed on armv7 because we use alignas to get strcture-alignment,
but that also implies (to the compiler) that the structure itself
is aligned properly.
There was two related issues:
- we need to "latch" the new TextureView size when its resized. That
can only be done by recreating the EGLSurface (i.e. recreating the
SwapChain). UiHelper now calls onNativeWindowChanged in the case of
the TextureView resize, so clients can recreate their SwapChain.
- we also needed to make sure that all current filament frames have
finished to render (i.e. the last eglSwapBuffers has been called) so
that they don't pick-up a new size (this happens after
eglSwapBuffers) that doesn't match the viewport.
Fixes b/282220665
- flush() and wait() before destroying a swapchain
- Make sure the debug marker extension is enabled under correct
circumstances.
- Change shared_ptrs to unique_ptrs and raw pointers.
- Rename most teardown methods to terminate()
Since cmake 3.25 LINUX is automatically set based on CMAKE_SYSTEM_NAME,
which the android cmake files are setting to "Linux". This created an
inconsistant state in our build system.
Since cmake 3.25 LINUX is automatically set based on CMAKE_SYSTEM_NAME,
which the android cmake files are setting to "Linux". This created an
inconsistant state in our build system.
WebGL complained about:
Precisions of uniform block 'ShadowUniforms' member
'ShadowUniforms.shadows.texelSizeAtOneMeter' differ between VERTEX and
FRAGMENT shaders.
this field didn't have a precision qualifier, this might be specific to
WebGL or a Chrome bug, unsure. Either we fix it by specifying all
qualifiers.
WebGL complained about:
Precisions of uniform block 'ShadowUniforms' member
'ShadowUniforms.shadows.texelSizeAtOneMeter' differ between VERTEX and
FRAGMENT shaders.
this field didn't have a precision qualifier, this might be specific to
WebGL or a Chrome bug, unsure. Either we fix it by specifying all
qualifiers.
glDispatchCompute requires Android API level 21, however bumping our
required minimum from 19 to 21 caused some clients' builds to fail.
Commenting-out that line for now to proceed with the 1.28.0 upgrade.
The VulkanProgram constructor was bailing out early and emitting a
warning because it saw that one of the stages wasn't fulfilled.
However it's okay for a pipeline to be missing a compute program.
Fixes regression that started with fabba73b1.
to emulate the bindless API in the gl backend we always used the highest
texture unit available. However at feature level 3, we support up to 62
textures, so the that max was bumped to 62 -- however, where we're not
on a feature level 2 device, that texture unit doesn't exist.
Instead we now always use binding 31, which is guaranteed to exist by
EGL's minspec.
This broke asyncGetLoadProgress() and caused WebGL to crash reliably
because ResourceLoader got destroyed too soon.
Bug was introduced with de7dfc2ea6.
I intend to cherry pick this to rc/1.27.0, which is where it was
introduced, so there's no need to update the release notes.
Filament does not yet fully support threads with WASM, but this is a
baby step in that direction.
To enable experimental pthreads support, enable the WEBGL_PTHREADS CMake
option. This will enable pthreads support in `gltfio` and `utils`, which
is known to work, but not when served with GitHub Pages.
The web server must emit COOP, COEP and CORP headers, so our build
instructions now recommend the use of `emrun` for local testing.
This also changes our demos so that they do not use unpkg, which
does not work when using `emrun`, due to cross-origin restrictions.
I have disabled building SDL with headless EGL, because
SDL_config_minimal.h doesn't work with EGL, and I don't know how to
implement a an SDL config that would work with EGL.
I have verified that this works in a separate project, and that it
compiles in this project.
```
$ ./build.sh -e release
$ find ./out/ -name "*EGL*"
./out/cmake-release/filament/backend/CMakeFiles/backend.dir/src/opengl/platforms/PlatformEGL.cpp.o
./out/cmake-release/filament/backend/CMakeFiles/backend.dir/src/opengl/platforms/PlatformEGLHeadless.cpp.o
./out/cmake-release/libs/bluegl/CMakeFiles/bluegl.dir/src/BlueGLLinuxEGL.cpp.o
```
Reflects a change from Betty and should be cherry picked to v1.23.3
Users could customize the ImGuiHelper camera, but they had no control
over the scissor coordinates. This allows them to use vertically flipped
coordinates, which, unfortunately, is required for MediaPipe
integration.
a 64 bytes pool seems to work with both clang and msvc, unfortunately,
c++ doesn't let us know the allocator object size at compile time
for map containers, so we have to guess.
This is a temporary workaround for a memory corruption issue observed on
some devices from a specific vendor. We will try to make this workaround
more targeted in a subequent change.
Partial revert for b2cdf9f2b4.
This fixes the emscripten binding errors that we've been seeing
with the <filament-viewer> test page, which prevented us from
including web in the last few Filament releases.
The binding errors were caused by double-initializing the emscripten
module.
I fixed this by allowing clients (e.g. FilamentViewer) to call
Filament.init() more than once. We now accumulate a list of "on ready"
callbacks that get triggered after the emscripten module becomes ready.
As far as I can tell, multiple canvases were actually always broken, and
the viewer test page worked in the past only because we got lucky.
The previous code would convert each element of the source data
into 8 bit-per-element, but we wnat to preserve the original format
that the user provides.
The new solution is to use `slice()` which is a robust way to clone
all the data in a typed array.
This fixes the new regression with Triangle that Ben caught.
If emscripten grows the heap inside one of our BufferDescriptor binding
functions, then the old heap becomes "detached" and an error can
occur.
This fixes the issue seen with the Parquet demo that Ben caught.
All three types of caches (descriptor sets, pipelines, and pipeline
layouts) are now managed in exactly the same way. They all use an LRU
eviction scheme that is based on a count of command buffer flush
events.
Vulkan objects can only be destroyed if there are no in-flight command
buffers that reference them, so an easy way to know when it is safe to
evict a given entry is to wait for "N" flushes after its last use, where
"N" is the number of command buffers in the command buffer ring.
Another big simplification is that there are no more dirty flags,
instead we store two sets of state vectors for each type of cache: the
"currently bound" state, and the "current requirements" state.
Fixes#5142 by replacing unsafe pointers with map keys.
One of the differences between robin_map and unordered_map is the
following:
pointers to keys or values in the map are invalidated in the same
way as iterators to these keys-values
Therefore it is unsafe to track the pointer to a value that is stored
in a robin_map.
This is mostly just code cleanup. One actual bug was the fact that the
dummy sampler was re-created every time a new pipeline layout was
created.
It also felt strange to use `auto&` to refer to a C-style array. I
changed this into a `std::array` which is more consistent with other
fixed size arrays in this class.
Support legacy morphing (morphing with targets supplied via VertexAttributes) for older clients. This gives clients more time to transition over to the new MorphTargetBuffer API.
This allows `MorphStressTest` to work on Vulkan.
However, `Horse` is still broken because it provides positions but not
tangents. Separate fix for that is coming.
Partial fix for #5109.
This fixes validation errors and makes a first pass at simplification.
VulkanTexture now tracks image layout using RangeMap, which paves the
way for further simplification.
This will allow the Vulkan backend to efficiently track the subresource
image layouts for each texture.
This is a sparse container for a series of ordered non-overlapping
integer intervals, where each interval maps to a concrete value.
This is because we're using the same program variant for skinning
and morphing, in the skinning-only case, the buffer won't be accessed
in the shader, but it must be present.
fixes#5085
A recent refactor was causing the following error when the vertex domain
was set to `device`:
```
ERROR: main.vs:23: 'material' : undeclared identifier
ERROR: main.vs:23: 'materialVertex' : no matching overloaded function found
```
Bring color grading back into the Rec.709 color space to match
previous behaviors. This change also implements an exact inverse
tone map function for the "Filmic" operator.
SamplerGroup was comparing texture handles to decide if a texture needed
to be updated, however, texture handles are (quickly) recycled and
therefore can't be used for that purpose. e.g. if a texture is destroyed,
its handle could be reused quickly by another texture, if that texture
is now set on the SamplerGroup, it will ignore it, thinking it's not
different.
We were inserting the colorgrading subpass command between the
refracted and blended objects, instead of after all of them.
Another bad side effect of this was to trigger the refraction pass for
no reason.
The operator!= in std::array compares SPLIT_COUNT elements, which
is potentially greater than cascadeCount, which was the number of
initialized elements in splitPercentages.
std::allocator::deallocate() expects the same value that was given
during allocate().
Interestingly, this bug did not manifest any issues (even with ASAN) on
some platforms.
We should take care not to call glVertexAttribPointer when there is
no bound ARRAY_BUFFER (i.e. when its binding is zero).
This fixes the black screen seen with some WebGL samples after
the recent memory leak fix related to the new BufferObject API.
This leak was introduced in the following PR on April 7.
https://github.com/google/filament/pull/3775
The guilty party has been contacted and properly admonished for his
transgression.
This was tested by adding the following code after applyAnimation in
gltf_viewer.cpp
static int nframes = 0;
if (!gpath.empty() && nframes++ > 100) {
static int count = 0;
printf("reloading %d\n", count++);
nframes = 0;
app.resourceLoader->asyncCancelLoad();
app.resourceLoader->evictResourceData();
app.viewer->removeAsset();
app.assetLoader->destroyAsset(app.asset);
loadAsset(gpath, app);
loadResources(gpath, app);
}
The hang was caused by a subtle race. When a job is completed, its
thread must signal all the threads that might be waiting on this job.
The signaling code was attempting to signal only the minimum number
of threads -- this was important especially in the case where no threads
were waiting, then the call to notify() could be avoided.
Unfortunately, for performance reasons we're not calling notify() with
the condition lock held, this meant that between the time the number of
waiting threads was latched and the time of the notify() call, more
threads could enter their condition variable wait(), and it would
then be possible for these threads to wake up, instead of the thread
we were trying to wake up (the one waiting on the job).
It would then get stuck forever.
This bug was introduced in 2df639133b
Also add some debugging code for this kind of failure (disabled)
This wasn't very useful in the first place because we're recycling
handles very quickly. Additionally there was a race condition
which cause false positives.
This reverts commit bc6acd5c5a.
This reverts commit 3a15756c78.
When running semantic analysis on a material, we were arbitrarily choosing the first code gen permutation to analyze. So, running matc with arguments --api metal versus --api all would run analysis on slightly different shader code. This causes bugs when flags passed to glslang differ during semantic analysis. This change updates all semantic analysis to always use the same shader code.
When passing only 1 fence to vkWaitForFences, the `waitAll` argument
should not have any effect, but SwiftShader seems to skip the wait
when this argument is set to VK_FALSE.
More specifically, the failure to wait in `acquireWorkCommandBuffer`
causes the subsequent destruction of an in-use fence, which causes
a TSAN failure with Google's internal tests.
I am consulting with the SwiftShader team on a real fix, meanwhile
we can commit this easy workaround.
We have 5 usages of vkWaitForFences, one of which uses multiple fences
and should have used VK_TRUE anyway.
This prevents a SwiftShader crash and/or a slew of "no texture bound"
warnings that would appear when the client provides an IBL without
providing reflections texture, which should be a valid thing to do.
Note that it is okay to declare a sampler in GLSL that never gets bound,
as long as it is never sampled from. Since we always sample from the
IBL specular texture, we should always bind something to it.
With Vulkan, this warning would sometimes be a false positive. It could
trigger for internal samplers like `ssao` and `structure`, even though
they were not declared in SPIR-V.
With OpenGL, this warning would never be a false positive because it has
the luxury of calling `glGetUniformLocation`.
This adds a private attribute to our samplers called `strict` that
indicates whether or not a sampler should always have a bound texture.
For now the only strict samplers are the custom ones declared in the
user's material.
At some point I think we should consider adding `spirv-reflect` to our
tree to help with problems like this.
This fixes a bug seen with client applications that use ClearOptions
instead of Skybox, and one or more offscreen RenderTarget objects.
These apps would see junk pixels because Filament would only clear the
first render target in the frame.
The fix is to factor some the flag-setting logic in `beginFrame()` into
a private method, and call this method from `render()` each time
the user-level RenderTarget has been changed.
I wrote a simple C++ demo to reproduce the issue and to verify that
this fix works.