diff --git a/include/libcamera/internal/media_pipeline.h b/include/libcamera/internal/media_pipeline.h
index a7a4b8c559cd..f62e3e8c58b0 100644
--- a/include/libcamera/internal/media_pipeline.h
+++ b/include/libcamera/internal/media_pipeline.h
@@ -23,36 +23,21 @@ struct V4L2SubdeviceFormat;
 class MediaPipeline
 {
 public:
-	int init(MediaEntity *source, std::string_view sink);
-	int initLinks();
-	int configure(CameraSensor *sensor, V4L2SubdeviceFormat *);
-
-private:
 	struct Entity {
-		/* The media entity, always valid. */
 		MediaEntity *entity;
-		/*
-		 * Whether or not the entity is a subdev that supports the
-		 * routing API.
-		 */
 		bool supportsRouting;
-		/*
-		 * The local sink pad connected to the upstream entity, null for
-		 * the camera sensor at the beginning of the pipeline.
-		 */
 		const MediaPad *sink;
-		/*
-		 * The local source pad connected to the downstream entity, null
-		 * for the video node at the end of the pipeline.
-		 */
 		const MediaPad *source;
-		/*
-		 * The link on the source pad, to the downstream entity, null
-		 * for the video node at the end of the pipeline.
-		 */
 		MediaLink *sourceLink;
 	};
 
+	int init(MediaEntity *source, std::string_view sink);
+	int initLinks();
+	int configure(CameraSensor *sensor, V4L2SubdeviceFormat *);
+
+	const std::list<Entity> &entities() const { return entities_; }
+
+private:
 	std::list<Entity> entities_;
 };
 
diff --git a/src/libcamera/media_pipeline.cpp b/src/libcamera/media_pipeline.cpp
index c4e9f69b8f6a..3c5517314a4a 100644
--- a/src/libcamera/media_pipeline.cpp
+++ b/src/libcamera/media_pipeline.cpp
@@ -43,6 +43,52 @@ LOG_DEFINE_CATEGORY(MediaPipeline)
  * two entities in a media graph.
  */
 
+/**
+ * \struct MediaPipeline::Entity
+ * \brief A node composing the media pipeline
+ *
+ * The MediaPipeline::Entity structure stores how a MediaEntity composing a
+ * media pipeline is connected to other media entities. It stores pointers
+ * to the source pad, the sink pad and the media link traversed by the media
+ * pipeline, as well as a flag that reports if the entity supports internal
+ * routing.
+ */
+
+/**
+ * \var MediaPipeline::Entity::entity
+ * \brief Pointer to the libcamera::MediaEntity, always valid
+ */
+
+/**
+ * \var MediaPipeline::Entity::supportsRouting
+ * \brief Whether or not the entity is a subdev that supports the routing API
+ */
+
+/**
+ * \var MediaPipeline::Entity::sink
+ * \brief The local libcamera::MediaPad sink pad connected to the upstream entity,
+ * null for the camera sensor at the beginning of the pipeline
+ */
+
+/**
+ * \var MediaPipeline::Entity::source
+ * \brief The local libcamera::MediaPad source pad connected to the upstream entity,
+ * null for the last node at the end of the pipeline
+ */
+
+/**
+ * \var MediaPipeline::Entity::sourceLink
+ * \brief The link on the libcamera::MediaLink source pad, to the downstream entity,
+ * null for the last node at the end of the pipeline
+ */
+
+/**
+ * \fn MediaPipeline::entities()
+ * \brief Retrieve list of entities composing the media pipeline
+ * \return The list of MediaPipeline::Entity entities composing the media
+ * pipeline
+ */
+
 /**
  * \brief Retrieve all source pads connected to a sink pad through active routes
  *
