19e86db79SHyon Kim /* 29e86db79SHyon Kim * CDDL HEADER START 39e86db79SHyon Kim * 49e86db79SHyon Kim * The contents of this file are subject to the terms of the 59e86db79SHyon Kim * Common Development and Distribution License (the "License"). 69e86db79SHyon Kim * You may not use this file except in compliance with the License. 79e86db79SHyon Kim * 89e86db79SHyon Kim * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 99e86db79SHyon Kim * or http://www.opensolaris.org/os/licensing. 109e86db79SHyon Kim * See the License for the specific language governing permissions 119e86db79SHyon Kim * and limitations under the License. 129e86db79SHyon Kim * 139e86db79SHyon Kim * When distributing Covered Code, include this CDDL HEADER in each 149e86db79SHyon Kim * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 159e86db79SHyon Kim * If applicable, add the following below this CDDL HEADER, with the 169e86db79SHyon Kim * fields enclosed by brackets "[]" replaced with your own identifying 179e86db79SHyon Kim * information: Portions Copyright [yyyy] [name of copyright owner] 189e86db79SHyon Kim * 199e86db79SHyon Kim * CDDL HEADER END 209e86db79SHyon Kim */ 219e86db79SHyon Kim 229e86db79SHyon Kim /* 239e86db79SHyon Kim * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 249e86db79SHyon Kim * Use is subject to license terms. 259e86db79SHyon Kim */ 2600f453f4SRob Johnston /* 2700f453f4SRob Johnston * Copyright 2019 Joyent, Inc. 2800f453f4SRob Johnston */ 299e86db79SHyon Kim 309e86db79SHyon Kim #include <sun_sas.h> 319e86db79SHyon Kim 329e86db79SHyon Kim /* 339e86db79SHyon Kim * Frees the HBA Library. Must be called after all HBA library functions 349e86db79SHyon Kim * to free all resources 359e86db79SHyon Kim */ 3600f453f4SRob Johnston HBA_STATUS Sun_sasFreeLibrary(void)3700f453f4SRob JohnstonSun_sasFreeLibrary(void) 3800f453f4SRob Johnston { 3900f453f4SRob Johnston HBA_STATUS status; 409e86db79SHyon Kim 419e86db79SHyon Kim lock(&all_hbas_lock); 429e86db79SHyon Kim 439e86db79SHyon Kim status = FreeHBA(global_hba_head); 449e86db79SHyon Kim 459e86db79SHyon Kim /* re-initialize all global variables */ 469e86db79SHyon Kim global_hba_head = NULL; 479e86db79SHyon Kim hba_count = 0; 489e86db79SHyon Kim open_handle_index = 1; 499e86db79SHyon Kim unlock(&all_hbas_lock); 509e86db79SHyon Kim (void) mutex_destroy(&all_hbas_lock); 51*c1ba8596SToomas Soome (void) mutex_destroy(&open_handles_lock); 529e86db79SHyon Kim 539e86db79SHyon Kim /* free sysevent handle. */ 549e86db79SHyon Kim if (gSysEventHandle != NULL) 559e86db79SHyon Kim sysevent_unbind_handle(gSysEventHandle); 569e86db79SHyon Kim 579e86db79SHyon Kim /* Reset our load count so we can be reloaded now */ 589e86db79SHyon Kim loadCount = 0; 599e86db79SHyon Kim 609e86db79SHyon Kim return (status); 619e86db79SHyon Kim } 629e86db79SHyon Kim 639e86db79SHyon Kim /* 649e86db79SHyon Kim * Internal routine to free up hba_ptr's (and all sub-structures) 659e86db79SHyon Kim */ 6600f453f4SRob Johnston HBA_STATUS FreeHBA(struct sun_sas_hba * hba)6700f453f4SRob JohnstonFreeHBA(struct sun_sas_hba *hba) 6800f453f4SRob Johnston { 699e86db79SHyon Kim struct sun_sas_hba *hba_ptr = NULL; 709e86db79SHyon Kim struct sun_sas_hba *last_hba_ptr = NULL; 719e86db79SHyon Kim struct sun_sas_port *hba_port = NULL; 729e86db79SHyon Kim struct sun_sas_port *last_hba_port = NULL; 739e86db79SHyon Kim struct sun_sas_port *tgt_port = NULL; 749e86db79SHyon Kim struct sun_sas_port *last_tgt_port = NULL; 759e86db79SHyon Kim struct ScsiEntryList *scsi_info = NULL; 769e86db79SHyon Kim struct ScsiEntryList *last_scsi_info = NULL; 779e86db79SHyon Kim struct phy_info *phy_ptr = NULL; 789e86db79SHyon Kim struct phy_info *last_phy = NULL; 799e86db79SHyon Kim struct open_handle *open_handle = NULL; 809e86db79SHyon Kim struct open_handle *last_open_handle = NULL; 819e86db79SHyon Kim 829e86db79SHyon Kim last_hba_ptr = NULL; 839e86db79SHyon Kim /* walk through global_hba_head list freeing each handle */ 8400f453f4SRob Johnston for (hba_ptr = hba; hba_ptr != NULL; hba_ptr = hba_ptr->next) { 859e86db79SHyon Kim /* Free the nested structures (port and attached port) */ 869e86db79SHyon Kim hba_port = hba_ptr->first_port; 879e86db79SHyon Kim while (hba_port != NULL) { 8800f453f4SRob Johnston /* Free discovered port structure list. */ 8900f453f4SRob Johnston tgt_port = hba_port->first_attached_port; 9000f453f4SRob Johnston while (tgt_port != NULL) { 9100f453f4SRob Johnston /* Free target mapping data list first. */ 9200f453f4SRob Johnston scsi_info = tgt_port->scsiInfo; 9300f453f4SRob Johnston while (scsi_info != NULL) { 9400f453f4SRob Johnston last_scsi_info = scsi_info; 9500f453f4SRob Johnston scsi_info = scsi_info->next; 9600f453f4SRob Johnston free(last_scsi_info); 9700f453f4SRob Johnston } 9800f453f4SRob Johnston last_tgt_port = tgt_port; 9900f453f4SRob Johnston tgt_port = tgt_port->next; 10000f453f4SRob Johnston free(last_tgt_port->port_attributes.\ 10100f453f4SRob Johnston PortSpecificAttribute.SASPort); 10200f453f4SRob Johnston free(last_tgt_port); 10300f453f4SRob Johnston } 10400f453f4SRob Johnston 10500f453f4SRob Johnston phy_ptr = hba_port->first_phy; 10600f453f4SRob Johnston while (phy_ptr != NULL) { 10700f453f4SRob Johnston last_phy = phy_ptr; 10800f453f4SRob Johnston phy_ptr = phy_ptr->next; 10900f453f4SRob Johnston free(last_phy); 11000f453f4SRob Johnston } 11100f453f4SRob Johnston 11200f453f4SRob Johnston last_hba_port = hba_port; 11300f453f4SRob Johnston hba_port = hba_port->next; 11400f453f4SRob Johnston free(last_hba_port->port_attributes.\ 1159e86db79SHyon Kim PortSpecificAttribute.SASPort); 11600f453f4SRob Johnston free(last_hba_port); 1179e86db79SHyon Kim } 1189e86db79SHyon Kim 1199e86db79SHyon Kim open_handle = hba_ptr->open_handles; 1209e86db79SHyon Kim while (open_handle != NULL) { 12100f453f4SRob Johnston last_open_handle = open_handle; 12200f453f4SRob Johnston open_handle = open_handle->next; 12300f453f4SRob Johnston free(last_open_handle); 1249e86db79SHyon Kim } 1259e86db79SHyon Kim /* Free up the top level HBA structure from the last spin */ 1269e86db79SHyon Kim if (last_hba_ptr != NULL) { 12700f453f4SRob Johnston free(last_hba_ptr); 1289e86db79SHyon Kim } 1299e86db79SHyon Kim last_hba_ptr = hba_ptr; 1309e86db79SHyon Kim } 1319e86db79SHyon Kim if (last_hba_ptr != NULL) { 13200f453f4SRob Johnston free(last_hba_ptr); 1339e86db79SHyon Kim } 1349e86db79SHyon Kim 1359e86db79SHyon Kim return (HBA_STATUS_OK); 1369e86db79SHyon Kim } 137