Commit d629c47171ccc281bbb02507f9521a6125782e9b
Committed by
James Bottomley
1 parent
6763daae8f
Exists in
smarc-l5.0.0_1.0.0-ga
and in
5 other branches
[SCSI] be2iscsi: Fix memory leak in control path of driver
In contorl path of the driver the task was mapped using pci_map_single which was not unmapped when the completion for the task had come. Signed-off-by: John Soni Jose <sony.john-n@emulex.com> Signed-off-by: Jayamohan Kallickal <jayamohan.kallickal@emulex.com> Reviewed-by: Mike Christie <michaelc@cs.wisc.edu> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Showing 2 changed files with 31 additions and 10 deletions Side-by-side Diff
drivers/scsi/be2iscsi/be_main.c
... | ... | @@ -2242,10 +2242,14 @@ |
2242 | 2242 | AMAP_SET_BITS(struct amap_iscsi_sge, last_sge, psgl, 1); |
2243 | 2243 | } |
2244 | 2244 | |
2245 | +/** | |
2246 | + * hwi_write_buffer()- Populate the WRB with task info | |
2247 | + * @pwrb: ptr to the WRB entry | |
2248 | + * @task: iscsi task which is to be executed | |
2249 | + **/ | |
2245 | 2250 | static void hwi_write_buffer(struct iscsi_wrb *pwrb, struct iscsi_task *task) |
2246 | 2251 | { |
2247 | 2252 | struct iscsi_sge *psgl; |
2248 | - unsigned long long addr; | |
2249 | 2253 | struct beiscsi_io_task *io_task = task->dd_data; |
2250 | 2254 | struct beiscsi_conn *beiscsi_conn = io_task->conn; |
2251 | 2255 | struct beiscsi_hba *phba = beiscsi_conn->phba; |
2252 | 2256 | |
2253 | 2257 | |
2254 | 2258 | |
2255 | 2259 | |
... | ... | @@ -2259,24 +2263,27 @@ |
2259 | 2263 | if (task->data) { |
2260 | 2264 | if (task->data_count) { |
2261 | 2265 | AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 1); |
2262 | - addr = (u64) pci_map_single(phba->pcidev, | |
2263 | - task->data, | |
2264 | - task->data_count, 1); | |
2266 | + io_task->mtask_addr = pci_map_single(phba->pcidev, | |
2267 | + task->data, | |
2268 | + task->data_count, | |
2269 | + PCI_DMA_TODEVICE); | |
2270 | + | |
2271 | + io_task->mtask_data_count = task->data_count; | |
2265 | 2272 | } else { |
2266 | 2273 | AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 0); |
2267 | - addr = 0; | |
2274 | + io_task->mtask_addr = 0; | |
2268 | 2275 | } |
2269 | 2276 | AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_addr_lo, pwrb, |
2270 | - ((u32)(addr & 0xFFFFFFFF))); | |
2277 | + lower_32_bits(io_task->mtask_addr)); | |
2271 | 2278 | AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_addr_hi, pwrb, |
2272 | - ((u32)(addr >> 32))); | |
2279 | + upper_32_bits(io_task->mtask_addr)); | |
2273 | 2280 | AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_len, pwrb, |
2274 | 2281 | task->data_count); |
2275 | 2282 | |
2276 | 2283 | AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_last, pwrb, 1); |
2277 | 2284 | } else { |
2278 | 2285 | AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 0); |
2279 | - addr = 0; | |
2286 | + io_task->mtask_addr = 0; | |
2280 | 2287 | } |
2281 | 2288 | |
2282 | 2289 | psgl = (struct iscsi_sge *)io_task->psgl_handle->pfrag; |
2283 | 2290 | |
... | ... | @@ -2299,9 +2306,9 @@ |
2299 | 2306 | psgl++; |
2300 | 2307 | if (task->data) { |
2301 | 2308 | AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, psgl, |
2302 | - ((u32)(addr & 0xFFFFFFFF))); | |
2309 | + lower_32_bits(io_task->mtask_addr)); | |
2303 | 2310 | AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, psgl, |
2304 | - ((u32)(addr >> 32))); | |
2311 | + upper_32_bits(io_task->mtask_addr)); | |
2305 | 2312 | } |
2306 | 2313 | AMAP_SET_BITS(struct amap_iscsi_sge, len, psgl, 0x106); |
2307 | 2314 | } |
... | ... | @@ -3893,6 +3900,11 @@ |
3893 | 3900 | kfree(phba->ep_array); |
3894 | 3901 | } |
3895 | 3902 | |
3903 | +/** | |
3904 | + * beiscsi_cleanup_task()- Free driver resources of the task | |
3905 | + * @task: ptr to the iscsi task | |
3906 | + * | |
3907 | + **/ | |
3896 | 3908 | static void beiscsi_cleanup_task(struct iscsi_task *task) |
3897 | 3909 | { |
3898 | 3910 | struct beiscsi_io_task *io_task = task->dd_data; |
... | ... | @@ -3939,6 +3951,13 @@ |
3939 | 3951 | io_task->psgl_handle); |
3940 | 3952 | spin_unlock(&phba->mgmt_sgl_lock); |
3941 | 3953 | io_task->psgl_handle = NULL; |
3954 | + } | |
3955 | + if (io_task->mtask_addr) { | |
3956 | + pci_unmap_single(phba->pcidev, | |
3957 | + io_task->mtask_addr, | |
3958 | + io_task->mtask_data_count, | |
3959 | + PCI_DMA_TODEVICE); | |
3960 | + io_task->mtask_addr = 0; | |
3942 | 3961 | } |
3943 | 3962 | } |
3944 | 3963 | } |
drivers/scsi/be2iscsi/be_main.h