diff --git a/django/contrib/contenttypes/fields.py b/django/contrib/contenttypes/fields.py
index 4015f16c6b..163e3a9c50 100644
--- a/django/contrib/contenttypes/fields.py
+++ b/django/contrib/contenttypes/fields.py
@@ -583,11 +583,12 @@ def create_generic_related_manager(superclass, rel):
             # We (possibly) need to convert object IDs to the type of the
             # instances' PK in order to match up instances:
             object_id_converter = instances[0]._meta.pk.to_python
+            content_type_id_field_name = '%s_id' % self.content_type_field_name
             return (
                 queryset.filter(query),
                 lambda relobj: (
                     object_id_converter(getattr(relobj, self.object_id_field_name)),
-                    relobj.content_type_id
+                    getattr(relobj, content_type_id_field_name),
                 ),
                 lambda obj: (obj.pk, self.get_content_type(obj).pk),
                 False,
diff --git a/docs/releases/3.0.3.txt b/docs/releases/3.0.3.txt
index 2726e2d3ab..ed92938e09 100644
--- a/docs/releases/3.0.3.txt
+++ b/docs/releases/3.0.3.txt
@@ -35,3 +35,7 @@ Bugfixes
 * Fixed a regression in Django 2.2.7 that caused
   :meth:`~django.db.models.Model.get_FOO_display` to work incorrectly when
   overriding inherited choices (:ticket:`31124`).
+
+* Fixed a regression in Django 3.0 that caused a crash of
+  ``QuerySet.prefetch_related()`` for ``GenericForeignKey`` with a custom
+  ``ContentType`` foreign key (:ticket:`31190`).
diff --git a/tests/generic_relations/tests.py b/tests/generic_relations/tests.py
index 7c0db95908..683efaddfb 100644
--- a/tests/generic_relations/tests.py
+++ b/tests/generic_relations/tests.py
@@ -564,6 +564,19 @@ class GenericRelationsTests(TestCase):
         for tag in tags:
             self.assertSequenceEqual(tag.content_object.tags.all(), [tag])
 
+    def test_prefetch_related_custom_object_id(self):
+        tiger = Animal.objects.create(common_name='tiger')
+        cheetah = Animal.objects.create(common_name='cheetah')
+        Comparison.objects.create(
+            first_obj=cheetah, other_obj=tiger, comparative='faster',
+        )
+        Comparison.objects.create(
+            first_obj=tiger, other_obj=cheetah, comparative='cooler',
+        )
+        qs = Comparison.objects.prefetch_related('first_obj__comparisons')
+        for comparison in qs:
+            self.assertSequenceEqual(comparison.first_obj.comparisons.all(), [comparison])
+
 
 class ProxyRelatedModelTest(TestCase):
     def test_default_behavior(self):