diff options
author | Kristian Høgsberg <krh@redhat.com> | 2007-05-09 19:23:15 -0400 |
---|---|---|
committer | Stefan Richter <stefanr@s5r6.in-berlin.de> | 2007-05-10 12:24:14 -0400 |
commit | d79406dd140a3e6eed6f26b17f0c6620fe30b50c (patch) | |
tree | ed08893adb8ce46712b1602dacc227c065697ce6 /drivers | |
parent | 2d826cc5c791bdc5f5651324c485746be9492be0 (diff) |
firewire: Convert OHCI driver to use standard goto unwinding for error handling.
Signed-off-by: Kristian Hoegsberg <krh@redhat.com>
Signed-off-by: Stefan Richter <stefanr@s5r6.in-berlin.de>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/firewire/fw-ohci.c | 86 |
1 files changed, 42 insertions, 44 deletions
diff --git a/drivers/firewire/fw-ohci.c b/drivers/firewire/fw-ohci.c index 5833ce1b040b..1f5c70461b8b 100644 --- a/drivers/firewire/fw-ohci.c +++ b/drivers/firewire/fw-ohci.c | |||
@@ -1715,44 +1715,13 @@ static int software_reset(struct fw_ohci *ohci) | |||
1715 | return -EBUSY; | 1715 | return -EBUSY; |
1716 | } | 1716 | } |
1717 | 1717 | ||
1718 | enum { | ||
1719 | CLEANUP_SELF_ID, | ||
1720 | CLEANUP_REGISTERS, | ||
1721 | CLEANUP_IOMEM, | ||
1722 | CLEANUP_DISABLE, | ||
1723 | CLEANUP_PUT_CARD, | ||
1724 | }; | ||
1725 | |||
1726 | static int cleanup(struct fw_ohci *ohci, int stage, int code) | ||
1727 | { | ||
1728 | struct pci_dev *dev = to_pci_dev(ohci->card.device); | ||
1729 | |||
1730 | switch (stage) { | ||
1731 | case CLEANUP_SELF_ID: | ||
1732 | dma_free_coherent(ohci->card.device, SELF_ID_BUF_SIZE, | ||
1733 | ohci->self_id_cpu, ohci->self_id_bus); | ||
1734 | case CLEANUP_REGISTERS: | ||
1735 | kfree(ohci->it_context_list); | ||
1736 | kfree(ohci->ir_context_list); | ||
1737 | pci_iounmap(dev, ohci->registers); | ||
1738 | case CLEANUP_IOMEM: | ||
1739 | pci_release_region(dev, 0); | ||
1740 | case CLEANUP_DISABLE: | ||
1741 | pci_disable_device(dev); | ||
1742 | case CLEANUP_PUT_CARD: | ||
1743 | fw_card_put(&ohci->card); | ||
1744 | } | ||
1745 | |||
1746 | return code; | ||
1747 | } | ||
1748 | |||
1749 | static int __devinit | 1718 | static int __devinit |
1750 | pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) | 1719 | pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) |
1751 | { | 1720 | { |
1752 | struct fw_ohci *ohci; | 1721 | struct fw_ohci *ohci; |
1753 | u32 bus_options, max_receive, link_speed; | 1722 | u32 bus_options, max_receive, link_speed; |
1754 | u64 guid; | 1723 | u64 guid; |
1755 | int error_code; | 1724 | int err; |
1756 | size_t size; | 1725 | size_t size; |
1757 | 1726 | ||
1758 | ohci = kzalloc(sizeof(*ohci), GFP_KERNEL); | 1727 | ohci = kzalloc(sizeof(*ohci), GFP_KERNEL); |
@@ -1763,9 +1732,10 @@ pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) | |||
1763 | 1732 | ||
1764 | fw_card_initialize(&ohci->card, &ohci_driver, &dev->dev); | 1733 | fw_card_initialize(&ohci->card, &ohci_driver, &dev->dev); |
1765 | 1734 | ||
1766 | if (pci_enable_device(dev)) { | 1735 | err = pci_enable_device(dev); |
1736 | if (err) { | ||
1767 | fw_error("Failed to enable OHCI hardware.\n"); | 1737 | fw_error("Failed to enable OHCI hardware.\n"); |
1768 | return cleanup(ohci, CLEANUP_PUT_CARD, -ENODEV); | 1738 | goto fail_put_card; |
1769 | } | 1739 | } |
1770 | 1740 | ||
1771 | pci_set_master(dev); | 1741 | pci_set_master(dev); |
@@ -1777,20 +1747,23 @@ pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) | |||
1777 | tasklet_init(&ohci->bus_reset_tasklet, | 1747 | tasklet_init(&ohci->bus_reset_tasklet, |
1778 | bus_reset_tasklet, (unsigned long)ohci); | 1748 | bus_reset_tasklet, (unsigned long)ohci); |
1779 | 1749 | ||
1780 | if (pci_request_region(dev, 0, ohci_driver_name)) { | 1750 | err = pci_request_region(dev, 0, ohci_driver_name); |
1751 | if (err) { | ||
1781 | fw_error("MMIO resource unavailable\n"); | 1752 | fw_error("MMIO resource unavailable\n"); |
1782 | return cleanup(ohci, CLEANUP_DISABLE, -EBUSY); | 1753 | goto fail_disable; |
1783 | } | 1754 | } |
1784 | 1755 | ||
1785 | ohci->registers = pci_iomap(dev, 0, OHCI1394_REGISTER_SIZE); | 1756 | ohci->registers = pci_iomap(dev, 0, OHCI1394_REGISTER_SIZE); |
1786 | if (ohci->registers == NULL) { | 1757 | if (ohci->registers == NULL) { |
1787 | fw_error("Failed to remap registers\n"); | 1758 | fw_error("Failed to remap registers\n"); |
1788 | return cleanup(ohci, CLEANUP_IOMEM, -ENXIO); | 1759 | err = -ENXIO; |
1760 | goto fail_iomem; | ||
1789 | } | 1761 | } |
1790 | 1762 | ||
1791 | if (software_reset(ohci)) { | 1763 | if (software_reset(ohci)) { |
1792 | fw_error("Failed to reset ohci card.\n"); | 1764 | fw_error("Failed to reset ohci card.\n"); |
1793 | return cleanup(ohci, CLEANUP_REGISTERS, -EBUSY); | 1765 | err = -EBUSY; |
1766 | goto fail_registers; | ||
1794 | } | 1767 | } |
1795 | 1768 | ||
1796 | /* | 1769 | /* |
@@ -1845,7 +1818,8 @@ pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) | |||
1845 | 1818 | ||
1846 | if (ohci->it_context_list == NULL || ohci->ir_context_list == NULL) { | 1819 | if (ohci->it_context_list == NULL || ohci->ir_context_list == NULL) { |
1847 | fw_error("Out of memory for it/ir contexts.\n"); | 1820 | fw_error("Out of memory for it/ir contexts.\n"); |
1848 | return cleanup(ohci, CLEANUP_REGISTERS, -ENOMEM); | 1821 | err = -ENOMEM; |
1822 | goto fail_registers; | ||
1849 | } | 1823 | } |
1850 | 1824 | ||
1851 | /* self-id dma buffer allocation */ | 1825 | /* self-id dma buffer allocation */ |
@@ -1855,7 +1829,8 @@ pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) | |||
1855 | GFP_KERNEL); | 1829 | GFP_KERNEL); |
1856 | if (ohci->self_id_cpu == NULL) { | 1830 | if (ohci->self_id_cpu == NULL) { |
1857 | fw_error("Out of memory for self ID buffer.\n"); | 1831 | fw_error("Out of memory for self ID buffer.\n"); |
1858 | return cleanup(ohci, CLEANUP_REGISTERS, -ENOMEM); | 1832 | err = -ENOMEM; |
1833 | goto fail_registers; | ||
1859 | } | 1834 | } |
1860 | 1835 | ||
1861 | reg_write(ohci, OHCI1394_SelfIDBuffer, ohci->self_id_bus); | 1836 | reg_write(ohci, OHCI1394_SelfIDBuffer, ohci->self_id_bus); |
@@ -1876,15 +1851,31 @@ pci_probe(struct pci_dev *dev, const struct pci_device_id *ent) | |||
1876 | guid = ((u64) reg_read(ohci, OHCI1394_GUIDHi) << 32) | | 1851 | guid = ((u64) reg_read(ohci, OHCI1394_GUIDHi) << 32) | |
1877 | reg_read(ohci, OHCI1394_GUIDLo); | 1852 | reg_read(ohci, OHCI1394_GUIDLo); |
1878 | 1853 | ||
1879 | error_code = fw_card_add(&ohci->card, max_receive, link_speed, guid); | 1854 | err = fw_card_add(&ohci->card, max_receive, link_speed, guid); |
1880 | if (error_code < 0) | 1855 | if (err < 0) |
1881 | return cleanup(ohci, CLEANUP_SELF_ID, error_code); | 1856 | goto fail_self_id; |
1882 | 1857 | ||
1883 | ohci->version = reg_read(ohci, OHCI1394_Version) & 0x00ff00ff; | 1858 | ohci->version = reg_read(ohci, OHCI1394_Version) & 0x00ff00ff; |
1884 | fw_notify("Added fw-ohci device %s, OHCI version %x.%x\n", | 1859 | fw_notify("Added fw-ohci device %s, OHCI version %x.%x\n", |
1885 | dev->dev.bus_id, ohci->version >> 16, ohci->version & 0xff); | 1860 | dev->dev.bus_id, ohci->version >> 16, ohci->version & 0xff); |
1886 | 1861 | ||
1887 | return 0; | 1862 | return 0; |
1863 | |||
1864 | fail_self_id: | ||
1865 | dma_free_coherent(ohci->card.device, SELF_ID_BUF_SIZE, | ||
1866 | ohci->self_id_cpu, ohci->self_id_bus); | ||
1867 | fail_registers: | ||
1868 | kfree(ohci->it_context_list); | ||
1869 | kfree(ohci->ir_context_list); | ||
1870 | pci_iounmap(dev, ohci->registers); | ||
1871 | fail_iomem: | ||
1872 | pci_release_region(dev, 0); | ||
1873 | fail_disable: | ||
1874 | pci_disable_device(dev); | ||
1875 | fail_put_card: | ||
1876 | fw_card_put(&ohci->card); | ||
1877 | |||
1878 | return err; | ||
1888 | } | 1879 | } |
1889 | 1880 | ||
1890 | static void pci_remove(struct pci_dev *dev) | 1881 | static void pci_remove(struct pci_dev *dev) |
@@ -1903,7 +1894,14 @@ static void pci_remove(struct pci_dev *dev) | |||
1903 | 1894 | ||
1904 | software_reset(ohci); | 1895 | software_reset(ohci); |
1905 | free_irq(dev->irq, ohci); | 1896 | free_irq(dev->irq, ohci); |
1906 | cleanup(ohci, CLEANUP_SELF_ID, 0); | 1897 | dma_free_coherent(ohci->card.device, SELF_ID_BUF_SIZE, |
1898 | ohci->self_id_cpu, ohci->self_id_bus); | ||
1899 | kfree(ohci->it_context_list); | ||
1900 | kfree(ohci->ir_context_list); | ||
1901 | pci_iounmap(dev, ohci->registers); | ||
1902 | pci_release_region(dev, 0); | ||
1903 | pci_disable_device(dev); | ||
1904 | fw_card_put(&ohci->card); | ||
1907 | 1905 | ||
1908 | fw_notify("Removed fw-ohci device.\n"); | 1906 | fw_notify("Removed fw-ohci device.\n"); |
1909 | } | 1907 | } |