diff --git a/src/abg-dwarf-reader.cc b/src/abg-dwarf-reader.cc
index ce6b52d4..79322490 100644
--- a/src/abg-dwarf-reader.cc
+++ b/src/abg-dwarf-reader.cc
@@ -424,6 +424,9 @@ pointer_or_qual_die_of_anonymous_class_type(const Dwarf_Die* die);
 static bool
 die_is_reference_type(const Dwarf_Die* die);
 
+static bool
+die_is_pointer_array_or_reference_type(const Dwarf_Die* die);
+
 static bool
 die_is_pointer_or_reference_type(const Dwarf_Die* die);
 
@@ -570,6 +573,9 @@ die_function_signature(const reader& rdr,
 static bool
 die_peel_qual_ptr(Dwarf_Die *die, Dwarf_Die& peeled_die);
 
+static bool
+die_peel_qualified(Dwarf_Die *die, Dwarf_Die& peeled_die);
+
 static bool
 die_function_type_is_method_type(const reader& rdr,
 				 const Dwarf_Die *die,
@@ -6912,7 +6918,7 @@ die_is_pointer_type(const Dwarf_Die* die)
 static bool
 pointer_or_qual_die_of_anonymous_class_type(const Dwarf_Die* die)
 {
-  if (!die_is_pointer_or_reference_type(die)
+  if (!die_is_pointer_array_or_reference_type(die)
       && !die_is_qualified_type(die))
     return false;
 
@@ -6970,11 +6976,20 @@ die_is_array_type(const Dwarf_Die* die)
 ///
 /// @return true iff @p die represents a pointer or reference type.
 static bool
-die_is_pointer_or_reference_type(const Dwarf_Die* die)
+die_is_pointer_array_or_reference_type(const Dwarf_Die* die)
 {return (die_is_pointer_type(die)
 	 || die_is_reference_type(die)
 	 || die_is_array_type(die));}
 
+/// Test if a DIE represents a pointer or a reference type.
+///
+/// @param die the die to consider.
+///
+/// @return true iff @p die represents a pointer or reference type.
+static bool
+die_is_pointer_or_reference_type(const Dwarf_Die* die)
+{return (die_is_pointer_type(die) || die_is_reference_type(die));}
+
 /// Test if a DIE represents a pointer, a reference or a typedef type.
 ///
 /// @param die the die to consider.
@@ -6983,7 +6998,7 @@ die_is_pointer_or_reference_type(const Dwarf_Die* die)
 /// typedef type.
 static bool
 die_is_pointer_reference_or_typedef_type(const Dwarf_Die* die)
-{return (die_is_pointer_or_reference_type(die)
+{return (die_is_pointer_array_or_reference_type(die)
 	 || dwarf_tag(const_cast<Dwarf_Die*>(die)) == DW_TAG_typedef);}
 
 /// Test if a DIE represents a class type.
@@ -7225,6 +7240,38 @@ die_peel_qual_ptr(Dwarf_Die *die, Dwarf_Die& peeled_die)
   return true;
 }
 
+/// Return the leaf object under a qualified type DIE.
+///
+/// @param die the DIE of the type to consider.
+///
+/// @param peeled_die out parameter.  Set to the DIE of the leaf
+/// object iff the function actually peeled anything.
+///
+/// @return true upon successful completion.
+static bool
+die_peel_qualified(Dwarf_Die *die, Dwarf_Die& peeled_die)
+{
+  if (!die)
+    return false;
+
+  memcpy(&peeled_die, die, sizeof(peeled_die));
+
+  int tag = dwarf_tag(&peeled_die);
+
+  bool result = false;
+  while (tag == DW_TAG_const_type
+	 || tag == DW_TAG_volatile_type
+	 || tag == DW_TAG_restrict_type)
+    {
+      if (!die_die_attribute(&peeled_die, DW_AT_type, peeled_die))
+	break;
+      tag = dwarf_tag(&peeled_die);
+      result = true;
+    }
+
+  return result;
+}
+
 /// Return the leaf object under a typedef type DIE.
 ///
 /// @param die the DIE of the type to consider.
@@ -9096,9 +9143,15 @@ die_qualified_type_name(const reader& rdr,
 	  repr.clear();
 	else
 	  {
-	    if (has_underlying_type_die
-		&& die_is_pointer_or_reference_type(&underlying_type_die))
-	      repr = underlying_type_repr + " " + repr;
+	    if (has_underlying_type_die)
+	      {
+		Dwarf_Die peeled;
+		die_peel_qualified(&underlying_type_die, peeled);
+		if (die_is_pointer_or_reference_type(&peeled))
+		  repr = underlying_type_repr + " " + repr;
+		else
+		  repr += " " + underlying_type_repr;
+	      }
 	    else
 	      repr += " " + underlying_type_repr;
 	  }
diff --git a/src/abg-ir.cc b/src/abg-ir.cc
index 4a598bde..ff7573ea 100644
--- a/src/abg-ir.cc
+++ b/src/abg-ir.cc
@@ -8740,9 +8740,8 @@ get_name_of_qualified_type(const type_base_sptr& underlying_type,
 
   if (!quals_repr.empty())
     {
-      if (is_pointer_type(underlying_type)
-	  || is_reference_type(underlying_type)
-	  || is_array_type(underlying_type))
+      if (is_pointer_type(peel_qualified_type(underlying_type))
+	  || is_reference_type(peel_qualified_type(underlying_type)))
 	{
 	  name += " ";
 	  name += quals_repr;
diff --git a/tests/data/Makefile.am b/tests/data/Makefile.am
index a4740e3e..00b8126b 100644
--- a/tests/data/Makefile.am
+++ b/tests/data/Makefile.am
@@ -248,6 +248,11 @@ test-abidiff-exit/btf/test0-v0.c	\
 test-abidiff-exit/btf/test0-v0.o	\
 test-abidiff-exit/btf/test0-v1.c	\
 test-abidiff-exit/btf/test0-v1.o	\
+test-abidiff-exit/PR30048-test-report-0.txt \
+test-abidiff-exit/PR30048-test-v0.c \
+test-abidiff-exit/PR30048-test-v1.c \
+test-abidiff-exit/PR30048-test-v0.o \
+test-abidiff-exit/PR30048-test-v1.o \
 \
 test-diff-dwarf/test0-v0.cc		\
 test-diff-dwarf/test0-v0.o			\
diff --git a/tests/data/test-abidiff-exit/PR30048-test-report-0.txt b/tests/data/test-abidiff-exit/PR30048-test-report-0.txt
new file mode 100644
index 00000000..23a4c10b
--- /dev/null
+++ b/tests/data/test-abidiff-exit/PR30048-test-report-0.txt
@@ -0,0 +1,19 @@
+Functions changes summary: 0 Removed, 0 Changed, 0 Added function
+Variables changes summary: 0 Removed, 1 Changed, 0 Added variable
+
+1 Changed variable:
+
+  [C] 'S s' was changed at PR30048-test-v1.c:6:1:
+    size of symbol changed from 56 to 16
+    type of variable changed:
+      type size changed from 448 to 128 (in bits)
+      5 data member deletions:
+        'int (int)* f01', at offset 0 (in bits) at PR30048-test-v0.c:2:1
+        'int (const int*)* f02', at offset 64 (in bits) at PR30048-test-v0.c:3:1
+        'int (int* const)* f03', at offset 128 (in bits) at PR30048-test-v0.c:4:1
+        'int (int* restrict)* f04', at offset 192 (in bits) at PR30048-test-v0.c:5:1
+        'int (const int* restrict)* f05', at offset 256 (in bits) at PR30048-test-v0.c:6:1
+      2 data member changes:
+        'int (int* restrict const)* f06' offset changed from 320 to 0 (in bits) (by -320 bits)
+        'int (int* restrict const)* f07' offset changed from 384 to 64 (in bits) (by -320 bits)
+
diff --git a/tests/data/test-abidiff-exit/PR30048-test-v0.c b/tests/data/test-abidiff-exit/PR30048-test-v0.c
new file mode 100644
index 00000000..b00f6d7d
--- /dev/null
+++ b/tests/data/test-abidiff-exit/PR30048-test-v0.c
@@ -0,0 +1,12 @@
+struct S {
+  int (*f01)(int);
+  int (*f02)(const int*);
+  int (*f03)(int* const);
+  int (*f04)(int* restrict);
+  int (*f05)(const int* restrict);
+  int (*f06)(int* restrict const);
+  int (*f07)(int* const restrict);
+};
+
+struct S s;
+
diff --git a/tests/data/test-abidiff-exit/PR30048-test-v0.o b/tests/data/test-abidiff-exit/PR30048-test-v0.o
new file mode 100644
index 0000000000000000000000000000000000000000..91e136f4e8d9a108aed18b7af55d92415ef5c1d4
GIT binary patch
diff --git a/tests/data/test-abidiff-exit/PR30048-test-v1.c b/tests/data/test-abidiff-exit/PR30048-test-v1.c
--- /dev/null
+++ b/tests/data/test-abidiff-exit/PR30048-test-v1.c
@@ -0,0 +1,6 @@
+struct S {
+  int (*f06)(int* restrict const);
+  int (*f07)(int* const restrict);
+};
+
+struct S s;
diff --git a/tests/data/test-abidiff-exit/PR30048-test-v1.o b/tests/data/test-abidiff-exit/PR30048-test-v1.o
new file mode 100644
index 0000000000000000000000000000000000000000..161e45656fc168d917eae9b9bca9465786d35205
GIT binary patch
diff --git a/tests/data/test-abidiff-exit/qualifier-typedef-array-report-1.txt b/tests/data/test-abidiff-exit/qualifier-typedef-array-report-1.txt
--- a/tests/data/test-abidiff-exit/qualifier-typedef-array-report-1.txt
+++ b/tests/data/test-abidiff-exit/qualifier-typedef-array-report-1.txt
@@ -47,39 +47,39 @@ Variables changes summary: 0 Removed, 0 Changed, 0 Added variable
             underlying type 'typedef A' at qualifier-typedef-array-v0.c:1:1 changed:
               entity changed from 'typedef A' to compatible type 'void*[7]'
           type of 'C v_c' changed:
-            entity changed from 'typedef C' to compatible type 'const volatile void*[7]'
+            entity changed from 'typedef C' to compatible type 'void* const volatile[7]'
               array element type 'void* const' changed:
-                'void* const' changed to 'const volatile void*'
-              type name changed from 'void* const[7]' to 'const volatile void*[7]'
+                'void* const' changed to 'void* const volatile'
+              type name changed from 'void* const[7]' to 'void* const volatile[7]'
               type size hasn't changed
           type of 'C r_c' changed:
-            entity changed from 'typedef C' to compatible type 'restrict const void*[7]'
+            entity changed from 'typedef C' to compatible type 'void* restrict const[7]'
               array element type 'void* const' changed:
-                'void* const' changed to 'restrict const void*'
-              type name changed from 'void* const[7]' to 'restrict const void*[7]'
+                'void* const' changed to 'void* restrict const'
+              type name changed from 'void* const[7]' to 'void* restrict const[7]'
               type size hasn't changed
           type of 'D v_d' changed:
-            entity changed from 'typedef D' to compatible type 'const volatile void*[7]'
+            entity changed from 'typedef D' to compatible type 'void* const volatile[7]'
               array element type 'void* const' changed:
-                'void* const' changed to 'const volatile void*'
-              type name changed from 'void* const[7]' to 'const volatile void*[7]'
+                'void* const' changed to 'void* const volatile'
+              type name changed from 'void* const[7]' to 'void* const volatile[7]'
               type size hasn't changed
           type of 'D r_d' changed:
-            entity changed from 'typedef D' to compatible type 'restrict const void*[7]'
+            entity changed from 'typedef D' to compatible type 'void* restrict const[7]'
               array element type 'void* const' changed:
-                'void* const' changed to 'restrict const void*'
-              type name changed from 'void* const[7]' to 'restrict const void*[7]'
+                'void* const' changed to 'void* restrict const'
+              type name changed from 'void* const[7]' to 'void* restrict const[7]'
               type size hasn't changed
           type of 'E r_e' changed:
-            entity changed from 'typedef E' to compatible type 'restrict const volatile void*[7]'
-              array element type 'const volatile void*' changed:
-                'const volatile void*' changed to 'restrict const volatile void*'
-              type name changed from 'const volatile void*[7]' to 'restrict const volatile void*[7]'
+            entity changed from 'typedef E' to compatible type 'void* restrict const volatile[7]'
+              array element type 'void* const volatile' changed:
+                'void* const volatile' changed to 'void* restrict const volatile'
+              type name changed from 'void* const volatile[7]' to 'void* restrict const volatile[7]'
               type size hasn't changed
           type of 'F r_f' changed:
-            entity changed from 'typedef F' to compatible type 'restrict const volatile void*[7]'
-              array element type 'const volatile void*' changed:
-                'const volatile void*' changed to 'restrict const volatile void*'
-              type name changed from 'const volatile void*[7]' to 'restrict const volatile void*[7]'
+            entity changed from 'typedef F' to compatible type 'void* restrict const volatile[7]'
+              array element type 'void* const volatile' changed:
+                'void* const volatile' changed to 'void* restrict const volatile'
+              type name changed from 'void* const volatile[7]' to 'void* restrict const volatile[7]'
               type size hasn't changed
 
diff --git a/tests/test-abidiff-exit.cc b/tests/test-abidiff-exit.cc
index df2f087c..73f9c0d4 100644
--- a/tests/test-abidiff-exit.cc
+++ b/tests/test-abidiff-exit.cc
@@ -471,6 +471,17 @@ InOutSpec in_out_specs[] =
     "data/test-abidiff-exit/test-rhbz2114909-report-1.txt",
     "output/test-abidiff-exit/test-rhbz2114909-report-1.txt"
   },
+  {
+    "data/test-abidiff-exit/PR30048-test-v0.o",
+    "data/test-abidiff-exit/PR30048-test-v1.o",
+    "",
+    "",
+    "",
+    "--no-default-suppression",
+    abigail::tools_utils::ABIDIFF_ABI_CHANGE,
+    "data/test-abidiff-exit/PR30048-test-report-0.txt",
+    "output/test-abidiff-exit/PR30048-test-report-0.txt"
+  },
 #ifdef WITH_BTF
   {
     "data/test-abidiff-exit/btf/test0-v0.o",
