about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--compiler/rustc_ast_lowering/src/lib.rs4
-rw-r--r--compiler/rustc_borrowck/src/facts.rs2
-rw-r--r--compiler/rustc_borrowck/src/lib.rs2
-rw-r--r--compiler/rustc_borrowck/src/nll.rs4
-rw-r--r--compiler/rustc_borrowck/src/region_infer/mod.rs2
-rw-r--r--compiler/rustc_builtin_macros/src/test_harness.rs2
-rw-r--r--compiler/rustc_codegen_cranelift/src/allocator.rs2
-rw-r--r--compiler/rustc_codegen_cranelift/src/cast.rs2
-rw-r--r--compiler/rustc_codegen_cranelift/src/debuginfo/line_info.rs2
-rw-r--r--compiler/rustc_codegen_cranelift/src/driver/aot.rs2
-rw-r--r--compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs4
-rw-r--r--compiler/rustc_codegen_gcc/src/allocator.rs2
-rw-r--r--compiler/rustc_codegen_gcc/src/base.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/abi.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/allocator.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/attributes.rs8
-rw-r--r--compiler/rustc_codegen_llvm/src/back/archive.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/back/write.rs14
-rw-r--r--compiler/rustc_codegen_llvm/src/consts.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/context.rs8
-rw-r--r--compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs10
-rw-r--r--compiler/rustc_codegen_llvm/src/debuginfo/mod.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/lib.rs2
-rw-r--r--compiler/rustc_codegen_llvm/src/llvm_util.rs12
-rw-r--r--compiler/rustc_codegen_ssa/src/back/link.rs24
-rw-r--r--compiler/rustc_codegen_ssa/src/back/linker.rs4
-rw-r--r--compiler/rustc_codegen_ssa/src/back/symbol_export.rs6
-rw-r--r--compiler/rustc_codegen_ssa/src/back/write.rs43
-rw-r--r--compiler/rustc_codegen_ssa/src/base.rs2
-rw-r--r--compiler/rustc_codegen_ssa/src/meth.rs2
-rw-r--r--compiler/rustc_codegen_ssa/src/mir/block.rs2
-rw-r--r--compiler/rustc_codegen_ssa/src/mir/debuginfo.rs2
-rw-r--r--compiler/rustc_codegen_ssa/src/traits/builder.rs2
-rw-r--r--compiler/rustc_const_eval/src/interpret/intrinsics.rs4
-rw-r--r--compiler/rustc_const_eval/src/interpret/intrinsics/caller_location.rs2
-rw-r--r--compiler/rustc_const_eval/src/interpret/operator.rs2
-rw-r--r--compiler/rustc_const_eval/src/transform/check_consts/check.rs2
-rw-r--r--compiler/rustc_const_eval/src/transform/validate.rs2
-rw-r--r--compiler/rustc_driver/src/lib.rs28
-rw-r--r--compiler/rustc_expand/src/config.rs2
-rw-r--r--compiler/rustc_expand/src/expand.rs2
-rw-r--r--compiler/rustc_incremental/src/assert_dep_graph.rs6
-rw-r--r--compiler/rustc_incremental/src/assert_module_sources.rs2
-rw-r--r--compiler/rustc_incremental/src/persist/dirty_clean.rs2
-rw-r--r--compiler/rustc_incremental/src/persist/fs.rs2
-rw-r--r--compiler/rustc_incremental/src/persist/load.rs6
-rw-r--r--compiler/rustc_incremental/src/persist/save.rs6
-rw-r--r--compiler/rustc_infer/src/infer/higher_ranked/mod.rs2
-rw-r--r--compiler/rustc_interface/src/interface.rs4
-rw-r--r--compiler/rustc_interface/src/passes.rs26
-rw-r--r--compiler/rustc_interface/src/queries.rs2
-rw-r--r--compiler/rustc_interface/src/tests.rs14
-rw-r--r--compiler/rustc_interface/src/util.rs8
-rw-r--r--compiler/rustc_lint/src/early.rs2
-rw-r--r--compiler/rustc_lint/src/late.rs4
-rw-r--r--compiler/rustc_metadata/src/creader.rs10
-rw-r--r--compiler/rustc_metadata/src/dependency_format.rs4
-rw-r--r--compiler/rustc_metadata/src/locator.rs2
-rw-r--r--compiler/rustc_metadata/src/rmeta/decoder.rs6
-rw-r--r--compiler/rustc_metadata/src/rmeta/encoder.rs12
-rw-r--r--compiler/rustc_middle/src/hir/map/mod.rs2
-rw-r--r--compiler/rustc_middle/src/lint.rs2
-rw-r--r--compiler/rustc_middle/src/middle/limits.rs2
-rw-r--r--compiler/rustc_middle/src/middle/stability.rs2
-rw-r--r--compiler/rustc_middle/src/mir/generic_graph.rs2
-rw-r--r--compiler/rustc_middle/src/mir/generic_graphviz.rs4
-rw-r--r--compiler/rustc_middle/src/mir/graphviz.rs4
-rw-r--r--compiler/rustc_middle/src/mir/mod.rs4
-rw-r--r--compiler/rustc_middle/src/mir/mono.rs4
-rw-r--r--compiler/rustc_middle/src/mir/pretty.rs10
-rw-r--r--compiler/rustc_middle/src/ty/instance.rs2
-rw-r--r--compiler/rustc_middle/src/ty/layout.rs4
-rw-r--r--compiler/rustc_middle/src/ty/mod.rs4
-rw-r--r--compiler/rustc_middle/src/ty/print/pretty.rs8
-rw-r--r--compiler/rustc_mir_build/src/check_unsafety.rs2
-rw-r--r--compiler/rustc_mir_dataflow/src/framework/engine.rs6
-rw-r--r--compiler/rustc_mir_dataflow/src/impls/mod.rs8
-rw-r--r--compiler/rustc_mir_transform/src/abort_unwinding_calls.rs2
-rw-r--r--compiler/rustc_mir_transform/src/add_retag.rs2
-rw-r--r--compiler/rustc_mir_transform/src/const_debuginfo.rs2
-rw-r--r--compiler/rustc_mir_transform/src/coverage/mod.rs4
-rw-r--r--compiler/rustc_mir_transform/src/dest_prop.rs2
-rw-r--r--compiler/rustc_mir_transform/src/early_otherwise_branch.rs2
-rw-r--r--compiler/rustc_mir_transform/src/generator.rs4
-rw-r--r--compiler/rustc_mir_transform/src/inline.rs6
-rw-r--r--compiler/rustc_mir_transform/src/lib.rs2
-rw-r--r--compiler/rustc_mir_transform/src/pass_manager.rs4
-rw-r--r--compiler/rustc_mir_transform/src/shim.rs2
-rw-r--r--compiler/rustc_mir_transform/src/simplify_try.rs4
-rw-r--r--compiler/rustc_monomorphize/src/collector.rs3
-rw-r--r--compiler/rustc_monomorphize/src/partitioning/default.rs2
-rw-r--r--compiler/rustc_monomorphize/src/partitioning/merging.rs2
-rw-r--r--compiler/rustc_monomorphize/src/partitioning/mod.rs6
-rw-r--r--compiler/rustc_monomorphize/src/polymorphize.rs2
-rw-r--r--compiler/rustc_passes/src/check_attr.rs2
-rw-r--r--compiler/rustc_passes/src/check_const.rs2
-rw-r--r--compiler/rustc_passes/src/hir_id_validator.rs2
-rw-r--r--compiler/rustc_passes/src/stability.rs4
-rw-r--r--compiler/rustc_query_system/src/dep_graph/dep_node.rs4
-rw-r--r--compiler/rustc_query_system/src/dep_graph/graph.rs2
-rw-r--r--compiler/rustc_query_system/src/ich/hcx.rs8
-rw-r--r--compiler/rustc_query_system/src/query/plumbing.rs4
-rw-r--r--compiler/rustc_session/src/config.rs92
-rw-r--r--compiler/rustc_session/src/options.rs9
-rw-r--r--compiler/rustc_session/src/session.rs104
-rw-r--r--compiler/rustc_span/src/hygiene.rs2
-rw-r--r--compiler/rustc_span/src/lib.rs4
-rw-r--r--compiler/rustc_trait_selection/src/traits/engine.rs2
-rw-r--r--compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs2
-rw-r--r--compiler/rustc_trait_selection/src/traits/select/confirmation.rs2
-rw-r--r--compiler/rustc_ty_utils/src/ty.rs2
-rw-r--r--compiler/rustc_typeck/src/check/generator_interior.rs2
-rw-r--r--compiler/rustc_typeck/src/check/generator_interior/drop_ranges.rs2
-rw-r--r--compiler/rustc_typeck/src/check/generator_interior/drop_ranges/cfg_build.rs2
-rw-r--r--compiler/rustc_typeck/src/check/method/probe.rs4
-rw-r--r--compiler/rustc_typeck/src/check/upvar.rs2
-rw-r--r--src/doc/man/rustc.12
-rw-r--r--src/librustdoc/clean/mod.rs2
-rw-r--r--src/librustdoc/config.rs26
-rw-r--r--src/librustdoc/core.rs16
-rw-r--r--src/librustdoc/doctest.rs4
-rw-r--r--src/librustdoc/lib.rs6
-rw-r--r--src/test/run-make/issue-88756-default-output/output-default.stdout3
-rw-r--r--src/test/ui/invalid-compile-flags/branch-protection-missing-pac-ret.BADFLAGS.stderr2
-rw-r--r--src/tools/clippy/src/driver.rs2
125 files changed, 396 insertions, 394 deletions
diff --git a/compiler/rustc_ast_lowering/src/lib.rs b/compiler/rustc_ast_lowering/src/lib.rs
index 4da3096f7c3..b79c1cafba0 100644
--- a/compiler/rustc_ast_lowering/src/lib.rs
+++ b/compiler/rustc_ast_lowering/src/lib.rs
@@ -427,7 +427,7 @@ pub fn lower_to_hir<'hir>(tcx: TyCtxt<'hir>, (): ()) -> hir::Crate<'hir> {
     sess.time("drop_ast", || std::mem::drop(krate));
 
     // Discard hygiene data, which isn't required after lowering to HIR.
