Date: Sun, 13 Aug 2017 18:09:22 +0000 (UTC) From: Kirk McKusick <mckusick@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r322464 - head/sys/geom/journal Message-ID: <201708131809.v7DI9MP3094462@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: mckusick Date: Sun Aug 13 18:09:22 2017 New Revision: 322464 URL: https://svnweb.freebsd.org/changeset/base/322464 Log: When read requests are sent from a filesystem running above g_journal, the g_journal level needs to check whether it is holding a newer copy of the block than that which exists on the disk. If so, it needs to return its copy. If not, it should pass the request down to the disk to fulfill. It currently considers six queues: 0) delayed queue, 1) unsent (current queue), 2) in-flight to the journal (flush queue), 3) active journal (active queue), 4) inactive journal (inactive queue), and 5) inflight to the disk (copy queue). Checking on two of these queues is unnecessary: 0) The delayed requests should not be used for reads because they have not yet been entered into the journal, so their value should reflect the disk contents, not the future contents that are not yet committed. 2) Because all the bio's in the flush queue are also found on the active queue, there is no need to inspect the flush queue for reads since they will be found when searching the active queue. Submitted by: Dr. Andreas Longwitz <longwitz@incore.de> Discussed with: kib MFC after: 1 week Modified: head/sys/geom/journal/g_journal.c Modified: head/sys/geom/journal/g_journal.c ============================================================================== --- head/sys/geom/journal/g_journal.c Sun Aug 13 18:06:38 2017 (r322463) +++ head/sys/geom/journal/g_journal.c Sun Aug 13 18:09:22 2017 (r322464) @@ -1514,49 +1514,10 @@ g_journal_read_find(struct bio *head, int sorted, stru } /* - * Try to find requested data in cache. - */ -static struct bio * -g_journal_read_queue_find(struct bio_queue *head, struct bio *pbp, off_t ostart, - off_t oend) -{ - off_t cstart, cend; - struct bio *bp; - - TAILQ_FOREACH(bp, head, bio_queue) { - cstart = MAX(ostart, bp->bio_offset); - cend = MIN(oend, bp->bio_offset + bp->bio_length); - if (cend <= ostart) - continue; - else if (cstart >= oend) - continue; - KASSERT(bp->bio_data != NULL, - ("%s: bio_data == NULL", __func__)); - GJ_DEBUG(3, "READ(%p): (%jd, %jd) (bp=%p)", head, cstart, cend, - bp); - bcopy(bp->bio_data + cstart - bp->bio_offset, - pbp->bio_data + cstart - pbp->bio_offset, cend - cstart); - pbp->bio_completed += cend - cstart; - if (pbp->bio_completed == pbp->bio_length) { - /* - * Cool, the whole request was in cache, deliver happy - * message. - */ - g_io_deliver(pbp, 0); - return (pbp); - } - break; - } - return (bp); -} - -/* - * This function is used for colecting data on read. + * This function is used for collecting data on read. * The complexity is because parts of the data can be stored in four different * places: - * - in delayed requests * - in memory - the data not yet send to the active journal provider - * - in requests which are going to be sent to the active journal * - in the active journal * - in the inactive journal * - in the data provider @@ -1574,20 +1535,14 @@ g_journal_read(struct g_journal_softc *sc, struct bio cstart = cend = -1; bp = NULL; head = NULL; - for (i = 0; i <= 5; i++) { + for (i = 1; i <= 5; i++) { switch (i) { - case 0: /* Delayed requests. */ - head = NULL; - sorted = 0; - break; case 1: /* Not-yet-send data. */ head = sc->sc_current_queue; sorted = 1; break; - case 2: /* In-flight to the active journal. */ - head = sc->sc_flush_queue; - sorted = 0; - break; + case 2: /* Skip flush queue as they are also in active queue */ + continue; case 3: /* Active journal. */ head = sc->sc_active.jj_queue; sorted = 1; @@ -1606,10 +1561,7 @@ g_journal_read(struct g_journal_softc *sc, struct bio default: panic("gjournal %s: i=%d", __func__, i); } - if (i == 0) - bp = g_journal_read_queue_find(&sc->sc_delayed_queue.queue, pbp, ostart, oend); - else - bp = g_journal_read_find(head, sorted, pbp, ostart, oend); + bp = g_journal_read_find(head, sorted, pbp, ostart, oend); if (bp == pbp) { /* Got the whole request. */ GJ_DEBUG(2, "Got the whole request from %u.", i); return;
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201708131809.v7DI9MP3094462>