(&mut self, resolve: &mut Resolve, id: WorldId, files: &mut Files)
| 24 | |
| 25 | pub trait WorldGenerator { |
| 26 | fn generate(&mut self, resolve: &mut Resolve, id: WorldId, files: &mut Files) -> Result<()> { |
| 27 | if self.uses_nominal_type_ids() { |
| 28 | resolve.generate_nominal_type_ids(id); |
| 29 | } |
| 30 | let world = &resolve.worlds[id]; |
| 31 | self.preprocess(resolve, id); |
| 32 | |
| 33 | fn unwrap_name(key: &WorldKey) -> &str { |
| 34 | match key { |
| 35 | WorldKey::Name(name) => name, |
| 36 | WorldKey::Interface(_) => panic!("unexpected interface key"), |
| 37 | } |
| 38 | } |
| 39 | |
| 40 | let mut funcs = Vec::new(); |
| 41 | let mut types = Vec::new(); |
| 42 | for (name, import) in world.imports.iter() { |
| 43 | match import { |
| 44 | WorldItem::Function(f) => funcs.push((unwrap_name(name), f)), |
| 45 | WorldItem::Interface { id, .. } => { |
| 46 | self.import_interface(resolve, name, *id, files)? |
| 47 | } |
| 48 | WorldItem::Type { id, .. } => types.push((unwrap_name(name), *id)), |
| 49 | } |
| 50 | } |
| 51 | if !types.is_empty() { |
| 52 | self.import_types(resolve, id, &types, files); |
| 53 | } |
| 54 | if !funcs.is_empty() { |
| 55 | self.import_funcs(resolve, id, &funcs, files); |
| 56 | } |
| 57 | funcs.clear(); |
| 58 | |
| 59 | self.finish_imports(resolve, id, files); |
| 60 | |
| 61 | // First generate bindings for any freestanding functions, if any. If |
| 62 | // these refer to types defined in the world they need to refer to the |
| 63 | // imported types generated above. |
| 64 | // |
| 65 | // Interfaces are then generated afterwards so if the same interface is |
| 66 | // both imported and exported the right types are all used everywhere. |
| 67 | let mut interfaces = Vec::new(); |
| 68 | for (name, export) in world.exports.iter() { |
| 69 | match export { |
| 70 | WorldItem::Function(f) => funcs.push((unwrap_name(name), f)), |
| 71 | WorldItem::Interface { id, .. } => interfaces.push((name, id)), |
| 72 | WorldItem::Type { .. } => unreachable!(), |
| 73 | } |
| 74 | } |
| 75 | if !funcs.is_empty() { |
| 76 | self.export_funcs(resolve, id, &funcs, files)?; |
| 77 | } |
| 78 | |
| 79 | self.pre_export_interface(resolve, files)?; |
| 80 | |
| 81 | for (name, id) in interfaces { |
| 82 | self.export_interface(resolve, name, *id, files)?; |
| 83 | } |
nothing calls this directly
no test coverage detected