-    if !sess.opts.debugging_opts.keep_hygiene_data {
+    if !sess.opts.unstable_opts.keep_hygiene_data {
         rustc_span::hygiene::clear_syntax_context_map();
     }
 
@@ -699,7 +699,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
     /// Intercept all spans entering HIR.
     /// Mark a span as relative to the current owning item.
     fn lower_span(&self, span: Span) -> Span {
-        if self.tcx.sess.opts.debugging_opts.incremental_relative_spans {
+        if self.tcx.sess.opts.unstable_opts.incremental_relative_spans {
             span.with_parent(Some(self.current_hir_id_owner))
         } else {
             // Do not make spans relative when not using incremental compilation.
diff --git a/compiler/rustc_borrowck/src/facts.rs b/compiler/rustc_borrowck/src/facts.rs
index 7f0a637c9d3..22134d5a71c 100644
--- a/compiler/rustc_borrowck/src/facts.rs
+++ b/compiler/rustc_borrowck/src/facts.rs
@@ -40,7 +40,7 @@ pub(crate) trait AllFactsExt {
 impl AllFactsExt for AllFacts {
     /// Return
     fn enabled(tcx: TyCtxt<'_>) -> bool {
-        tcx.sess.opts.debugging_opts.nll_facts || tcx.sess.opts.debugging_opts.polonius
+        tcx.sess.opts.unstable_opts.nll_facts || tcx.sess.opts.unstable_opts.polonius
     }
 
     fn write_to_dir(
diff --git a/compiler/rustc_borrowck/src/lib.rs b/compiler/rustc_borrowck/src/lib.rs
index e6142cab5c2..e8673ecd3a0 100644
--- a/compiler/rustc_borrowck/src/lib.rs
+++ b/compiler/rustc_borrowck/src/lib.rs
@@ -231,7 +231,7 @@ fn do_mir_borrowck<'a, 'tcx>(
     let borrow_set =
         Rc::new(BorrowSet::build(tcx, body, locals_are_invalidated_at_exit, &mdpe.move_data));
 
-    let use_polonius = return_body_with_facts || infcx.tcx.sess.opts.debugging_opts.polonius;
+    let use_polonius = return_body_with_facts || infcx.tcx.sess.opts.unstable_opts.polonius;
 
     // Compute non-lexical lifetimes.
     let nll::NllOutput {
diff --git a/compiler/rustc_borrowck/src/nll.rs b/compiler/rustc_borrowck/src/nll.rs
index 3a919e954a4..d2e82274792 100644
--- a/compiler/rustc_borrowck/src/nll.rs
+++ b/compiler/rustc_borrowck/src/nll.rs
@@ -278,9 +278,9 @@ pub(crate) fn compute_regions<'cx, 'tcx>(
 
     // Dump facts if requested.
     let polonius_output = all_facts.as_ref().and_then(|all_facts| {
-        if infcx.tcx.sess.opts.debugging_opts.nll_facts {
+        if infcx.tcx.sess.opts.unstable_opts.nll_facts {
             let def_path = infcx.tcx.def_path(def_id);
-            let dir_path = PathBuf::from(&infcx.tcx.sess.opts.debugging_opts.nll_facts_dir)
+            let dir_path = PathBuf::from(&infcx.tcx.sess.opts.unstable_opts.nll_facts_dir)
                 .join(def_path.to_filename_friendly_no_crate());
             all_facts.write_to_dir(dir_path, location_table).unwrap();
         }
diff --git a/compiler/rustc_borrowck/src/region_infer/mod.rs b/compiler/rustc_borrowck/src/region_infer/mod.rs
index 0cf04b369de..9040cfcf54f 100644
--- a/compiler/rustc_borrowck/src/region_infer/mod.rs
+++ b/compiler/rustc_borrowck/src/region_infer/mod.rs
@@ -589,7 +589,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
         // In Polonius mode, the errors about missing universal region relations are in the output
         // and need to be emitted or propagated. Otherwise, we need to check whether the
         // constraints were too strong, and if so, emit or propagate those errors.
-        if infcx.tcx.sess.opts.debugging_opts.polonius {
+        if infcx.tcx.sess.opts.unstable_opts.polonius {
             self.check_polonius_subset_errors(
                 body,
                 outlives_requirements.as_mut(),
diff --git a/compiler/rustc_builtin_macros/src/test_harness.rs b/compiler/rustc_builtin_macros/src/test_harness.rs
index e2a6e77ab44..0ebe29df95f 100644
--- a/compiler/rustc_builtin_macros/src/test_harness.rs
+++ b/compiler/rustc_builtin_macros/src/test_harness.rs
@@ -51,7 +51,7 @@ pub fn inject(sess: &Session, resolver: &mut dyn ResolverExpand, krate: &mut ast
     let test_runner = get_test_runner(sess, span_diagnostic, &krate);
 
     if sess.opts.test {
-        let panic_strategy = match (panic_strategy, sess.opts.debugging_opts.panic_abort_tests) {
+        let panic_strategy = match (panic_strategy, sess.opts.unstable_opts.panic_abort_tests) {
             (PanicStrategy::Abort, true) => PanicStrategy::Abort,
             (PanicStrategy::Abort, false) => {
                 if panic_strategy == platform_panic_strategy {
diff --git a/compiler/rustc_codegen_cranelift/src/allocator.rs b/compiler/rustc_codegen_cranelift/src/allocator.rs
index c3b99b64263..6d321c7b298 100644
--- a/compiler/rustc_codegen_cranelift/src/allocator.rs
+++ b/compiler/rustc_codegen_cranelift/src/allocator.rs
@@ -24,7 +24,7 @@ pub(crate) fn codegen(
             unwind_context,
             kind,
             tcx.lang_items().oom().is_some(),
-            tcx.sess.opts.debugging_opts.oom,
+            tcx.sess.opts.unstable_opts.oom,
         );
         true
     } else {
diff --git a/compiler/rustc_codegen_cranelift/src/cast.rs b/compiler/rustc_codegen_cranelift/src/cast.rs
index e19070774c6..b24e49e94c9 100644
--- a/compiler/rustc_codegen_cranelift/src/cast.rs
+++ b/compiler/rustc_codegen_cranelift/src/cast.rs
@@ -144,7 +144,7 @@ pub(crate) fn clif_int_or_float_cast(
             fx.bcx.ins().fcvt_to_uint_sat(to_ty, from)
         };
 
-        if let Some(false) = fx.tcx.sess.opts.debugging_opts.saturating_float_casts {
+        if let Some(false) = fx.tcx.sess.opts.unstable_opts.saturating_float_casts {
             return val;
         }
 
diff --git a/compiler/rustc_codegen_cranelift/src/debuginfo/line_info.rs b/compiler/rustc_codegen_cranelift/src/debuginfo/line_info.rs
index 476d6a54e12..bbcb9591373 100644
--- a/compiler/rustc_codegen_cranelift/src/debuginfo/line_info.rs
+++ b/compiler/rustc_codegen_cranelift/src/debuginfo/line_info.rs
@@ -140,7 +140,7 @@ impl<'tcx> DebugContext<'tcx> {
             // In order to have a good line stepping behavior in debugger, we overwrite debug
             // locations of macro expansions with that of the outermost expansion site
             // (unless the crate is being compiled with `-Z debug-macros`).
-            let span = if !span.from_expansion() || tcx.sess.opts.debugging_opts.debug_macros {
+            let span = if !span.from_expansion() || tcx.sess.opts.unstable_opts.debug_macros {
                 span
             } else {
                 // Walk up the macro expansion chain until we reach a non-expanded span.
diff --git a/compiler/rustc_codegen_cranelift/src/driver/aot.rs b/compiler/rustc_codegen_cranelift/src/driver/aot.rs
index 50d8fc30d7d..3cd1ef5639e 100644
--- a/compiler/rustc_codegen_cranelift/src/driver/aot.rs
+++ b/compiler/rustc_codegen_cranelift/src/driver/aot.rs
@@ -33,7 +33,7 @@ fn make_module(sess: &Session, isa: Box<dyn TargetIsa>, name: String) -> ObjectM
     // Unlike cg_llvm, cg_clif defaults to disabling -Zfunction-sections. For cg_llvm binary size
     // is important, while cg_clif cares more about compilation times. Enabling -Zfunction-sections
     // can easily double the amount of time necessary to perform linking.
-    builder.per_function_section(sess.opts.debugging_opts.function_sections.unwrap_or(false));
+    builder.per_function_section(sess.opts.unstable_opts.function_sections.unwrap_or(false));
     ObjectModule::new(builder)
 }
 
diff --git a/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs b/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs
index 6937e658ed5..eafae1cdc8a 100644
--- a/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs
+++ b/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs
@@ -676,7 +676,7 @@ fn codegen_regular_intrinsic_call<'tcx>(
                 && !layout.might_permit_raw_init(
                     fx,
                     InitKind::Zero,
-                    fx.tcx.sess.opts.debugging_opts.strict_init_checks) {
+                    fx.tcx.sess.opts.unstable_opts.strict_init_checks) {
 
                 with_no_trimmed_paths!({
                     crate::base::codegen_panic(
@@ -692,7 +692,7 @@ fn codegen_regular_intrinsic_call<'tcx>(
                 && !layout.might_permit_raw_init(
                     fx,
                     InitKind::Uninit,
-                    fx.tcx.sess.opts.debugging_opts.strict_init_checks) {
+                    fx.tcx.sess.opts.unstable_opts.strict_init_checks) {
 
                 with_no_trimmed_paths!({
                     crate::base::codegen_panic(
diff --git a/compiler/rustc_codegen_gcc/src/allocator.rs b/compiler/rustc_codegen_gcc/src/allocator.rs
index c761e5aabd1..58efb81e800 100644
--- a/compiler/rustc_codegen_gcc/src/allocator.rs
+++ b/compiler/rustc_codegen_gcc/src/allocator.rs
@@ -117,7 +117,7 @@ pub(crate) unsafe fn codegen(tcx: TyCtxt<'_>, mods: &mut GccContext, _module_nam
 
     let name = OomStrategy::SYMBOL.to_string();
     let global = context.new_global(None, GlobalKind::Exported, i8, name);
-    let value = tcx.sess.opts.debugging_opts.oom.should_panic();
+    let value = tcx.sess.opts.unstable_opts.oom.should_panic();
     let value = context.new_rvalue_from_int(i8, value as i32);
     global.global_set_initializer_rvalue(value);
 }
diff --git a/compiler/rustc_codegen_gcc/src/base.rs b/compiler/rustc_codegen_gcc/src/base.rs
index e4ecbd46f0c..8f9f6f98faf 100644
--- a/compiler/rustc_codegen_gcc/src/base.rs
+++ b/compiler/rustc_codegen_gcc/src/base.rs
@@ -96,7 +96,7 @@ pub fn compile_codegen_unit<'tcx>(tcx: TyCtxt<'tcx>, cgu_name: Symbol, supports_
         // NOTE: Rust relies on LLVM not doing TBAA (https://github.com/rust-lang/unsafe-code-guidelines/issues/292).
         context.add_command_line_option("-fno-strict-aliasing");
 
-        if tcx.sess.opts.debugging_opts.function_sections.unwrap_or(tcx.sess.target.function_sections) {
+        if tcx.sess.opts.unstable_opts.function_sections.unwrap_or(tcx.sess.target.function_sections) {
             context.add_command_line_option("-ffunction-sections");
             context.add_command_line_option("-fdata-sections");
         }
diff --git a/compiler/rustc_codegen_llvm/src/abi.rs b/compiler/rustc_codegen_llvm/src/abi.rs
index cc8b3a1a4e4..d4437bd449d 100644
--- a/compiler/rustc_codegen_llvm/src/abi.rs
+++ b/compiler/rustc_codegen_llvm/src/abi.rs
@@ -37,7 +37,7 @@ fn should_use_mutable_noalias(cx: &CodegenCx<'_, '_>) -> bool {
     // LLVM prior to version 12 had known miscompiles in the presence of
     // noalias attributes (see #54878), but we don't support earlier
     // versions at all anymore. We now enable mutable noalias by default.
-    cx.tcx.sess.opts.debugging_opts.mutable_noalias.unwrap_or(true)
+    cx.tcx.sess.opts.unstable_opts.mutable_noalias.unwrap_or(true)
 }
 
 const ABI_AFFECTING_ATTRIBUTES: [(ArgAttribute, llvm::AttributeKind); 1] =
diff --git a/compiler/rustc_codegen_llvm/src/allocator.rs b/compiler/rustc_codegen_llvm/src/allocator.rs
index f935acb1a7e..72961ae888e 100644
--- a/compiler/rustc_codegen_llvm/src/allocator.rs
+++ b/compiler/rustc_codegen_llvm/src/allocator.rs
@@ -145,7 +145,7 @@ pub(crate) unsafe fn codegen(
     if tcx.sess.target.default_hidden_visibility {
         llvm::LLVMRustSetVisibility(ll_g, llvm::Visibility::Hidden);
     }
-    let val = tcx.sess.opts.debugging_opts.oom.should_panic();
+    let val = tcx.sess.opts.unstable_opts.oom.should_panic();
     let llval = llvm::LLVMConstInt(i8, val as u64, False);
     llvm::LLVMSetInitializer(ll_g, llval);
 
diff --git a/compiler/rustc_codegen_llvm/src/attributes.rs b/compiler/rustc_codegen_llvm/src/attributes.rs
index 9394d60134f..32bfa5094c3 100644
--- a/compiler/rustc_codegen_llvm/src/attributes.rs
+++ b/compiler/rustc_codegen_llvm/src/attributes.rs
@@ -56,7 +56,7 @@ pub fn sanitize_attrs<'ll>(
     no_sanitize: SanitizerSet,
 ) -> SmallVec<[&'ll Attribute; 4]> {
     let mut attrs = SmallVec::new();
-    let enabled = cx.tcx.sess.opts.debugging_opts.sanitizer - no_sanitize;
+    let enabled = cx.tcx.sess.opts.unstable_opts.sanitizer - no_sanitize;
     if enabled.contains(SanitizerSet::ADDRESS) {
         attrs.push(llvm::AttributeKind::SanitizeAddress.create_attr(cx.llcx));
     }
@@ -136,7 +136,7 @@ fn probestack_attr<'ll>(cx: &CodegenCx<'ll, '_>) -> Option<&'ll Attribute> {
     if cx
         .sess()
         .opts
-        .debugging_opts
+        .unstable_opts
         .sanitizer
         .intersects(SanitizerSet::ADDRESS | SanitizerSet::THREAD)
     {
@@ -149,7 +149,7 @@ fn probestack_attr<'ll>(cx: &CodegenCx<'ll, '_>) -> Option<&'ll Attribute> {
     }
 
     // probestack doesn't play nice either with gcov profiling.
-    if cx.sess().opts.debugging_opts.profile {
+    if cx.sess().opts.unstable_opts.profile {
         return None;
     }
 
@@ -275,7 +275,7 @@ pub fn from_fn_attrs<'ll, 'tcx>(
         to_add.push(uwtable_attr(cx.llcx));
     }
 
-    if cx.sess().opts.debugging_opts.profile_sample_use.is_some() {
+    if cx.sess().opts.unstable_opts.profile_sample_use.is_some() {
         to_add.push(llvm::CreateAttrString(cx.llcx, "use-sample-profile"));
     }
 
diff --git a/compiler/rustc_codegen_llvm/src/back/archive.rs b/compiler/rustc_codegen_llvm/src/back/archive.rs
index da9d8b5fb33..bccc2a995a3 100644
--- a/compiler/rustc_codegen_llvm/src/back/archive.rs
+++ b/compiler/rustc_codegen_llvm/src/back/archive.rs
@@ -351,7 +351,7 @@ fn string_to_io_error(s: String) -> io::Error {
 
 fn find_binutils_dlltool(sess: &Session) -> OsString {
     assert!(sess.target.options.is_like_windows && !sess.target.options.is_like_msvc);
-    if let Some(dlltool_path) = &sess.opts.debugging_opts.dlltool {
+    if let Some(dlltool_path) = &sess.opts.unstable_opts.dlltool {
         return dlltool_path.clone().into_os_string();
     }
 
diff --git a/compiler/rustc_codegen_llvm/src/back/write.rs b/compiler/rustc_codegen_llvm/src/back/write.rs
index ab8874d796d..2b465ce40e7 100644
--- a/compiler/rustc_codegen_llvm/src/back/write.rs
+++ b/compiler/rustc_codegen_llvm/src/back/write.rs
@@ -107,7 +107,7 @@ pub fn create_target_machine(tcx: TyCtxt<'_>, mod_name: &str) -> &'static mut ll
     let split_dwarf_file = if tcx.sess.target_can_use_split_dwarf() {
         tcx.output_filenames(()).split_dwarf_path(
             tcx.sess.split_debuginfo(),
-            tcx.sess.opts.debugging_opts.split_dwarf_kind,
+            tcx.sess.opts.unstable_opts.split_dwarf_kind,
             Some(mod_name),
         )
     } else {
@@ -182,9 +182,9 @@ pub fn target_machine_factory(
     let use_softfp = sess.opts.cg.soft_float;
 
     let ffunction_sections =
-        sess.opts.debugging_opts.function_sections.unwrap_or(sess.target.function_sections);
+        sess.opts.unstable_opts.function_sections.unwrap_or(sess.target.function_sections);
     let fdata_sections = ffunction_sections;
-    let funique_section_names = !sess.opts.debugging_opts.no_unique_section_names;
+    let funique_section_names = !sess.opts.unstable_opts.no_unique_section_names;
 
     let code_model = to_llvm_code_model(sess.code_model());
 
@@ -202,15 +202,15 @@ pub fn target_machine_factory(
     let features = CString::new(target_features.join(",")).unwrap();
     let abi = SmallCStr::new(&sess.target.llvm_abiname);
     let trap_unreachable =
-        sess.opts.debugging_opts.trap_unreachable.unwrap_or(sess.target.trap_unreachable);
-    let emit_stack_size_section = sess.opts.debugging_opts.emit_stack_sizes;
+        sess.opts.unstable_opts.trap_unreachable.unwrap_or(sess.target.trap_unreachable);
+    let emit_stack_size_section = sess.opts.unstable_opts.emit_stack_sizes;
 
     let asm_comments = sess.asm_comments();
     let relax_elf_relocations =
-        sess.opts.debugging_opts.relax_elf_relocations.unwrap_or(sess.target.relax_elf_relocations);
+        sess.opts.unstable_opts.relax_elf_relocations.unwrap_or(sess.target.relax_elf_relocations);
 
     let use_init_array =
-        !sess.opts.debugging_opts.use_ctors_section.unwrap_or(sess.target.use_ctors_section);
+        !sess.opts.unstable_opts.use_ctors_section.unwrap_or(sess.target.use_ctors_section);
 
     let path_mapping = sess.source_map().path_mapping().clone();
 
diff --git a/compiler/rustc_codegen_llvm/src/consts.rs b/compiler/rustc_codegen_llvm/src/consts.rs
index 5bbbfe9a4ab..2b16ae1a88d 100644
--- a/compiler/rustc_codegen_llvm/src/consts.rs
+++ b/compiler/rustc_codegen_llvm/src/consts.rs
@@ -64,7 +64,7 @@ pub fn const_alloc_to_llvm<'ll>(cx: &CodegenCx<'ll, '_>, alloc: ConstAllocation<
             // See https://github.com/rust-lang/rust/issues/84565.
             1
         } else {
-            cx.sess().opts.debugging_opts.uninit_const_chunk_threshold
+            cx.sess().opts.unstable_opts.uninit_const_chunk_threshold
         };
         let allow_uninit_chunks = chunks.clone().take(max.saturating_add(1)).count() <= max;
 
diff --git a/compiler/rustc_codegen_llvm/src/context.rs b/compiler/rustc_codegen_llvm/src/context.rs
index 55e4a4a7255..5857b83f6c9 100644
--- a/compiler/rustc_codegen_llvm/src/context.rs
+++ b/compiler/rustc_codegen_llvm/src/context.rs
@@ -275,7 +275,7 @@ pub unsafe fn create_module<'ll>(
         }
     }
 
-    if let Some(BranchProtection { bti, pac_ret }) = sess.opts.debugging_opts.branch_protection {
+    if let Some(BranchProtection { bti, pac_ret }) = sess.opts.unstable_opts.branch_protection {
         if sess.target.arch != "aarch64" {
             sess.err("-Zbranch-protection is only supported on aarch64");
         } else {
@@ -308,7 +308,7 @@ pub unsafe fn create_module<'ll>(
     }
 
     // Pass on the control-flow protection flags to LLVM (equivalent to `-fcf-protection` in Clang).
-    if let CFProtection::Branch | CFProtection::Full = sess.opts.debugging_opts.cf_protection {
+    if let CFProtection::Branch | CFProtection::Full = sess.opts.unstable_opts.cf_protection {
         llvm::LLVMRustAddModuleFlag(
             llmod,
             llvm::LLVMModFlagBehavior::Override,
@@ -316,7 +316,7 @@ pub unsafe fn create_module<'ll>(
             1,
         )
     }
-    if let CFProtection::Return | CFProtection::Full = sess.opts.debugging_opts.cf_protection {
+    if let CFProtection::Return | CFProtection::Full = sess.opts.unstable_opts.cf_protection {
         llvm::LLVMRustAddModuleFlag(
             llmod,
             llvm::LLVMModFlagBehavior::Override,
@@ -325,7 +325,7 @@ pub unsafe fn create_module<'ll>(
         )
     }
 
-    if sess.opts.debugging_opts.virtual_function_elimination {
+    if sess.opts.unstable_opts.virtual_function_elimination {
         llvm::LLVMRustAddModuleFlag(
             llmod,
             llvm::LLVMModFlagBehavior::Error,
diff --git a/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs b/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs
index d5f39a45670..f8bd2d234f3 100644
--- a/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs
+++ b/compiler/rustc_codegen_llvm/src/debuginfo/metadata.rs
@@ -824,7 +824,7 @@ pub fn build_compile_unit_di_node<'ll, 'tcx>(
         output_filenames
             .split_dwarf_path(
                 tcx.sess.split_debuginfo(),
-                tcx.sess.opts.debugging_opts.split_dwarf_kind,
+                tcx.sess.opts.unstable_opts.split_dwarf_kind,
                 Some(codegen_unit_name),
             )
             // We get a path relative to the working directory from split_dwarf_path
@@ -881,15 +881,15 @@ pub fn build_compile_unit_di_node<'ll, 'tcx>(
             split_name.len(),
             kind,
             0,
-            tcx.sess.opts.debugging_opts.split_dwarf_inlining,
+            tcx.sess.opts.unstable_opts.split_dwarf_inlining,
         );
 
-        if tcx.sess.opts.debugging_opts.profile {
+        if tcx.sess.opts.unstable_opts.profile {
             let cu_desc_metadata =
                 llvm::LLVMRustMetadataAsValue(debug_context.llcontext, unit_metadata);
             let default_gcda_path = &output_filenames.with_extension("gcda");
             let gcda_path =
-                tcx.sess.opts.debugging_opts.profile_emit.as_ref().unwrap_or(default_gcda_path);
+                tcx.sess.opts.unstable_opts.profile_emit.as_ref().unwrap_or(default_gcda_path);
 
             let gcov_cu_info = [
                 path_to_mdstring(debug_context.llcontext, &output_filenames.with_extension("gcno")),
@@ -1559,7 +1559,7 @@ pub fn create_vtable_di_node<'ll, 'tcx>(
 ) {
     // FIXME(flip1995): The virtual function elimination optimization only works with full LTO in
     // LLVM at the moment.
-    if cx.sess().opts.debugging_opts.virtual_function_elimination && cx.sess().lto() == Lto::Fat {
+    if cx.sess().opts.unstable_opts.virtual_function_elimination && cx.sess().lto() == Lto::Fat {
         vcall_visibility_metadata(cx, ty, poly_trait_ref, vtable);
     }
 
diff --git a/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs b/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs
index 730048d061b..69813792fcf 100644
--- a/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs
+++ b/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs
@@ -104,7 +104,7 @@ impl<'ll, 'tcx> CodegenUnitDebugContext<'ll, 'tcx> {
             // This can be overridden using --llvm-opts -dwarf-version,N.
             // Android has the same issue (#22398)
             let dwarf_version =
-                sess.opts.debugging_opts.dwarf_version.unwrap_or(sess.target.default_dwarf_version);
+                sess.opts.unstable_opts.dwarf_version.unwrap_or(sess.target.default_dwarf_version);
             llvm::LLVMRustAddModuleFlag(
                 self.llmod,
                 llvm::LLVMModFlagBehavior::Warning,
diff --git a/compiler/rustc_codegen_llvm/src/lib.rs b/compiler/rustc_codegen_llvm/src/lib.rs
index fb196ee9f5d..e67568b7b8f 100644
--- a/compiler/rustc_codegen_llvm/src/lib.rs
+++ b/compiler/rustc_codegen_llvm/src/lib.rs
@@ -355,7 +355,7 @@ impl CodegenBackend for LlvmCodegenBackend {
             .join(sess);
 
         sess.time("llvm_dump_timing_file", || {
-            if sess.opts.debugging_opts.llvm_time_trace {
+            if sess.opts.unstable_opts.llvm_time_trace {
                 let file_name = outputs.with_extension("llvm_timings.json");
                 llvm_util::time_trace_profiler_finish(&file_name);
             }
diff --git a/compiler/rustc_codegen_llvm/src/llvm_util.rs b/compiler/rustc_codegen_llvm/src/llvm_util.rs
index 5b3b7db12b7..a0a640473eb 100644
--- a/compiler/rustc_codegen_llvm/src/llvm_util.rs
+++ b/compiler/rustc_codegen_llvm/src/llvm_util.rs
@@ -87,7 +87,7 @@ unsafe fn configure_llvm(sess: &Session) {
             add("-debug-pass=Structure", false);
         }
         if sess.target.generate_arange_section
-            && !sess.opts.debugging_opts.no_generate_arange_section
+            && !sess.opts.unstable_opts.no_generate_arange_section
         {
             add("-generate-arange-section", false);
         }
@@ -102,7 +102,7 @@ unsafe fn configure_llvm(sess: &Session) {
             add("-enable-machine-outliner=never", false);
         }
 
-        match sess.opts.debugging_opts.merge_functions.unwrap_or(sess.target.merge_functions) {
+        match sess.opts.unstable_opts.merge_functions.unwrap_or(sess.target.merge_functions) {
             MergeFunctions::Disabled | MergeFunctions::Trampolines => {}
             MergeFunctions::Aliases => {
                 add("-mergefunc-use-aliases", false);
@@ -125,7 +125,7 @@ unsafe fn configure_llvm(sess: &Session) {
         }
     }
 
-    if sess.opts.debugging_opts.llvm_time_trace {
+    if sess.opts.unstable_opts.llvm_time_trace {
         llvm::LLVMTimeTraceProfilerInitialize();
     }
 
@@ -133,11 +133,11 @@ unsafe fn configure_llvm(sess: &Session) {
 
     // Use the legacy plugin registration if we don't use the new pass manager
     if !should_use_new_llvm_pass_manager(
-        &sess.opts.debugging_opts.new_llvm_pass_manager,
+        &sess.opts.unstable_opts.new_llvm_pass_manager,
         &sess.target.arch,
     ) {
         // Register LLVM plugins by loading them into the compiler process.
-        for plugin in &sess.opts.debugging_opts.llvm_plugins {
+        for plugin in &sess.opts.unstable_opts.llvm_plugins {
             let lib = Library::new(plugin).unwrap_or_else(|e| bug!("couldn't load plugin: {}", e));
             debug!("LLVM plugin loaded successfully {:?} ({})", lib, plugin);
 
@@ -541,7 +541,7 @@ fn backend_feature_name(s: &str) -> Option<&str> {
 }
 
 pub fn tune_cpu(sess: &Session) -> Option<&str> {
-    let name = sess.opts.debugging_opts.tune_cpu.as_ref()?;
+    let name = sess.opts.unstable_opts.tune_cpu.as_ref()?;
     Some(handle_native(name))
 }
 
diff --git a/compiler/rustc_codegen_ssa/src/back/link.rs b/compiler/rustc_codegen_ssa/src/back/link.rs
index 1628d580b88..94acdea894b 100644
--- a/compiler/rustc_codegen_ssa/src/back/link.rs
+++ b/compiler/rustc_codegen_ssa/src/back/link.rs
@@ -67,7 +67,7 @@ pub fn link_binary<'a, B: ArchiveBuilder<'a>>(
     let output_metadata = sess.opts.output_types.contains_key(&OutputType::Metadata);
     for &crate_type in sess.crate_types().iter() {
         // Ignore executable crates if we have -Z no-codegen, as they will error.
-        if (sess.opts.debugging_opts.no_codegen || !sess.opts.output_types.should_codegen())
+        if (sess.opts.unstable_opts.no_codegen || !sess.opts.output_types.should_codegen())
             && !output_metadata
             && crate_type == CrateType::Executable
         {
@@ -595,7 +595,7 @@ fn link_dwarf_object<'a>(
         let mut package = thorin::DwarfPackage::new(&thorin_sess);
 
         // Input objs contain .o/.dwo files from the current crate.
-        match sess.opts.debugging_opts.split_dwarf_kind {
+        match sess.opts.unstable_opts.split_dwarf_kind {
             SplitDwarfKind::Single => {
                 for input_obj in cg_results.modules.iter().filter_map(|m| m.object.as_ref()) {
                     package.add_input_object(input_obj)?;
@@ -1022,7 +1022,7 @@ fn link_natively<'a, B: ArchiveBuilder<'a>>(
 
 // Temporarily support both -Z strip and -C strip
 fn strip_value(sess: &Session) -> Strip {
-    match (sess.opts.debugging_opts.strip, sess.opts.cg.strip) {
+    match (sess.opts.unstable_opts.strip, sess.opts.cg.strip) {
         (s, Strip::None) => s,
         (_, s) => s,
     }
@@ -1074,7 +1074,7 @@ fn add_sanitizer_libraries(sess: &Session, crate_type: CrateType, linker: &mut d
         return;
     }
 
-    let sanitizer = sess.opts.debugging_opts.sanitizer;
+    let sanitizer = sess.opts.unstable_opts.sanitizer;
     if sanitizer.contains(SanitizerSet::ADDRESS) {
         link_sanitizer_runtime(sess, linker, "asan");
     }
@@ -1253,7 +1253,7 @@ fn preserve_objects_for_their_debuginfo(sess: &Session) -> (bool, bool) {
         return (false, false);
     }
 
-    match (sess.split_debuginfo(), sess.opts.debugging_opts.split_dwarf_kind) {
+    match (sess.split_debuginfo(), sess.opts.unstable_opts.split_dwarf_kind) {
         // If there is no split debuginfo then do not preserve objects.
         (SplitDebuginfo::Off, _) => (false, false),
         // If there is packed split debuginfo, then the debuginfo in the objects
@@ -1601,7 +1601,7 @@ fn add_pre_link_args(cmd: &mut dyn Linker, sess: &Session, flavor: LinkerFlavor)
     if let Some(args) = sess.target.pre_link_args.get(&flavor) {
         cmd.args(args.iter().map(Deref::deref));
     }
-    cmd.args(&sess.opts.debugging_opts.pre_link_args);
+    cmd.args(&sess.opts.unstable_opts.pre_link_args);
 }
 
 /// Add a link script embedded in the target, if applicable.
@@ -1809,7 +1809,7 @@ fn add_library_search_dirs(cmd: &mut dyn Linker, sess: &Session, self_contained:
 /// Add options making relocation sections in the produced ELF files read-only
 /// and suppressing lazy binding.
 fn add_relro_args(cmd: &mut dyn Linker, sess: &Session) {
-    match sess.opts.debugging_opts.relro_level.unwrap_or(sess.target.relro_level) {
+    match sess.opts.unstable_opts.relro_level.unwrap_or(sess.target.relro_level) {
         RelroLevel::Full => cmd.full_relro(),
         RelroLevel::Partial => cmd.partial_relro(),
         RelroLevel::Off => cmd.no_relro(),
@@ -1957,7 +1957,7 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
     // (or alternatively link all native libraries after their respective crates).
     // This change is somewhat breaking in practice due to local static libraries being linked
     // as whole-archive (#85144), so removing whole-archive may be a pre-requisite.
-    if sess.opts.debugging_opts.link_native_libraries {
+    if sess.opts.unstable_opts.link_native_libraries {
         add_local_native_libraries(cmd, sess, codegen_results);
     }
 
@@ -1969,7 +1969,7 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
     // If -Zlink-native-libraries=false is set, then the assumption is that an
     // external build system already has the native dependencies defined, and it
     // will provide them to the linker itself.
-    if sess.opts.debugging_opts.link_native_libraries {
+    if sess.opts.unstable_opts.link_native_libraries {
         add_upstream_native_libraries(cmd, sess, codegen_results);
     }
 
@@ -2037,7 +2037,7 @@ fn add_order_independent_options(
     add_link_script(cmd, sess, tmpdir, crate_type);
 
     if sess.target.os == "fuchsia" && crate_type == CrateType::Executable {
-        let prefix = if sess.opts.debugging_opts.sanitizer.contains(SanitizerSet::ADDRESS) {
+        let prefix = if sess.opts.unstable_opts.sanitizer.contains(SanitizerSet::ADDRESS) {
             "asan/"
         } else {
             ""
@@ -2362,7 +2362,7 @@ fn add_upstream_rust_crates<'a, B: ArchiveBuilder<'a>>(
                 // If -Zlink-native-libraries=false is set, then the assumption is that an
                 // external build system already has the native dependencies defined, and it
                 // will provide them to the linker itself.
-                if sess.opts.debugging_opts.link_native_libraries {
+                if sess.opts.unstable_opts.link_native_libraries {
                     let mut last = (None, NativeLibKind::Unspecified, None);
                     for lib in &codegen_results.crate_info.native_libraries[&cnum] {
                         let Some(name) = lib.name else {
@@ -2709,7 +2709,7 @@ fn get_apple_sdk_root(sdk_name: &str) -> Result<String, String> {
 }
 
 fn add_gcc_ld_path(cmd: &mut dyn Linker, sess: &Session, flavor: LinkerFlavor) {
-    if let Some(ld_impl) = sess.opts.debugging_opts.gcc_ld {
+    if let Some(ld_impl) = sess.opts.unstable_opts.gcc_ld {
         if let LinkerFlavor::Gcc = flavor {
             match ld_impl {
                 LdImpl::Lld => {
diff --git a/compiler/rustc_codegen_ssa/src/back/linker.rs b/compiler/rustc_codegen_ssa/src/back/linker.rs
index 955ee245b28..d4a9db4af23 100644
--- a/compiler/rustc_codegen_ssa/src/back/linker.rs
+++ b/compiler/rustc_codegen_ssa/src/back/linker.rs
@@ -303,7 +303,7 @@ impl<'a> GccLinker<'a> {
             config::OptLevel::Aggressive => "O3",
         };
 
-        if let Some(path) = &self.sess.opts.debugging_opts.profile_sample_use {
+        if let Some(path) = &self.sess.opts.unstable_opts.profile_sample_use {
             self.linker_arg(&format!("-plugin-opt=sample-profile={}", path.display()));
         };
         self.linker_args(&[
@@ -325,7 +325,7 @@ impl<'a> GccLinker<'a> {
             // purely to support rustbuild right now, we should get a more
             // principled solution at some point to force the compiler to pass
             // the right `-Wl,-install_name` with an `@rpath` in it.
-            if self.sess.opts.cg.rpath || self.sess.opts.debugging_opts.osx_rpath_install_name {
+            if self.sess.opts.cg.rpath || self.sess.opts.unstable_opts.osx_rpath_install_name {
                 let mut rpath = OsString::from("@rpath/");
                 rpath.push(out_filename.file_name().unwrap());
                 self.linker_args(&[OsString::from("-install_name"), rpath]);
diff --git a/compiler/rustc_codegen_ssa/src/back/symbol_export.rs b/compiler/rustc_codegen_ssa/src/back/symbol_export.rs
index f651814be7e..d1a267f7643 100644
--- a/compiler/rustc_codegen_ssa/src/back/symbol_export.rs
+++ b/compiler/rustc_codegen_ssa/src/back/symbol_export.rs
@@ -232,15 +232,15 @@ fn exported_symbols_provider_local<'tcx>(
         }));
     }
 
-    if tcx.sess.opts.debugging_opts.sanitizer.contains(SanitizerSet::MEMORY) {
+    if tcx.sess.opts.unstable_opts.sanitizer.contains(SanitizerSet::MEMORY) {
         let mut msan_weak_symbols = Vec::new();
 
         // Similar to profiling, preserve weak msan symbol during LTO.
-        if tcx.sess.opts.debugging_opts.sanitizer_recover.contains(SanitizerSet::MEMORY) {
+        if tcx.sess.opts.unstable_opts.sanitizer_recover.contains(SanitizerSet::MEMORY) {
             msan_weak_symbols.push("__msan_keep_going");
         }
 
-        if tcx.sess.opts.debugging_opts.sanitizer_memory_track_origins != 0 {
+        if tcx.sess.opts.unstable_opts.sanitizer_memory_track_origins != 0 {
             msan_weak_symbols.push("__msan_track_origins");
         }
 
diff --git a/compiler/rustc_codegen_ssa/src/back/write.rs b/compiler/rustc_codegen_ssa/src/back/write.rs
index f4a5cac872e..c2ac21eec67 100644
--- a/compiler/rustc_codegen_ssa/src/back/write.rs
+++ b/compiler/rustc_codegen_ssa/src/back/write.rs
@@ -179,24 +179,24 @@ impl ModuleConfig {
                 SwitchWithOptPath::Disabled
             ),
             pgo_use: if_regular!(sess.opts.cg.profile_use.clone(), None),
-            pgo_sample_use: if_regular!(sess.opts.debugging_opts.profile_sample_use.clone(), None),
-            debug_info_for_profiling: sess.opts.debugging_opts.debug_info_for_profiling,
+            pgo_sample_use: if_regular!(sess.opts.unstable_opts.profile_sample_use.clone(), None),
+            debug_info_for_profiling: sess.opts.unstable_opts.debug_info_for_profiling,
             instrument_coverage: if_regular!(sess.instrument_coverage(), false),
             instrument_gcov: if_regular!(
                 // compiler_builtins overrides the codegen-units settings,
                 // which is incompatible with -Zprofile which requires that
                 // only a single codegen unit is used per crate.
-                sess.opts.debugging_opts.profile && !is_compiler_builtins,
+                sess.opts.unstable_opts.profile && !is_compiler_builtins,
                 false
             ),
 
-            sanitizer: if_regular!(sess.opts.debugging_opts.sanitizer, SanitizerSet::empty()),
+            sanitizer: if_regular!(sess.opts.unstable_opts.sanitizer, SanitizerSet::empty()),
             sanitizer_recover: if_regular!(
-                sess.opts.debugging_opts.sanitizer_recover,
+                sess.opts.unstable_opts.sanitizer_recover,
                 SanitizerSet::empty()
             ),
             sanitizer_memory_track_origins: if_regular!(
-                sess.opts.debugging_opts.sanitizer_memory_track_origins,
+                sess.opts.unstable_opts.sanitizer_memory_track_origins,
                 0
             ),
 
@@ -247,7 +247,7 @@ impl ModuleConfig {
             // O2 and O3) since it can be useful for reducing code size.
             merge_functions: match sess
                 .opts
-                .debugging_opts
+                .unstable_opts
                 .merge_functions
                 .unwrap_or(sess.target.merge_functions)
             {
@@ -259,9 +259,9 @@ impl ModuleConfig {
             },
 
             inline_threshold: sess.opts.cg.inline_threshold,
-            new_llvm_pass_manager: sess.opts.debugging_opts.new_llvm_pass_manager,
+            new_llvm_pass_manager: sess.opts.unstable_opts.new_llvm_pass_manager,
             emit_lifetime_markers: sess.emit_lifetime_markers(),
-            llvm_plugins: if_regular!(sess.opts.debugging_opts.llvm_plugins.clone(), vec![]),
+            llvm_plugins: if_regular!(sess.opts.unstable_opts.llvm_plugins.clone(), vec![]),
         }
     }
 
@@ -926,7 +926,7 @@ fn finish_intra_module_work<B: ExtraBackendMethods>(
 ) -> Result<WorkItemResult<B>, FatalError> {
     let diag_handler = cgcx.create_diag_handler();
 
-    if !cgcx.opts.debugging_opts.combine_cgu
+    if !cgcx.opts.unstable_opts.combine_cgu
         || module.kind == ModuleKind::Metadata
         || module.kind == ModuleKind::Allocator
     {
@@ -1048,14 +1048,13 @@ fn start_executing_work<B: ExtraBackendMethods>(
         each_linked_rlib_for_lto.push((cnum, path.to_path_buf()));
     }));
 
-    let ol = if tcx.sess.opts.debugging_opts.no_codegen
-        || !tcx.sess.opts.output_types.should_codegen()
-    {
-        // If we know that we won’t be doing codegen, create target machines without optimisation.
-        config::OptLevel::No
-    } else {
-        tcx.backend_optimization_level(())
-    };
+    let ol =
+        if tcx.sess.opts.unstable_opts.no_codegen || !tcx.sess.opts.output_types.should_codegen() {
+            // If we know that we won’t be doing codegen, create target machines without optimisation.
+            config::OptLevel::No
+        } else {
+            tcx.backend_optimization_level(())
+        };
     let backend_features = tcx.global_backend_features(());
     let cgcx = CodegenContext::<B> {
         backend: backend.clone(),
@@ -1064,7 +1063,7 @@ fn start_executing_work<B: ExtraBackendMethods>(
         lto: sess.lto(),
         fewer_names: sess.fewer_names(),
         save_temps: sess.opts.cg.save_temps,
-        time_trace: sess.opts.debugging_opts.llvm_time_trace,
+        time_trace: sess.opts.unstable_opts.llvm_time_trace,
         opts: Arc::new(sess.opts.clone()),
         prof: sess.prof.clone(),
         exported_symbols,
@@ -1087,7 +1086,7 @@ fn start_executing_work<B: ExtraBackendMethods>(
         target_arch: tcx.sess.target.arch.to_string(),
         debuginfo: tcx.sess.opts.debuginfo,
         split_debuginfo: tcx.sess.split_debuginfo(),
-        split_dwarf_kind: tcx.sess.opts.debugging_opts.split_dwarf_kind,
+        split_dwarf_kind: tcx.sess.opts.unstable_opts.split_dwarf_kind,
     };
 
     // This is the "main loop" of parallel work happening for parallel codegen.
@@ -1346,7 +1345,7 @@ fn start_executing_work<B: ExtraBackendMethods>(
                             .binary_search_by_key(&cost, |&(_, cost)| cost)
                             .unwrap_or_else(|e| e);
                         work_items.insert(insertion_index, (work, cost));
-                        if !cgcx.opts.debugging_opts.no_parallel_llvm {
+                        if !cgcx.opts.unstable_opts.no_parallel_llvm {
                             helper.request_token();
                         }
                     }
@@ -1466,7 +1465,7 @@ fn start_executing_work<B: ExtraBackendMethods>(
                     };
                     work_items.insert(insertion_index, (llvm_work_item, cost));
 
-                    if !cgcx.opts.debugging_opts.no_parallel_llvm {
+                    if !cgcx.opts.unstable_opts.no_parallel_llvm {
                         helper.request_token();
                     }
                     assert!(!codegen_aborted);
diff --git a/compiler/rustc_codegen_ssa/src/base.rs b/compiler/rustc_codegen_ssa/src/base.rs
index 7e2e85ead54..7def30af2b3 100644
--- a/compiler/rustc_codegen_ssa/src/base.rs
+++ b/compiler/rustc_codegen_ssa/src/base.rs
@@ -521,7 +521,7 @@ pub fn codegen_crate<B: ExtraBackendMethods>(
     need_metadata_module: bool,
 ) -> OngoingCodegen<B> {
     // Skip crate items and just output metadata in -Z no-codegen mode.
-    if tcx.sess.opts.debugging_opts.no_codegen || !tcx.sess.opts.output_types.should_codegen() {
+    if tcx.sess.opts.unstable_opts.no_codegen || !tcx.sess.opts.output_types.should_codegen() {
         let ongoing_codegen = start_async_codegen(backend, tcx, target_cpu, metadata, None, 1);
 
         ongoing_codegen.codegen_finished(tcx);
diff --git a/compiler/rustc_codegen_ssa/src/meth.rs b/compiler/rustc_codegen_ssa/src/meth.rs
index 5203ebfad75..df42d804566 100644
--- a/compiler/rustc_codegen_ssa/src/meth.rs
+++ b/compiler/rustc_codegen_ssa/src/meth.rs
@@ -25,7 +25,7 @@ impl<'a, 'tcx> VirtualIndex {
         let llty = bx.fn_ptr_backend_type(fn_abi);
         let llvtable = bx.pointercast(llvtable, bx.type_ptr_to(llty));
 
-        if bx.cx().sess().opts.debugging_opts.virtual_function_elimination
+        if bx.cx().sess().opts.unstable_opts.virtual_function_elimination
             && bx.cx().sess().lto() == Lto::Fat
         {
             let typeid =
diff --git a/compiler/rustc_codegen_ssa/src/mir/block.rs b/compiler/rustc_codegen_ssa/src/mir/block.rs
index b8e3cb32ef6..745da821c9d 100644
--- a/compiler/rustc_codegen_ssa/src/mir/block.rs
+++ b/compiler/rustc_codegen_ssa/src/mir/block.rs
@@ -687,7 +687,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
             source_info,
             target,
             cleanup,
-            self.cx.tcx().sess.opts.debugging_opts.strict_init_checks,
+            self.cx.tcx().sess.opts.unstable_opts.strict_init_checks,
         ) {
             return;
         }
diff --git a/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs b/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs
index f2d1827c792..8c3186efc63 100644
--- a/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs
+++ b/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs
@@ -101,7 +101,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
             return span;
         }
 
-        if span.from_expansion() && !self.cx.sess().opts.debugging_opts.debug_macros {
+        if span.from_expansion() && !self.cx.sess().opts.unstable_opts.debug_macros {
             // Walk up the macro expansion chain until we reach a non-expanded span.
             // We also stop at the function body level because no line stepping can occur
             // at the level above that.
diff --git a/compiler/rustc_codegen_ssa/src/traits/builder.rs b/compiler/rustc_codegen_ssa/src/traits/builder.rs
index 37f2bfd3c4f..1bbe10141fc 100644
--- a/compiler/rustc_codegen_ssa/src/traits/builder.rs
+++ b/compiler/rustc_codegen_ssa/src/traits/builder.rs
@@ -221,7 +221,7 @@ pub trait BuilderMethods<'a, 'tcx>:
         assert!(matches!(self.cx().type_kind(float_ty), TypeKind::Float | TypeKind::Double));
         assert_eq!(self.cx().type_kind(int_ty), TypeKind::Integer);
 
-        if let Some(false) = self.cx().sess().opts.debugging_opts.saturating_float_casts {
+        if let Some(false) = self.cx().sess().opts.unstable_opts.saturating_float_casts {
             return if signed { self.fptosi(x, dest_ty) } else { self.fptoui(x, dest_ty) };
         }
 
diff --git a/compiler/rustc_const_eval/src/interpret/intrinsics.rs b/compiler/rustc_const_eval/src/interpret/intrinsics.rs
index 93b64d9d37a..e2a8a9891f7 100644
--- a/compiler/rustc_const_eval/src/interpret/intrinsics.rs
+++ b/compiler/rustc_const_eval/src/interpret/intrinsics.rs
@@ -417,7 +417,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
                     && !layout.might_permit_raw_init(
                         self,
                         InitKind::Zero,
-                        self.tcx.sess.opts.debugging_opts.strict_init_checks,
+                        self.tcx.sess.opts.unstable_opts.strict_init_checks,
                     )
                 {
                     M::abort(
@@ -432,7 +432,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
                     && !layout.might_permit_raw_init(
                         self,
                         InitKind::Uninit,
-                        self.tcx.sess.opts.debugging_opts.strict_init_checks,
+                        self.tcx.sess.opts.unstable_opts.strict_init_checks,
                     )
                 {
                     M::abort(
diff --git a/compiler/rustc_const_eval/src/interpret/intrinsics/caller_location.rs b/compiler/rustc_const_eval/src/interpret/intrinsics/caller_location.rs
index 23ae2db6438..14fde2c305e 100644
--- a/compiler/rustc_const_eval/src/interpret/intrinsics/caller_location.rs
+++ b/compiler/rustc_const_eval/src/interpret/intrinsics/caller_location.rs
@@ -80,7 +80,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
         line: u32,
         col: u32,
     ) -> MPlaceTy<'tcx, M::PointerTag> {
-        let loc_details = &self.tcx.sess.opts.debugging_opts.location_detail;
+        let loc_details = &self.tcx.sess.opts.unstable_opts.location_detail;
         let file = if loc_details.file {
             self.allocate_str(filename.as_str(), MemoryKind::CallerLocation, Mutability::Not)
         } else {
diff --git a/compiler/rustc_const_eval/src/interpret/operator.rs b/compiler/rustc_const_eval/src/interpret/operator.rs
index f0c113376ea..88999e3b47b 100644
--- a/compiler/rustc_const_eval/src/interpret/operator.rs
+++ b/compiler/rustc_const_eval/src/interpret/operator.rs
@@ -41,7 +41,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
             let pair = Immediate::ScalarPair(val.into(), Scalar::from_bool(overflowed).into());
             self.write_immediate(pair, dest)?;
         } else {
-            assert!(self.tcx.sess.opts.debugging_opts.randomize_layout);
+            assert!(self.tcx.sess.opts.unstable_opts.randomize_layout);
             // With randomized layout, `(int, bool)` might cease to be a `ScalarPair`, so we have to
             // do a component-wise write here. This code path is slower than the above because
             // `place_field` will have to `force_allocate` locals here.
diff --git a/compiler/rustc_const_eval/src/transform/check_consts/check.rs b/compiler/rustc_const_eval/src/transform/check_consts/check.rs
index 39fabd17c52..628298df473 100644
--- a/compiler/rustc_const_eval/src/transform/check_consts/check.rs
+++ b/compiler/rustc_const_eval/src/transform/check_consts/check.rs
@@ -312,7 +312,7 @@ impl<'mir, 'tcx> Checker<'mir, 'tcx> {
             Status::Forbidden => None,
         };
 
-        if self.tcx.sess.opts.debugging_opts.unleash_the_miri_inside_of_you {
+        if self.tcx.sess.opts.unstable_opts.unleash_the_miri_inside_of_you {
             self.tcx.sess.miri_unleashed_feature(span, gate);
             return;
         }
diff --git a/compiler/rustc_const_eval/src/transform/validate.rs b/compiler/rustc_const_eval/src/transform/validate.rs
index cd2b8be0acd..15e820f2d19 100644
--- a/compiler/rustc_const_eval/src/transform/validate.rs
+++ b/compiler/rustc_const_eval/src/transform/validate.rs
@@ -223,7 +223,7 @@ impl<'a, 'tcx> Visitor<'tcx> for TypeChecker<'a, 'tcx> {
 
     fn visit_operand(&mut self, operand: &Operand<'tcx>, location: Location) {
         // This check is somewhat expensive, so only run it when -Zvalidate-mir is passed.
-        if self.tcx.sess.opts.debugging_opts.validate_mir && self.mir_phase < MirPhase::DropsLowered
+        if self.tcx.sess.opts.unstable_opts.validate_mir && self.mir_phase < MirPhase::DropsLowered
         {
             // `Operand::Copy` is only supposed to be used with `Copy` types.
             if let Operand::Copy(place) = operand {
diff --git a/compiler/rustc_driver/src/lib.rs b/compiler/rustc_driver/src/lib.rs
index b71cdad718a..f5b059793cf 100644
--- a/compiler/rustc_driver/src/lib.rs
+++ b/compiler/rustc_driver/src/lib.rs
@@ -29,7 +29,7 @@ use rustc_log::stdout_isatty;
 use rustc_metadata::locator;
 use rustc_save_analysis as save;
 use rustc_save_analysis::DumpHandler;
-use rustc_session::config::{nightly_options, CG_OPTIONS, DB_OPTIONS};
+use rustc_session::config::{nightly_options, CG_OPTIONS, Z_OPTIONS};
 use rustc_session::config::{ErrorOutputType, Input, OutputType, PrintRequest, TrimmedDefPaths};
 use rustc_session::cstore::MetadataLoader;
 use rustc_session::getopts;
@@ -124,7 +124,7 @@ impl Callbacks for TimePassesCallbacks {
         // If a --prints=... option has been given, we don't print the "total"
         // time because it will mess up the --prints output. See #64339.
         self.time_passes = config.opts.prints.is_empty()
-            && (config.opts.debugging_opts.time_passes || config.opts.debugging_opts.time);
+            && (config.opts.unstable_opts.time_passes || config.opts.unstable_opts.time);
         config.opts.trimmed_def_paths = TrimmedDefPaths::GoodPath;
     }
 }
@@ -248,7 +248,7 @@ fn run_compiler(
                     let sopts = &compiler.session().opts;
                     if sopts.describe_lints {
                         let mut lint_store = rustc_lint::new_lint_store(
-                            sopts.debugging_opts.no_interleave_lints,
+                            sopts.unstable_opts.no_interleave_lints,
                             compiler.session().unstable_options(),
                         );
                         let registered_lints =
@@ -342,7 +342,7 @@ fn run_compiler(
                 return early_exit();
             }
 
-            if sess.opts.debugging_opts.parse_only || sess.opts.debugging_opts.show_span.is_some() {
+            if sess.opts.unstable_opts.parse_only || sess.opts.unstable_opts.show_span.is_some() {
                 return early_exit();
             }
 
@@ -371,13 +371,13 @@ fn run_compiler(
 
             queries.global_ctxt()?;
 
-            if sess.opts.debugging_opts.no_analysis {
+            if sess.opts.unstable_opts.no_analysis {
                 return early_exit();
             }
 
             queries.global_ctxt()?.peek_mut().enter(|tcx| {
                 let result = tcx.analysis(());
-                if sess.opts.debugging_opts.save_analysis {
+                if sess.opts.unstable_opts.save_analysis {
                     let crate_name = queries.crate_name()?.peek().clone();
                     sess.time("save_analysis", || {
                         save::process_crate(
@@ -401,7 +401,7 @@ fn run_compiler(
 
             queries.ongoing_codegen()?;
 
-            if sess.opts.debugging_opts.print_type_sizes {
+            if sess.opts.unstable_opts.print_type_sizes {
                 sess.code_stats.print_type_sizes();
             }
 
@@ -414,14 +414,14 @@ fn run_compiler(
             linker.link()?
         }
 
-        if sess.opts.debugging_opts.perf_stats {
+        if sess.opts.unstable_opts.perf_stats {
             sess.print_perf_stats();
         }
 
-        if sess.opts.debugging_opts.print_fuel.is_some() {
+        if sess.opts.unstable_opts.print_fuel.is_some() {
             eprintln!(
                 "Fuel used by {}: {}",
-                sess.opts.debugging_opts.print_fuel.as_ref().unwrap(),
+                sess.opts.unstable_opts.print_fuel.as_ref().unwrap(),
                 sess.print_fuel.load(SeqCst)
             );
         }
@@ -576,7 +576,7 @@ fn show_content_with_pager(content: &str) {
 }
 
 pub fn try_process_rlink(sess: &Session, compiler: &interface::Compiler) -> Compilation {
-    if sess.opts.debugging_opts.link_only {
+    if sess.opts.unstable_opts.link_only {
         if let Input::File(file) = compiler.input() {
             // FIXME: #![crate_type] and #![crate_name] support not implemented yet
             sess.init_crate_types(collect_crate_types(sess, &[]));
@@ -606,7 +606,7 @@ pub fn list_metadata(
     metadata_loader: &dyn MetadataLoader,
     input: &Input,
 ) -> Compilation {
-    if sess.opts.debugging_opts.ls {
+    if sess.opts.unstable_opts.ls {
         match *input {
             Input::File(ref ifile) => {
                 let path = &(*ifile);
@@ -928,7 +928,7 @@ Available lint options:
 
 fn describe_debug_flags() {
     println!("\nAvailable options:\n");
-    print_flag_list("-Z", config::DB_OPTIONS);
+    print_flag_list("-Z", config::Z_OPTIONS);
 }
 
 fn describe_codegen_flags() {
@@ -1000,7 +1000,7 @@ pub fn handle_options(args: &[String]) -> Option<getopts::Matches> {
             getopts::Fail::UnrecognizedOption(ref opt) => CG_OPTIONS
                 .iter()
                 .map(|&(name, ..)| ('C', name))
-                .chain(DB_OPTIONS.iter().map(|&(name, ..)| ('Z', name)))
+                .chain(Z_OPTIONS.iter().map(|&(name, ..)| ('Z', name)))
                 .find(|&(_, name)| *opt == name.replace('_', "-"))
                 .map(|(flag, _)| format!("{}. Did you mean `-{} {}`?", e, flag, opt)),
             _ => None,
diff --git a/compiler/rustc_expand/src/config.rs b/compiler/rustc_expand/src/config.rs
index 3cada372570..2b941ec6809 100644
--- a/compiler/rustc_expand/src/config.rs
+++ b/compiler/rustc_expand/src/config.rs
@@ -171,7 +171,7 @@ fn get_features(
                 continue;
             }
 
-            if let Some(allowed) = sess.opts.debugging_opts.allow_features.as_ref() {
+            if let Some(allowed) = sess.opts.unstable_opts.allow_features.as_ref() {
                 if allowed.iter().all(|f| name.as_str() != f) {
                     struct_span_err!(
                         span_handler,
diff --git a/compiler/rustc_expand/src/expand.rs b/compiler/rustc_expand/src/expand.rs
index 978f87b1d13..93eeca5b289 100644
--- a/compiler/rustc_expand/src/expand.rs
+++ b/compiler/rustc_expand/src/expand.rs
@@ -564,7 +564,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
                 .resolver
                 .visit_ast_fragment_with_placeholders(self.cx.current_expansion.id, &fragment);
 
-            if self.cx.sess.opts.debugging_opts.incremental_relative_spans {
+            if self.cx.sess.opts.unstable_opts.incremental_relative_spans {
                 for (invoc, _) in invocations.iter_mut() {
                     let expn_id = invoc.expansion_data.id;
                     let parent_def = self.cx.resolver.invocation_parent(expn_id);
diff --git a/compiler/rustc_incremental/src/assert_dep_graph.rs b/compiler/rustc_incremental/src/assert_dep_graph.rs
index 93528b4514b..69e482ce854 100644
--- a/compiler/rustc_incremental/src/assert_dep_graph.rs
+++ b/compiler/rustc_incremental/src/assert_dep_graph.rs
@@ -55,11 +55,11 @@ use std::io::{BufWriter, Write};
 #[allow(missing_docs)]
 pub fn assert_dep_graph(tcx: TyCtxt<'_>) {
     tcx.dep_graph.with_ignore(|| {
-        if tcx.sess.opts.debugging_opts.dump_dep_graph {
+        if tcx.sess.opts.unstable_opts.dump_dep_graph {
             tcx.dep_graph.with_query(dump_graph);
         }
 
-        if !tcx.sess.opts.debugging_opts.query_dep_graph {
+        if !tcx.sess.opts.unstable_opts.query_dep_graph {
             return;
         }
 
@@ -81,7 +81,7 @@ pub fn assert_dep_graph(tcx: TyCtxt<'_>) {
 
         if !if_this_changed.is_empty() || !then_this_would_need.is_empty() {
             assert!(
-                tcx.sess.opts.debugging_opts.query_dep_graph,
+                tcx.sess.opts.unstable_opts.query_dep_graph,
                 "cannot use the `#[{}]` or `#[{}]` annotations \
                     without supplying `-Z query-dep-graph`",
                 sym::rustc_if_this_changed,
diff --git a/compiler/rustc_incremental/src/assert_module_sources.rs b/compiler/rustc_incremental/src/assert_module_sources.rs
index 61b1dd8cb01..00aefac645f 100644
--- a/compiler/rustc_incremental/src/assert_module_sources.rs
+++ b/compiler/rustc_incremental/src/assert_module_sources.rs
@@ -76,7 +76,7 @@ impl<'tcx> AssertModuleSource<'tcx> {
             return;
         };
 
-        if !self.tcx.sess.opts.debugging_opts.query_dep_graph {
+        if !self.tcx.sess.opts.unstable_opts.query_dep_graph {
             self.tcx.sess.span_fatal(
                 attr.span,
                 "found CGU-reuse attribute but `-Zquery-dep-graph` was not specified",
diff --git a/compiler/rustc_incremental/src/persist/dirty_clean.rs b/compiler/rustc_incremental/src/persist/dirty_clean.rs
index 94097357f8c..35a278e6c92 100644
--- a/compiler/rustc_incremental/src/persist/dirty_clean.rs
+++ b/compiler/rustc_incremental/src/persist/dirty_clean.rs
@@ -134,7 +134,7 @@ struct Assertion {
 }
 
 pub fn check_dirty_clean_annotations(tcx: TyCtxt<'_>) {
-    if !tcx.sess.opts.debugging_opts.query_dep_graph {
+    if !tcx.sess.opts.unstable_opts.query_dep_graph {
         return;
     }
 
diff --git a/compiler/rustc_incremental/src/persist/fs.rs b/compiler/rustc_incremental/src/persist/fs.rs
index 9b328842056..25c1b2e1c43 100644
--- a/compiler/rustc_incremental/src/persist/fs.rs
+++ b/compiler/rustc_incremental/src/persist/fs.rs
@@ -447,7 +447,7 @@ fn copy_files(sess: &Session, target_dir: &Path, source_dir: &Path) -> Result<bo
         }
     }
 
-    if sess.opts.debugging_opts.incremental_info {
+    if sess.opts.unstable_opts.incremental_info {
         eprintln!(
             "[incremental] session directory: \
                   {} files hard-linked",
diff --git a/compiler/rustc_incremental/src/persist/load.rs b/compiler/rustc_incremental/src/persist/load.rs
index f59d8d596b9..1c5fd916902 100644
--- a/compiler/rustc_incremental/src/persist/load.rs
+++ b/compiler/rustc_incremental/src/persist/load.rs
@@ -141,7 +141,7 @@ pub fn load_dep_graph(sess: &Session) -> DepGraphFuture {
     // Calling `sess.incr_comp_session_dir()` will panic if `sess.opts.incremental.is_none()`.
     // Fortunately, we just checked that this isn't the case.
     let path = dep_graph_path(&sess);
-    let report_incremental_info = sess.opts.debugging_opts.incremental_info;
+    let report_incremental_info = sess.opts.unstable_opts.incremental_info;
     let expected_hash = sess.opts.dep_tracking_hash(false);
 
     let mut prev_work_products = FxHashMap::default();
@@ -163,7 +163,7 @@ pub fn load_dep_graph(sess: &Session) -> DepGraphFuture {
             for swp in work_products {
                 let all_files_exist = swp.work_product.saved_files.iter().all(|(_, path)| {
                     let exists = in_incr_comp_dir_sess(sess, path).exists();
-                    if !exists && sess.opts.debugging_opts.incremental_info {
+                    if !exists && sess.opts.unstable_opts.incremental_info {
                         eprintln!("incremental: could not find file for work product: {path}",);
                     }
                     exists
@@ -225,7 +225,7 @@ pub fn load_query_result_cache<'a, C: OnDiskCache<'a>>(sess: &'a Session) -> Opt
     let _prof_timer = sess.prof.generic_activity("incr_comp_load_query_result_cache");
 
     match load_data(
-        sess.opts.debugging_opts.incremental_info,
+        sess.opts.unstable_opts.incremental_info,
         &query_cache_path(sess),
         sess.is_nightly_build(),
     ) {
diff --git a/compiler/rustc_incremental/src/persist/save.rs b/compiler/rustc_incremental/src/persist/save.rs
index 4059b7cfc8e..71035031497 100644
--- a/compiler/rustc_incremental/src/persist/save.rs
+++ b/compiler/rustc_incremental/src/persist/save.rs
@@ -39,7 +39,7 @@ pub fn save_dep_graph(tcx: TyCtxt<'_>) {
         sess.time("assert_dep_graph", || crate::assert_dep_graph(tcx));
         sess.time("check_dirty_clean", || dirty_clean::check_dirty_clean_annotations(tcx));
 
-        if sess.opts.debugging_opts.incremental_info {
+        if sess.opts.unstable_opts.incremental_info {
             tcx.dep_graph.print_incremental_info()
         }
 
@@ -182,7 +182,7 @@ pub fn build_dep_graph(
         prev_graph,
         prev_work_products,
         encoder,
-        sess.opts.debugging_opts.query_dep_graph,
-        sess.opts.debugging_opts.incremental_info,
+        sess.opts.unstable_opts.query_dep_graph,
+        sess.opts.unstable_opts.incremental_info,
     ))
 }
diff --git a/compiler/rustc_infer/src/infer/higher_ranked/mod.rs b/compiler/rustc_infer/src/infer/higher_ranked/mod.rs
index 12c44b4baaa..e543ae1fcda 100644
--- a/compiler/rustc_infer/src/infer/higher_ranked/mod.rs
+++ b/compiler/rustc_infer/src/infer/higher_ranked/mod.rs
@@ -122,7 +122,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
         // subtyping errors that it would have caught will now be
         // caught later on, during region checking. However, we
         // continue to use it for a transition period.
-        if self.tcx.sess.opts.debugging_opts.no_leak_check || self.skip_leak_check.get() {
+        if self.tcx.sess.opts.unstable_opts.no_leak_check || self.skip_leak_check.get() {
             return Ok(());
         }
 
diff --git a/compiler/rustc_interface/src/interface.rs b/compiler/rustc_interface/src/interface.rs
index e7563933c88..6c7ddb4531e 100644
--- a/compiler/rustc_interface/src/interface.rs
+++ b/compiler/rustc_interface/src/interface.rs
@@ -300,7 +300,7 @@ pub fn create_compiler_and_run<R>(config: Config, f: impl FnOnce(&Compiler) -> R
         );
     }
 
-    let temps_dir = sess.opts.debugging_opts.temps_dir.as_ref().map(|o| PathBuf::from(&o));
+    let temps_dir = sess.opts.unstable_opts.temps_dir.as_ref().map(|o| PathBuf::from(&o));
 
     let compiler = Compiler {
         sess,
@@ -333,7 +333,7 @@ pub fn run_compiler<R: Send>(config: Config, f: impl FnOnce(&Compiler) -> R + Se
     tracing::trace!("run_compiler");
     util::run_in_thread_pool_with_globals(
         config.opts.edition,
-        config.opts.debugging_opts.threads,
+        config.opts.unstable_opts.threads,
         || create_compiler_and_run(config, f),
     )
 }
diff --git a/compiler/rustc_interface/src/passes.rs b/compiler/rustc_interface/src/passes.rs
index b7d1d6edfaa..97b8139f9da 100644
--- a/compiler/rustc_interface/src/passes.rs
+++ b/compiler/rustc_interface/src/passes.rs
@@ -58,16 +58,16 @@ pub fn parse<'a>(sess: &'a Session, input: &Input) -> PResult<'a, ast::Crate> {
         }
     })?;
 
-    if sess.opts.debugging_opts.input_stats {
+    if sess.opts.unstable_opts.input_stats {
         eprintln!("Lines of code:             {}", sess.source_map().count_lines());
         eprintln!("Pre-expansion node count:  {}", count_nodes(&krate));
     }
 
-    if let Some(ref s) = sess.opts.debugging_opts.show_span {
+    if let Some(ref s) = sess.opts.unstable_opts.show_span {
         rustc_ast_passes::show_span::run(sess.diagnostic(), s, &krate);
     }
 
-    if sess.opts.debugging_opts.hir_stats {
+    if sess.opts.unstable_opts.hir_stats {
         hir_stats::print_ast_stats(&krate, "PRE EXPANSION AST STATS");
     }
 
@@ -181,7 +181,7 @@ pub fn register_plugins<'a>(
         rustc_builtin_macros::cmdline_attrs::inject(
             krate,
             &sess.parse_sess,
-            &sess.opts.debugging_opts.crate_attr,
+            &sess.opts.unstable_opts.crate_attr,
         )
     });
 
@@ -213,7 +213,7 @@ pub fn register_plugins<'a>(
     }
 
     let mut lint_store = rustc_lint::new_lint_store(
-        sess.opts.debugging_opts.no_interleave_lints,
+        sess.opts.unstable_opts.no_interleave_lints,
         sess.unstable_options(),
     );
     register_lints(sess, &mut lint_store);
@@ -327,10 +327,10 @@ pub fn configure_and_expand(
         let cfg = rustc_expand::expand::ExpansionConfig {
             features: Some(features),
             recursion_limit,
-            trace_mac: sess.opts.debugging_opts.trace_macros,
+            trace_mac: sess.opts.unstable_opts.trace_macros,
             should_test: sess.opts.test,
-            span_debug: sess.opts.debugging_opts.span_debug,
-            proc_macro_backtrace: sess.opts.debugging_opts.proc_macro_backtrace,
+            span_debug: sess.opts.unstable_opts.span_debug,
+            proc_macro_backtrace: sess.opts.unstable_opts.proc_macro_backtrace,
             ..rustc_expand::expand::ExpansionConfig::default(crate_name.to_string())
         };
 
@@ -413,11 +413,11 @@ pub fn configure_and_expand(
 
     // Done with macro expansion!
 
-    if sess.opts.debugging_opts.input_stats {
+    if sess.opts.unstable_opts.input_stats {
         eprintln!("Post-expansion node count: {}", count_nodes(&krate));
     }
 
-    if sess.opts.debugging_opts.hir_stats {
+    if sess.opts.unstable_opts.hir_stats {
         hir_stats::print_ast_stats(&krate, "POST EXPANSION AST STATS");
     }
 
@@ -500,7 +500,7 @@ fn generated_output_paths(
                     out_filenames.push(p);
                 }
             }
-            OutputType::DepInfo if sess.opts.debugging_opts.dep_info_omit_d_target => {
+            OutputType::DepInfo if sess.opts.unstable_opts.dep_info_omit_d_target => {
                 // Don't add the dep-info output when omitting it from dep-info targets
             }
             _ => {
@@ -598,7 +598,7 @@ fn write_out_deps(
         files.extend(extra_tracked_files);
 
         if sess.binary_dep_depinfo() {
-            if let Some(ref backend) = sess.opts.debugging_opts.codegen_backend {
+            if let Some(ref backend) = sess.opts.unstable_opts.codegen_backend {
                 if backend.contains('.') {
                     // If the backend name contain a `.`, it is the path to an external dynamic
                     // library. If not, it is not a path.
@@ -928,7 +928,7 @@ fn analysis(tcx: TyCtxt<'_>, (): ()) -> Result<()> {
     sess.time("MIR_effect_checking", || {
         for def_id in tcx.hir().body_owners() {
             tcx.ensure().thir_check_unsafety(def_id);
-            if !tcx.sess.opts.debugging_opts.thir_unsafeck {
+            if !tcx.sess.opts.unstable_opts.thir_unsafeck {
                 rustc_mir_transform::check_unsafety::check_unsafety(tcx, def_id);
             }
             tcx.ensure().has_ffi_unwind_calls(def_id);
diff --git a/compiler/rustc_interface/src/queries.rs b/compiler/rustc_interface/src/queries.rs
index 8ffb1ad0539..73402ae0842 100644
--- a/compiler/rustc_interface/src/queries.rs
+++ b/compiler/rustc_interface/src/queries.rs
@@ -357,7 +357,7 @@ impl Linker {
             return Ok(());
         }
 
-        if sess.opts.debugging_opts.no_link {
+        if sess.opts.unstable_opts.no_link {
             let encoded = CodegenResults::serialize_rlink(&codegen_results);
             let rlink_file = self.prepare_outputs.with_extension(config::RLINK_EXT);
             std::fs::write(&rlink_file, encoded).map_err(|err| {
diff --git a/compiler/rustc_interface/src/tests.rs b/compiler/rustc_interface/src/tests.rs
index 55827ff583a..9c0b534798e 100644
--- a/compiler/rustc_interface/src/tests.rs
+++ b/compiler/rustc_interface/src/tests.rs
@@ -629,14 +629,14 @@ fn test_top_level_options_tracked_no_crate() {
 }
 
 #[test]
-fn test_debugging_options_tracking_hash() {
+fn test_unstable_options_tracking_hash() {
     let reference = Options::default();
     let mut opts = Options::default();
 
     macro_rules! untracked {
         ($name: ident, $non_default_value: expr) => {
-            assert_ne!(opts.debugging_opts.$name, $non_default_value);
-            opts.debugging_opts.$name = $non_default_value;
+            assert_ne!(opts.unstable_opts.$name, $non_default_value);
+            opts.unstable_opts.$name = $non_default_value;
             assert_same_hash(&reference, &opts);
         };
     }
@@ -705,8 +705,8 @@ fn test_debugging_options_tracking_hash() {
     macro_rules! tracked {
         ($name: ident, $non_default_value: expr) => {
             opts = reference.clone();
-            assert_ne!(opts.debugging_opts.$name, $non_default_value);
-            opts.debugging_opts.$name = $non_default_value;
+            assert_ne!(opts.unstable_opts.$name, $non_default_value);
+            opts.unstable_opts.$name = $non_default_value;
             assert_different_hash(&reference, &opts);
         };
     }
@@ -804,8 +804,8 @@ fn test_debugging_options_tracking_hash() {
     macro_rules! tracked_no_crate_hash {
         ($name: ident, $non_default_value: expr) => {
             opts = reference.clone();
-            assert_ne!(opts.debugging_opts.$name, $non_default_value);
-            opts.debugging_opts.$name = $non_default_value;
+            assert_ne!(opts.unstable_opts.$name, $non_default_value);
+            opts.unstable_opts.$name = $non_default_value;
             assert_non_crate_hash_different(&reference, &opts);
         };
     }
diff --git a/compiler/rustc_interface/src/util.rs b/compiler/rustc_interface/src/util.rs
index f4b51b5a442..01173bff126 100644
--- a/compiler/rustc_interface/src/util.rs
+++ b/compiler/rustc_interface/src/util.rs
@@ -79,7 +79,7 @@ pub fn create_session(
     } else {
         get_codegen_backend(
             &sopts.maybe_sysroot,
-            sopts.debugging_opts.codegen_backend.as_ref().map(|name| &name[..]),
+            sopts.unstable_opts.codegen_backend.as_ref().map(|name| &name[..]),
         )
     };
 
@@ -89,9 +89,9 @@ pub fn create_session(
     let bundle = match rustc_errors::fluent_bundle(
         sopts.maybe_sysroot.clone(),
         sysroot_candidates(),
-        sopts.debugging_opts.translate_lang.clone(),
-        sopts.debugging_opts.translate_additional_ftl.as_deref(),
-        sopts.debugging_opts.translate_directionality_markers,
+        sopts.unstable_opts.translate_lang.clone(),
+        sopts.unstable_opts.translate_additional_ftl.as_deref(),
+        sopts.unstable_opts.translate_directionality_markers,
     ) {
         Ok(bundle) => bundle,
         Err(e) => {
diff --git a/compiler/rustc_lint/src/early.rs b/compiler/rustc_lint/src/early.rs
index 5de35dc0856..3d42325d544 100644
--- a/compiler/rustc_lint/src/early.rs
+++ b/compiler/rustc_lint/src/early.rs
@@ -416,7 +416,7 @@ pub fn check_ast_node<'a>(
     let mut passes: Vec<_> = passes.iter().map(|p| (p)()).collect();
     let mut buffered = lint_buffer.unwrap_or_default();
 
-    if sess.opts.debugging_opts.no_interleave_lints {
+    if sess.opts.unstable_opts.no_interleave_lints {
         for (i, pass) in passes.iter_mut().enumerate() {
             buffered =
                 sess.prof.extra_verbose_generic_activity("run_lint", pass.name()).run(|| {
diff --git a/compiler/rustc_lint/src/late.rs b/compiler/rustc_lint/src/late.rs
index 27f67207209..afb18451cf3 100644
--- a/compiler/rustc_lint/src/late.rs
+++ b/compiler/rustc_lint/src/late.rs
@@ -402,7 +402,7 @@ pub fn late_lint_mod<'tcx, T: LateLintPass<'tcx>>(
     module_def_id: LocalDefId,
     builtin_lints: T,
 ) {
-    if tcx.sess.opts.debugging_opts.no_interleave_lints {
+    if tcx.sess.opts.unstable_opts.no_interleave_lints {
         // These passes runs in late_lint_crate with -Z no_interleave_lints
         return;
     }
@@ -448,7 +448,7 @@ fn late_lint_pass_crate<'tcx, T: LateLintPass<'tcx>>(tcx: TyCtxt<'tcx>, pass: T)
 fn late_lint_crate<'tcx, T: LateLintPass<'tcx>>(tcx: TyCtxt<'tcx>, builtin_lints: T) {
     let mut passes = unerased_lint_store(tcx).late_passes.iter().map(|p| (p)()).collect::<Vec<_>>();
 
-    if !tcx.sess.opts.debugging_opts.no_interleave_lints {
+    if !tcx.sess.opts.unstable_opts.no_interleave_lints {
         if !passes.is_empty() {
             late_lint_pass_crate(tcx, LateLintPassObjects { lints: &mut passes[..] });
         }
diff --git a/compiler/rustc_metadata/src/creader.rs b/compiler/rustc_metadata/src/creader.rs
index cb50c0fb738..708d0b1fd8a 100644
--- a/compiler/rustc_metadata/src/creader.rs
+++ b/compiler/rustc_metadata/src/creader.rs
@@ -456,7 +456,7 @@ impl<'a> CrateLoader<'a> {
         proc_macro_locator.is_proc_macro = true;
 
         // Load the proc macro crate for the target
-        let (locator, target_result) = if self.sess.opts.debugging_opts.dual_proc_macros {
+        let (locator, target_result) = if self.sess.opts.unstable_opts.dual_proc_macros {
             proc_macro_locator.reset();
             let result = match self.load(&mut proc_macro_locator)? {
                 Some(LoadResult::Previous(cnum)) => {
@@ -485,7 +485,7 @@ impl<'a> CrateLoader<'a> {
             return Ok(None);
         };
 
-        Ok(Some(if self.sess.opts.debugging_opts.dual_proc_macros {
+        Ok(Some(if self.sess.opts.unstable_opts.dual_proc_macros {
             let host_result = match host_result {
                 LoadResult::Previous(..) => {
                     panic!("host and target proc macros must be loaded in lock-step")
@@ -762,9 +762,9 @@ impl<'a> CrateLoader<'a> {
     }
 
     fn inject_profiler_runtime(&mut self, krate: &ast::Crate) {
-        if self.sess.opts.debugging_opts.no_profiler_runtime
+        if self.sess.opts.unstable_opts.no_profiler_runtime
             || !(self.sess.instrument_coverage()
-                || self.sess.opts.debugging_opts.profile
+                || self.sess.opts.unstable_opts.profile
                 || self.sess.opts.cg.profile_generate.enabled())
         {
             return;
@@ -772,7 +772,7 @@ impl<'a> CrateLoader<'a> {
 
         info!("loading profiler");
 
-        let name = Symbol::intern(&self.sess.opts.debugging_opts.profiler_runtime);
+        let name = Symbol::intern(&self.sess.opts.unstable_opts.profiler_runtime);
         if name == sym::profiler_builtins && self.sess.contains_name(&krate.attrs, sym::no_core) {
             self.sess.err(
                 "`profiler_builtins` crate (required by compiler options) \
diff --git a/compiler/rustc_metadata/src/dependency_format.rs b/compiler/rustc_metadata/src/dependency_format.rs
index 770d164894a..b765c34f8e3 100644
--- a/compiler/rustc_metadata/src/dependency_format.rs
+++ b/compiler/rustc_metadata/src/dependency_format.rs
@@ -419,7 +419,7 @@ fn verify_ok(tcx: TyCtxt<'_>, list: &[Linkage]) {
             }
 
             let found_drop_strategy = tcx.panic_in_drop_strategy(cnum);
-            if tcx.sess.opts.debugging_opts.panic_in_drop != found_drop_strategy {
+            if tcx.sess.opts.unstable_opts.panic_in_drop != found_drop_strategy {
                 sess.err(&format!(
                     "the crate `{}` is compiled with the \
                                panic-in-drop strategy `{}` which is \
@@ -427,7 +427,7 @@ fn verify_ok(tcx: TyCtxt<'_>, list: &[Linkage]) {
                                strategy of `{}`",
                     tcx.crate_name(cnum),
                     found_drop_strategy.desc(),
-                    tcx.sess.opts.debugging_opts.panic_in_drop.desc()
+                    tcx.sess.opts.unstable_opts.panic_in_drop.desc()
                 ));
             }
         }
diff --git a/compiler/rustc_metadata/src/locator.rs b/compiler/rustc_metadata/src/locator.rs
index dbe53224e2a..a72bcb9a2db 100644
--- a/compiler/rustc_metadata/src/locator.rs
+++ b/compiler/rustc_metadata/src/locator.rs
@@ -1179,7 +1179,7 @@ impl CrateError {
                             err.help("consider building the standard library from source with `cargo build -Zbuild-std`");
                         }
                     } else if crate_name
-                        == Symbol::intern(&sess.opts.debugging_opts.profiler_runtime)
+                        == Symbol::intern(&sess.opts.unstable_opts.profiler_runtime)
                     {
                         err.note("the compiler may have been built without the profiler runtime");
                     } else if crate_name.as_str().starts_with("rustc_") {
diff --git a/compiler/rustc_metadata/src/rmeta/decoder.rs b/compiler/rustc_metadata/src/rmeta/decoder.rs
index f0ccf02c9fa..ef5cb88c8f9 100644
--- a/compiler/rustc_metadata/src/rmeta/decoder.rs
+++ b/compiler/rustc_metadata/src/rmeta/decoder.rs
@@ -1475,14 +1475,14 @@ impl<'a, 'tcx> CrateMetadataRef<'a> {
         // the `rust-src` component in `Src::run` in `src/bootstrap/dist.rs`.
         let virtual_rust_source_base_dir = [
             option_env!("CFG_VIRTUAL_RUST_SOURCE_BASE_DIR").map(PathBuf::from),
-            sess.opts.debugging_opts.simulate_remapped_rust_src_base.clone(),
+            sess.opts.unstable_opts.simulate_remapped_rust_src_base.clone(),
         ]
         .into_iter()
         .filter(|_| {
             // Only spend time on further checks if we have what to translate *to*.
             sess.opts.real_rust_source_base_dir.is_some()
                 // Some tests need the translation to be always skipped.
-                && sess.opts.debugging_opts.translate_remapped_path_to_local_path
+                && sess.opts.unstable_opts.translate_remapped_path_to_local_path
         })
         .flatten()
         .filter(|virtual_dir| {
@@ -1584,7 +1584,7 @@ impl<'a, 'tcx> CrateMetadataRef<'a> {
                     // `try_to_translate_virtual_to_real` don't have to worry about how the
                     // compiler is bootstrapped.
                     if let Some(virtual_dir) =
-                        &sess.opts.debugging_opts.simulate_remapped_rust_src_base
+                        &sess.opts.unstable_opts.simulate_remapped_rust_src_base
                     {
                         if let Some(real_dir) = &sess.opts.real_rust_source_base_dir {
                             if let rustc_span::FileName::Real(ref mut old_name) = name {
diff --git a/compiler/rustc_metadata/src/rmeta/encoder.rs b/compiler/rustc_metadata/src/rmeta/encoder.rs
index caf5965c3a4..cd6847245e6 100644
--- a/compiler/rustc_metadata/src/rmeta/encoder.rs
+++ b/compiler/rustc_metadata/src/rmeta/encoder.rs
@@ -665,7 +665,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
             hash: tcx.crate_hash(LOCAL_CRATE),
             stable_crate_id: tcx.def_path_hash(LOCAL_CRATE.as_def_id()).stable_crate_id(),
             required_panic_strategy: tcx.required_panic_strategy(LOCAL_CRATE),
-            panic_in_drop_strategy: tcx.sess.opts.debugging_opts.panic_in_drop,
+            panic_in_drop_strategy: tcx.sess.opts.unstable_opts.panic_in_drop,
             edition: tcx.sess.edition(),
             has_global_allocator: tcx.has_global_allocator(LOCAL_CRATE),
             has_panic_handler: tcx.has_panic_handler(LOCAL_CRATE),
@@ -862,7 +862,7 @@ fn should_encode_mir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> (bool, bool) {
         // Constructors
         DefKind::Ctor(_, _) => {
             let mir_opt_base = tcx.sess.opts.output_types.should_codegen()
-                || tcx.sess.opts.debugging_opts.always_encode_mir;
+                || tcx.sess.opts.unstable_opts.always_encode_mir;
             (true, mir_opt_base)
         }
         // Constants
@@ -880,7 +880,7 @@ fn should_encode_mir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> (bool, bool) {
             // The function has a `const` modifier or is in a `#[const_trait]`.
             let is_const_fn = tcx.is_const_fn_raw(def_id.to_def_id())
                 || tcx.is_const_default_method(def_id.to_def_id());
-            let always_encode_mir = tcx.sess.opts.debugging_opts.always_encode_mir;
+            let always_encode_mir = tcx.sess.opts.unstable_opts.always_encode_mir;
             (is_const_fn, needs_inline || always_encode_mir)
         }
         // Closures can't be const fn.
@@ -889,7 +889,7 @@ fn should_encode_mir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> (bool, bool) {
             let needs_inline = (generics.requires_monomorphization(tcx)
                 || tcx.codegen_fn_attrs(def_id).requests_inline())
                 && tcx.sess.opts.output_types.should_codegen();
-            let always_encode_mir = tcx.sess.opts.debugging_opts.always_encode_mir;
+            let always_encode_mir = tcx.sess.opts.unstable_opts.always_encode_mir;
             (false, needs_inline || always_encode_mir)
         }
         // Generators require optimized MIR to compute layout.
@@ -1360,7 +1360,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
 
         // The query lookup can take a measurable amount of time in crates with many items. Check if
         // the stability attributes are even enabled before using their queries.
-        if self.feat.staged_api || self.tcx.sess.opts.debugging_opts.force_unstable_if_unmarked {
+        if self.feat.staged_api || self.tcx.sess.opts.unstable_opts.force_unstable_if_unmarked {
             if let Some(stab) = self.tcx.lookup_stability(def_id) {
                 record!(self.tables.lookup_stability[def_id] <- stab)
             }
@@ -1372,7 +1372,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
 
         // The query lookup can take a measurable amount of time in crates with many items. Check if
         // the stability attributes are even enabled before using their queries.
-        if self.feat.staged_api || self.tcx.sess.opts.debugging_opts.force_unstable_if_unmarked {
+        if self.feat.staged_api || self.tcx.sess.opts.unstable_opts.force_unstable_if_unmarked {
             if let Some(stab) = self.tcx.lookup_const_stability(def_id) {
                 record!(self.tables.lookup_const_stability[def_id] <- stab)
             }
diff --git a/compiler/rustc_middle/src/hir/map/mod.rs b/compiler/rustc_middle/src/hir/map/mod.rs
index 3e99ba5742a..d3e10fce8a0 100644
--- a/compiler/rustc_middle/src/hir/map/mod.rs
+++ b/compiler/rustc_middle/src/hir/map/mod.rs
@@ -1149,7 +1149,7 @@ pub(super) fn crate_hash(tcx: TyCtxt<'_>, crate_num: CrateNum) -> Svh {
         hir_body_hash.hash_stable(&mut hcx, &mut stable_hasher);
         upstream_crates.hash_stable(&mut hcx, &mut stable_hasher);
         source_file_names.hash_stable(&mut hcx, &mut stable_hasher);
-        if tcx.sess.opts.debugging_opts.incremental_relative_spans {
+        if tcx.sess.opts.unstable_opts.incremental_relative_spans {
             let definitions = tcx.definitions_untracked();
             let mut owner_spans: Vec<_> = krate
                 .owners
diff --git a/compiler/rustc_middle/src/lint.rs b/compiler/rustc_middle/src/lint.rs
index 4b156de410d..2f45222de47 100644
--- a/compiler/rustc_middle/src/lint.rs
+++ b/compiler/rustc_middle/src/lint.rs
@@ -300,7 +300,7 @@ pub fn struct_lint_level<'s, 'd>(
 
         let has_future_breakage = future_incompatible.map_or(
             // Default allow lints trigger too often for testing.
-            sess.opts.debugging_opts.future_incompat_test && lint.default_level != Level::Allow,
+            sess.opts.unstable_opts.future_incompat_test && lint.default_level != Level::Allow,
             |incompat| {
                 matches!(incompat.reason, FutureIncompatibilityReason::FutureReleaseErrorReportNow)
             },
diff --git a/compiler/rustc_middle/src/middle/limits.rs b/compiler/rustc_middle/src/middle/limits.rs
index 20dcb670cd6..acced0492ef 100644
--- a/compiler/rustc_middle/src/middle/limits.rs
+++ b/compiler/rustc_middle/src/middle/limits.rs
@@ -25,7 +25,7 @@ pub fn provide(providers: &mut ty::query::Providers) {
             tcx.hir().krate_attrs(),
             tcx.sess,
             sym::move_size_limit,
-            tcx.sess.opts.debugging_opts.move_size_limit.unwrap_or(0),
+            tcx.sess.opts.unstable_opts.move_size_limit.unwrap_or(0),
         ),
         type_length_limit: get_limit(
             tcx.hir().krate_attrs(),
diff --git a/compiler/rustc_middle/src/middle/stability.rs b/compiler/rustc_middle/src/middle/stability.rs
index 802b7852bac..2de8d318090 100644
--- a/compiler/rustc_middle/src/middle/stability.rs
+++ b/compiler/rustc_middle/src/middle/stability.rs
@@ -443,7 +443,7 @@ impl<'tcx> TyCtxt<'tcx> {
                 // compiling a compiler crate), then let this missing feature
                 // annotation slide.
                 if feature == sym::rustc_private && issue == NonZeroU32::new(27812) {
-                    if self.sess.opts.debugging_opts.force_unstable_if_unmarked {
+                    if self.sess.opts.unstable_opts.force_unstable_if_unmarked {
                         return EvalResult::Allow;
                     }
                 }
diff --git a/compiler/rustc_middle/src/mir/generic_graph.rs b/compiler/rustc_middle/src/mir/generic_graph.rs
index a4d78911b27..f3621cd99d3 100644
--- a/compiler/rustc_middle/src/mir/generic_graph.rs
+++ b/compiler/rustc_middle/src/mir/generic_graph.rs
@@ -8,7 +8,7 @@ pub fn mir_fn_to_generic_graph<'tcx>(tcx: TyCtxt<'tcx>, body: &Body<'_>) -> Grap
     let def_id = body.source.def_id();
     let def_name = graphviz_safe_def_name(def_id);
     let graph_name = format!("Mir_{}", def_name);
-    let dark_mode = tcx.sess.opts.debugging_opts.graphviz_dark_mode;
+    let dark_mode = tcx.sess.opts.unstable_opts.graphviz_dark_mode;
 
     // Nodes
     let nodes: Vec<Node> = body
diff --git a/compiler/rustc_middle/src/mir/generic_graphviz.rs b/compiler/rustc_middle/src/mir/generic_graphviz.rs
index c907680bda1..11ac45943ac 100644
--- a/compiler/rustc_middle/src/mir/generic_graphviz.rs
+++ b/compiler/rustc_middle/src/mir/generic_graphviz.rs
@@ -56,11 +56,11 @@ impl<
         writeln!(w, "{} {}{} {{", kind, cluster, self.graphviz_name)?;
 
         // Global graph properties
-        let font = format!(r#"fontname="{}""#, tcx.sess.opts.debugging_opts.graphviz_font);
+        let font = format!(r#"fontname="{}""#, tcx.sess.opts.unstable_opts.graphviz_font);
         let mut graph_attrs = vec![&font[..]];
         let mut content_attrs = vec![&font[..]];
 
-        let dark_mode = tcx.sess.opts.debugging_opts.graphviz_dark_mode;
+        let dark_mode = tcx.sess.opts.unstable_opts.graphviz_dark_mode;
         if dark_mode {
             graph_attrs.push(r#"bgcolor="black""#);
             graph_attrs.push(r#"fontcolor="white""#);
diff --git a/compiler/rustc_middle/src/mir/graphviz.rs b/compiler/rustc_middle/src/mir/graphviz.rs
index 92c7a358c0a..5de56dad07a 100644
--- a/compiler/rustc_middle/src/mir/graphviz.rs
+++ b/compiler/rustc_middle/src/mir/graphviz.rs
@@ -57,11 +57,11 @@ where
     W: Write,
 {
     // Global graph properties
-    let font = format!(r#"fontname="{}""#, tcx.sess.opts.debugging_opts.graphviz_font);
+    let font = format!(r#"fontname="{}""#, tcx.sess.opts.unstable_opts.graphviz_font);
     let mut graph_attrs = vec![&font[..]];
     let mut content_attrs = vec![&font[..]];
 
-    let dark_mode = tcx.sess.opts.debugging_opts.graphviz_dark_mode;
+    let dark_mode = tcx.sess.opts.unstable_opts.graphviz_dark_mode;
     if dark_mode {
         graph_attrs.push(r#"bgcolor="black""#);
         graph_attrs.push(r#"fontcolor="white""#);
diff --git a/compiler/rustc_middle/src/mir/mod.rs b/compiler/rustc_middle/src/mir/mod.rs
index 333a88ba520..f61cb7e8c47 100644
--- a/compiler/rustc_middle/src/mir/mod.rs
+++ b/compiler/rustc_middle/src/mir/mod.rs
@@ -1884,7 +1884,7 @@ impl<'tcx> Debug for Rvalue<'tcx> {
 
                 // When printing regions, add trailing space if necessary.
                 let print_region = ty::tls::with(|tcx| {
-                    tcx.sess.verbose() || tcx.sess.opts.debugging_opts.identify_regions
+                    tcx.sess.verbose() || tcx.sess.opts.unstable_opts.identify_regions
                 });
                 let region = if print_region {
                     let mut region = region.to_string();
@@ -1954,7 +1954,7 @@ impl<'tcx> Debug for Rvalue<'tcx> {
 
                     AggregateKind::Closure(def_id, substs) => ty::tls::with(|tcx| {
                         if let Some(def_id) = def_id.as_local() {
-                            let name = if tcx.sess.opts.debugging_opts.span_free_formats {
+                            let name = if tcx.sess.opts.unstable_opts.span_free_formats {
                                 let substs = tcx.lift(substs).unwrap();
                                 format!(
                                     "[closure@{}]",
diff --git a/compiler/rustc_middle/src/mir/mono.rs b/compiler/rustc_middle/src/mir/mono.rs
index 021f2782736..8b51c5b3da5 100644
--- a/compiler/rustc_middle/src/mir/mono.rs
+++ b/compiler/rustc_middle/src/mir/mono.rs
@@ -90,7 +90,7 @@ impl<'tcx> MonoItem<'tcx> {
         let generate_cgu_internal_copies = tcx
             .sess
             .opts
-            .debugging_opts
+            .unstable_opts
             .inline_in_all_cgus
             .unwrap_or_else(|| tcx.sess.opts.optimize != OptLevel::No)
             && !tcx.sess.link_dead_code();
@@ -459,7 +459,7 @@ impl<'tcx> CodegenUnitNameBuilder<'tcx> {
     {
         let cgu_name = self.build_cgu_name_no_mangle(cnum, components, special_suffix);
 
-        if self.tcx.sess.opts.debugging_opts.human_readable_cgu_names {
+        if self.tcx.sess.opts.unstable_opts.human_readable_cgu_names {
             cgu_name
         } else {
             Symbol::intern(&CodegenUnit::mangle_name(cgu_name.as_str()))
diff --git a/compiler/rustc_middle/src/mir/pretty.rs b/compiler/rustc_middle/src/mir/pretty.rs
index e2fa37ee7be..970043d427f 100644
--- a/compiler/rustc_middle/src/mir/pretty.rs
+++ b/compiler/rustc_middle/src/mir/pretty.rs
@@ -90,7 +90,7 @@ pub fn dump_mir<'tcx, F>(
 }
 
 pub fn dump_enabled<'tcx>(tcx: TyCtxt<'tcx>, pass_name: &str, def_id: DefId) -> bool {
-    let Some(ref filters) = tcx.sess.opts.debugging_opts.dump_mir else {
+    let Some(ref filters) = tcx.sess.opts.unstable_opts.dump_mir else {
         return false;
     };
     // see notes on #41697 below
@@ -141,7 +141,7 @@ fn dump_matched_mir_node<'tcx, F>(
         extra_data(PassWhere::AfterCFG, &mut file)?;
     };
 
-    if tcx.sess.opts.debugging_opts.dump_mir_graphviz {
+    if tcx.sess.opts.unstable_opts.dump_mir_graphviz {
         let _: io::Result<()> = try {
             let mut file =
                 create_dump_file(tcx, "dot", pass_num, pass_name, disambiguator, body.source)?;
@@ -149,7 +149,7 @@ fn dump_matched_mir_node<'tcx, F>(
         };
     }
 
-    if let Some(spanview) = tcx.sess.opts.debugging_opts.dump_mir_spanview {
+    if let Some(spanview) = tcx.sess.opts.unstable_opts.dump_mir_spanview {
         let _: io::Result<()> = try {
             let file_basename =
                 dump_file_basename(tcx, pass_num, pass_name, disambiguator, body.source);
@@ -175,7 +175,7 @@ fn dump_file_basename<'tcx>(
         None => String::new(),
     };
 
-    let pass_num = if tcx.sess.opts.debugging_opts.dump_mir_exclude_pass_number {
+    let pass_num = if tcx.sess.opts.unstable_opts.dump_mir_exclude_pass_number {
         String::new()
     } else {
         match pass_num {
@@ -214,7 +214,7 @@ fn dump_file_basename<'tcx>(
 /// graphviz data or other things.
 fn dump_path(tcx: TyCtxt<'_>, basename: &str, extension: &str) -> PathBuf {
     let mut file_path = PathBuf::new();
-    file_path.push(Path::new(&tcx.sess.opts.debugging_opts.dump_mir_dir));
+    file_path.push(Path::new(&tcx.sess.opts.unstable_opts.dump_mir_dir));
 
     let file_name = format!("{}.{}", basename, extension,);
 
diff --git a/compiler/rustc_middle/src/ty/instance.rs b/compiler/rustc_middle/src/ty/instance.rs
index 391abdbe84c..4f9bbc135ec 100644
--- a/compiler/rustc_middle/src/ty/instance.rs
+++ b/compiler/rustc_middle/src/ty/instance.rs
@@ -605,7 +605,7 @@ impl<'tcx> Instance<'tcx> {
     /// identity parameters if they are determined to be unused in `instance.def`.
     pub fn polymorphize(self, tcx: TyCtxt<'tcx>) -> Self {
         debug!("polymorphize: running polymorphization analysis");
-        if !tcx.sess.opts.debugging_opts.polymorphize {
+        if !tcx.sess.opts.unstable_opts.polymorphize {
             return self;
         }
 
diff --git a/compiler/rustc_middle/src/ty/layout.rs b/compiler/rustc_middle/src/ty/layout.rs
index 1ed41db099c..71c93d05792 100644
--- a/compiler/rustc_middle/src/ty/layout.rs
+++ b/compiler/rustc_middle/src/ty/layout.rs
@@ -1914,7 +1914,7 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> {
     fn record_layout_for_printing(&self, layout: TyAndLayout<'tcx>) {
         // If we are running with `-Zprint-type-sizes`, maybe record layouts
         // for dumping later.
-        if self.tcx.sess.opts.debugging_opts.print_type_sizes {
+        if self.tcx.sess.opts.unstable_opts.print_type_sizes {
             self.record_layout_for_printing_outlined(layout)
         }
     }
@@ -2916,7 +2916,7 @@ pub fn fn_can_unwind<'tcx>(tcx: TyCtxt<'tcx>, fn_def_id: Option<DefId>, abi: Spe
         //
         // This is not part of `codegen_fn_attrs` as it can differ between crates
         // and therefore cannot be computed in core.
-        if tcx.sess.opts.debugging_opts.panic_in_drop == PanicStrategy::Abort {
+        if tcx.sess.opts.unstable_opts.panic_in_drop == PanicStrategy::Abort {
             if Some(did) == tcx.lang_items().drop_in_place_fn() {
                 return false;
             }
diff --git a/compiler/rustc_middle/src/ty/mod.rs b/compiler/rustc_middle/src/ty/mod.rs
index c2c7b3df844..22a1fd34e27 100644
--- a/compiler/rustc_middle/src/ty/mod.rs
+++ b/compiler/rustc_middle/src/ty/mod.rs
@@ -1761,7 +1761,7 @@ impl ReprOptions {
         // If the user defined a custom seed for layout randomization, xor the item's
         // path hash with the user defined seed, this will allowing determinism while
         // still allowing users to further randomize layout generation for e.g. fuzzing
-        if let Some(user_seed) = tcx.sess.opts.debugging_opts.layout_seed {
+        if let Some(user_seed) = tcx.sess.opts.unstable_opts.layout_seed {
             field_shuffle_seed ^= user_seed;
         }
 
@@ -1794,7 +1794,7 @@ impl ReprOptions {
 
         // If `-Z randomize-layout` was enabled for the type definition then we can
         // consider performing layout randomization
-        if tcx.sess.opts.debugging_opts.randomize_layout {
+        if tcx.sess.opts.unstable_opts.randomize_layout {
             flags.insert(ReprFlags::RANDOMIZE_LAYOUT);
         }
 
diff --git a/compiler/rustc_middle/src/ty/print/pretty.rs b/compiler/rustc_middle/src/ty/print/pretty.rs
index f721a175c98..81c4d2ae346 100644
--- a/compiler/rustc_middle/src/ty/print/pretty.rs
+++ b/compiler/rustc_middle/src/ty/print/pretty.rs
@@ -297,7 +297,7 @@ pub trait PrettyPrinter<'tcx>:
         mut self,
         def_id: DefId,
     ) -> Result<(Self::Path, bool), Self::Error> {
-        if !self.tcx().sess.opts.debugging_opts.trim_diagnostic_paths
+        if !self.tcx().sess.opts.unstable_opts.trim_diagnostic_paths
             || matches!(self.tcx().sess.opts.trimmed_def_paths, TrimmedDefPaths::Never)
             || NO_TRIMMED_PATH.with(|flag| flag.get())
             || SHOULD_PREFIX_WITH_CRATE.with(|flag| flag.get())
@@ -712,7 +712,7 @@ pub trait PrettyPrinter<'tcx>:
                     p!(write("closure"));
                     // FIXME(eddyb) should use `def_span`.
                     if let Some(did) = did.as_local() {
-                        if self.tcx().sess.opts.debugging_opts.span_free_formats {
+                        if self.tcx().sess.opts.unstable_opts.span_free_formats {
                             p!("@", print_def_path(did.to_def_id(), substs));
                         } else {
                             let span = self.tcx().def_span(did);
@@ -1919,7 +1919,7 @@ impl<'tcx> PrettyPrinter<'tcx> for FmtPrinter<'_, 'tcx> {
             return true;
         }
 
-        let identify_regions = self.tcx.sess.opts.debugging_opts.identify_regions;
+        let identify_regions = self.tcx.sess.opts.unstable_opts.identify_regions;
 
         match *region {
             ty::ReEarlyBound(ref data) => {
@@ -1992,7 +1992,7 @@ impl<'tcx> FmtPrinter<'_, 'tcx> {
             return Ok(self);
         }
 
-        let identify_regions = self.tcx.sess.opts.debugging_opts.identify_regions;
+        let identify_regions = self.tcx.sess.opts.unstable_opts.identify_regions;
 
         // These printouts are concise.  They do not contain all the information
         // the user might want to diagnose an error, but there is basically no way
diff --git a/compiler/rustc_mir_build/src/check_unsafety.rs b/compiler/rustc_mir_build/src/check_unsafety.rs
index 8585199faaf..cbd790bd6df 100644
--- a/compiler/rustc_mir_build/src/check_unsafety.rs
+++ b/compiler/rustc_mir_build/src/check_unsafety.rs
@@ -632,7 +632,7 @@ impl UnsafeOpKind {
 
 pub fn check_unsafety<'tcx>(tcx: TyCtxt<'tcx>, def: ty::WithOptConstParam<LocalDefId>) {
     // THIR unsafeck is gated under `-Z thir-unsafeck`
-    if !tcx.sess.opts.debugging_opts.thir_unsafeck {
+    if !tcx.sess.opts.unstable_opts.thir_unsafeck {
         return;
     }
 
diff --git a/compiler/rustc_mir_dataflow/src/framework/engine.rs b/compiler/rustc_mir_dataflow/src/framework/engine.rs
index 180376d648a..f374658ceb6 100644
--- a/compiler/rustc_mir_dataflow/src/framework/engine.rs
+++ b/compiler/rustc_mir_dataflow/src/framework/engine.rs
@@ -289,7 +289,7 @@ where
             io::BufWriter::new(fs::File::create(&path)?)
         }
 
-        None if tcx.sess.opts.debugging_opts.dump_mir_dataflow
+        None if tcx.sess.opts.unstable_opts.dump_mir_dataflow
             && dump_enabled(tcx, A::NAME, def_id) =>
         {
             create_dump_file(
@@ -314,8 +314,8 @@ where
 
     let graphviz = graphviz::Formatter::new(body, results, style);
     let mut render_opts =
-        vec![dot::RenderOption::Fontname(tcx.sess.opts.debugging_opts.graphviz_font.clone())];
-    if tcx.sess.opts.debugging_opts.graphviz_dark_mode {
+        vec![dot::RenderOption::Fontname(tcx.sess.opts.unstable_opts.graphviz_font.clone())];
+    if tcx.sess.opts.unstable_opts.graphviz_dark_mode {
         render_opts.push(dot::RenderOption::DarkTheme);
     }
     dot::render_opts(&graphviz, &mut buf, &render_opts)?;
diff --git a/compiler/rustc_mir_dataflow/src/impls/mod.rs b/compiler/rustc_mir_dataflow/src/impls/mod.rs
index af6a1bb1545..fd1e492779f 100644
--- a/compiler/rustc_mir_dataflow/src/impls/mod.rs
+++ b/compiler/rustc_mir_dataflow/src/impls/mod.rs
@@ -317,7 +317,7 @@ impl<'tcx> GenKillAnalysis<'tcx> for MaybeInitializedPlaces<'_, 'tcx> {
             Self::update_bits(trans, path, s)
         });
 
-        if !self.tcx.sess.opts.debugging_opts.precise_enum_drop_elaboration {
+        if !self.tcx.sess.opts.unstable_opts.precise_enum_drop_elaboration {
             return;
         }
 
@@ -340,7 +340,7 @@ impl<'tcx> GenKillAnalysis<'tcx> for MaybeInitializedPlaces<'_, 'tcx> {
             Self::update_bits(trans, path, s)
         });
 
-        if !self.tcx.sess.opts.debugging_opts.precise_enum_drop_elaboration {
+        if !self.tcx.sess.opts.unstable_opts.precise_enum_drop_elaboration {
             return;
         }
 
@@ -379,7 +379,7 @@ impl<'tcx> GenKillAnalysis<'tcx> for MaybeInitializedPlaces<'_, 'tcx> {
         discr: &mir::Operand<'tcx>,
         edge_effects: &mut impl SwitchIntEdgeEffects<G>,
     ) {
-        if !self.tcx.sess.opts.debugging_opts.precise_enum_drop_elaboration {
+        if !self.tcx.sess.opts.unstable_opts.precise_enum_drop_elaboration {
             return;
         }
 
@@ -495,7 +495,7 @@ impl<'tcx> GenKillAnalysis<'tcx> for MaybeUninitializedPlaces<'_, 'tcx> {
         discr: &mir::Operand<'tcx>,
         edge_effects: &mut impl SwitchIntEdgeEffects<G>,
     ) {
-        if !self.tcx.sess.opts.debugging_opts.precise_enum_drop_elaboration {
+        if !self.tcx.sess.opts.unstable_opts.precise_enum_drop_elaboration {
             return;
         }
 
diff --git a/compiler/rustc_mir_transform/src/abort_unwinding_calls.rs b/compiler/rustc_mir_transform/src/abort_unwinding_calls.rs
index 2c8389e532d..2502e8b603c 100644
--- a/compiler/rustc_mir_transform/src/abort_unwinding_calls.rs
+++ b/compiler/rustc_mir_transform/src/abort_unwinding_calls.rs
@@ -75,7 +75,7 @@ impl<'tcx> MirPass<'tcx> for AbortUnwindingCalls {
                     layout::fn_can_unwind(tcx, fn_def_id, sig.abi())
                 }
                 TerminatorKind::Drop { .. } | TerminatorKind::DropAndReplace { .. } => {
-                    tcx.sess.opts.debugging_opts.panic_in_drop == PanicStrategy::Unwind
+                    tcx.sess.opts.unstable_opts.panic_in_drop == PanicStrategy::Unwind
                         && layout::fn_can_unwind(tcx, None, Abi::Rust)
                 }
                 TerminatorKind::Assert { .. } | TerminatorKind::FalseUnwind { .. } => {
diff --git a/compiler/rustc_mir_transform/src/add_retag.rs b/compiler/rustc_mir_transform/src/add_retag.rs
index 13ec1e7bb72..b91ae083cf5 100644
--- a/compiler/rustc_mir_transform/src/add_retag.rs
+++ b/compiler/rustc_mir_transform/src/add_retag.rs
@@ -72,7 +72,7 @@ fn may_contain_reference<'tcx>(ty: Ty<'tcx>, depth: u32, tcx: TyCtxt<'tcx>) -> b
 
 impl<'tcx> MirPass<'tcx> for AddRetag {
     fn is_enabled(&self, sess: &rustc_session::Session) -> bool {
-        sess.opts.debugging_opts.mir_emit_retag
+        sess.opts.unstable_opts.mir_emit_retag
     }
 
     fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
diff --git a/compiler/rustc_mir_transform/src/const_debuginfo.rs b/compiler/rustc_mir_transform/src/const_debuginfo.rs
index 48aea61b191..6f0ae4f07ab 100644
--- a/compiler/rustc_mir_transform/src/const_debuginfo.rs
+++ b/compiler/rustc_mir_transform/src/const_debuginfo.rs
@@ -16,7 +16,7 @@ pub struct ConstDebugInfo;
 
 impl<'tcx> MirPass<'tcx> for ConstDebugInfo {
     fn is_enabled(&self, sess: &rustc_session::Session) -> bool {
-        sess.opts.debugging_opts.unsound_mir_opts && sess.mir_opt_level() > 0
+        sess.opts.unstable_opts.unsound_mir_opts && sess.mir_opt_level() > 0
     }
 
     fn run_pass(&self, _tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
diff --git a/compiler/rustc_mir_transform/src/coverage/mod.rs b/compiler/rustc_mir_transform/src/coverage/mod.rs
index 88ad5b7ef14..2619626a567 100644
--- a/compiler/rustc_mir_transform/src/coverage/mod.rs
+++ b/compiler/rustc_mir_transform/src/coverage/mod.rs
@@ -160,8 +160,8 @@ impl<'a, 'tcx> Instrumentor<'a, 'tcx> {
         let mut debug_used_expressions = debug::UsedExpressions::new();
 
         let dump_mir = dump_enabled(tcx, self.pass_name, def_id);
-        let dump_graphviz = dump_mir && tcx.sess.opts.debugging_opts.dump_mir_graphviz;
-        let dump_spanview = dump_mir && tcx.sess.opts.debugging_opts.dump_mir_spanview.is_some();
+        let dump_graphviz = dump_mir && tcx.sess.opts.unstable_opts.dump_mir_graphviz;
+        let dump_spanview = dump_mir && tcx.sess.opts.unstable_opts.dump_mir_spanview.is_some();
 
         if dump_graphviz {
             graphviz_data.enable();
diff --git a/compiler/rustc_mir_transform/src/dest_prop.rs b/compiler/rustc_mir_transform/src/dest_prop.rs
index 84c7aada5e5..33572068f5c 100644
--- a/compiler/rustc_mir_transform/src/dest_prop.rs
+++ b/compiler/rustc_mir_transform/src/dest_prop.rs
@@ -122,7 +122,7 @@ impl<'tcx> MirPass<'tcx> for DestinationPropagation {
         //
         // Only run at mir-opt-level=3 or higher for now (we don't fix up debuginfo and remove
         // storage statements at the moment).
-        sess.opts.debugging_opts.unsound_mir_opts && sess.mir_opt_level() >= 3
+        sess.opts.unstable_opts.unsound_mir_opts && sess.mir_opt_level() >= 3
     }
 
     fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
diff --git a/compiler/rustc_mir_transform/src/early_otherwise_branch.rs b/compiler/rustc_mir_transform/src/early_otherwise_branch.rs
index 33f201cbd28..dba42f7aff0 100644
--- a/compiler/rustc_mir_transform/src/early_otherwise_branch.rs
+++ b/compiler/rustc_mir_transform/src/early_otherwise_branch.rs
@@ -95,7 +95,7 @@ pub struct EarlyOtherwiseBranch;
 
 impl<'tcx> MirPass<'tcx> for EarlyOtherwiseBranch {
     fn is_enabled(&self, sess: &rustc_session::Session) -> bool {
-        sess.mir_opt_level() >= 3 && sess.opts.debugging_opts.unsound_mir_opts
+        sess.mir_opt_level() >= 3 && sess.opts.unstable_opts.unsound_mir_opts
     }
 
     fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
diff --git a/compiler/rustc_mir_transform/src/generator.rs b/compiler/rustc_mir_transform/src/generator.rs
index 9fdea835967..91ecf387922 100644
--- a/compiler/rustc_mir_transform/src/generator.rs
+++ b/compiler/rustc_mir_transform/src/generator.rs
@@ -957,7 +957,7 @@ fn create_generator_drop_shim<'tcx>(
         tcx.mk_ptr(ty::TypeAndMut { ty: gen_ty, mutbl: hir::Mutability::Mut }),
         source_info,
     );
-    if tcx.sess.opts.debugging_opts.mir_emit_retag {
+    if tcx.sess.opts.unstable_opts.mir_emit_retag {
         // Alias tracking must know we changed the type
         body.basic_blocks_mut()[START_BLOCK].statements.insert(
             0,
@@ -1386,7 +1386,7 @@ impl<'tcx> MirPass<'tcx> for StateTransform {
 
         sanitize_witness(tcx, body, interior, upvars, &liveness_info.saved_locals);
 
-        if tcx.sess.opts.debugging_opts.validate_mir {
+        if tcx.sess.opts.unstable_opts.validate_mir {
             let mut vis = EnsureGeneratorFieldAssignmentsNeverAlias {
                 assigned_local: None,
                 saved_locals: &liveness_info.saved_locals,
diff --git a/compiler/rustc_mir_transform/src/inline.rs b/compiler/rustc_mir_transform/src/inline.rs
index 8f049a182ee..dc5d5cee879 100644
--- a/compiler/rustc_mir_transform/src/inline.rs
+++ b/compiler/rustc_mir_transform/src/inline.rs
@@ -40,7 +40,7 @@ struct CallSite<'tcx> {
 
 impl<'tcx> MirPass<'tcx> for Inline {
     fn is_enabled(&self, sess: &rustc_session::Session) -> bool {
-        if let Some(enabled) = sess.opts.debugging_opts.inline_mir {
+        if let Some(enabled) = sess.opts.unstable_opts.inline_mir {
             return enabled;
         }
 
@@ -395,9 +395,9 @@ impl<'tcx> Inliner<'tcx> {
         let tcx = self.tcx;
 
         let mut threshold = if callee_attrs.requests_inline() {
-            self.tcx.sess.opts.debugging_opts.inline_mir_hint_threshold.unwrap_or(100)
+            self.tcx.sess.opts.unstable_opts.inline_mir_hint_threshold.unwrap_or(100)
         } else {
-            self.tcx.sess.opts.debugging_opts.inline_mir_threshold.unwrap_or(50)
+            self.tcx.sess.opts.unstable_opts.inline_mir_threshold.unwrap_or(50)
         };
 
         // Give a bonus functions with a small number of blocks,
diff --git a/compiler/rustc_mir_transform/src/lib.rs b/compiler/rustc_mir_transform/src/lib.rs
index 9e5c22308e7..d968a488519 100644
--- a/compiler/rustc_mir_transform/src/lib.rs
+++ b/compiler/rustc_mir_transform/src/lib.rs
@@ -217,7 +217,7 @@ fn mir_const<'tcx>(
     }
 
     // Unsafety check uses the raw mir, so make sure it is run.
-    if !tcx.sess.opts.debugging_opts.thir_unsafeck {
+    if !tcx.sess.opts.unstable_opts.thir_unsafeck {
         if let Some(param_did) = def.const_param_did {
             tcx.ensure().unsafety_check_result_for_const_arg((def.did, param_did));
         } else {
diff --git a/compiler/rustc_mir_transform/src/pass_manager.rs b/compiler/rustc_mir_transform/src/pass_manager.rs
index 2380391d09a..e27d4ab1688 100644
--- a/compiler/rustc_mir_transform/src/pass_manager.rs
+++ b/compiler/rustc_mir_transform/src/pass_manager.rs
@@ -76,8 +76,8 @@ pub fn run_passes<'tcx>(tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>, passes: &[&dyn
     let start_phase = body.phase;
     let mut cnt = 0;
 
-    let validate = tcx.sess.opts.debugging_opts.validate_mir;
-    let overridden_passes = &tcx.sess.opts.debugging_opts.mir_enable_passes;
+    let validate = tcx.sess.opts.unstable_opts.validate_mir;
+    let overridden_passes = &tcx.sess.opts.unstable_opts.mir_enable_passes;
     trace!(?overridden_passes);
 
     if validate {
diff --git a/compiler/rustc_mir_transform/src/shim.rs b/compiler/rustc_mir_transform/src/shim.rs
index f3153a64820..eaa61d8614d 100644
--- a/compiler/rustc_mir_transform/src/shim.rs
+++ b/compiler/rustc_mir_transform/src/shim.rs
@@ -176,7 +176,7 @@ fn build_drop_shim<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId, ty: Option<Ty<'tcx>>)
     if ty.is_some() {
         // The first argument (index 0), but add 1 for the return value.
         let dropee_ptr = Place::from(Local::new(1 + 0));
-        if tcx.sess.opts.debugging_opts.mir_emit_retag {
+        if tcx.sess.opts.unstable_opts.mir_emit_retag {
             // Function arguments should be retagged, and we make this one raw.
             body.basic_blocks_mut()[START_BLOCK].statements.insert(
                 0,
diff --git a/compiler/rustc_mir_transform/src/simplify_try.rs b/compiler/rustc_mir_transform/src/simplify_try.rs
index fca9f7eeb24..d52f1261b23 100644
--- a/compiler/rustc_mir_transform/src/simplify_try.rs
+++ b/compiler/rustc_mir_transform/src/simplify_try.rs
@@ -378,7 +378,7 @@ fn optimization_applies<'tcx>(
 impl<'tcx> MirPass<'tcx> for SimplifyArmIdentity {
     fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
         // FIXME(77359): This optimization can result in unsoundness.
-        if !tcx.sess.opts.debugging_opts.unsound_mir_opts {
+        if !tcx.sess.opts.unstable_opts.unsound_mir_opts {
             return;
         }
 
@@ -551,7 +551,7 @@ impl<'tcx> MirPass<'tcx> for SimplifyBranchSame {
     fn run_pass(&self, tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
         // This optimization is disabled by default for now due to
         // soundness concerns; see issue #89485 and PR #89489.
-        if !tcx.sess.opts.debugging_opts.unsound_mir_opts {
+        if !tcx.sess.opts.unstable_opts.unsound_mir_opts {
             return;
         }
 
diff --git a/compiler/rustc_monomorphize/src/collector.rs b/compiler/rustc_monomorphize/src/collector.rs
index b3ac0f4cbea..d9fa4d65b3a 100644
--- a/compiler/rustc_monomorphize/src/collector.rs
+++ b/compiler/rustc_monomorphize/src/collector.rs
@@ -1141,8 +1141,7 @@ fn create_fn_mono_item<'tcx>(
     debug!("create_fn_mono_item(instance={})", instance);
 
     let def_id = instance.def_id();
-    if tcx.sess.opts.debugging_opts.profile_closures && def_id.is_local() && tcx.is_closure(def_id)
-    {
+    if tcx.sess.opts.unstable_opts.profile_closures && def_id.is_local() && tcx.is_closure(def_id) {
         crate::util::dump_closure_profile(tcx, instance);
     }
 
diff --git a/compiler/rustc_monomorphize/src/partitioning/default.rs b/compiler/rustc_monomorphize/src/partitioning/default.rs
index 9190e5fe4eb..d18b1c26c17 100644
--- a/compiler/rustc_monomorphize/src/partitioning/default.rs
+++ b/compiler/rustc_monomorphize/src/partitioning/default.rs
@@ -303,7 +303,7 @@ fn characteristic_def_id_of_mono_item<'tcx>(
 
                 // When polymorphization is enabled, methods which do not depend on their generic
                 // parameters, but the self-type of their impl block do will fail to normalize.
-                if !tcx.sess.opts.debugging_opts.polymorphize || !instance.needs_subst() {
+                if !tcx.sess.opts.unstable_opts.polymorphize || !instance.needs_subst() {
                     // This is a method within an impl, find out what the self-type is:
                     let impl_self_ty = tcx.subst_and_normalize_erasing_regions(
                         instance.substs,
diff --git a/compiler/rustc_monomorphize/src/partitioning/merging.rs b/compiler/rustc_monomorphize/src/partitioning/merging.rs
index 09cadc907b1..02bb8dea0c0 100644
--- a/compiler/rustc_monomorphize/src/partitioning/merging.rs
+++ b/compiler/rustc_monomorphize/src/partitioning/merging.rs
@@ -83,7 +83,7 @@ pub fn merge_codegen_units<'tcx>(
 
         for cgu in codegen_units.iter_mut() {
             if let Some(new_cgu_name) = new_cgu_names.get(&cgu.name()) {
-                if cx.tcx.sess.opts.debugging_opts.human_readable_cgu_names {
+                if cx.tcx.sess.opts.unstable_opts.human_readable_cgu_names {
                     cgu.set_name(Symbol::intern(&new_cgu_name));
                 } else {
                     // If we don't require CGU names to be human-readable, we
diff --git a/compiler/rustc_monomorphize/src/partitioning/mod.rs b/compiler/rustc_monomorphize/src/partitioning/mod.rs
index c1992137575..36243803f99 100644
--- a/compiler/rustc_monomorphize/src/partitioning/mod.rs
+++ b/compiler/rustc_monomorphize/src/partitioning/mod.rs
@@ -141,7 +141,7 @@ trait Partitioner<'tcx> {
 }
 
 fn get_partitioner<'tcx>(tcx: TyCtxt<'tcx>) -> Box<dyn Partitioner<'tcx>> {
-    let strategy = match &tcx.sess.opts.debugging_opts.cgu_partitioning_strategy {
+    let strategy = match &tcx.sess.opts.unstable_opts.cgu_partitioning_strategy {
         None => "default",
         Some(s) => &s[..],
     };
@@ -345,7 +345,7 @@ fn collect_and_partition_mono_items<'tcx>(
     tcx: TyCtxt<'tcx>,
     (): (),
 ) -> (&'tcx DefIdSet, &'tcx [CodegenUnit<'tcx>]) {
-    let collection_mode = match tcx.sess.opts.debugging_opts.print_mono_items {
+    let collection_mode = match tcx.sess.opts.unstable_opts.print_mono_items {
         Some(ref s) => {
             let mode_string = s.to_lowercase();
             let mode_string = mode_string.trim();
@@ -413,7 +413,7 @@ fn collect_and_partition_mono_items<'tcx>(
         })
         .collect();
 
-    if tcx.sess.opts.debugging_opts.print_mono_items.is_some() {
+    if tcx.sess.opts.unstable_opts.print_mono_items.is_some() {
         let mut item_to_cgus: FxHashMap<_, Vec<_>> = Default::default();
 
         for cgu in codegen_units {
diff --git a/compiler/rustc_monomorphize/src/polymorphize.rs b/compiler/rustc_monomorphize/src/polymorphize.rs
index aaa924d7fa0..394843e510d 100644
--- a/compiler/rustc_monomorphize/src/polymorphize.rs
+++ b/compiler/rustc_monomorphize/src/polymorphize.rs
@@ -36,7 +36,7 @@ fn unused_generic_params<'tcx>(
     tcx: TyCtxt<'tcx>,
     instance: ty::InstanceDef<'tcx>,
 ) -> FiniteBitSet<u32> {
-    if !tcx.sess.opts.debugging_opts.polymorphize {
+    if !tcx.sess.opts.unstable_opts.polymorphize {
         // If polymorphization disabled, then all parameters are used.
         return FiniteBitSet::new_empty();
     }
diff --git a/compiler/rustc_passes/src/check_attr.rs b/compiler/rustc_passes/src/check_attr.rs
index 20d03d797fe..f3d8a09a297 100644
--- a/compiler/rustc_passes/src/check_attr.rs
+++ b/compiler/rustc_passes/src/check_attr.rs
@@ -1625,7 +1625,7 @@ impl CheckAttrVisitor<'_> {
     /// Checks that the dep-graph debugging attributes are only present when the query-dep-graph
     /// option is passed to the compiler.
     fn check_rustc_dirty_clean(&self, attr: &Attribute) -> bool {
-        if self.tcx.sess.opts.debugging_opts.query_dep_graph {
+        if self.tcx.sess.opts.unstable_opts.query_dep_graph {
             true
         } else {
             self.tcx
diff --git a/compiler/rustc_passes/src/check_const.rs b/compiler/rustc_passes/src/check_const.rs
index 31c159c1f75..f1a81b65329 100644
--- a/compiler/rustc_passes/src/check_const.rs
+++ b/compiler/rustc_passes/src/check_const.rs
@@ -122,7 +122,7 @@ impl<'tcx> CheckConstVisitor<'tcx> {
             // `-Zunleash-the-miri-inside-of-you` only works for expressions that don't have a
             // corresponding feature gate. This encourages nightly users to use feature gates when
             // possible.
-            None if tcx.sess.opts.debugging_opts.unleash_the_miri_inside_of_you => {
+            None if tcx.sess.opts.unstable_opts.unleash_the_miri_inside_of_you => {
                 tcx.sess.span_warn(span, "skipping const checks");
                 return;
             }
diff --git a/compiler/rustc_passes/src/hir_id_validator.rs b/compiler/rustc_passes/src/hir_id_validator.rs
index 9deb0042ff3..212ea9e57a3 100644
--- a/compiler/rustc_passes/src/hir_id_validator.rs
+++ b/compiler/rustc_passes/src/hir_id_validator.rs
@@ -11,7 +11,7 @@ use rustc_middle::ty::TyCtxt;
 pub fn check_crate(tcx: TyCtxt<'_>) {
     tcx.dep_graph.assert_ignored();
 
-    if tcx.sess.opts.debugging_opts.hir_stats {
+    if tcx.sess.opts.unstable_opts.hir_stats {
         crate::hir_stats::print_hir_stats(tcx);
     }
 
diff --git a/compiler/rustc_passes/src/stability.rs b/compiler/rustc_passes/src/stability.rs
index 12050dceb60..2a1db584ccb 100644
--- a/compiler/rustc_passes/src/stability.rs
+++ b/compiler/rustc_passes/src/stability.rs
@@ -628,7 +628,7 @@ fn stability_index(tcx: TyCtxt<'_>, (): ()) -> Index {
         // compiling `librustc_*` crates themselves so we can leverage crates.io
         // while maintaining the invariant that all sysroot crates are unstable
         // by default and are unable to be used.
-        if tcx.sess.opts.debugging_opts.force_unstable_if_unmarked {
+        if tcx.sess.opts.unstable_opts.force_unstable_if_unmarked {
             let reason = "this crate is being loaded from the sysroot, an \
                           unstable location; did you mean to load this crate \
                           from crates.io via `Cargo.toml` instead?";
@@ -884,7 +884,7 @@ impl<'tcx> Visitor<'tcx> for CheckTraitImplStable<'tcx> {
 /// libraries, identify activated features that don't exist and error about them.
 pub fn check_unused_or_stable_features(tcx: TyCtxt<'_>) {
     let is_staged_api =
-        tcx.sess.opts.debugging_opts.force_unstable_if_unmarked || tcx.features().staged_api;
+        tcx.sess.opts.unstable_opts.force_unstable_if_unmarked || tcx.features().staged_api;
     if is_staged_api {
         let access_levels = &tcx.privacy_access_levels(());
         let mut missing = MissingStabilityAnnotations { tcx, access_levels };
diff --git a/compiler/rustc_query_system/src/dep_graph/dep_node.rs b/compiler/rustc_query_system/src/dep_graph/dep_node.rs
index c6210095b60..162c274d8a2 100644
--- a/compiler/rustc_query_system/src/dep_graph/dep_node.rs
+++ b/compiler/rustc_query_system/src/dep_graph/dep_node.rs
@@ -79,8 +79,8 @@ impl<K: DepKind> DepNode<K> {
         #[cfg(debug_assertions)]
         {
             if !tcx.fingerprint_style(kind).reconstructible()
-                && (tcx.sess().opts.debugging_opts.incremental_info
-                    || tcx.sess().opts.debugging_opts.query_dep_graph)
+                && (tcx.sess().opts.unstable_opts.incremental_info
+                    || tcx.sess().opts.unstable_opts.query_dep_graph)
             {
                 tcx.dep_graph().register_dep_node_debug_str(dep_node, || arg.to_debug_str(tcx));
             }
diff --git a/compiler/rustc_query_system/src/dep_graph/graph.rs b/compiler/rustc_query_system/src/dep_graph/graph.rs
index e7026096e7b..8ff56132749 100644
--- a/compiler/rustc_query_system/src/dep_graph/graph.rs
+++ b/compiler/rustc_query_system/src/dep_graph/graph.rs
@@ -347,7 +347,7 @@ impl<K: DepKind> DepGraph<K> {
         let current_fingerprint =
             hash_result.map(|f| dcx.with_stable_hashing_context(|mut hcx| f(&mut hcx, &result)));
 
-        let print_status = cfg!(debug_assertions) && dcx.sess().opts.debugging_opts.dep_tasks;
+        let print_status = cfg!(debug_assertions) && dcx.sess().opts.unstable_opts.dep_tasks;
 
         // Intern the new `DepNode`.
         let (dep_node_index, prev_and_color) = data.current.intern_node(
diff --git a/compiler/rustc_query_system/src/ich/hcx.rs b/compiler/rustc_query_system/src/ich/hcx.rs
index 843f6f9d703..217fac341ed 100644
--- a/compiler/rustc_query_system/src/ich/hcx.rs
+++ b/compiler/rustc_query_system/src/ich/hcx.rs
@@ -24,7 +24,7 @@ pub struct StableHashingContext<'a> {
     cstore: &'a dyn CrateStore,
     source_span: &'a IndexVec<LocalDefId, Span>,
     // The value of `-Z incremental-ignore-spans`.
-    // This field should only be used by `debug_opts_incremental_ignore_span`
+    // This field should only be used by `unstable_opts_incremental_ignore_span`
     incremental_ignore_spans: bool,
     pub(super) body_resolver: BodyResolver<'a>,
     // Very often, we are hashing something that does not need the
@@ -57,14 +57,14 @@ impl<'a> StableHashingContext<'a> {
         always_ignore_spans: bool,
     ) -> Self {
         let hash_spans_initial =
-            !always_ignore_spans && !sess.opts.debugging_opts.incremental_ignore_spans;
+            !always_ignore_spans && !sess.opts.unstable_opts.incremental_ignore_spans;
 
         StableHashingContext {
             body_resolver: BodyResolver::Forbidden,
             definitions,
             cstore,
             source_span,
-            incremental_ignore_spans: sess.opts.debugging_opts.incremental_ignore_spans,
+            incremental_ignore_spans: sess.opts.unstable_opts.incremental_ignore_spans,
             caching_source_map: None,
             raw_source_map: sess.source_map(),
             hashing_controls: HashingControls { hash_spans: hash_spans_initial },
@@ -186,7 +186,7 @@ impl<'a> rustc_span::HashStableContext for StableHashingContext<'a> {
     }
 
     #[inline]
-    fn debug_opts_incremental_ignore_spans(&self) -> bool {
+    fn unstable_opts_incremental_ignore_spans(&self) -> bool {
         self.incremental_ignore_spans
     }
 
diff --git a/compiler/rustc_query_system/src/query/plumbing.rs b/compiler/rustc_query_system/src/query/plumbing.rs
index bbcd00be943..792f2b03173 100644
--- a/compiler/rustc_query_system/src/query/plumbing.rs
+++ b/compiler/rustc_query_system/src/query/plumbing.rs
@@ -467,7 +467,7 @@ where
 
         if let Some(result) = result {
             if std::intrinsics::unlikely(
-                tcx.dep_context().sess().opts.debugging_opts.query_dep_graph,
+                tcx.dep_context().sess().opts.unstable_opts.query_dep_graph,
             ) {
                 dep_graph.mark_debug_loaded_from_disk(*dep_node)
             }
@@ -486,7 +486,7 @@ where
             // give us some coverage of potential bugs though.
             let try_verify = prev_fingerprint.as_value().1 % 32 == 0;
             if std::intrinsics::unlikely(
-                try_verify || tcx.dep_context().sess().opts.debugging_opts.incremental_verify_ich,
+                try_verify || tcx.dep_context().sess().opts.unstable_opts.incremental_verify_ich,
             ) {
                 incremental_verify_ich(*tcx.dep_context(), &result, dep_node, query);
             }
diff --git a/compiler/rustc_session/src/config.rs b/compiler/rustc_session/src/config.rs
index b7da0f22942..0e52bf34661 100644
--- a/compiler/rustc_session/src/config.rs
+++ b/compiler/rustc_session/src/config.rs
@@ -722,7 +722,7 @@ impl Default for Options {
             target_triple: TargetTriple::from_triple(host_triple()),
             test: false,
             incremental: None,
-            debugging_opts: Default::default(),
+            unstable_opts: Default::default(),
             prints: Vec::new(),
             cg: Default::default(),
             error_format: ErrorOutputType::default(),
@@ -752,8 +752,8 @@ impl Options {
     /// Returns `true` if there is a reason to build the dep graph.
     pub fn build_dep_graph(&self) -> bool {
         self.incremental.is_some()
-            || self.debugging_opts.dump_dep_graph
-            || self.debugging_opts.query_dep_graph
+            || self.unstable_opts.dump_dep_graph
+            || self.unstable_opts.query_dep_graph
     }
 
     pub fn file_path_mapping(&self) -> FilePathMapping {
@@ -762,13 +762,13 @@ impl Options {
 
     /// Returns `true` if there will be an output file generated.
     pub fn will_create_output_file(&self) -> bool {
-        !self.debugging_opts.parse_only && // The file is just being parsed
-            !self.debugging_opts.ls // The file is just being queried
+        !self.unstable_opts.parse_only && // The file is just being parsed
+            !self.unstable_opts.ls // The file is just being queried
     }
 
     #[inline]
     pub fn share_generics(&self) -> bool {
-        match self.debugging_opts.share_generics {
+        match self.unstable_opts.share_generics {
             Some(setting) => setting,
             None => match self.optimize {
                 OptLevel::No | OptLevel::Less | OptLevel::Size | OptLevel::SizeMin => true,
@@ -782,7 +782,7 @@ impl Options {
     }
 }
 
-impl DebuggingOptions {
+impl UnstableOptions {
     pub fn diagnostic_handler_flags(&self, can_emit_warnings: bool) -> HandlerFlags {
         HandlerFlags {
             can_emit_warnings,
@@ -940,7 +940,7 @@ fn default_configuration(sess: &Session) -> CrateConfig {
     let panic_strategy = sess.panic_strategy();
     ret.insert((sym::panic, Some(panic_strategy.desc_symbol())));
 
-    for s in sess.opts.debugging_opts.sanitizer {
+    for s in sess.opts.unstable_opts.sanitizer {
         let symbol = Symbol::intern(&s.to_string());
         ret.insert((sym::sanitize, Some(symbol)));
     }
@@ -1403,6 +1403,7 @@ pub fn rustc_short_optgroups() -> Vec<RustcOptGroup> {
 /// long-term interface for rustc.
 pub fn rustc_optgroups() -> Vec<RustcOptGroup> {
     let mut opts = rustc_short_optgroups();
+    // FIXME: none of these descriptions are actually used
     opts.extend(vec![
         opt::multi_s(
             "",
@@ -1411,7 +1412,7 @@ pub fn rustc_optgroups() -> Vec<RustcOptGroup> {
             "NAME[=PATH]",
         ),
         opt::opt_s("", "sysroot", "Override the system root", "PATH"),
-        opt::multi("Z", "", "Set internal debugging options", "FLAG"),
+        opt::multi("Z", "", "Set unstable / perma-unstable options", "FLAG"),
         opt::opt_s(
             "",
             "error-format",
@@ -1659,12 +1660,12 @@ pub fn parse_crate_edition(matches: &getopts::Matches) -> Edition {
     edition
 }
 
-fn check_debug_option_stability(
-    debugging_opts: &DebuggingOptions,
+fn check_error_format_stability(
+    unstable_opts: &UnstableOptions,
     error_format: ErrorOutputType,
     json_rendered: HumanReadableErrorType,
 ) {
-    if !debugging_opts.unstable_options {
+    if !unstable_opts.unstable_options {
         if let ErrorOutputType::Json { pretty: true, json_rendered } = error_format {
             early_error(
                 ErrorOutputType::Json { pretty: false, json_rendered },
@@ -1683,12 +1684,12 @@ fn check_debug_option_stability(
 }
 
 fn parse_output_types(
-    debugging_opts: &DebuggingOptions,
+    unstable_opts: &UnstableOptions,
     matches: &getopts::Matches,
     error_format: ErrorOutputType,
 ) -> OutputTypes {
     let mut output_types = BTreeMap::new();
-    if !debugging_opts.parse_only {
+    if !unstable_opts.parse_only {
         for list in matches.opt_strs("emit") {
             for output_type in list.split(',') {
                 let (shorthand, path) = match output_type.split_once('=') {
@@ -1762,19 +1763,19 @@ fn should_override_cgus_and_disable_thinlto(
     (disable_thinlto, codegen_units)
 }
 
-fn check_thread_count(debugging_opts: &DebuggingOptions, error_format: ErrorOutputType) {
-    if debugging_opts.threads == 0 {
+fn check_thread_count(unstable_opts: &UnstableOptions, error_format: ErrorOutputType) {
+    if unstable_opts.threads == 0 {
         early_error(error_format, "value for threads must be a positive non-zero integer");
     }
 
-    if debugging_opts.threads > 1 && debugging_opts.fuel.is_some() {
+    if unstable_opts.threads > 1 && unstable_opts.fuel.is_some() {
         early_error(error_format, "optimization fuel is incompatible with multiple threads");
     }
 }
 
 fn collect_print_requests(
     cg: &mut CodegenOptions,
-    dopts: &mut DebuggingOptions,
+    unstable_opts: &mut UnstableOptions,
     matches: &getopts::Matches,
     error_format: ErrorOutputType,
 ) -> Vec<PrintRequest> {
@@ -1803,7 +1804,7 @@ fn collect_print_requests(
         "native-static-libs" => PrintRequest::NativeStaticLibs,
         "stack-protector-strategies" => PrintRequest::StackProtectorStrategies,
         "target-spec-json" => {
-            if dopts.unstable_options {
+            if unstable_opts.unstable_options {
                 PrintRequest::TargetSpec
             } else {
                 early_error(
@@ -2069,10 +2070,10 @@ fn parse_libs(matches: &getopts::Matches, error_format: ErrorOutputType) -> Vec<
 
 pub fn parse_externs(
     matches: &getopts::Matches,
-    debugging_opts: &DebuggingOptions,
+    unstable_opts: &UnstableOptions,
     error_format: ErrorOutputType,
 ) -> Externs {
-    let is_unstable_enabled = debugging_opts.unstable_options;
+    let is_unstable_enabled = unstable_opts.unstable_options;
     let mut externs: BTreeMap<String, ExternEntry> = BTreeMap::new();
     for arg in matches.opt_strs("extern") {
         let (name, path) = match arg.split_once('=') {
@@ -2171,7 +2172,7 @@ pub fn parse_externs(
 
 fn parse_remap_path_prefix(
     matches: &getopts::Matches,
-    debugging_opts: &DebuggingOptions,
+    unstable_opts: &UnstableOptions,
     error_format: ErrorOutputType,
 ) -> Vec<(PathBuf, PathBuf)> {
     let mut mapping: Vec<(PathBuf, PathBuf)> = matches
@@ -2185,7 +2186,7 @@ fn parse_remap_path_prefix(
             Some((from, to)) => (PathBuf::from(from), PathBuf::from(to)),
         })
         .collect();
-    match &debugging_opts.remap_cwd_prefix {
+    match &unstable_opts.remap_cwd_prefix {
         Some(to) => match std::env::current_dir() {
             Ok(cwd) => mapping.push((cwd, to.clone())),
             Err(_) => (),
@@ -2217,12 +2218,12 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
     let crate_types = parse_crate_types_from_list(unparsed_crate_types)
         .unwrap_or_else(|e| early_error(error_format, &e));
 
-    let mut debugging_opts = DebuggingOptions::build(matches, error_format);
+    let mut unstable_opts = UnstableOptions::build(matches, error_format);
     let (lint_opts, describe_lints, lint_cap) = get_cmd_lint_options(matches, error_format);
 
-    check_debug_option_stability(&debugging_opts, error_format, json_rendered);
+    check_error_format_stability(&unstable_opts, error_format, json_rendered);
 
-    if !debugging_opts.unstable_options && json_unused_externs.is_enabled() {
+    if !unstable_opts.unstable_options && json_unused_externs.is_enabled() {
         early_error(
             error_format,
             "the `-Z unstable-options` flag must also be passed to enable \
@@ -2230,7 +2231,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         );
     }
 
-    let output_types = parse_output_types(&debugging_opts, matches, error_format);
+    let output_types = parse_output_types(&unstable_opts, matches, error_format);
 
     let mut cg = CodegenOptions::build(matches, error_format);
     let (disable_thinlto, mut codegen_units) = should_override_cgus_and_disable_thinlto(
@@ -2240,20 +2241,19 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         cg.codegen_units,
     );
 
-    check_thread_count(&debugging_opts, error_format);
+    check_thread_count(&unstable_opts, error_format);
 
     let incremental = cg.incremental.as_ref().map(PathBuf::from);
 
-    let assert_incr_state =
-        parse_assert_incr_state(&debugging_opts.assert_incr_state, error_format);
+    let assert_incr_state = parse_assert_incr_state(&unstable_opts.assert_incr_state, error_format);
 
-    if debugging_opts.profile && incremental.is_some() {
+    if unstable_opts.profile && incremental.is_some() {
         early_error(
             error_format,
             "can't instrument with gcov profiling when compiling incrementally",
         );
     }
-    if debugging_opts.profile {
+    if unstable_opts.profile {
         match codegen_units {
             Some(1) => {}
             None => codegen_units = Some(1),
@@ -2271,7 +2271,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         );
     }
 
-    if debugging_opts.profile_sample_use.is_some()
+    if unstable_opts.profile_sample_use.is_some()
         && (cg.profile_generate.enabled() || cg.profile_use.is_some())
     {
         early_error(
@@ -2282,7 +2282,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
 
     // Handle both `-Z symbol-mangling-version` and `-C symbol-mangling-version`; the latter takes
     // precedence.
-    match (cg.symbol_mangling_version, debugging_opts.symbol_mangling_version) {
+    match (cg.symbol_mangling_version, unstable_opts.symbol_mangling_version) {
         (Some(smv_c), Some(smv_z)) if smv_c != smv_z => {
             early_error(
                 error_format,
@@ -2291,7 +2291,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
             );
         }
         (Some(SymbolManglingVersion::V0), _) => {}
-        (Some(_), _) if !debugging_opts.unstable_options => {
+        (Some(_), _) if !unstable_opts.unstable_options => {
             early_error(
                 error_format,
                 "`-C symbol-mangling-version=legacy` requires `-Z unstable-options`",
@@ -2310,7 +2310,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
 
     // Handle both `-Z instrument-coverage` and `-C instrument-coverage`; the latter takes
     // precedence.
-    match (cg.instrument_coverage, debugging_opts.instrument_coverage) {
+    match (cg.instrument_coverage, unstable_opts.instrument_coverage) {
         (Some(ic_c), Some(ic_z)) if ic_c != ic_z => {
             early_error(
                 error_format,
@@ -2319,7 +2319,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
             );
         }
         (Some(InstrumentCoverage::Off | InstrumentCoverage::All), _) => {}
-        (Some(_), _) if !debugging_opts.unstable_options => {
+        (Some(_), _) if !unstable_opts.unstable_options => {
             early_error(
                 error_format,
                 "`-C instrument-coverage=except-*` requires `-Z unstable-options`",
@@ -2363,7 +2363,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
     }
 
     if let Ok(graphviz_font) = std::env::var("RUSTC_GRAPHVIZ_FONT") {
-        debugging_opts.graphviz_font = graphviz_font;
+        unstable_opts.graphviz_font = graphviz_font;
     }
 
     if !cg.embed_bitcode {
@@ -2386,7 +2386,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         );
     }
 
-    let prints = collect_print_requests(&mut cg, &mut debugging_opts, matches, error_format);
+    let prints = collect_print_requests(&mut cg, &mut unstable_opts, matches, error_format);
 
     let cg = cg;
 
@@ -2412,15 +2412,15 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         early_warn(error_format, "-C remark requires \"-C debuginfo=n\" to show source locations");
     }
 
-    let externs = parse_externs(matches, &debugging_opts, error_format);
+    let externs = parse_externs(matches, &unstable_opts, error_format);
 
     let crate_name = matches.opt_str("crate-name");
 
-    let remap_path_prefix = parse_remap_path_prefix(matches, &debugging_opts, error_format);
+    let remap_path_prefix = parse_remap_path_prefix(matches, &unstable_opts, error_format);
 
-    let pretty = parse_pretty(&debugging_opts, error_format);
+    let pretty = parse_pretty(&unstable_opts, error_format);
 
-    if !debugging_opts.unstable_options
+    if !unstable_opts.unstable_options
         && !target_triple.triple().contains("apple")
         && cg.split_debuginfo.is_some()
     {
@@ -2481,7 +2481,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         target_triple,
         test,
         incremental,
-        debugging_opts,
+        unstable_opts,
         prints,
         cg,
         error_format,
@@ -2506,10 +2506,10 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
     }
 }
 
-fn parse_pretty(debugging_opts: &DebuggingOptions, efmt: ErrorOutputType) -> Option<PpMode> {
+fn parse_pretty(unstable_opts: &UnstableOptions, efmt: ErrorOutputType) -> Option<PpMode> {
     use PpMode::*;
 
-    let first = match debugging_opts.unpretty.as_deref()? {
+    let first = match unstable_opts.unpretty.as_deref()? {
         "normal" => Source(PpSourceMode::Normal),
         "identified" => Source(PpSourceMode::Identified),
         "expanded" => Source(PpSourceMode::Expanded),
diff --git a/compiler/rustc_session/src/options.rs b/compiler/rustc_session/src/options.rs
index 8f1057b793f..01ff9e254f7 100644
--- a/compiler/rustc_session/src/options.rs
+++ b/compiler/rustc_session/src/options.rs
@@ -104,7 +104,7 @@ macro_rules! top_level_options {
 
 impl Options {
     pub fn mir_opt_level(&self) -> usize {
-        self.debugging_opts
+        self.unstable_opts
             .mir_opt_level
             .unwrap_or_else(|| if self.optimize != OptLevel::No { 2 } else { 1 })
     }
@@ -177,7 +177,7 @@ top_level_options!(
         incremental: Option<PathBuf> [UNTRACKED],
         assert_incr_state: Option<IncrementalStateAssertion> [UNTRACKED],
 
-        debugging_opts: DebuggingOptions [SUBSTRUCT],
+        unstable_opts: UnstableOptions [SUBSTRUCT],
         prints: Vec<PrintRequest> [UNTRACKED],
         cg: CodegenOptions [SUBSTRUCT],
         externs: Externs [UNTRACKED],
@@ -1187,12 +1187,13 @@ options! {
 }
 
 options! {
-    DebuggingOptions, DB_OPTIONS, dbopts, "Z", "debugging",
+    UnstableOptions, Z_OPTIONS, dbopts, "Z", "unstable",
 
     // This list is in alphabetical order.
     //
     // If you add a new option, please update:
     // - compiler/rustc_interface/src/tests.rs
+    // - src/doc/unstable-book/src/compiler-flags
 
     allow_features: Option<Vec<String>> = (None, parse_opt_comma_list, [TRACKED],
         "only allow the listed language features to be enabled in code (space separated)"),
@@ -1580,6 +1581,8 @@ options! {
         `mir` (the MIR), or `mir-cfg` (graphviz formatted MIR)"),
     unsound_mir_opts: bool = (false, parse_bool, [TRACKED],
         "enable unsound and buggy MIR optimizations (default: no)"),
+    /// This name is kind of confusing: Most unstable options enable something themselves, while
+    /// this just allows "normal" options to be feature-gated.
     unstable_options: bool = (false, parse_bool, [UNTRACKED],
         "adds unstable command line options to rustc interface (default: no)"),
     use_ctors_section: Option<bool> = (None, parse_opt_bool, [TRACKED],
diff --git a/compiler/rustc_session/src/session.rs b/compiler/rustc_session/src/session.rs
index 16f4a099d80..854cad79a20 100644
--- a/compiler/rustc_session/src/session.rs
+++ b/compiler/rustc_session/src/session.rs
@@ -544,10 +544,10 @@ impl Session {
     /// warnings or errors are emitted. If no messages are emitted ("good path"), then
     /// it's likely a bug.
     pub fn delay_good_path_bug(&self, msg: impl Into<DiagnosticMessage>) {
-        if self.opts.debugging_opts.print_type_sizes
-            || self.opts.debugging_opts.query_dep_graph
-            || self.opts.debugging_opts.dump_mir.is_some()
-            || self.opts.debugging_opts.unpretty.is_some()
+        if self.opts.unstable_opts.print_type_sizes
+            || self.opts.unstable_opts.query_dep_graph
+            || self.opts.unstable_opts.dump_mir.is_some()
+            || self.opts.unstable_opts.unpretty.is_some()
             || self.opts.output_types.contains_key(&OutputType::Mir)
             || std::env::var_os("RUSTC_LOG").is_some()
         {
@@ -584,31 +584,31 @@ impl Session {
         self.parse_sess.source_map()
     }
     pub fn verbose(&self) -> bool {
-        self.opts.debugging_opts.verbose
+        self.opts.unstable_opts.verbose
     }
     pub fn time_passes(&self) -> bool {
-        self.opts.debugging_opts.time_passes || self.opts.debugging_opts.time
+        self.opts.unstable_opts.time_passes || self.opts.unstable_opts.time
     }
     pub fn instrument_mcount(&self) -> bool {
-        self.opts.debugging_opts.instrument_mcount
+        self.opts.unstable_opts.instrument_mcount
     }
     pub fn time_llvm_passes(&self) -> bool {
-        self.opts.debugging_opts.time_llvm_passes
+        self.opts.unstable_opts.time_llvm_passes
     }
     pub fn meta_stats(&self) -> bool {
-        self.opts.debugging_opts.meta_stats
+        self.opts.unstable_opts.meta_stats
     }
     pub fn asm_comments(&self) -> bool {
-        self.opts.debugging_opts.asm_comments
+        self.opts.unstable_opts.asm_comments
     }
     pub fn verify_llvm_ir(&self) -> bool {
-        self.opts.debugging_opts.verify_llvm_ir || option_env!("RUSTC_VERIFY_LLVM_IR").is_some()
+        self.opts.unstable_opts.verify_llvm_ir || option_env!("RUSTC_VERIFY_LLVM_IR").is_some()
     }
     pub fn print_llvm_passes(&self) -> bool {
-        self.opts.debugging_opts.print_llvm_passes
+        self.opts.unstable_opts.print_llvm_passes
     }
     pub fn binary_dep_depinfo(&self) -> bool {
-        self.opts.debugging_opts.binary_dep_depinfo
+        self.opts.unstable_opts.binary_dep_depinfo
     }
     pub fn mir_opt_level(&self) -> usize {
         self.opts.mir_opt_level()
@@ -675,7 +675,7 @@ impl Session {
 
         // If `-Z thinlto` specified process that, but note that this is mostly
         // a deprecated option now that `-C lto=thin` exists.
-        if let Some(enabled) = self.opts.debugging_opts.thinlto {
+        if let Some(enabled) = self.opts.unstable_opts.thinlto {
             if enabled {
                 return config::Lto::ThinLocal;
             } else {
@@ -703,25 +703,25 @@ impl Session {
         self.opts.cg.panic.unwrap_or(self.target.panic_strategy)
     }
     pub fn fewer_names(&self) -> bool {
-        if let Some(fewer_names) = self.opts.debugging_opts.fewer_names {
+        if let Some(fewer_names) = self.opts.unstable_opts.fewer_names {
             fewer_names
         } else {
             let more_names = self.opts.output_types.contains_key(&OutputType::LlvmAssembly)
                 || self.opts.output_types.contains_key(&OutputType::Bitcode)
                 // AddressSanitizer and MemorySanitizer use alloca name when reporting an issue.
-                || self.opts.debugging_opts.sanitizer.intersects(SanitizerSet::ADDRESS | SanitizerSet::MEMORY);
+                || self.opts.unstable_opts.sanitizer.intersects(SanitizerSet::ADDRESS | SanitizerSet::MEMORY);
             !more_names
         }
     }
 
     pub fn unstable_options(&self) -> bool {
-        self.opts.debugging_opts.unstable_options
+        self.opts.unstable_opts.unstable_options
     }
     pub fn is_nightly_build(&self) -> bool {
         self.opts.unstable_features.is_nightly_build()
     }
     pub fn is_sanitizer_cfi_enabled(&self) -> bool {
-        self.opts.debugging_opts.sanitizer.contains(SanitizerSet::CFI)
+        self.opts.unstable_opts.sanitizer.contains(SanitizerSet::CFI)
     }
     pub fn overflow_checks(&self) -> bool {
         self.opts.cg.overflow_checks.unwrap_or(self.opts.debug_assertions)
@@ -761,13 +761,13 @@ impl Session {
     }
 
     pub fn tls_model(&self) -> TlsModel {
-        self.opts.debugging_opts.tls_model.unwrap_or(self.target.tls_model)
+        self.opts.unstable_opts.tls_model.unwrap_or(self.target.tls_model)
     }
 
     pub fn is_wasi_reactor(&self) -> bool {
         self.target.options.os == "wasi"
             && matches!(
-                self.opts.debugging_opts.wasi_exec_model,
+                self.opts.unstable_opts.wasi_exec_model,
                 Some(config::WasiExecModel::Reactor)
             )
     }
@@ -778,7 +778,7 @@ impl Session {
 
     pub fn stack_protector(&self) -> StackProtector {
         if self.target.options.supports_stack_protector {
-            self.opts.debugging_opts.stack_protector
+            self.opts.unstable_opts.stack_protector
         } else {
             StackProtector::None
         }
@@ -933,7 +933,7 @@ impl Session {
     /// This expends fuel if applicable, and records fuel if applicable.
     pub fn consider_optimizing<T: Fn() -> String>(&self, crate_name: &str, msg: T) -> bool {
         let mut ret = true;
-        if let Some((ref c, _)) = self.opts.debugging_opts.fuel {
+        if let Some((ref c, _)) = self.opts.unstable_opts.fuel {
             if c == crate_name {
                 assert_eq!(self.threads(), 1);
                 let mut fuel = self.optimization_fuel.lock();
@@ -951,7 +951,7 @@ impl Session {
                 }
             }
         }
-        if let Some(ref c) = self.opts.debugging_opts.print_fuel {
+        if let Some(ref c) = self.opts.unstable_opts.print_fuel {
             if c == crate_name {
                 assert_eq!(self.threads(), 1);
                 self.print_fuel.fetch_add(1, SeqCst);
@@ -963,7 +963,7 @@ impl Session {
     /// Returns the number of query threads that should be used for this
     /// compilation
     pub fn threads(&self) -> usize {
-        self.opts.debugging_opts.threads
+        self.opts.unstable_opts.threads
     }
 
     /// Returns the number of codegen units that should be used for this
@@ -1037,7 +1037,7 @@ impl Session {
     }
 
     pub fn teach(&self, code: &DiagnosticId) -> bool {
-        self.opts.debugging_opts.teach && self.diagnostic().must_teach(code)
+        self.opts.unstable_opts.teach && self.diagnostic().must_teach(code)
     }
 
     pub fn rust_2015(&self) -> bool {
@@ -1069,7 +1069,7 @@ impl Session {
         // The user can use the command line flag to override it.
         let needs_plt = self.target.needs_plt;
 
-        let dbg_opts = &self.opts.debugging_opts;
+        let dbg_opts = &self.opts.unstable_opts;
 
         let relro_level = dbg_opts.relro_level.unwrap_or(self.target.relro_level);
 
@@ -1089,7 +1089,7 @@ impl Session {
         // AddressSanitizer uses lifetimes to detect use after scope bugs.
         // MemorySanitizer uses lifetimes to detect use of uninitialized stack variables.
         // HWAddressSanitizer will use lifetimes to detect use after scope bugs in the future.
-        || self.opts.debugging_opts.sanitizer.intersects(SanitizerSet::ADDRESS | SanitizerSet::MEMORY | SanitizerSet::HWADDRESS)
+        || self.opts.unstable_opts.sanitizer.intersects(SanitizerSet::ADDRESS | SanitizerSet::MEMORY | SanitizerSet::HWADDRESS)
     }
 
     pub fn link_dead_code(&self) -> bool {
@@ -1151,7 +1151,7 @@ fn default_emitter(
     fallback_bundle: LazyFallbackBundle,
     emitter_dest: Option<Box<dyn Write + Send>>,
 ) -> Box<dyn Emitter + sync::Send> {
-    let macro_backtrace = sopts.debugging_opts.macro_backtrace;
+    let macro_backtrace = sopts.unstable_opts.macro_backtrace;
     match (sopts.error_format, emitter_dest) {
         (config::ErrorOutputType::HumanReadable(kind), dst) => {
             let (short, color_config) = kind.unzip();
@@ -1164,7 +1164,7 @@ fn default_emitter(
                     short,
                     macro_backtrace,
                 );
-                Box::new(emitter.ui_testing(sopts.debugging_opts.ui_testing))
+                Box::new(emitter.ui_testing(sopts.unstable_opts.ui_testing))
             } else {
                 let emitter = match dst {
                     None => EmitterWriter::stderr(
@@ -1173,7 +1173,7 @@ fn default_emitter(
                         bundle,
                         fallback_bundle,
                         short,
-                        sopts.debugging_opts.teach,
+                        sopts.unstable_opts.teach,
                         sopts.diagnostic_width,
                         macro_backtrace,
                     ),
@@ -1189,7 +1189,7 @@ fn default_emitter(
                         macro_backtrace,
                     ),
                 };
-                Box::new(emitter.ui_testing(sopts.debugging_opts.ui_testing))
+                Box::new(emitter.ui_testing(sopts.unstable_opts.ui_testing))
             }
         }
         (config::ErrorOutputType::Json { pretty, json_rendered }, None) => Box::new(
@@ -1203,7 +1203,7 @@ fn default_emitter(
                 sopts.diagnostic_width,
                 macro_backtrace,
             )
-            .ui_testing(sopts.debugging_opts.ui_testing),
+            .ui_testing(sopts.unstable_opts.ui_testing),
         ),
         (config::ErrorOutputType::Json { pretty, json_rendered }, Some(dst)) => Box::new(
             JsonEmitter::new(
@@ -1217,7 +1217,7 @@ fn default_emitter(
                 sopts.diagnostic_width,
                 macro_backtrace,
             )
-            .ui_testing(sopts.debugging_opts.ui_testing),
+            .ui_testing(sopts.unstable_opts.ui_testing),
         ),
     }
 }
@@ -1270,7 +1270,7 @@ pub fn build_session(
     }
 
     let loader = file_loader.unwrap_or_else(|| Box::new(RealFileLoader));
-    let hash_kind = sopts.debugging_opts.src_hash_algorithm.unwrap_or_else(|| {
+    let hash_kind = sopts.unstable_opts.src_hash_algorithm.unwrap_or_else(|| {
         if target_cfg.is_like_msvc {
             SourceFileHashAlgorithm::Sha1
         } else {
@@ -1285,17 +1285,17 @@ pub fn build_session(
 
     let fallback_bundle = fallback_fluent_bundle(
         rustc_errors::DEFAULT_LOCALE_RESOURCES,
-        sopts.debugging_opts.translate_directionality_markers,
+        sopts.unstable_opts.translate_directionality_markers,
     );
     let emitter =
         default_emitter(&sopts, registry, source_map.clone(), bundle, fallback_bundle, write_dest);
 
     let span_diagnostic = rustc_errors::Handler::with_emitter_and_flags(
         emitter,
-        sopts.debugging_opts.diagnostic_handler_flags(can_emit_warnings),
+        sopts.unstable_opts.diagnostic_handler_flags(can_emit_warnings),
     );
 
-    let self_profiler = if let SwitchWithOptPath::Enabled(ref d) = sopts.debugging_opts.self_profile
+    let self_profiler = if let SwitchWithOptPath::Enabled(ref d) = sopts.unstable_opts.self_profile
     {
         let directory =
             if let Some(ref directory) = d { directory } else { std::path::Path::new(".") };
@@ -1303,8 +1303,8 @@ pub fn build_session(
         let profiler = SelfProfiler::new(
             directory,
             sopts.crate_name.as_deref(),
-            sopts.debugging_opts.self_profile_events.as_ref().map(|xs| &xs[..]),
-            &sopts.debugging_opts.self_profile_counter,
+            sopts.unstable_opts.self_profile_events.as_ref().map(|xs| &xs[..]),
+            &sopts.unstable_opts.self_profile_counter,
         );
         match profiler {
             Ok(profiler) => Some(Arc::new(profiler)),
@@ -1318,7 +1318,7 @@ pub fn build_session(
     };
 
     let mut parse_sess = ParseSess::with_span_handler(span_diagnostic, source_map);
-    parse_sess.assume_incomplete_release = sopts.debugging_opts.assume_incomplete_release;
+    parse_sess.assume_incomplete_release = sopts.unstable_opts.assume_incomplete_release;
 
     let host_triple = config::host_triple();
     let target_triple = sopts.target_triple.triple();
@@ -1337,12 +1337,12 @@ pub fn build_session(
         local_crate_source_file.map(|path| file_path_mapping.map_prefix(path).0);
 
     let optimization_fuel = Lock::new(OptimizationFuel {
-        remaining: sopts.debugging_opts.fuel.as_ref().map_or(0, |i| i.1),
+        remaining: sopts.unstable_opts.fuel.as_ref().map_or(0, |i| i.1),
         out_of_fuel: false,
     });
     let print_fuel = AtomicU64::new(0);
 
-    let cgu_reuse_tracker = if sopts.debugging_opts.query_dep_graph {
+    let cgu_reuse_tracker = if sopts.unstable_opts.query_dep_graph {
         CguReuseTracker::new()
     } else {
         CguReuseTracker::new_disabled()
@@ -1350,8 +1350,8 @@ pub fn build_session(
 
     let prof = SelfProfilerRef::new(
         self_profiler,
-        sopts.debugging_opts.time_passes || sopts.debugging_opts.time,
-        sopts.debugging_opts.time_passes,
+        sopts.unstable_opts.time_passes || sopts.unstable_opts.time,
+        sopts.unstable_opts.time_passes,
     );
 
     let ctfe_backtrace = Lock::new(match env::var("RUSTC_CTFE_BACKTRACE") {
@@ -1433,7 +1433,7 @@ fn validate_commandline_args_with_session_available(sess: &Session) {
     }
 
     // Do the same for sample profile data.
-    if let Some(ref path) = sess.opts.debugging_opts.profile_sample_use {
+    if let Some(ref path) = sess.opts.unstable_opts.profile_sample_use {
         if !path.exists() {
             sess.err(&format!(
                 "File `{}` passed to `-C profile-sample-use` does not exist.",
@@ -1454,7 +1454,7 @@ fn validate_commandline_args_with_session_available(sess: &Session) {
 
     // Sanitizers can only be used on platforms that we know have working sanitizer codegen.
     let supported_sanitizers = sess.target.options.supported_sanitizers;
-    let unsupported_sanitizers = sess.opts.debugging_opts.sanitizer - supported_sanitizers;
+    let unsupported_sanitizers = sess.opts.unstable_opts.sanitizer - supported_sanitizers;
     match unsupported_sanitizers.into_iter().count() {
         0 => {}
         1 => {
@@ -1471,13 +1471,13 @@ fn validate_commandline_args_with_session_available(sess: &Session) {
         }
     }
     // Cannot mix and match sanitizers.
-    let mut sanitizer_iter = sess.opts.debugging_opts.sanitizer.into_iter();
+    let mut sanitizer_iter = sess.opts.unstable_opts.sanitizer.into_iter();
     if let (Some(first), Some(second)) = (sanitizer_iter.next(), sanitizer_iter.next()) {
         sess.err(&format!("`-Zsanitizer={first}` is incompatible with `-Zsanitizer={second}`"));
     }
 
     // Cannot enable crt-static with sanitizers on Linux
-    if sess.crt_static(None) && !sess.opts.debugging_opts.sanitizer.is_empty() {
+    if sess.crt_static(None) && !sess.opts.unstable_opts.sanitizer.is_empty() {
         sess.err(
             "sanitizer is incompatible with statically linked libc, \
                                 disable it using `-C target-feature=-crt-static`",
@@ -1489,21 +1489,21 @@ fn validate_commandline_args_with_session_available(sess: &Session) {
         if sess.is_sanitizer_cfi_enabled() {
             sess.err("`-Zsanitizer=cfi` requires `-Clto`");
         }
-        if sess.opts.debugging_opts.virtual_function_elimination {
+        if sess.opts.unstable_opts.virtual_function_elimination {
             sess.err("`-Zvirtual-function-elimination` requires `-Clto`");
         }
     }
 
-    if sess.opts.debugging_opts.stack_protector != StackProtector::None {
+    if sess.opts.unstable_opts.stack_protector != StackProtector::None {
         if !sess.target.options.supports_stack_protector {
             sess.warn(&format!(
                 "`-Z stack-protector={}` is not supported for target {} and will be ignored",
-                sess.opts.debugging_opts.stack_protector, sess.opts.target_triple
+                sess.opts.unstable_opts.stack_protector, sess.opts.target_triple
             ))
         }
     }
 
-    if let Some(dwarf_version) = sess.opts.debugging_opts.dwarf_version {
+    if let Some(dwarf_version) = sess.opts.unstable_opts.dwarf_version {
         if dwarf_version > 5 {
             sess.err(&format!("requested DWARF version {} is greater than 5", dwarf_version));
         }
diff --git a/compiler/rustc_span/src/hygiene.rs b/compiler/rustc_span/src/hygiene.rs
index 29879c48b04..1d509a45d41 100644
--- a/compiler/rustc_span/src/hygiene.rs
+++ b/compiler/rustc_span/src/hygiene.rs
@@ -108,7 +108,7 @@ fn assert_default_hashing_controls<CTX: HashStableContext>(ctx: &CTX, msg: &str)
         // which will cause us to require that this method always be called with `Span` hashing
         // enabled.
         HashingControls { hash_spans }
-            if hash_spans == !ctx.debug_opts_incremental_ignore_spans() => {}
+            if hash_spans == !ctx.unstable_opts_incremental_ignore_spans() => {}
         other => panic!("Attempted hashing of {msg} with non-default HashingControls: {:?}", other),
     }
 }
diff --git a/compiler/rustc_span/src/lib.rs b/compiler/rustc_span/src/lib.rs
index a1f34287a5f..ce08f87ecdf 100644
--- a/compiler/rustc_span/src/lib.rs
+++ b/compiler/rustc_span/src/lib.rs
@@ -2029,9 +2029,9 @@ impl InnerSpan {
 pub trait HashStableContext {
     fn def_path_hash(&self, def_id: DefId) -> DefPathHash;
     fn hash_spans(&self) -> bool;
-    /// Accesses `sess.opts.debugging_opts.incremental_ignore_spans` since
+    /// Accesses `sess.opts.unstable_opts.incremental_ignore_spans` since
     /// we don't have easy access to a `Session`
-    fn debug_opts_incremental_ignore_spans(&self) -> bool;
+    fn unstable_opts_incremental_ignore_spans(&self) -> bool;
     fn def_span(&self, def_id: LocalDefId) -> Span;
     fn span_data_to_lines_and_cols(
         &mut self,
diff --git a/compiler/rustc_trait_selection/src/traits/engine.rs b/compiler/rustc_trait_selection/src/traits/engine.rs
index 4d477886979..348397cea67 100644
--- a/compiler/rustc_trait_selection/src/traits/engine.rs
+++ b/compiler/rustc_trait_selection/src/traits/engine.rs
@@ -9,7 +9,7 @@ pub trait TraitEngineExt<'tcx> {
 
 impl<'tcx> TraitEngineExt<'tcx> for dyn TraitEngine<'tcx> {
     fn new(tcx: TyCtxt<'tcx>) -> Box<Self> {
-        if tcx.sess.opts.debugging_opts.chalk {
+        if tcx.sess.opts.unstable_opts.chalk {
             Box::new(ChalkFulfillmentContext::new())
         } else {
             Box::new(FulfillmentContext::new())
diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
index 8d7c6b26ba1..379fc54349a 100644
--- a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
+++ b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
@@ -884,7 +884,7 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> {
                     }
 
                     ty::PredicateKind::WellFormed(ty) => {
-                        if !self.tcx.sess.opts.debugging_opts.chalk {
+                        if !self.tcx.sess.opts.unstable_opts.chalk {
                             // WF predicates cannot themselves make
                             // errors. They can only block due to
                             // ambiguity; otherwise, they always
diff --git a/compiler/rustc_trait_selection/src/traits/select/confirmation.rs b/compiler/rustc_trait_selection/src/traits/select/confirmation.rs
index 4862631980e..da8ca6e5749 100644
--- a/compiler/rustc_trait_selection/src/traits/select/confirmation.rs
+++ b/compiler/rustc_trait_selection/src/traits/select/confirmation.rs
@@ -683,7 +683,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
 
         // FIXME: Chalk
 
-        if !self.tcx().sess.opts.debugging_opts.chalk {
+        if !self.tcx().sess.opts.unstable_opts.chalk {
             nested.push(Obligation::new(
                 obligation.cause.clone(),
                 obligation.param_env,
diff --git a/compiler/rustc_ty_utils/src/ty.rs b/compiler/rustc_ty_utils/src/ty.rs
index 1d345caf699..d542a9b5997 100644
--- a/compiler/rustc_ty_utils/src/ty.rs
+++ b/compiler/rustc_ty_utils/src/ty.rs
@@ -126,7 +126,7 @@ fn param_env(tcx: TyCtxt<'_>, def_id: DefId) -> ty::ParamEnv<'_> {
     // are any errors at that point, so outside of type inference you can be
     // sure that this will succeed without errors anyway.
 
-    if tcx.sess.opts.debugging_opts.chalk {
+    if tcx.sess.opts.unstable_opts.chalk {
         let environment = well_formed_types_in_env(tcx, def_id);
         predicates.extend(environment);
     }
diff --git a/compiler/rustc_typeck/src/check/generator_interior.rs b/compiler/rustc_typeck/src/check/generator_interior.rs
index 6ee989070b4..81875fbc0b0 100644
--- a/compiler/rustc_typeck/src/check/generator_interior.rs
+++ b/compiler/rustc_typeck/src/check/generator_interior.rs
@@ -69,7 +69,7 @@ impl<'a, 'tcx> InteriorVisitor<'a, 'tcx> {
                                 yield_data.expr_and_pat_count, self.expr_count, source_span
                             );
 
-                            if self.fcx.sess().opts.debugging_opts.drop_tracking
+                            if self.fcx.sess().opts.unstable_opts.drop_tracking
                                 && self
                                     .drop_ranges
                                     .is_dropped_at(hir_id, yield_data.expr_and_pat_count)
diff --git a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges.rs b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges.rs
index 887c791af76..14b226d91cb 100644
--- a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges.rs
+++ b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges.rs
@@ -38,7 +38,7 @@ pub fn compute_drop_ranges<'a, 'tcx>(
     def_id: DefId,
     body: &'tcx Body<'tcx>,
 ) -> DropRanges {
-    if fcx.sess().opts.debugging_opts.drop_tracking {
+    if fcx.sess().opts.unstable_opts.drop_tracking {
         let consumed_borrowed_places = find_consumed_and_borrowed(fcx, def_id, body);
 
         let typeck_results = &fcx.typeck_results.borrow();
diff --git a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/cfg_build.rs b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/cfg_build.rs
index 111d534abf8..da2db3f2e30 100644
--- a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/cfg_build.rs
+++ b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/cfg_build.rs
@@ -33,7 +33,7 @@ pub(super) fn build_control_flow_graph<'tcx>(
     intravisit::walk_body(&mut drop_range_visitor, body);
 
     drop_range_visitor.drop_ranges.process_deferred_edges();
-    if let Some(filename) = &tcx.sess.opts.debugging_opts.dump_drop_tracking_cfg {
+    if let Some(filename) = &tcx.sess.opts.unstable_opts.dump_drop_tracking_cfg {
         super::cfg_visualize::write_graph_to_file(&drop_range_visitor.drop_ranges, filename, tcx);
     }
 
diff --git a/compiler/rustc_typeck/src/check/method/probe.rs b/compiler/rustc_typeck/src/check/method/probe.rs
index 2de22530356..416d33c7aa0 100644
--- a/compiler/rustc_typeck/src/check/method/probe.rs
+++ b/compiler/rustc_typeck/src/check/method/probe.rs
@@ -1065,7 +1065,7 @@ impl<'a, 'tcx> ProbeContext<'a, 'tcx> {
         let pick = self.pick_all_method(Some(&mut unstable_candidates));
 
         // In this case unstable picking is done by `pick_method`.
-        if !self.tcx.sess.opts.debugging_opts.pick_stable_methods_before_any_unstable {
+        if !self.tcx.sess.opts.unstable_opts.pick_stable_methods_before_any_unstable {
             return pick;
         }
 
@@ -1269,7 +1269,7 @@ impl<'a, 'tcx> ProbeContext<'a, 'tcx> {
         self_ty: Ty<'tcx>,
         mut unstable_candidates: Option<&mut Vec<(Candidate<'tcx>, Symbol)>>,
     ) -> Option<PickResult<'tcx>> {
-        if !self.tcx.sess.opts.debugging_opts.pick_stable_methods_before_any_unstable {
+        if !self.tcx.sess.opts.unstable_opts.pick_stable_methods_before_any_unstable {
             return self.pick_method_with_unstable(self_ty);
         }
 
diff --git a/compiler/rustc_typeck/src/check/upvar.rs b/compiler/rustc_typeck/src/check/upvar.rs
index 74546ed9080..824ddb10a37 100644
--- a/compiler/rustc_typeck/src/check/upvar.rs
+++ b/compiler/rustc_typeck/src/check/upvar.rs
@@ -315,7 +315,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
             .collect();
         self.typeck_results.borrow_mut().closure_fake_reads.insert(closure_def_id, fake_reads);
 
-        if self.tcx.sess.opts.debugging_opts.profile_closures {
+        if self.tcx.sess.opts.unstable_opts.profile_closures {
             self.typeck_results.borrow_mut().closure_size_eval.insert(
                 closure_def_id,
                 ClosureSizeProfileData {
diff --git a/src/doc/man/rustc.1 b/src/doc/man/rustc.1
index 4e7170806d4..ff41324ef26 100644
--- a/src/doc/man/rustc.1
+++ b/src/doc/man/rustc.1
@@ -143,7 +143,7 @@ Specify where an external rust library is located. These should match
 Override the system root.
 .TP
 \fB\-Z\fR \fIFLAG\fR
-Set internal debugging options.
+Set unstable / perma-unstable options.
 Use \fI\-Z help\fR to print available options.
 .TP
 \fB\-\-color\fR auto|always|never
diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs
index fa2efb00416..2c98cba90d7 100644
--- a/src/librustdoc/clean/mod.rs
+++ b/src/librustdoc/clean/mod.rs
@@ -1502,7 +1502,7 @@ impl<'tcx> Clean<'tcx, Type> for hir::Ty<'tcx> {
 /// Returns `None` if the type could not be normalized
 fn normalize<'tcx>(cx: &mut DocContext<'tcx>, ty: Ty<'_>) -> Option<Ty<'tcx>> {
     // HACK: low-churn fix for #79459 while we wait for a trait normalization fix
-    if !cx.tcx.sess.opts.debugging_opts.normalize_docs {
+    if !cx.tcx.sess.opts.unstable_opts.normalize_docs {
         return None;
     }
 
diff --git a/src/librustdoc/config.rs b/src/librustdoc/config.rs
index 1f30c7006f5..8a8cc272e81 100644
--- a/src/librustdoc/config.rs
+++ b/src/librustdoc/config.rs
@@ -12,7 +12,7 @@ use rustc_session::config::{
 };
 use rustc_session::config::{get_cmd_lint_options, nightly_options};
 use rustc_session::config::{
-    CodegenOptions, DebuggingOptions, ErrorOutputType, Externs, JsonUnusedExterns,
+    CodegenOptions, ErrorOutputType, Externs, JsonUnusedExterns, UnstableOptions,
 };
 use rustc_session::getopts;
 use rustc_session::lint::Level;
@@ -91,10 +91,10 @@ pub(crate) struct Options {
     pub(crate) codegen_options: CodegenOptions,
     /// Codegen options strings to hand to the compiler.
     pub(crate) codegen_options_strs: Vec<String>,
-    /// Debugging (`-Z`) options to pass to the compiler.
-    pub(crate) debugging_opts: DebuggingOptions,
-    /// Debugging (`-Z`) options strings to pass to the compiler.
-    pub(crate) debugging_opts_strs: Vec<String>,
+    /// Unstable (`-Z`) options to pass to the compiler.
+    pub(crate) unstable_opts: UnstableOptions,
+    /// Unstable (`-Z`) options strings to pass to the compiler.
+    pub(crate) unstable_opts_strs: Vec<String>,
     /// The target used to compile the crate against.
     pub(crate) target: TargetTriple,
     /// Edition used when reading the crate. Defaults to "2015". Also used by default when
@@ -181,7 +181,7 @@ impl fmt::Debug for Options {
             .field("cfgs", &self.cfgs)
             .field("check-cfgs", &self.check_cfgs)
             .field("codegen_options", &"...")
-            .field("debugging_options", &"...")
+            .field("unstable_options", &"...")
             .field("target", &self.target)
             .field("edition", &self.edition)
             .field("maybe_sysroot", &self.maybe_sysroot)
@@ -331,7 +331,7 @@ impl Options {
 
         let z_flags = matches.opt_strs("Z");
         if z_flags.iter().any(|x| *x == "help") {
-            print_flag_list("-Z", config::DB_OPTIONS);
+            print_flag_list("-Z", config::Z_OPTIONS);
             return Err(0);
         }
         let c_flags = matches.opt_strs("C");
@@ -347,9 +347,9 @@ impl Options {
         let diagnostic_width = matches.opt_get("diagnostic-width").unwrap_or_default();
 
         let codegen_options = CodegenOptions::build(matches, error_format);
-        let debugging_opts = DebuggingOptions::build(matches, error_format);
+        let unstable_opts = UnstableOptions::build(matches, error_format);
 
-        let diag = new_handler(error_format, None, diagnostic_width, &debugging_opts);
+        let diag = new_handler(error_format, None, diagnostic_width, &unstable_opts);
 
         // check for deprecated options
         check_deprecated_options(matches, &diag);
@@ -454,7 +454,7 @@ impl Options {
             .iter()
             .map(|s| SearchPath::from_cli_opt(s, error_format))
             .collect();
-        let externs = parse_externs(matches, &debugging_opts, error_format);
+        let externs = parse_externs(matches, &unstable_opts, error_format);
         let extern_html_root_urls = match parse_extern_html_roots(matches) {
             Ok(ex) => ex,
             Err(err) => {
@@ -670,7 +670,7 @@ impl Options {
         let persist_doctests = matches.opt_str("persist-doctests").map(PathBuf::from);
         let test_builder = matches.opt_str("test-builder").map(PathBuf::from);
         let codegen_options_strs = matches.opt_strs("C");
-        let debugging_opts_strs = matches.opt_strs("Z");
+        let unstable_opts_strs = matches.opt_strs("Z");
         let lib_strs = matches.opt_strs("L");
         let extern_strs = matches.opt_strs("extern");
         let runtool = matches.opt_str("runtool");
@@ -711,8 +711,8 @@ impl Options {
             check_cfgs,
             codegen_options,
             codegen_options_strs,
-            debugging_opts,
-            debugging_opts_strs,
+            unstable_opts,
+            unstable_opts_strs,
             target,
             edition,
             maybe_sysroot,
diff --git a/src/librustdoc/core.rs b/src/librustdoc/core.rs
index 25438ff85aa..a658e78bf60 100644
--- a/src/librustdoc/core.rs
+++ b/src/librustdoc/core.rs
@@ -32,7 +32,7 @@ use crate::formats::cache::Cache;
 use crate::passes::collect_intra_doc_links::PreprocessedMarkdownLink;
 use crate::passes::{self, Condition::*};
 
-pub(crate) use rustc_session::config::{DebuggingOptions, Input, Options};
+pub(crate) use rustc_session::config::{Input, Options, UnstableOptions};
 
 pub(crate) struct ResolverCaches {
     pub(crate) markdown_links: Option<FxHashMap<String, Vec<PreprocessedMarkdownLink>>>,
@@ -155,7 +155,7 @@ pub(crate) fn new_handler(
     error_format: ErrorOutputType,
     source_map: Option<Lrc<source_map::SourceMap>>,
     diagnostic_width: Option<usize>,
-    debugging_opts: &DebuggingOptions,
+    unstable_opts: &UnstableOptions,
 ) -> rustc_errors::Handler {
     let fallback_bundle =
         rustc_errors::fallback_fluent_bundle(rustc_errors::DEFAULT_LOCALE_RESOURCES, false);
@@ -169,11 +169,11 @@ pub(crate) fn new_handler(
                     None,
                     fallback_bundle,
                     short,
-                    debugging_opts.teach,
+                    unstable_opts.teach,
                     diagnostic_width,
                     false,
                 )
-                .ui_testing(debugging_opts.ui_testing),
+                .ui_testing(unstable_opts.ui_testing),
             )
         }
         ErrorOutputType::Json { pretty, json_rendered } => {
@@ -191,14 +191,14 @@ pub(crate) fn new_handler(
                     diagnostic_width,
                     false,
                 )
-                .ui_testing(debugging_opts.ui_testing),
+                .ui_testing(unstable_opts.ui_testing),
             )
         }
     };
 
     rustc_errors::Handler::with_emitter_and_flags(
         emitter,
-        debugging_opts.diagnostic_handler_flags(true),
+        unstable_opts.diagnostic_handler_flags(true),
     )
 }
 
@@ -215,7 +215,7 @@ pub(crate) fn create_config(
         mut cfgs,
         check_cfgs,
         codegen_options,
-        debugging_opts,
+        unstable_opts,
         target,
         edition,
         maybe_sysroot,
@@ -266,7 +266,7 @@ pub(crate) fn create_config(
         target_triple: target,
         unstable_features: UnstableFeatures::from_environment(crate_name.as_deref()),
         actually_rustdoc: true,
-        debugging_opts,
+        unstable_opts,
         error_format,
         diagnostic_width,
         edition,
diff --git a/src/librustdoc/doctest.rs b/src/librustdoc/doctest.rs
index fe26e53b963..568bad2a382 100644
--- a/src/librustdoc/doctest.rs
+++ b/src/librustdoc/doctest.rs
@@ -357,8 +357,8 @@ fn run_test(
     for codegen_options_str in &rustdoc_options.codegen_options_strs {
         compiler.arg("-C").arg(&codegen_options_str);
     }
-    for debugging_option_str in &rustdoc_options.debugging_opts_strs {
-        compiler.arg("-Z").arg(&debugging_option_str);
+    for unstable_option_str in &rustdoc_options.unstable_opts_strs {
+        compiler.arg("-Z").arg(&unstable_option_str);
     }
     if no_run && !lang_string.compile_fail && rustdoc_options.persist_doctests.is_none() {
         compiler.arg("--emit=metadata");
diff --git a/src/librustdoc/lib.rs b/src/librustdoc/lib.rs
index 0d3ec7ecb64..f7dc91a7832 100644
--- a/src/librustdoc/lib.rs
+++ b/src/librustdoc/lib.rs
@@ -366,7 +366,7 @@ fn opts() -> Vec<RustcOptGroup> {
             )
         }),
         unstable("Z", |o| {
-            o.optmulti("Z", "", "internal and debugging options (only on nightly build)", "FLAG")
+            o.optmulti("Z", "", "unstable / perma-unstable options (only on nightly build)", "FLAG")
         }),
         stable("sysroot", |o| o.optopt("", "sysroot", "Override the system root", "PATH")),
         unstable("playground-url", |o| {
@@ -745,7 +745,7 @@ fn main_options(options: config::Options) -> MainResult {
         options.error_format,
         None,
         options.diagnostic_width,
-        &options.debugging_opts,
+        &options.unstable_opts,
     );
 
     match (options.should_test, options.markdown_input()) {
@@ -787,7 +787,7 @@ fn main_options(options: config::Options) -> MainResult {
 
         if sess.opts.describe_lints {
             let mut lint_store = rustc_lint::new_lint_store(
-                sess.opts.debugging_opts.no_interleave_lints,
+                sess.opts.unstable_opts.no_interleave_lints,
                 sess.unstable_options(),
             );
             let registered_lints = if let Some(register_lints) = compiler.register_lints() {
diff --git a/src/test/run-make/issue-88756-default-output/output-default.stdout b/src/test/run-make/issue-88756-default-output/output-default.stdout
index 08877af9286..80cd08ee167 100644
--- a/src/test/run-make/issue-88756-default-output/output-default.stdout
+++ b/src/test/run-make/issue-88756-default-output/output-default.stdout
@@ -68,7 +68,8 @@ Options:
                         doc with your own theme. However, your theme might
                         break if the rustdoc's generated HTML changes, so be
                         careful!
-    -Z FLAG             internal and debugging options (only on nightly build)
+    -Z FLAG             unstable / perma-unstable options (only on nightly
+                        build)
         --sysroot PATH  Override the system root
         --playground-url URL
                         URL to send code snippets to, may be reset by
diff --git a/src/test/ui/invalid-compile-flags/branch-protection-missing-pac-ret.BADFLAGS.stderr b/src/test/ui/invalid-compile-flags/branch-protection-missing-pac-ret.BADFLAGS.stderr
index 5528d2a0729..d0e8d4719d3 100644
--- a/src/test/ui/invalid-compile-flags/branch-protection-missing-pac-ret.BADFLAGS.stderr
+++ b/src/test/ui/invalid-compile-flags/branch-protection-missing-pac-ret.BADFLAGS.stderr
@@ -1,2 +1,2 @@
-error: incorrect value `leaf` for debugging option `branch-protection` - a `,` separated combination of `bti`, `b-key`, `pac-ret`, or `leaf` was expected
+error: incorrect value `leaf` for unstable option `branch-protection` - a `,` separated combination of `bti`, `b-key`, `pac-ret`, or `leaf` was expected
 
diff --git a/src/tools/clippy/src/driver.rs b/src/tools/clippy/src/driver.rs
index 96d542cfe10..c219c7de830 100644
--- a/src/tools/clippy/src/driver.rs
+++ b/src/tools/clippy/src/driver.rs
@@ -117,7 +117,7 @@ impl rustc_driver::Callbacks for ClippyCallbacks {
         // run on the unoptimized MIR. On the other hand this results in some false negatives. If
         // MIR passes can be enabled / disabled separately, we should figure out, what passes to
         // use for Clippy.
-        config.opts.debugging_opts.mir_opt_level = Some(0);
+        config.opts.unstable_opts.mir_opt_level = Some(0);
     }
 }