Fix memory leak in __blk_rq_map_kern_sg() reported by "Hauser, Stefan" <stefan.hauser@bdt.de>

git-svn-id: http://svn.code.sf.net/p/scst/svn/trunk@2840 d57e44dd-8a1f-0410-8b47-8ef2f437770f
This commit is contained in:
Vladislav Bolkhovitin
2010-11-26 15:07:35 +00:00
parent f4da51e7b7
commit 308aca8883
7 changed files with 70 additions and 73 deletions

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.30.1/block/blk-map.c linux-2.6.30.1/block/blk-map.c
--- linux-2.6.30.1/block/blk-map.c 2009-07-10 21:13:25.000000000 +0400
+++ linux-2.6.30.1/block/blk-map.c 2009-08-12 20:01:43.000000000 +0400
diff -upkr linux-2.6.30/block/blk-map.c linux-2.6.30/block/blk-map.c
--- linux-2.6.30/block/blk-map.c 2009-06-10 07:05:27.000000000 +0400
+++ linux-2.6.30/block/blk-map.c 2010-11-26 17:35:41.027689874 +0300
@@ -5,6 +5,7 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -9,7 +9,7 @@ diff -upkr linux-2.6.30.1/block/blk-map.c linux-2.6.30.1/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -272,6 +273,336 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -272,6 +273,335 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -266,6 +266,9 @@ diff -upkr linux-2.6.30.1/block/blk-map.c linux-2.6.30.1/block/blk-map.c
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -273,10 +276,6 @@ diff -upkr linux-2.6.30.1/block/blk-map.c linux-2.6.30.1/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**
@@ -346,9 +345,9 @@ diff -upkr linux-2.6.30.1/block/blk-map.c linux-2.6.30.1/block/blk-map.c
/**
* blk_rq_map_kern - map kernel data to a request, for REQ_TYPE_BLOCK_PC usage
* @q: request queue where request should be inserted
diff -upkr linux-2.6.30.1/include/linux/blkdev.h linux-2.6.30.1/include/linux/blkdev.h
--- linux-2.6.30.1/include/linux/blkdev.h 2009-07-10 21:13:25.000000000 +0400
+++ linux-2.6.30.1/include/linux/blkdev.h 2009-08-12 19:48:06.000000000 +0400
diff -upkr linux-2.6.30/include/linux/blkdev.h linux-2.6.30/include/linux/blkdev.h
--- linux-2.6.30/include/linux/blkdev.h 2009-06-10 07:05:27.000000000 +0400
+++ linux-2.6.30/include/linux/blkdev.h 2009-08-12 19:48:06.000000000 +0400
@@ -704,6 +704,8 @@ extern unsigned long blk_max_low_pfn, bl
#define BLK_DEFAULT_SG_TIMEOUT (60 * HZ)
#define BLK_MIN_SG_TIMEOUT (7 * HZ)
@@ -368,9 +367,9 @@ diff -upkr linux-2.6.30.1/include/linux/blkdev.h linux-2.6.30.1/include/linux/bl
extern int blk_execute_rq(struct request_queue *, struct gendisk *,
struct request *, int);
extern void blk_execute_rq_nowait(struct request_queue *, struct gendisk *,
diff -upkr linux-2.6.30.1/include/linux/scatterlist.h linux-2.6.30.1/include/linux/scatterlist.h
--- linux-2.6.30.1/include/linux/scatterlist.h 2009-06-10 07:05:27.000000000 +0400
+++ linux-2.6.30.1/include/linux/scatterlist.h 2009-08-12 19:50:02.000000000 +0400
diff -upkr linux-2.6.30/include/linux/scatterlist.h linux-2.6.30/include/linux/scatterlist.h
--- linux-2.6.30/include/linux/scatterlist.h 2009-06-10 07:05:27.000000000 +0400
+++ linux-2.6.30/include/linux/scatterlist.h 2009-08-12 19:50:02.000000000 +0400
@@ -3,6 +3,7 @@
#include <asm/types.h>
@@ -390,9 +389,9 @@ diff -upkr linux-2.6.30.1/include/linux/scatterlist.h linux-2.6.30.1/include/lin
/*
* Maximum number of entries that will be allocated in one piece, if
* a list larger than this is required then chaining will be utilized.
diff -upkr linux-2.6.30.1/lib/scatterlist.c linux-2.6.30.1/lib/scatterlist.c
--- linux-2.6.30.1/lib/scatterlist.c 2009-06-10 07:05:27.000000000 +0400
+++ linux-2.6.30.1/lib/scatterlist.c 2009-08-12 19:56:04.000000000 +0400
diff -upkr linux-2.6.30/lib/scatterlist.c linux-2.6.30/lib/scatterlist.c
--- linux-2.6.30/lib/scatterlist.c 2009-06-10 07:05:27.000000000 +0400
+++ linux-2.6.30/lib/scatterlist.c 2009-08-12 19:56:04.000000000 +0400
@@ -485,3 +485,132 @@ size_t sg_copy_to_buffer(struct scatterl
return sg_copy_buffer(sgl, nents, buf, buflen, 1);
}
@@ -526,3 +525,4 @@ diff -upkr linux-2.6.30.1/lib/scatterlist.c linux-2.6.30.1/lib/scatterlist.c
+ return res;
+}
+EXPORT_SYMBOL(sg_copy);

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.31/block/blk-map.c linux-2.6.31/block/blk-map.c
--- linux-2.6.31/block/blk-map.c 2009-09-10 02:13:59.000000000 +0400
+++ linux-2.6.31/block/blk-map.c 2009-09-23 14:48:36.000000000 +0400
+++ linux-2.6.31/block/blk-map.c 2010-11-26 17:39:55.415689756 +0300
@@ -5,6 +5,7 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -9,7 +9,7 @@ diff -upkr linux-2.6.31/block/blk-map.c linux-2.6.31/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -271,6 +272,336 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -271,6 +272,335 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -266,6 +266,9 @@ diff -upkr linux-2.6.31/block/blk-map.c linux-2.6.31/block/blk-map.c
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -273,10 +276,6 @@ diff -upkr linux-2.6.31/block/blk-map.c linux-2.6.31/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**
@@ -526,3 +525,4 @@ diff -upkr linux-2.6.31/lib/scatterlist.c linux-2.6.31/lib/scatterlist.c
+ return res;
+}
+EXPORT_SYMBOL(sg_copy);

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.32.1/block/blk-map.c linux-2.6.32.1/block/blk-map.c
--- linux-2.6.32.1/block/blk-map.c 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32.1/block/blk-map.c 2009-12-16 15:21:35.000000000 +0300
diff -upkr linux-2.6.32/block/blk-map.c linux-2.6.32/block/blk-map.c
--- linux-2.6.32/block/blk-map.c 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32/block/blk-map.c 2010-11-26 17:48:24.811689511 +0300
@@ -5,6 +5,7 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -9,7 +9,7 @@ diff -upkr linux-2.6.32.1/block/blk-map.c linux-2.6.32.1/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -271,6 +272,336 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -271,6 +272,335 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -266,6 +266,9 @@ diff -upkr linux-2.6.32.1/block/blk-map.c linux-2.6.32.1/block/blk-map.c
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -273,10 +276,6 @@ diff -upkr linux-2.6.32.1/block/blk-map.c linux-2.6.32.1/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**
@@ -346,9 +345,9 @@ diff -upkr linux-2.6.32.1/block/blk-map.c linux-2.6.32.1/block/blk-map.c
/**
* blk_rq_map_kern - map kernel data to a request, for REQ_TYPE_BLOCK_PC usage
* @q: request queue where request should be inserted
diff -upkr linux-2.6.32.1/include/linux/blkdev.h linux-2.6.32.1/include/linux/blkdev.h
--- linux-2.6.32.1/include/linux/blkdev.h 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32.1/include/linux/blkdev.h 2009-12-16 15:21:35.000000000 +0300
diff -upkr linux-2.6.32/include/linux/blkdev.h linux-2.6.32/include/linux/blkdev.h
--- linux-2.6.32/include/linux/blkdev.h 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32/include/linux/blkdev.h 2009-12-16 15:21:35.000000000 +0300
@@ -708,6 +708,8 @@ extern unsigned long blk_max_low_pfn, bl
#define BLK_DEFAULT_SG_TIMEOUT (60 * HZ)
#define BLK_MIN_SG_TIMEOUT (7 * HZ)
@@ -368,9 +367,9 @@ diff -upkr linux-2.6.32.1/include/linux/blkdev.h linux-2.6.32.1/include/linux/bl
extern int blk_execute_rq(struct request_queue *, struct gendisk *,
struct request *, int);
extern void blk_execute_rq_nowait(struct request_queue *, struct gendisk *,
diff -upkr linux-2.6.32.1/include/linux/scatterlist.h linux-2.6.32.1/include/linux/scatterlist.h
--- linux-2.6.32.1/include/linux/scatterlist.h 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32.1/include/linux/scatterlist.h 2009-12-16 15:21:35.000000000 +0300
diff -upkr linux-2.6.32/include/linux/scatterlist.h linux-2.6.32/include/linux/scatterlist.h
--- linux-2.6.32/include/linux/scatterlist.h 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32/include/linux/scatterlist.h 2009-12-16 15:21:35.000000000 +0300
@@ -3,6 +3,7 @@
#include <asm/types.h>
@@ -390,9 +389,9 @@ diff -upkr linux-2.6.32.1/include/linux/scatterlist.h linux-2.6.32.1/include/lin
/*
* Maximum number of entries that will be allocated in one piece, if
* a list larger than this is required then chaining will be utilized.
diff -upkr linux-2.6.32.1/lib/scatterlist.c linux-2.6.32.1/lib/scatterlist.c
--- linux-2.6.32.1/lib/scatterlist.c 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32.1/lib/scatterlist.c 2009-12-16 15:21:35.000000000 +0300
diff -upkr linux-2.6.32/lib/scatterlist.c linux-2.6.32/lib/scatterlist.c
--- linux-2.6.32/lib/scatterlist.c 2009-12-03 06:51:21.000000000 +0300
+++ linux-2.6.32/lib/scatterlist.c 2009-12-16 15:21:35.000000000 +0300
@@ -493,3 +493,132 @@ size_t sg_copy_to_buffer(struct scatterl
return sg_copy_buffer(sgl, nents, buf, buflen, 1);
}
@@ -526,3 +525,4 @@ diff -upkr linux-2.6.32.1/lib/scatterlist.c linux-2.6.32.1/lib/scatterlist.c
+ return res;
+}
+EXPORT_SYMBOL(sg_copy);

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.33/block/blk-map.c linux-2.6.33/block/blk-map.c
--- linux-2.6.33/block/blk-map.c 2010-02-24 21:52:17.000000000 +0300
+++ linux-2.6.33/block/blk-map.c 2010-03-01 15:41:59.000000000 +0300
+++ linux-2.6.33/block/blk-map.c 2010-11-26 17:50:39.511689888 +0300
@@ -5,6 +5,7 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -9,7 +9,7 @@ diff -upkr linux-2.6.33/block/blk-map.c linux-2.6.33/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -271,6 +272,336 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -271,6 +272,335 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -266,6 +266,9 @@ diff -upkr linux-2.6.33/block/blk-map.c linux-2.6.33/block/blk-map.c
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -273,10 +276,6 @@ diff -upkr linux-2.6.33/block/blk-map.c linux-2.6.33/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**
@@ -526,3 +525,4 @@ diff -upkr linux-2.6.33/lib/scatterlist.c linux-2.6.33/lib/scatterlist.c
+ return res;
+}
+EXPORT_SYMBOL(sg_copy);

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.34/block/blk-map.c linux-2.6.34/block/blk-map.c
--- linux-2.6.34/block/blk-map.c 2010-05-17 01:17:36.000000000 +0400
+++ linux-2.6.34/block/blk-map.c 2010-05-24 15:19:49.000000000 +0400
+++ linux-2.6.34/block/blk-map.c 2010-11-26 17:58:41.579690663 +0300
@@ -5,6 +5,8 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -10,7 +10,7 @@ diff -upkr linux-2.6.34/block/blk-map.c linux-2.6.34/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -271,6 +273,336 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -271,6 +273,335 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -267,6 +267,9 @@ diff -upkr linux-2.6.34/block/blk-map.c linux-2.6.34/block/blk-map.c
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -274,10 +277,6 @@ diff -upkr linux-2.6.34/block/blk-map.c linux-2.6.34/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**
@@ -527,3 +526,4 @@ diff -upkr linux-2.6.34/lib/scatterlist.c linux-2.6.34/lib/scatterlist.c
+ return res;
+}
+EXPORT_SYMBOL(sg_copy);

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.35/block/blk-map.c linux-2.6.35/block/blk-map.c
--- linux-2.6.35/block/blk-map.c 2010-05-17 01:17:36.000000000 +0400
+++ linux-2.6.35/block/blk-map.c 2010-05-24 15:19:49.000000000 +0400
--- linux-2.6.35/block/blk-map.c 2010-08-02 02:11:14.000000000 +0400
+++ linux-2.6.35/block/blk-map.c 2010-11-26 18:03:58.107693773 +0300
@@ -5,6 +5,8 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -10,7 +10,7 @@ diff -upkr linux-2.6.35/block/blk-map.c linux-2.6.35/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -271,6 +273,338 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -271,6 +273,335 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -263,12 +263,13 @@ diff -upkr linux-2.6.35/block/blk-map.c linux-2.6.35/block/blk-map.c
+ }
+ }
+
+ res = 0;
+
+ rq->buffer = NULL;
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -276,10 +277,6 @@ diff -upkr linux-2.6.35/block/blk-map.c linux-2.6.35/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**
@@ -350,8 +347,8 @@ diff -upkr linux-2.6.35/block/blk-map.c linux-2.6.35/block/blk-map.c
* blk_rq_map_kern - map kernel data to a request, for REQ_TYPE_BLOCK_PC usage
* @q: request queue where request should be inserted
diff -upkr linux-2.6.35/include/linux/blkdev.h linux-2.6.35/include/linux/blkdev.h
--- linux-2.6.35/include/linux/blkdev.h 2010-05-17 01:17:36.000000000 +0400
+++ linux-2.6.35/include/linux/blkdev.h 2010-05-24 14:51:22.000000000 +0400
--- linux-2.6.35/include/linux/blkdev.h 2010-08-02 02:11:14.000000000 +0400
+++ linux-2.6.35/include/linux/blkdev.h 2010-08-04 12:21:59.737128732 +0400
@@ -717,6 +717,8 @@ extern unsigned long blk_max_low_pfn, bl
#define BLK_DEFAULT_SG_TIMEOUT (60 * HZ)
#define BLK_MIN_SG_TIMEOUT (7 * HZ)
@@ -372,8 +369,8 @@ diff -upkr linux-2.6.35/include/linux/blkdev.h linux-2.6.35/include/linux/blkdev
struct request *, int);
extern void blk_execute_rq_nowait(struct request_queue *, struct gendisk *,
diff -upkr linux-2.6.35/include/linux/scatterlist.h linux-2.6.35/include/linux/scatterlist.h
--- linux-2.6.35/include/linux/scatterlist.h 2010-05-17 01:17:36.000000000 +0400
+++ linux-2.6.35/include/linux/scatterlist.h 2010-05-24 14:51:22.000000000 +0400
--- linux-2.6.35/include/linux/scatterlist.h 2010-08-02 02:11:14.000000000 +0400
+++ linux-2.6.35/include/linux/scatterlist.h 2010-08-04 12:21:59.741129485 +0400
@@ -3,6 +3,7 @@
#include <asm/types.h>
@@ -394,8 +391,8 @@ diff -upkr linux-2.6.35/include/linux/scatterlist.h linux-2.6.35/include/linux/s
* Maximum number of entries that will be allocated in one piece, if
* a list larger than this is required then chaining will be utilized.
diff -upkr linux-2.6.35/lib/scatterlist.c linux-2.6.35/lib/scatterlist.c
--- linux-2.6.35/lib/scatterlist.c 2010-05-17 01:17:36.000000000 +0400
+++ linux-2.6.35/lib/scatterlist.c 2010-05-24 14:51:22.000000000 +0400
--- linux-2.6.35/lib/scatterlist.c 2010-08-02 02:11:14.000000000 +0400
+++ linux-2.6.35/lib/scatterlist.c 2010-08-04 12:21:59.741129485 +0400
@@ -494,3 +494,132 @@ size_t sg_copy_to_buffer(struct scatterl
return sg_copy_buffer(sgl, nents, buf, buflen, 1);
}
@@ -529,3 +526,4 @@ diff -upkr linux-2.6.35/lib/scatterlist.c linux-2.6.35/lib/scatterlist.c
+ return res;
+}
+EXPORT_SYMBOL(sg_copy);

View File

@@ -1,6 +1,6 @@
diff -upkr linux-2.6.36/block/blk-map.c linux-2.6.36/block/blk-map.c
--- linux-2.6.36/block/blk-map.c 2010-10-21 00:30:22.000000000 +0400
+++ linux-2.6.36/block/blk-map.c 2010-10-26 15:41:45.911251773 +0400
+++ linux-2.6.36/block/blk-map.c 2010-11-26 17:52:19.467689539 +0300
@@ -5,6 +5,8 @@
#include <linux/module.h>
#include <linux/bio.h>
@@ -10,7 +10,7 @@ diff -upkr linux-2.6.36/block/blk-map.c linux-2.6.36/block/blk-map.c
#include <scsi/sg.h> /* for struct sg_iovec */
#include "blk.h"
@@ -271,6 +273,338 @@ int blk_rq_unmap_user(struct bio *bio)
@@ -271,6 +273,337 @@ int blk_rq_unmap_user(struct bio *bio)
}
EXPORT_SYMBOL(blk_rq_unmap_user);
@@ -269,6 +269,9 @@ diff -upkr linux-2.6.36/block/blk-map.c linux-2.6.36/block/blk-map.c
+out:
+ return res;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+
+out_free_bios:
+ while (hbio != NULL) {
+ bio = hbio;
@@ -276,10 +279,6 @@ diff -upkr linux-2.6.36/block/blk-map.c linux-2.6.36/block/blk-map.c
+ bio_put(bio);
+ }
+ goto out;
+
+out_unmap_bios:
+ blk_rq_unmap_kern_sg(rq, res);
+ goto out;
+}
+
+/**