diff --git a/src/librustdoc/html/markdown.rs b/src/librustdoc/html/markdown.rs
index dee0a01a65413..0ff73eb79de03 100644
--- a/src/librustdoc/html/markdown.rs
+++ b/src/librustdoc/html/markdown.rs
@@ -1180,14 +1180,23 @@ pub(crate) fn short_markdown_summary(markdown: &str, link_names: &[RenderedLink]
/// - Headings, links, and formatting are stripped.
/// - Inline code is rendered as-is, surrounded by backticks.
/// - HTML and code blocks are ignored.
-pub(crate) fn plain_text_summary(md: &str) -> String {
+pub(crate) fn plain_text_summary(md: &str, link_names: &[RenderedLink]) -> String {
if md.is_empty() {
return String::new();
}
let mut s = String::with_capacity(md.len() * 3 / 2);
- for event in Parser::new_ext(md, summary_opts()) {
+ let mut replacer = |broken_link: BrokenLink<'_>| {
+ link_names
+ .iter()
+ .find(|link| link.original_text.as_str() == &*broken_link.reference)
+ .map(|link| (link.href.as_str().into(), link.new_text.as_str().into()))
+ };
+
+ let p = Parser::new_with_broken_link_callback(md, summary_opts(), Some(&mut replacer));
+
+ for event in p {
match &event {
Event::Text(text) => s.push_str(text),
Event::Code(code) => {
diff --git a/src/librustdoc/html/markdown/tests.rs b/src/librustdoc/html/markdown/tests.rs
index 5878c58264ec3..e05635a020756 100644
--- a/src/librustdoc/html/markdown/tests.rs
+++ b/src/librustdoc/html/markdown/tests.rs
@@ -249,7 +249,7 @@ fn test_short_markdown_summary() {
#[test]
fn test_plain_text_summary() {
fn t(input: &str, expect: &str) {
- let output = plain_text_summary(input);
+ let output = plain_text_summary(input, &[]);
assert_eq!(output, expect, "original: {}", input);
}
diff --git a/src/librustdoc/html/render/context.rs b/src/librustdoc/html/render/context.rs
index 1216a8d71c8cf..6762fba9275cf 100644
--- a/src/librustdoc/html/render/context.rs
+++ b/src/librustdoc/html/render/context.rs
@@ -182,7 +182,10 @@ impl<'tcx> Context<'tcx> {
};
title.push_str(" - Rust");
let tyname = it.type_();
- let desc = it.doc_value().as_ref().map(|doc| plain_text_summary(doc));
+ let desc = it
+ .doc_value()
+ .as_ref()
+ .map(|doc| plain_text_summary(doc, &it.link_names(&self.cache())));
let desc = if let Some(desc) = desc {
desc
} else if it.is_crate() {
diff --git a/tests/rustdoc/description.rs b/tests/rustdoc/description.rs
index 05ec428220847..43cd59ebd0924 100644
--- a/tests/rustdoc/description.rs
+++ b/tests/rustdoc/description.rs
@@ -22,3 +22,9 @@ pub mod foo_mod {
// 'Only paragraph.'
/// Only paragraph.
pub fn foo_fn() {}
+
+// @has 'foo/fn.bar_fn.html' '//meta[@name="description"]/@content' \
+// 'Description with intra-doc link to foo_fn and [nonexistent_item] and foo_fn.'
+#[allow(rustdoc::broken_intra_doc_links)]
+/// Description with intra-doc link to [foo_fn] and [nonexistent_item] and [foo_fn](self::foo_fn).
+pub fn bar_fn() {}