mirror of
				https://github.com/torvalds/linux.git
				synced 2025-11-04 10:40:15 +02:00 
			
		
		
		
	omap-serial: Fix the error handling in the omap_serial probe
The patch does the following - The pm_runtime_disable is called in the remove not in the error case of probe.The patch calls the pm_runtime_disable in the error case. - Calls pm_runtime_put in the error case. - The up is not freed in the error path. Fix the memory leak by using devm_* so that the memory need not be freed in the driver. - Also the iounmap is not called fix the same by calling using devm_ioremap. - Make the name of the error tags more meaningful. Cc: Mark Brown <broonie@opensource.wolfsonmicro.com> Cc: Govindraj.R <govindraj.raja@ti.com> Signed-off-by: Shubhrajyoti D <shubhrajyoti@ti.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:
		
							parent
							
								
									c3d8b76f61
								
							
						
					
					
						commit
						388bc26226
					
				
					 1 changed files with 20 additions and 23 deletions
				
			
		| 
						 | 
				
			
			@ -1381,29 +1381,24 @@ static int serial_omap_probe(struct platform_device *pdev)
 | 
			
		|||
		return -ENODEV;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if (!request_mem_region(mem->start, resource_size(mem),
 | 
			
		||||
	if (!devm_request_mem_region(&pdev->dev, mem->start, resource_size(mem),
 | 
			
		||||
				pdev->dev.driver->name)) {
 | 
			
		||||
		dev_err(&pdev->dev, "memory region already claimed\n");
 | 
			
		||||
		return -EBUSY;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	dma_rx = platform_get_resource_byname(pdev, IORESOURCE_DMA, "rx");
 | 
			
		||||
	if (!dma_rx) {
 | 
			
		||||
		ret = -EINVAL;
 | 
			
		||||
		goto err;
 | 
			
		||||
	}
 | 
			
		||||
	if (!dma_rx)
 | 
			
		||||
		return -ENXIO;
 | 
			
		||||
 | 
			
		||||
	dma_tx = platform_get_resource_byname(pdev, IORESOURCE_DMA, "tx");
 | 
			
		||||
	if (!dma_tx) {
 | 
			
		||||
		ret = -EINVAL;
 | 
			
		||||
		goto err;
 | 
			
		||||
	}
 | 
			
		||||
	if (!dma_tx)
 | 
			
		||||
		return -ENXIO;
 | 
			
		||||
 | 
			
		||||
	up = devm_kzalloc(&pdev->dev, sizeof(*up), GFP_KERNEL);
 | 
			
		||||
	if (!up)
 | 
			
		||||
		return -ENOMEM;
 | 
			
		||||
 | 
			
		||||
	up = kzalloc(sizeof(*up), GFP_KERNEL);
 | 
			
		||||
	if (up == NULL) {
 | 
			
		||||
		ret = -ENOMEM;
 | 
			
		||||
		goto do_release_region;
 | 
			
		||||
	}
 | 
			
		||||
	up->pdev = pdev;
 | 
			
		||||
	up->port.dev = &pdev->dev;
 | 
			
		||||
	up->port.type = PORT_OMAP;
 | 
			
		||||
| 
						 | 
				
			
			@ -1423,16 +1418,17 @@ static int serial_omap_probe(struct platform_device *pdev)
 | 
			
		|||
		dev_err(&pdev->dev, "failed to get alias/pdev id, errno %d\n",
 | 
			
		||||
								up->port.line);
 | 
			
		||||
		ret = -ENODEV;
 | 
			
		||||
		goto err;
 | 
			
		||||
		goto err_port_line;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	sprintf(up->name, "OMAP UART%d", up->port.line);
 | 
			
		||||
	up->port.mapbase = mem->start;
 | 
			
		||||
	up->port.membase = ioremap(mem->start, resource_size(mem));
 | 
			
		||||
	up->port.membase = devm_ioremap(&pdev->dev, mem->start,
 | 
			
		||||
						resource_size(mem));
 | 
			
		||||
	if (!up->port.membase) {
 | 
			
		||||
		dev_err(&pdev->dev, "can't ioremap UART\n");
 | 
			
		||||
		ret = -ENOMEM;
 | 
			
		||||
		goto err;
 | 
			
		||||
		goto err_ioremap;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	up->port.flags = omap_up_info->flags;
 | 
			
		||||
| 
						 | 
				
			
			@ -1478,16 +1474,19 @@ static int serial_omap_probe(struct platform_device *pdev)
 | 
			
		|||
 | 
			
		||||
	ret = uart_add_one_port(&serial_omap_reg, &up->port);
 | 
			
		||||
	if (ret != 0)
 | 
			
		||||
		goto do_release_region;
 | 
			
		||||
		goto err_add_port;
 | 
			
		||||
 | 
			
		||||
	pm_runtime_put(&pdev->dev);
 | 
			
		||||
	platform_set_drvdata(pdev, up);
 | 
			
		||||
	return 0;
 | 
			
		||||
err:
 | 
			
		||||
 | 
			
		||||
err_add_port:
 | 
			
		||||
	pm_runtime_put(&pdev->dev);
 | 
			
		||||
	pm_runtime_disable(&pdev->dev);
 | 
			
		||||
err_ioremap:
 | 
			
		||||
err_port_line:
 | 
			
		||||
	dev_err(&pdev->dev, "[UART%d]: failure [%s]: %d\n",
 | 
			
		||||
				pdev->id, __func__, ret);
 | 
			
		||||
do_release_region:
 | 
			
		||||
	release_mem_region(mem->start, resource_size(mem));
 | 
			
		||||
	return ret;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -1499,8 +1498,6 @@ static int serial_omap_remove(struct platform_device *dev)
 | 
			
		|||
		pm_runtime_disable(&up->pdev->dev);
 | 
			
		||||
		uart_remove_one_port(&serial_omap_reg, &up->port);
 | 
			
		||||
		pm_qos_remove_request(&up->pm_qos_request);
 | 
			
		||||
 | 
			
		||||
		kfree(up);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	platform_set_drvdata(dev, NULL);
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in a new issue