global_init.cpp 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. // Part of the Carbon Language project, under the Apache License v2.0 with LLVM
  2. // Exceptions. See /LICENSE for license information.
  3. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  4. #include "toolchain/check/global_init.h"
  5. #include "toolchain/check/context.h"
  6. #include "toolchain/check/inst.h"
  7. namespace Carbon::Check {
  8. auto GlobalInit::Resume() -> void {
  9. context_->inst_block_stack().Push(block_id_, block_);
  10. }
  11. auto GlobalInit::Suspend() -> void {
  12. // TODO: Consider splicing together blocks in order to avoid sizable copies
  13. // here.
  14. auto contents = context_->inst_block_stack().PeekCurrentBlockContents();
  15. block_.assign(contents.begin(), contents.end());
  16. block_id_ = context_->inst_block_stack().PeekOrAdd();
  17. context_->inst_block_stack().PopAndDiscard();
  18. }
  19. auto GlobalInit::Finalize() -> void {
  20. // __global_init is only added if there are initialization instructions.
  21. if (block_.empty() && block_id_ == SemIR::InstBlockId::GlobalInit) {
  22. return;
  23. }
  24. Resume();
  25. AddInst<SemIR::Return>(*context_, Parse::NodeId::None, {});
  26. // Pop the GlobalInit block here to finalize it.
  27. context_->inst_block_stack().Pop();
  28. auto name_id = context_->sem_ir().identifiers().Add("__global_init");
  29. context_->sem_ir().set_global_ctor_id(context_->sem_ir().functions().Add(
  30. {{.name_id = SemIR::NameId::ForIdentifier(name_id),
  31. .parent_scope_id = SemIR::NameScopeId::Package,
  32. .generic_id = SemIR::GenericId::None,
  33. .first_param_node_id = Parse::NodeId::None,
  34. .last_param_node_id = Parse::NodeId::None,
  35. .pattern_block_id = SemIR::InstBlockId::Empty,
  36. .implicit_param_patterns_id = SemIR::InstBlockId::None,
  37. .param_patterns_id = SemIR::InstBlockId::Empty,
  38. .is_extern = false,
  39. .extern_library_id = SemIR::LibraryNameId::None,
  40. .non_owning_decl_id = SemIR::InstId::None,
  41. .first_owning_decl_id = SemIR::InstId::None},
  42. {.call_param_patterns_id = SemIR::InstBlockId::Empty,
  43. .call_params_id = SemIR::InstBlockId::Empty,
  44. .call_param_ranges = SemIR::Function::CallParamIndexRanges::Empty,
  45. .return_type_inst_id = SemIR::TypeInstId::None,
  46. .return_form_inst_id = SemIR::InstId::None,
  47. .return_patterns_id = SemIR::InstBlockId::None,
  48. .body_block_ids = {SemIR::InstBlockId::GlobalInit}}}));
  49. }
  50. } // namespace Carbon::Check