CesiumGS / cesium-unreal

Bringing the 3D geospatial ecosystem to Unreal Engine
https://cesium.com/platform/cesium-for-unreal/
Apache License 2.0
885 stars 286 forks source link

Quest 2/Android build: Unable to parse EXT_structural_metadata extension (or perhaps any extension?) #1380

Open mikeucfl opened 3 months ago

mikeucfl commented 3 months ago

I have a 3D Tiles dataset that utilizes EXT_structural_metadata in the gLTF models, however when processing the models I see

[error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast

I built cesium-native in debug to see what was going on and noticed this line was failing https://github.com/CesiumGS/cesium-native/blob/5efd7ba94f61f27a7663bb8ef558120e45bbe71f/CesiumGltfReader/generated/src/GeneratedJsonHandlers.cpp#L808. Puzzling to me as nothing looks wrong with that code to me, seems like something is getting corrupted?

This only happens when I build for the Quest 2, but if I run it on Windows (and or use Quest Link to display on the headset) there is no issue processing the models.

Unfortunately I'm unable to share the model, is there any small sample out there that uses EXT_structural_metadata that I could test with?

csciguy8 commented 3 months ago

Hi @mikeucfl , we have a unit test for this extension here.

From what you described, it sounds like the gltf is being corrupted, but only when running on your Quest 2, which is odd.

I'm currently trying to modify that unit test to produce the same bad any cast. Ideally exceptions like that should be caught in the CesiumGltfReader and returned as in error in the GltfReaderResult.

This wouldn't actually fix your corruption problem though (if that's what it is).

kring commented 3 months ago

Just a guess: does std::any require a compiler feature (such as RTTI) that is not available or disabled on the Quest 2? If that were the case, I would expect loading any tile with EXT_structural_metadata would fail on that device. So: does the Cesium for Unreal Samples project, particularly level 6 work for you on the Quest 2?

mikeucfl commented 3 months ago

@kring Unfortunately the Cesium for Unreal Samples has a few issues when testing this out. It looks like it uses an older API as some of the blueprints have missing node links and deprecated calls. I removed those blueprint nodes to get past the error, as they seem to only be for displaying the attribution on screen, and I was able to see the buildings show up. With that said, when I look closer at the cesium ion dataset I notice the tileset.json references b3dms and they don't seem to contain this extension in the gLTF package.

@csciguy8 I'm trying to see if I can put together a small model that has this extension filled out properly to replicate it elsewhere. I am also wondering if any of the extensions that class handles (like KHR_materials_unlit) would also cause this same issue as the code is similar for how it adds to the map and retrieves.

kring commented 3 months ago

@mikeucfl can you please check that you have the latest version of the Samples? That sounds like an outdated version. You can find the latest here: https://github.com/CesiumGS/cesium-unreal-samples/releases

mikeucfl commented 3 months ago

