@@ -54,11 +54,14 @@ void SceneCacheInterface::_remove_node_cache(ObjectID p_oid) {
5454 if (nc->cache_id ) {
5555 assigned_ids.erase (nc->cache_id );
5656 }
57+ #if 0
58+ // TODO: Find a way to cleanup recv_nodes without breaking visibility and RPCs interactions.
5759 for (KeyValue<int, int> &E : nc->recv_ids) {
5860 PeerInfo *pinfo = peers_info.getptr(E.key);
5961 ERR_CONTINUE(!pinfo);
6062 pinfo->recv_nodes.erase(E.value);
6163 }
64+ #endif
6265 for (KeyValue<int , bool > &E : nc->confirmed_peers ) {
6366 PeerInfo *pinfo = peers_info.getptr (E.key );
6467 ERR_CONTINUE (!pinfo);
@@ -73,9 +76,12 @@ void SceneCacheInterface::on_peer_change(int p_id, bool p_connected) {
7376 } else {
7477 PeerInfo *pinfo = peers_info.getptr (p_id);
7578 ERR_FAIL_NULL (pinfo); // Bug.
76- for (KeyValue<int , ObjectID> E : pinfo->recv_nodes ) {
77- NodeCache *nc = nodes_cache.getptr (E.value );
78- ERR_CONTINUE (!nc);
79+ for (KeyValue<int , RecvNode> E : pinfo->recv_nodes ) {
80+ NodeCache *nc = nodes_cache.getptr (E.value .oid );
81+ if (!nc) {
82+ // Node might have already been deleted locally.
83+ continue ;
84+ }
7985 nc->recv_ids .erase (p_id);
8086 }
8187 for (const ObjectID &oid : pinfo->sent_nodes ) {
@@ -115,7 +121,7 @@ void SceneCacheInterface::process_simplify_path(int p_from, const uint8_t *p_pac
115121 ERR_PRINT (" The rpc node checksum failed. Make sure to have the same methods on both nodes. Node path: " + path);
116122 }
117123
118- peers_info[p_from].recv_nodes .insert (id, node->get_instance_id ());
124+ peers_info[p_from].recv_nodes .insert (id, RecvNode ( node->get_instance_id (), path ));
119125 NodeCache &cache = _track (node);
120126 cache.recv_ids .insert (p_from, id);
121127
@@ -269,14 +275,21 @@ bool SceneCacheInterface::send_object_cache(Object *p_obj, int p_peer_id, int &r
269275}
270276
271277Object *SceneCacheInterface::get_cached_object (int p_from, uint32_t p_cache_id) {
272- Node *root_node = SceneTree::get_singleton ()->get_root ()->get_node (multiplayer->get_root_path ());
273- ERR_FAIL_NULL_V (root_node, nullptr );
274278 PeerInfo *pinfo = peers_info.getptr (p_from);
275279 ERR_FAIL_NULL_V (pinfo, nullptr );
276280
277- const ObjectID *oid = pinfo->recv_nodes .getptr (p_cache_id);
278- ERR_FAIL_NULL_V_MSG (oid, nullptr , vformat (" ID %d not found in cache of peer %d." , p_cache_id, p_from));
279- Node *node = Object::cast_to<Node>(ObjectDB::get_instance (*oid));
281+ RecvNode *recv_node = pinfo->recv_nodes .getptr (p_cache_id);
282+ ERR_FAIL_NULL_V_MSG (recv_node, nullptr , vformat (" ID %d not found in cache of peer %d." , p_cache_id, p_from));
283+ Node *node = Object::cast_to<Node>(ObjectDB::get_instance (recv_node->oid ));
284+ if (!node) {
285+ // Fallback to path lookup.
286+ Node *root_node = SceneTree::get_singleton ()->get_root ()->get_node (multiplayer->get_root_path ());
287+ ERR_FAIL_NULL_V (root_node, nullptr );
288+ node = root_node->get_node (recv_node->path );
289+ if (node) {
290+ recv_node->oid = node->get_instance_id ();
291+ }
292+ }
280293 ERR_FAIL_NULL_V_MSG (node, nullptr , vformat (" Failed to get cached node from peer %d with cache ID %d." , p_from, p_cache_id));
281294 return node;
282295}
0 commit comments