Commit d30185f0 authored by Rolf Eike Beer's avatar Rolf Eike Beer Committed by Deepak Saxena

[PATCH] PCI Hotplug: Move an often used while loop to an inline function

Walking through a pci_resource list and freeing all members is done a lot of
times in unload functions. This patch moves this to an inline function in
pciehp_core.c, pciehp_pci.c, shpchp_core.c and shpchp_pci.c. This shrinks the
code a lot (some 200 lines) and makes it much easier to read. Also adds some
__exit.
parent a20313b1
......@@ -535,49 +535,35 @@ static int pcie_start_thread(void)
return retval;
}
static inline void __exit
free_pciehp_res(struct pci_resource *res)
{
struct pci_resource *tres;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
}
static void unload_pciehpd(void)
static void __exit unload_pciehpd(void)
{
struct pci_func *next;
struct pci_func *TempSlot;
int loop;
struct controller *ctrl;
struct controller *tctrl;
struct pci_resource *res;
struct pci_resource *tres;
ctrl = pciehp_ctrl_list;
while (ctrl) {
cleanup_slots(ctrl);
res = ctrl->io_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = ctrl->mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = ctrl->p_mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = ctrl->bus_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
free_pciehp_res(ctrl->io_head);
free_pciehp_res(ctrl->mem_head);
free_pciehp_res(ctrl->p_mem_head);
free_pciehp_res(ctrl->bus_head);
kfree (ctrl->pci_bus);
......@@ -592,33 +578,10 @@ static void unload_pciehpd(void)
for (loop = 0; loop < 256; loop++) {
next = pciehp_slot_list[loop];
while (next != NULL) {
res = next->io_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = next->mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = next->p_mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = next->bus_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
free_pciehp_res(ctrl->io_head);
free_pciehp_res(ctrl->mem_head);
free_pciehp_res(ctrl->p_mem_head);
free_pciehp_res(ctrl->bus_head);
TempSlot = next;
next = next->next;
......@@ -700,8 +663,5 @@ static void __exit pcied_cleanup(void)
info(DRIVER_DESC " version: " DRIVER_VERSION " unloaded\n");
}
module_init(pcied_init);
module_exit(pcied_cleanup);
......@@ -674,10 +674,29 @@ int pciehp_save_used_resources (struct controller *ctrl, struct pci_func *func,
func = pciehp_slot_find(func->bus, func->device, index++);
}
return(0);
return 0;
}
/**
* kfree_resource_list: release memory of all list members
* @res: resource list to free
*/
static inline void
return_resource_list(struct pci_resource **func, struct pci_resource **res)
{
struct pci_resource *node;
struct pci_resource *t_node;
node = *func;
*func = NULL;
while (node) {
t_node = node->next;
return_resource(res, node);
node = t_node;
}
}
/*
* pciehp_return_board_resources
*
......@@ -686,95 +705,40 @@ int pciehp_save_used_resources (struct controller *ctrl, struct pci_func *func,
*
* returns 0 if success
*/
int pciehp_return_board_resources(struct pci_func * func, struct resource_lists * resources)
int pciehp_return_board_resources(struct pci_func * func,
struct resource_lists * resources)
{
int rc = 0;
struct pci_resource *node;
struct pci_resource *t_node;
int rc;
dbg("%s\n", __FUNCTION__);
if (!func)
return(1);
return 1;
node = func->io_head;
func->io_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->io_head), node);
node = t_node;
}
return_resource_list(&(func->io_head),&(resources->io_head));
return_resource_list(&(func->mem_head),&(resources->mem_head));
return_resource_list(&(func->p_mem_head),&(resources->p_mem_head));
return_resource_list(&(func->bus_head),&(resources->bus_head));
node = func->mem_head;
func->mem_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->mem_head), node);
node = t_node;
}
node = func->p_mem_head;
func->p_mem_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->p_mem_head), node);
node = t_node;
}
node = func->bus_head;
func->bus_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->bus_head), node);
node = t_node;
}
rc |= pciehp_resource_sort_and_combine(&(resources->mem_head));
rc = pciehp_resource_sort_and_combine(&(resources->mem_head));
rc |= pciehp_resource_sort_and_combine(&(resources->p_mem_head));
rc |= pciehp_resource_sort_and_combine(&(resources->io_head));
rc |= pciehp_resource_sort_and_combine(&(resources->bus_head));
return(rc);
return rc;
}
/*
* pciehp_destroy_resource_list
*
* Puts node back in the resource list pointed to by head
/**
* kfree_resource_list: release memory of all list members
* @res: resource list to free
*/
void pciehp_destroy_resource_list (struct resource_lists * resources)
static inline void
kfree_resource_list(struct pci_resource **r)
{
struct pci_resource *res, *tres;
res = resources->io_head;
resources->io_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = resources->mem_head;
resources->mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = resources->p_mem_head;
resources->p_mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = resources->bus_head;
resources->bus_head = NULL;
res = *r;
*r = NULL;
while (res) {
tres = res;
......@@ -783,50 +747,26 @@ void pciehp_destroy_resource_list (struct resource_lists * resources)
}
}
/*
* pciehp_destroy_board_resources
*
* Puts node back in the resource list pointed to by head
/**
* pciehp_destroy_resource_list: put node back in the resource list
* @resources: list to put nodes back
*/
void pciehp_destroy_board_resources (struct pci_func * func)
void pciehp_destroy_resource_list(struct resource_lists * resources)
{
struct pci_resource *res, *tres;
res = func->io_head;
func->io_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = func->mem_head;
func->mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = func->p_mem_head;
func->p_mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = func->bus_head;
func->bus_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
kfree_resource_list(&(resources->io_head));
kfree_resource_list(&(resources->mem_head));
kfree_resource_list(&(resources->p_mem_head));
kfree_resource_list(&(resources->bus_head));
}
/**
* pciehp_destroy_board_resources: put node back in the resource list
* @resources: list to put nodes back
*/
void pciehp_destroy_board_resources(struct pci_func * func)
{
kfree_resource_list(&(func->io_head));
kfree_resource_list(&(func->mem_head));
kfree_resource_list(&(func->p_mem_head));
kfree_resource_list(&(func->bus_head));
}
......@@ -531,49 +531,35 @@ static int shpc_start_thread(void)
return retval;
}
static inline void __exit
free_shpchp_res(struct pci_resource *res)
{
struct pci_resource *tres;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
}
static void unload_shpchpd(void)
static void __exit unload_shpchpd(void)
{
struct pci_func *next;
struct pci_func *TempSlot;
int loop;
struct controller *ctrl;
struct controller *tctrl;
struct pci_resource *res;
struct pci_resource *tres;
ctrl = shpchp_ctrl_list;
while (ctrl) {
cleanup_slots(ctrl);
res = ctrl->io_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = ctrl->mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = ctrl->p_mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = ctrl->bus_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
free_shpchp_res(ctrl->io_head);
free_shpchp_res(ctrl->mem_head);
free_shpchp_res(ctrl->p_mem_head);
free_shpchp_res(ctrl->bus_head);
kfree (ctrl->pci_bus);
......@@ -589,33 +575,10 @@ static void unload_shpchpd(void)
for (loop = 0; loop < 256; loop++) {
next = shpchp_slot_list[loop];
while (next != NULL) {
res = next->io_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = next->mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = next->p_mem_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = next->bus_head;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
free_shpchp_res(ctrl->io_head);
free_shpchp_res(ctrl->mem_head);
free_shpchp_res(ctrl->p_mem_head);
free_shpchp_res(ctrl->bus_head);
TempSlot = next;
next = next->next;
......@@ -697,8 +660,5 @@ static void __exit shpcd_cleanup(void)
info(DRIVER_DESC " version: " DRIVER_VERSION " unloaded\n");
}
module_init(shpcd_init);
module_exit(shpcd_cleanup);
......@@ -664,9 +664,27 @@ int shpchp_save_used_resources (struct controller *ctrl, struct pci_func *func,
func = shpchp_slot_find(func->bus, func->device, index++);
}
return(0);
return 0;
}
/**
* kfree_resource_list: release memory of all list members
* @res: resource list to free
*/
static inline void
return_resource_list(struct pci_resource **func, struct pci_resource **res)
{
struct pci_resource *node;
struct pci_resource *t_node;
node = *func;
*func = NULL;
while (node) {
t_node = node->next;
return_resource(res, node);
node = t_node;
}
}
/*
* shpchp_return_board_resources
......@@ -676,95 +694,39 @@ int shpchp_save_used_resources (struct controller *ctrl, struct pci_func *func,
*
* returns 0 if success
*/
int shpchp_return_board_resources(struct pci_func * func, struct resource_lists * resources)
int shpchp_return_board_resources(struct pci_func * func,
struct resource_lists * resources)
{
int rc = 0;
struct pci_resource *node;
struct pci_resource *t_node;
int rc;
dbg("%s\n", __FUNCTION__);
if (!func)
return(1);
node = func->io_head;
func->io_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->io_head), node);
node = t_node;
}
node = func->mem_head;
func->mem_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->mem_head), node);
node = t_node;
}
node = func->p_mem_head;
func->p_mem_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->p_mem_head), node);
node = t_node;
}
return 1;
node = func->bus_head;
func->bus_head = NULL;
while (node) {
t_node = node->next;
return_resource(&(resources->bus_head), node);
node = t_node;
}
return_resource_list(&(func->io_head),&(resources->io_head));
return_resource_list(&(func->mem_head),&(resources->mem_head));
return_resource_list(&(func->p_mem_head),&(resources->p_mem_head));
return_resource_list(&(func->bus_head),&(resources->bus_head));
rc |= shpchp_resource_sort_and_combine(&(resources->mem_head));
rc = shpchp_resource_sort_and_combine(&(resources->mem_head));
rc |= shpchp_resource_sort_and_combine(&(resources->p_mem_head));
rc |= shpchp_resource_sort_and_combine(&(resources->io_head));
rc |= shpchp_resource_sort_and_combine(&(resources->bus_head));
return(rc);
return rc;
}
/*
* shpchp_destroy_resource_list
*
* Puts node back in the resource list pointed to by head
/**
* kfree_resource_list: release memory of all list members
* @res: resource list to free
*/
void shpchp_destroy_resource_list (struct resource_lists * resources)
static inline void
kfree_resource_list(struct pci_resource **r)
{
struct pci_resource *res, *tres;
res = resources->io_head;
resources->io_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = resources->mem_head;
resources->mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = resources->p_mem_head;
resources->p_mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = resources->bus_head;
resources->bus_head = NULL;
res = *r;
*r = NULL;
while (res) {
tres = res;
......@@ -773,50 +735,26 @@ void shpchp_destroy_resource_list (struct resource_lists * resources)
}
}
/*
* shpchp_destroy_board_resources
*
* Puts node back in the resource list pointed to by head
/**
* shpchp_destroy_resource_list: put node back in the resource list
* @resources: list to put nodes back
*/
void shpchp_destroy_board_resources (struct pci_func * func)
void shpchp_destroy_resource_list(struct resource_lists *resources)
{
struct pci_resource *res, *tres;
res = func->io_head;
func->io_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = func->mem_head;
func->mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = func->p_mem_head;
func->p_mem_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
res = func->bus_head;
func->bus_head = NULL;
while (res) {
tres = res;
res = res->next;
kfree(tres);
}
kfree_resource_list(&(resources->io_head));
kfree_resource_list(&(resources->mem_head));
kfree_resource_list(&(resources->p_mem_head));
kfree_resource_list(&(resources->bus_head));
}
/**
* shpchp_destroy_board_resources: put node back in the resource list
* @resources: list to put nodes back
*/
void shpchp_destroy_board_resources(struct pci_func * func)
{
kfree_resource_list(&(func->io_head));
kfree_resource_list(&(func->mem_head));
kfree_resource_list(&(func->p_mem_head));
kfree_resource_list(&(func->bus_head));
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment