linux-media.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Yong <yong.deng@magewell.com>
To: Maxime Ripard <maxime.ripard@free-electrons.com>
Cc: Mauro Carvalho Chehab <mchehab@kernel.org>,
	Rob Herring <robh+dt@kernel.org>,
	Mark Rutland <mark.rutland@arm.com>, Chen-Yu Tsai <wens@csie.org>,
	Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	"David S. Miller" <davem@davemloft.net>,
	Hans Verkuil <hverkuil@xs4all.nl>, Arnd Bergmann <arnd@arndb.de>,
	Hugues Fruchet <hugues.fruchet@st.com>,
	Yannick Fertre <yannick.fertre@st.com>,
	Philipp Zabel <p.zabel@pengutronix.de>,
	Benoit Parrot <bparrot@ti.com>,
	Benjamin Gaignard <benjamin.gaignard@linaro.org>,
	Jean-Christophe Trotin <jean-christophe.trotin@st.com>,
	Ramesh Shanmugasundaram <ramesh.shanmugasundaram@bp.renesas.com>,
	Minghsiu Tsai <minghsiu.tsai@mediatek.com>,
	Krzysztof Kozlowski <krzk@kernel.org>,
	Robert Jarzmik <robert.jarzmik@free.fr>,
	linux-media@vger.kernel.org, devicetree@vger.kernel.org,
	linux-arm-kernel@lists.infradead.org,
	linux-kernel@vger.kernel.org, linux-sunxi@googlegroups.com
Subject: Re: [PATCH v2 1/3] media: V3s: Add support for Allwinner CSI.
Date: Thu, 23 Nov 2017 09:14:44 +0800	[thread overview]
Message-ID: <20171123091444.4bed66dffeb36ecea8dfa706@magewell.com> (raw)
In-Reply-To: <20171122094526.nqxfy2e5jzxw7nl4@flea.lan>

[-- Attachment #1: Type: text/plain, Size: 2932 bytes --]

Hi,

On Wed, 22 Nov 2017 10:45:26 +0100
Maxime Ripard <maxime.ripard@free-electrons.com> wrote:

> Hi,
> 
> On Wed, Nov 22, 2017 at 09:33:06AM +0800, Yong wrote:
> > > On Thu, Jul 27, 2017 at 01:01:35PM +0800, Yong Deng wrote:
> > > > Allwinner V3s SoC have two CSI module. CSI0 is used for MIPI interface
> > > > and CSI1 is used for parallel interface. This is not documented in
> > > > datasheet but by testing and guess.
> > > > 
> > > > This patch implement a v4l2 framework driver for it.
> > > > 
> > > > Currently, the driver only support the parallel interface. MIPI-CSI2,
> > > > ISP's support are not included in this patch.
> > > > 
> > > > Signed-off-by: Yong Deng <yong.deng@magewell.com>
> > > 
> > > Thanks again for this driver.
> > > 
> > > It seems like at least this iteration is behaving in a weird way with
> > > DMA transfers for at least YU12 and NV12 (and I would assume YV12).
> > > 
> > > Starting a transfer of multiple frames in either of these formats,
> > > using either ffmpeg (ffmpeg -f v4l2 -video_size 640x480 -framerate 30
> > > -i /dev/video0 output.mkv) or yavta (yavta -c80 -p -F --skip 0 -f NV12
> > > -s 640x480 $(media-c tl -e 'sun6i-csi')) will end up in a panic.
> > > 
> > > The panic seems to be generated with random data going into parts of
> > > the kernel memory, the pattern being in my case something like
> > > 0x8287868a which is very odd (always around 0x88)
> > > 
> > > It turns out that when you cover the sensor, the values change to
> > > around 0x28, so it really seems like it's pixels that have been copied
> > > there.
> > > 
> > > I've looked quickly at the DMA setup, and it seems reasonable to
> > > me. Do you have the same issue on your side? Have you been able to
> > > test those formats using your hardware?
> > 
> > I had tested the following formats with BT1120 input:
> > V4L2_PIX_FMT_NV12		-> NV12
> > V4L2_PIX_FMT_NV21		-> NV21
> > V4L2_PIX_FMT_NV16		-> NV16
> > V4L2_PIX_FMT_NV61		-> NV61
> > V4L2_PIX_FMT_YUV420		-> YU12
> > V4L2_PIX_FMT_YVU420		-> YV12
> > V4L2_PIX_FMT_YUV422P		-> 422P
> > And they all work fine.
> 
> Ok, that's good to know.
> 
> > > Given that they all are planar formats and YUYV and the likes work
> > > just fine, maybe we can leave them aside for now?
> > 
> > V4L2_PIX_FMT_YUV422P and V4L2_PIX_FMT_YUYV is OK, and V4L2_PIX_FMT_NV12
> > is bad? It's really weird.
> > 
> > What's your input bus code format, type and width?
> 
> The sensor is an ov5640, so the MBUS code for the bus is
> MEDIA_BUS_FMT_YUYV8_2X8.

Did you test on V3s?
I haven't tested it with MEDIA_BUS_FMT_YUYV8_2X8.

The Allwinner CSI's DMA is definitely weird. Ondřej Jirman thought
that CSI has an internal queue (Ondřej's commit has explained in detail).
I think CSI just pick up the buffer address before the frame done 
interrupt triggered. 
The patch in attachment can deal with this. You can see if it is
useful to solve your problem.

Thanks,
Yong

[-- Attachment #2: sun6i_csi_fix_writing_to_incorrect_buffer.patch --]
[-- Type: application/octet-stream, Size: 10429 bytes --]

diff --git a/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.c b/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.c
index 3f4de09..80bc40b 100644
--- a/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.c
+++ b/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.c
@@ -566,7 +566,7 @@ int sun6i_csi_update_config(struct sun6i_csi *csi,
 	return 0;
 }
 
-int sun6i_csi_update_buf_addr(struct sun6i_csi *csi, dma_addr_t addr)
+void sun6i_csi_update_buf_addr(struct sun6i_csi *csi, dma_addr_t addr)
 {
 	struct sun6i_csi_dev *sdev = sun6i_csi_to_dev(csi);
 	/* transform physical address to bus address */
@@ -580,11 +580,9 @@ int sun6i_csi_update_buf_addr(struct sun6i_csi *csi, dma_addr_t addr)
 	if (sdev->planar_offset[2] != -1)
 		regmap_write(sdev->regmap, CSI_CH_F2_BUFA_REG,
 			     (bus_addr + sdev->planar_offset[2]) >> 2);
-
-	return 0;
 }
 
-int sun6i_csi_set_stream(struct sun6i_csi *csi, bool enable)
+void sun6i_csi_set_stream(struct sun6i_csi *csi, bool enable)
 {
 	struct sun6i_csi_dev *sdev = sun6i_csi_to_dev(csi);
 	struct regmap *regmap = sdev->regmap;
@@ -592,7 +590,7 @@ int sun6i_csi_set_stream(struct sun6i_csi *csi, bool enable)
 	if (!enable) {
 		regmap_update_bits(regmap, CSI_CAP_REG, CSI_CAP_CH0_VCAP_ON, 0);
 		regmap_write(regmap, CSI_CH_INT_EN_REG, 0);
-		return 0;
+		return;
 	}
 
 	regmap_write(regmap, CSI_CH_INT_STA_REG, 0xFF);
@@ -606,8 +604,6 @@ int sun6i_csi_set_stream(struct sun6i_csi *csi, bool enable)
 
 	regmap_update_bits(regmap, CSI_CAP_REG, CSI_CAP_CH0_VCAP_ON,
 			   CSI_CAP_CH0_VCAP_ON);
-
-	return 0;
 }
 
 /* -----------------------------------------------------------------------------
diff --git a/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.h b/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.h
index 12508ff..9bc758b 100644
--- a/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.h
+++ b/drivers/media/platform/sunxi/sun6i-csi/sun6i_csi.h
@@ -92,14 +92,14 @@ int sun6i_csi_update_config(struct sun6i_csi *csi,
  * @csi:	pointer to the csi
  * @addr:	frame buffer's physical address
  */
-int sun6i_csi_update_buf_addr(struct sun6i_csi *csi, dma_addr_t addr);
+void sun6i_csi_update_buf_addr(struct sun6i_csi *csi, dma_addr_t addr);
 
 /**
  * sun6i_csi_set_stream() - start/stop csi streaming
  * @csi:	pointer to the csi
  * @enable:	start/stop
  */
-int sun6i_csi_set_stream(struct sun6i_csi *csi, bool enable);
+void sun6i_csi_set_stream(struct sun6i_csi *csi, bool enable);
 
 static inline int v4l2_pixformat_get_bpp(unsigned int pixformat)
 {
diff --git a/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.c b/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.c
index 0cebcbd..0819b71 100644
--- a/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.c
+++ b/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.c
@@ -29,6 +29,7 @@ struct sun6i_csi_buffer {
 	struct list_head		list;
 
 	dma_addr_t			dma_addr;
+	bool				queued_to_csi;
 };
 
 static struct sun6i_csi_format *
@@ -135,6 +136,7 @@ static int sun6i_video_start_streaming(struct vb2_queue *vq, unsigned int count)
 {
 	struct sun6i_video *video = vb2_get_drv_priv(vq);
 	struct sun6i_csi_buffer *buf;
+	struct sun6i_csi_buffer *next_buf;
 	struct sun6i_csi_config config;
 	unsigned long flags;
 	int ret;
@@ -143,11 +145,7 @@ static int sun6i_video_start_streaming(struct vb2_queue *vq, unsigned int count)
 
 	ret = media_pipeline_start(&video->vdev.entity, &video->vdev.pipe);
 	if (ret < 0)
-		goto err_start_pipeline;
-
-	ret = sun6i_pipeline_set_stream(video, true);
-	if (ret < 0)
-		goto err_start_stream;
+		goto clear_dma_queue;
 
 	config.pixelformat = video->fmt.fmt.pix.pixelformat;
 	config.code = video->current_fmt->mbus_code;
@@ -157,31 +155,50 @@ static int sun6i_video_start_streaming(struct vb2_queue *vq, unsigned int count)
 
 	ret = sun6i_csi_update_config(video->csi, &config);
 	if (ret < 0)
-		goto err_update_config;
+		goto stop_media_pipeline;
 
 	spin_lock_irqsave(&video->dma_queue_lock, flags);
-	video->cur_frm = list_first_entry(&video->dma_queue,
-					  struct sun6i_csi_buffer, list);
-	list_del(&video->cur_frm->list);
-	spin_unlock_irqrestore(&video->dma_queue_lock, flags);
 
-	ret = sun6i_csi_update_buf_addr(video->csi, video->cur_frm->dma_addr);
-	if (ret < 0)
-		goto err_update_addr;
+	buf = list_first_entry(&video->dma_queue,
+			       struct sun6i_csi_buffer, list);
+	buf->queued_to_csi = true;
+	sun6i_csi_update_buf_addr(video->csi, buf->dma_addr);
+
+	sun6i_csi_set_stream(video->csi, true);
+
+	/* CSI will lookup the next dma buffer for next frame before the
+	 * the current frame done IRQ triggered. This is not documented
+	 * but reported by Ondřej Jirman.
+	 * The BSP code has workaround for this too. It skip to mark the
+	 * first buffer as frame done for VB2 and pass the second buffer
+	 * to CSI in the first frame done ISR call. Then in second frame
+	 * done ISR call, it mark the first buffer as frame done for VB2
+	 * and pass the third buffer to CSI. And so on. The bad thing is
+	 * that the first buffer will be written twice and the first frame
+	 * is dropped even the queued buffer is sufficient.
+	 * So, I make some improvement here. Pass the next buffer to CSI
+	 * just follow starting the CSI. In this case, the first frame
+	 * will be stored in first buffer, second frame in second buffer.
+	 * This mothed is used to avoid dropping the first frame, it
+	 * would also drop frame when lack of queued buffer.
+	 */
+	next_buf = list_next_entry(buf, list);
+	next_buf->queued_to_csi = true;
+	sun6i_csi_update_buf_addr(video->csi, next_buf->dma_addr);
 
-	ret = sun6i_csi_set_stream(video->csi, true);
+	spin_unlock_irqrestore(&video->dma_queue_lock, flags);
+
+	ret = sun6i_pipeline_set_stream(video, true);
 	if (ret < 0)
-		goto err_csi_stream;
+		goto stop_csi_stream;
 
 	return 0;
 
-err_csi_stream:
-err_update_addr:
-err_update_config:
-	sun6i_pipeline_set_stream(video, false);
-err_start_stream:
+stop_csi_stream:
+	sun6i_csi_set_stream(video->csi, false);
+stop_media_pipeline:
 	media_pipeline_stop(&video->vdev.entity);
-err_start_pipeline:
+clear_dma_queue:
 	spin_lock_irqsave(&video->dma_queue_lock, flags);
 	list_for_each_entry(buf, &video->dma_queue, list)
 		vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_QUEUED);
@@ -205,11 +222,6 @@ static void sun6i_video_stop_streaming(struct vb2_queue *vq)
 
 	/* Release all active buffers */
 	spin_lock_irqsave(&video->dma_queue_lock, flags);
-	if (unlikely(video->cur_frm)) {
-		vb2_buffer_done(&video->cur_frm->vb.vb2_buf,
-				VB2_BUF_STATE_ERROR);
-		video->cur_frm = NULL;
-	}
 	list_for_each_entry(buf, &video->dma_queue, list)
 		vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_ERROR);
 	INIT_LIST_HEAD(&video->dma_queue);
@@ -225,39 +237,58 @@ static void sun6i_video_buffer_queue(struct vb2_buffer *vb)
 	unsigned long flags;
 
 	spin_lock_irqsave(&video->dma_queue_lock, flags);
-	if (!video->cur_frm && list_empty(&video->dma_queue) &&
-		vb2_is_streaming(vb->vb2_queue)) {
-		video->cur_frm = buf;
-		sun6i_csi_update_buf_addr(video->csi, video->cur_frm->dma_addr);
-		sun6i_csi_set_stream(video->csi, 1);
-	} else
-		list_add_tail(&buf->list, &video->dma_queue);
+	buf->queued_to_csi = false;
+	list_add_tail(&buf->list, &video->dma_queue);
 	spin_unlock_irqrestore(&video->dma_queue_lock, flags);
 }
 
 void sun6i_video_frame_done(struct sun6i_video *video)
 {
+	struct sun6i_csi_buffer *buf;
+	struct sun6i_csi_buffer *next_buf;
+	struct vb2_v4l2_buffer *vbuf ;
+
 	spin_lock(&video->dma_queue_lock);
 
-	if (video->cur_frm) {
-		struct vb2_v4l2_buffer *vbuf = &video->cur_frm->vb;
-		struct vb2_buffer *vb = &vbuf->vb2_buf;
+	video->sequence++;
+
+	buf = list_first_entry(&video->dma_queue,
+			       struct sun6i_csi_buffer, list);
+	if (list_is_last(&buf->list, &video->dma_queue)) {
+		dev_dbg(video->csi->dev, "Frame droped!\n");
+		goto unlock;
+	}
 
-		vb->timestamp = ktime_get_ns();
-		vbuf->sequence = video->sequence++;
-		vb2_buffer_done(vb, VB2_BUF_STATE_DONE);
-		video->cur_frm = NULL;
+	next_buf = list_next_entry(buf, list);
+	/* If a new buffer (#next_buf) had not been queued to CSI, the old
+	 * buffer (#buf) is still holding by CSI for storing the next
+	 * frame. So, we queue a new buffer (#next_buf) to CSI then wait
+	 * for next ISR call.
+	 */
+	if (!next_buf->queued_to_csi) {
+		next_buf->queued_to_csi = true;
+		sun6i_csi_update_buf_addr(video->csi, next_buf->dma_addr);
+		dev_dbg(video->csi->dev, "Frame droped!\n");
+		goto unlock;
 	}
 
-	if (!list_empty(&video->dma_queue)
-	    && vb2_is_streaming(&video->vb2_vidq)) {
-		video->cur_frm = list_first_entry(&video->dma_queue,
-				struct sun6i_csi_buffer, list);
-		list_del(&video->cur_frm->list);
-		sun6i_csi_update_buf_addr(video->csi, video->cur_frm->dma_addr);
-	} else
-		sun6i_csi_set_stream(video->csi, 0);
+	list_del(&buf->list);
+	vbuf = &buf->vb;
+	vbuf->vb2_buf.timestamp = ktime_get_ns();
+	vbuf->sequence = video->sequence;
+	vb2_buffer_done(&vbuf->vb2_buf, VB2_BUF_STATE_DONE);
 
+	if (list_is_last(&next_buf->list, &video->dma_queue))
+		goto unlock;
+
+	/* Prepare buffer for next frame but one.  */
+	next_buf = list_next_entry(next_buf, list);
+	if (!list_is_last(&next_buf->list, &video->dma_queue)) {
+		next_buf->queued_to_csi = true;
+		sun6i_csi_update_buf_addr(video->csi, next_buf->dma_addr);
+	}
+
+unlock:
 	spin_unlock(&video->dma_queue_lock);
 }
 
@@ -664,7 +695,6 @@ int sun6i_video_init(struct sun6i_video *video, struct sun6i_csi *csi,
 	INIT_LIST_HEAD(&video->dma_queue);
 	spin_lock_init(&video->dma_queue_lock);
 
-	video->cur_frm = NULL;
 	video->sequence = 0;
 	video->num_formats = 0;
 
@@ -677,7 +707,7 @@ int sun6i_video_init(struct sun6i_video *video, struct sun6i_csi *csi,
 	vidq->mem_ops			= &vb2_dma_contig_memops;
 	vidq->timestamp_flags		= V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC;
 	vidq->lock			= &video->lock;
-	vidq->min_buffers_needed	= 1;
+	vidq->min_buffers_needed	= 2;
 	vidq->dev			= csi->dev;
 
 	ret = vb2_queue_init(vidq);
diff --git a/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.h b/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.h
index 14eac6e..b5a3d34 100644
--- a/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.h
+++ b/drivers/media/platform/sunxi/sun6i-csi/sun6i_video.h
@@ -43,7 +43,6 @@ struct sun6i_video {
 	spinlock_t			dma_queue_lock;
 	struct list_head		dma_queue;
 
-	struct sun6i_csi_buffer		*cur_frm;
 	unsigned int			sequence;
 
 	struct sun6i_csi_format		*formats;

  reply	other threads:[~2017-11-23  1:15 UTC|newest]

Thread overview: 52+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-07-27  5:01 [PATCH v2 0/3] Initial Allwinner V3s CSI Support Yong Deng
2017-07-27  5:01 ` [PATCH v2 1/3] media: V3s: Add support for Allwinner CSI Yong Deng
2017-07-27 12:16   ` Baruch Siach
2017-07-27 12:25     ` Maxime Ripard
2017-07-31  0:47       ` Yong
2017-07-28 16:02   ` Maxime Ripard
2017-07-30  6:08     ` Baruch Siach
2017-07-31  1:48       ` Yong
2017-07-31  5:13         ` Baruch Siach
2017-08-21 20:21       ` Maxime Ripard
2017-08-23  2:41         ` Yong
2017-08-23 19:24           ` Maxime Ripard
2017-08-24  1:43             ` Yong
2017-07-31  3:16     ` Yong
2017-08-22 17:43       ` Maxime Ripard
2017-08-23  2:32         ` Yong
2017-08-25 13:41           ` Maxime Ripard
2017-08-28  7:00             ` Yong
2017-08-21 14:37   ` Hans Verkuil
2017-08-22  3:01     ` Yong
2017-08-22  6:43       ` Hans Verkuil
2017-08-22  7:51         ` Yong
2017-08-22 20:17         ` Maxime Ripard
2017-08-22 20:52           ` Laurent Pinchart
2017-08-23  6:52           ` Hans Verkuil
2017-08-23  7:43             ` Laurent Pinchart
2017-08-23 11:13               ` icenowy
2017-09-21 13:45   ` [linux-sunxi] " Ondřej Jirman
2017-09-22  8:44   ` Mylene JOSSERAND
2017-09-22  9:08     ` Yong
2017-11-21 15:48   ` Maxime Ripard
2017-11-22  1:33     ` Yong
2017-11-22  9:45       ` Maxime Ripard
2017-11-23  1:14         ` Yong [this message]
2017-11-25 16:02           ` Maxime Ripard
2017-12-04  9:45             ` Yong
2017-12-15 10:50               ` Maxime Ripard
2017-12-15 11:01                 ` Yong
2017-12-15 22:14                   ` Maxime Ripard
2017-07-27  5:01 ` [PATCH v2 2/3] dt-bindings: media: Add Allwinner V3s Camera Sensor Interface (CSI) Yong Deng
2017-07-28 16:03   ` Maxime Ripard
2017-07-31  0:50     ` Yong
2017-08-03 19:14   ` Rob Herring
2017-08-07  1:00     ` Yong
2017-12-19 11:53   ` Sakari Ailus
2017-12-21  2:49     ` Yong
2017-12-27 21:47       ` Sakari Ailus
2017-12-28  1:04         ` Yong
2017-07-27  5:01 ` [PATCH v2 3/3] media: MAINTAINERS: add entries for Allwinner V3s CSI Yong Deng
2017-12-19 11:48   ` Sakari Ailus
2017-12-21  2:40     ` Yong
  -- strict thread matches above, loose matches on Subject: below --
2017-07-27  3:51 [PATCH v2 0/3] Initial Allwinner V3s CSI Support Yong Deng
2017-07-27  3:51 ` [PATCH v2 1/3] media: V3s: Add support for Allwinner CSI Yong Deng

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20171123091444.4bed66dffeb36ecea8dfa706@magewell.com \
    --to=yong.deng@magewell.com \
    --cc=arnd@arndb.de \
    --cc=benjamin.gaignard@linaro.org \
    --cc=bparrot@ti.com \
    --cc=davem@davemloft.net \
    --cc=devicetree@vger.kernel.org \
    --cc=gregkh@linuxfoundation.org \
    --cc=hugues.fruchet@st.com \
    --cc=hverkuil@xs4all.nl \
    --cc=jean-christophe.trotin@st.com \
    --cc=krzk@kernel.org \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-media@vger.kernel.org \
    --cc=linux-sunxi@googlegroups.com \
    --cc=mark.rutland@arm.com \
    --cc=maxime.ripard@free-electrons.com \
    --cc=mchehab@kernel.org \
    --cc=minghsiu.tsai@mediatek.com \
    --cc=p.zabel@pengutronix.de \
    --cc=ramesh.shanmugasundaram@bp.renesas.com \
    --cc=robert.jarzmik@free.fr \
    --cc=robh+dt@kernel.org \
    --cc=wens@csie.org \
    --cc=yannick.fertre@st.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).