@kring Oh oops. I was using the one from the marketplace (https://www.unrealengine.com/marketplace/en-US/product/cesium-samples), didn't realize it was on github as well. I ran it just now on level 6 and got spammed with the bad any cast error: [2024.03.29-04.17.14:275][507]LogCesium: Error: [2024-03-29 00:17:14.275] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast. Again works fine running on Windows, but packaging for the Quest 2 and running natively doesn't work.

I also was able to take a simple cube glb and add some simple EXT_structural_metadata and EXT_mesh_features inputs. I've attached a zip containing the original cube and tileset.json (in the no-crash) folder, and the attributed cube and tileset.json (in the crash folder). Interestingly enough, I'm not getting the bad cast, but its actually just out right crashing. Works fine running on Windows.

cube.zip

edit: Just wanted to add I am running this on Unreal Engine 5.3.2, upgrading the project from 5.1. Not sure if that matters or not but figured I'd mention it

kring commented 1 month ago

Also reported here: https://community.cesium.com/t/cesium-osm-building-load-bug-for-quest-3-build-android/32632

GhisBntly commented 3 weeks ago

Hello folks, I ran into the same error this week with my company tilesets. Thing is, I'm having it on mac arm64 boxes (not tested old Intel macpro yet, I am in the process of upgrading it to that purpose), with apple-clang from Xcode 14.3 and Xcode 15. I tested the cube.zip MRE and indeed the bad_any_cast is thrown:

LogCesium: Loading tileset from URL file:///Users/developer/Downloads/cube/crash/tileset.json
LogCesium: Loading tileset from URL file:///Users/developer/Downloads/cube/crash/tileset.json done
LogCesium: Error: [2024-06-20 09:21:45.902] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
LogCesium: Loading tileset from URL file:///Users/developer/Downloads/cube/no-crash/tileset.json
LogCesium: Loading tileset from URL file:///Users/developer/Downloads/cube/no-crash/tileset.json done

I did not suspect RTTI as I believe it is enabled by default in clang and did not find -fno-rtti in the build commands. I did find this thread though: https://stackoverflow.com/questions/51693605/clang-compiled-program-throws-stdbad-any-cast-during-stdany-cast, which hints at visibility and/or static archive symbol duplication issues, but with the "bad cast" occurring in the same compile unit, indeed two lines after the std::any is created, I am quite confused as to how this could apply... I will try a dylib build nonetheless. Maybe some kind of compiler bug, especially as building Debug libraries removes the issue :-/

kring commented 3 weeks ago

@GhisBntly is that when running in the Editor, or in a packaged game?

GhisBntly commented 3 weeks ago

@kring: in the Editor, it cannot be packaged for the moment.

No luck so far with visibilty changes (I removed the part about macOS symbols visibility -fms-compat etc. in cesium-unreal/extern/CMakeLists.txt) Same with dylibs, although I have one dylib per former static lib, so there may still be duplications: I see std::1::any_imp::__unique_typeinfo::__id in several dylibs, maybe this is the culprit?

But I find a bit strange to not see RTTI symbols for CesiumGltf::ExtensionExtMeshFeatures itself, they are present for example for other types:

00000000003dbe00 S typeinfo for CesiumGltfReader::ExtensionExtMeshFeaturesJsonHandler
00000000003232d0 S typeinfo name for CesiumGltfReader::ExtensionExtMeshFeaturesJsonHandler

Or maybe I'm misleaded...

GhisBntly commented 3 weeks ago

For the record, no problem on the mac Intel (latest macOS supporting the hardware = Monterey 12.7.5, Xcode 14.2, UE 5.2). So it looks like it's arm64-specific (or Xcode 14.3+ ie llvm-15+ only, or UE5.3+ only......)

kring commented 3 weeks ago

I can reproduce this on Linux by simply opening the 06_CesiumMetadata example in the Editor.

[2024.06.24-09.29.23:780][220]LogCesium: Error: [2024-06-24 19:29:23.780] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast

It happens in both v2.6.0 and in a build out of the vcpkg branch.

GhisBntly commented 3 weeks ago

Thanks, that's interesting, so this not arm-only, I guess the linux was running on an Intel chip, right? Did you test with both clang and gcc?

kring commented 2 weeks ago

Yep, Linux on x86-64 in my case. I only tested with the compiler that is shipped with Unreal, which is Clang. Using a different compiler would require recompiling the entire engine, I believe.

cdmoye commented 2 weeks ago

FWiW, I see what looks like this same issue in the Editor on Ubuntu 24.04 with Unreal 5.4.2 and Cesium 2.6.0 when just creating an empty level and adding the "Cesium World Terrain + Bing Maps Aerial" and "Cesium OSM Buildings" assets from the Quick Add (as described in the Quick Start).

As soon as I try to add the Cesium OSM Buildings asset, it's just a whole lot of this:

LogCesium: Error: [2024-06-27 09:16:55.976] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
LogCesium: Error: [2024-06-27 09:16:55.989] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
LogCesium: Error: [2024-06-27 09:16:55.997] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
LogCesium: Error: [2024-06-27 09:16:56.047] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
LogCesium: Error: [2024-06-27 09:16:56.080] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
LogCesium: Error: [2024-06-27 09:16:56.089] [error] [TilesetContentManager.cpp:997] An unexpected error occurs when loading tile: bad any cast
kring commented 2 weeks ago

I unfortunately have to move this one out of the release, because, even if I fix it right now, there isn't time to review and merge it before the release. I'm still going to look into it today and tomorrow though.

kring commented 1 week ago

To everyone who has been running into this problem: I believe we have a fix for it. Please try out the build from this pull request and see if it works for you: https://github.com/CesiumGS/cesium-unreal/pull/1468

Instructions for installing a build from a pull request can be found here: https://github.com/CesiumGS/cesium-unreal/blob/main/Documentation/using-prerelease-packages.md#download-a-pre-release-version-from-a-pull-request

Thanks!

CamilleChigot commented 1 week ago

Thanks @kring . I can confirm that it is working fine now on macos Arm64.

PS: I am working with @GhisBntly PS2: there is at least one cesium native test that does nto compile anymore ( TestTilesetJsonLoader.cpp). I am not sure this is the correct place to mention it.