I use a 3rd party library to parse a file. The parser creates a struct ParsedSource. ParsedSource represents a tree of data. I have a struct SchemyNode that wraps nodes found in ParsedSource, so that I can quickly reference them and retain metadata about them. I have a lifetime issue. SchemyNode holds references to nodes found in ParsedSource. This seems to work fine except in the very beginning when I try to pass the first child of ParsedSource, Module, to the first SchemyNode. What do I do?
error[E0515]: cannot return value referencing local variable `borrow`
--> src/typescript/module_cache.rs:39:9
|
38 | let source = borrow.get(path).unwrap();
| ---------------- `borrow` is borrowed here
39 | SchemyNode::from_module(source.module(), &self.context.clone())
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ returns a value referencing data owned by the current function
By the way, it looks like the module is a problem, too. The borrow guard returned by RefCell can't hand out references to the wrapped value directly, because then the very point of the RefCell would be moot (it couldn't track borrows at runtime, causing unsoundness). Any reference you get from a RefCell, mutable or immutable, will necessarily be tied to the scope of the guard object (Ref or RefMut).
Yes, but I'm afraid what you want is impossible (or at least not usefully possible). You can't have such borrows, as they fundamentally violate memory safety.
You could store the guard object directly in some returned wrapper similar to RefMut::map, and then get short-lived references out of it and construct nodes with them only locally. But that's not a solution, either, because as soon as you create the second such node, the RefCell::borrow_mut() call will panic.
crud, i think i need to learn some new tricks. I'm using the context to keep a reference to all nodes, so that I have quick access to them in the future. I'm trying to hide the context from the rest of the program, so that I can work exclusively with nodes.