merge.h 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  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. #ifndef CARBON_TOOLCHAIN_CHECK_MERGE_H_
  5. #define CARBON_TOOLCHAIN_CHECK_MERGE_H_
  6. #include "toolchain/check/context.h"
  7. #include "toolchain/check/subst.h"
  8. #include "toolchain/sem_ir/ids.h"
  9. namespace Carbon::Check {
  10. // Diagnoses an `extern` declaration that was not preceded by a declaration in
  11. // the API file.
  12. auto DiagnoseExternRequiresDeclInApiFile(Context& context, SemIRLoc loc)
  13. -> void;
  14. // Information on new and previous declarations for CheckIsAllowedRedecl.
  15. struct RedeclInfo {
  16. explicit RedeclInfo(SemIR::EntityWithParamsBase params, SemIRLoc loc,
  17. bool is_definition)
  18. : loc(loc),
  19. is_definition(is_definition),
  20. is_extern(params.is_extern),
  21. extern_library_id(params.extern_library_id) {}
  22. // The associated diagnostic location.
  23. SemIRLoc loc;
  24. // True if a definition.
  25. bool is_definition;
  26. // True if an `extern` declaration.
  27. bool is_extern;
  28. // The library name in `extern library`, or invalid if not present.
  29. SemIR::LibraryNameId extern_library_id;
  30. };
  31. // Checks if a redeclaration is allowed prior to merging. This may emit a
  32. // diagnostic, but diagnostics do not prevent merging.
  33. //
  34. // The kinds of things this verifies are:
  35. // - A declaration is not redundant.
  36. // - A definition doesn't redefine a prior definition.
  37. // - The use of `extern` is consistent within a library.
  38. // - Multiple libraries do not declare non-`extern`.
  39. auto CheckIsAllowedRedecl(Context& context, Lex::TokenKind decl_kind,
  40. SemIR::NameId name_id, RedeclInfo new_decl,
  41. RedeclInfo prev_decl,
  42. SemIR::ImportIRId prev_import_ir_id) -> void;
  43. // When the prior name lookup result is an import and we are successfully
  44. // merging, replace the name lookup result with the reference in the current
  45. // file.
  46. auto ReplacePrevInstForMerge(Context& context, SemIR::NameScopeId scope_id,
  47. SemIR::NameId name_id, SemIR::InstId new_inst_id)
  48. -> void;
  49. // Information about the parameters of a declaration, which is common across
  50. // different kinds of entity such as classes and functions.
  51. struct DeclParams {
  52. explicit DeclParams(const SemIR::EntityWithParamsBase& base)
  53. : loc(base.latest_decl_id()),
  54. first_param_node_id(base.first_param_node_id),
  55. last_param_node_id(base.last_param_node_id),
  56. implicit_param_patterns_id(base.implicit_param_patterns_id),
  57. param_patterns_id(base.param_patterns_id) {}
  58. DeclParams(SemIRLoc loc, Parse::NodeId first_param_node_id,
  59. Parse::NodeId last_param_node_id,
  60. SemIR::InstBlockId implicit_param_patterns_id,
  61. SemIR::InstBlockId param_patterns_id)
  62. : loc(loc),
  63. first_param_node_id(first_param_node_id),
  64. last_param_node_id(last_param_node_id),
  65. implicit_param_patterns_id(implicit_param_patterns_id),
  66. param_patterns_id(param_patterns_id) {}
  67. // The location of the declaration of the entity.
  68. SemIRLoc loc;
  69. // Parse tree bounds for the parameters, including both implicit and explicit
  70. // parameters. These will be compared to match between declaration and
  71. // definition.
  72. Parse::NodeId first_param_node_id;
  73. Parse::NodeId last_param_node_id;
  74. // The implicit parameters of the entity. Can be Invalid if there is no
  75. // implicit parameter list.
  76. SemIR::InstBlockId implicit_param_patterns_id;
  77. // The explicit parameters of the entity. Can be Invalid if there is no
  78. // explicit parameter list.
  79. SemIR::InstBlockId param_patterns_id;
  80. };
  81. // Checks that the parameters in a redeclaration of an entity match the
  82. // parameters in the prior declaration. If not, produces a diagnostic if
  83. // `diagnose` is true, and returns false.
  84. auto CheckRedeclParamsMatch(
  85. Context& context, const DeclParams& new_entity,
  86. const DeclParams& prev_entity,
  87. SemIR::SpecificId prev_specific_id = SemIR::SpecificId::Invalid,
  88. bool check_syntax = true, bool diagnose = true) -> bool;
  89. } // namespace Carbon::Check
  90. #endif // CARBON_TOOLCHAIN_CHECK_MERGE_H_