15331Samw /* 25331Samw * CDDL HEADER START 35331Samw * 45331Samw * The contents of this file are subject to the terms of the 55331Samw * Common Development and Distribution License (the "License"). 65331Samw * You may not use this file except in compliance with the License. 75331Samw * 85331Samw * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 95331Samw * or http://www.opensolaris.org/os/licensing. 105331Samw * See the License for the specific language governing permissions 115331Samw * and limitations under the License. 125331Samw * 135331Samw * When distributing Covered Code, include this CDDL HEADER in each 145331Samw * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 155331Samw * If applicable, add the following below this CDDL HEADER, with the 165331Samw * fields enclosed by brackets "[]" replaced with your own identifying 175331Samw * information: Portions Copyright [yyyy] [name of copyright owner] 185331Samw * 195331Samw * CDDL HEADER END 205331Samw */ 215331Samw /* 225772Sas200622 * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 235331Samw * Use is subject to license terms. 245331Samw */ 255331Samw 26*7348SJose.Borrego@Sun.COM #pragma ident "@(#)smb_scfutil.c 1.5 08/07/30 SMI" 275331Samw 285331Samw /* helper functions for using libscf with CIFS */ 295331Samw 305331Samw #include <libscf.h> 315331Samw #include <string.h> 325331Samw #include <stdio.h> 335331Samw #include <stdlib.h> 345331Samw #include <syslog.h> 355331Samw #include <errno.h> 365331Samw #include <libintl.h> 375331Samw #include <assert.h> 385331Samw #include <strings.h> 395331Samw 405331Samw #include <uuid/uuid.h> 415331Samw #include <sys/param.h> 425331Samw 435331Samw #include <smbsrv/libsmb.h> 445331Samw 455331Samw /* 465331Samw * smb_smf_scf_log_error(msg) 475331Samw * Logs error messages from scf API's 485331Samw */ 495331Samw static void 505331Samw smb_smf_scf_log_error(char *msg) 515331Samw { 525331Samw if (!msg) { 535331Samw syslog(LOG_ERR, " SMBD SMF problem: %s\n", 545331Samw scf_strerror(scf_error())); 555331Samw } else { /*LINTED E_SEC_PRINTF_E_VAR_FMT*/ 565331Samw syslog(LOG_ERR, msg, scf_strerror(scf_error())); 575331Samw } 585331Samw } 595331Samw 605331Samw /* 615331Samw * smb_smf_create_service_pgroup(handle, pgroup) 625331Samw * 635331Samw * create a new property group at service level. 645331Samw */ 655331Samw int 665331Samw smb_smf_create_service_pgroup(smb_scfhandle_t *handle, char *pgroup) 675331Samw { 685331Samw int ret = SMBD_SMF_OK; 695331Samw int err; 705331Samw 716030Sjb150015 if (handle == NULL) 725331Samw return (SMBD_SMF_SYSTEM_ERR); 735331Samw 745331Samw /* 755331Samw * only create a handle if it doesn't exist. It is ok to exist 765331Samw * since the pg handle will be set as a side effect. 775331Samw */ 785331Samw if (handle->scf_pg == NULL) 796030Sjb150015 if ((handle->scf_pg = 806030Sjb150015 scf_pg_create(handle->scf_handle)) == NULL) 816030Sjb150015 return (SMBD_SMF_SYSTEM_ERR); 825331Samw 835331Samw /* 845331Samw * if the pgroup exists, we are done. If it doesn't, then we 855331Samw * need to actually add one to the service instance. 865331Samw */ 875331Samw if (scf_service_get_pg(handle->scf_service, 885331Samw pgroup, handle->scf_pg) != 0) { 895331Samw /* doesn't exist so create one */ 905331Samw if (scf_service_add_pg(handle->scf_service, pgroup, 915331Samw SCF_GROUP_APPLICATION, 0, handle->scf_pg) != 0) { 925331Samw err = scf_error(); 935331Samw if (err != SCF_ERROR_NONE) 945331Samw smb_smf_scf_log_error(NULL); 955331Samw switch (err) { 965331Samw case SCF_ERROR_PERMISSION_DENIED: 975331Samw ret = SMBD_SMF_NO_PERMISSION; 985331Samw break; 995331Samw default: 1005331Samw ret = SMBD_SMF_SYSTEM_ERR; 1015331Samw break; 1025331Samw } 1035331Samw } 1045331Samw } 1055331Samw return (ret); 1065331Samw } 1075331Samw 1085331Samw /* 1095331Samw * Start transaction on current pg in handle. 1105331Samw * The pg could be service or instance level. 1115331Samw * Must be called after pg handle is obtained 1125331Samw * from create or get. 1135331Samw */ 1145331Samw int 1155331Samw smb_smf_start_transaction(smb_scfhandle_t *handle) 1165331Samw { 1175331Samw int ret = SMBD_SMF_OK; 1185331Samw 1195331Samw if (!handle || (!handle->scf_pg)) 1205331Samw return (SMBD_SMF_SYSTEM_ERR); 1215331Samw 1225331Samw /* 1235331Samw * lookup the property group and create it if it doesn't already 1245331Samw * exist. 1255331Samw */ 1265331Samw if (handle->scf_state == SCH_STATE_INIT) { 1275331Samw if (ret == SMBD_SMF_OK) { 1285331Samw handle->scf_trans = 1295331Samw scf_transaction_create(handle->scf_handle); 1305331Samw if (handle->scf_trans != NULL) { 1315331Samw if (scf_transaction_start(handle->scf_trans, 1325331Samw handle->scf_pg) != 0) { 1335331Samw ret = SMBD_SMF_SYSTEM_ERR; 1345331Samw scf_transaction_destroy( 1355331Samw handle->scf_trans); 1365331Samw handle->scf_trans = NULL; 1375331Samw } 1385331Samw } else { 1395331Samw ret = SMBD_SMF_SYSTEM_ERR; 1405331Samw } 1415331Samw } 1425331Samw } 1435331Samw if (ret == SMBD_SMF_SYSTEM_ERR && 1445331Samw scf_error() == SCF_ERROR_PERMISSION_DENIED) 1455331Samw ret = SMBD_SMF_NO_PERMISSION; 1465331Samw 1475331Samw return (ret); 1485331Samw } 1495331Samw 1505331Samw /* 1515331Samw * smb_smf_end_transaction(handle) 1525331Samw * 1535331Samw * Commit the changes that were added to the transaction in the 1545331Samw * handle. Do all necessary cleanup. 1555331Samw */ 1565331Samw int 1575331Samw smb_smf_end_transaction(smb_scfhandle_t *handle) 1585331Samw { 1595331Samw int ret = SMBD_SMF_OK; 1605331Samw 1615331Samw if (handle == NULL) 1625331Samw return (SMBD_SMF_SYSTEM_ERR); 1635331Samw 1645331Samw if (handle->scf_trans == NULL) { 1655331Samw ret = SMBD_SMF_SYSTEM_ERR; 1665331Samw } else { 1675331Samw if (scf_transaction_commit(handle->scf_trans) < 0) { 1685331Samw ret = SMBD_SMF_SYSTEM_ERR; 1695331Samw smb_smf_scf_log_error("Failed to commit " 1705331Samw "transaction: %s"); 1715331Samw } 1725331Samw scf_transaction_destroy_children(handle->scf_trans); 1735331Samw scf_transaction_destroy(handle->scf_trans); 1745331Samw handle->scf_trans = NULL; 1755331Samw } 1765331Samw return (ret); 1775331Samw } 1785331Samw 1795331Samw /* 1805331Samw * Sets string property in current pg 1815331Samw */ 1825331Samw int 1835331Samw smb_smf_set_string_property(smb_scfhandle_t *handle, 1845331Samw char *propname, char *valstr) 1855331Samw { 1865331Samw int ret = SMBD_SMF_OK; 1875331Samw scf_value_t *value = NULL; 1885331Samw scf_transaction_entry_t *entry = NULL; 1895331Samw 1905331Samw if (handle == NULL) 1915331Samw return (SMBD_SMF_SYSTEM_ERR); 1925331Samw 1935331Samw /* 1945331Samw * properties must be set in transactions and don't take 1955331Samw * effect until the transaction has been ended/committed. 1965331Samw */ 1975331Samw value = scf_value_create(handle->scf_handle); 1985331Samw entry = scf_entry_create(handle->scf_handle); 1995331Samw if (value != NULL && entry != NULL) { 2005331Samw if (scf_transaction_property_change(handle->scf_trans, entry, 2015331Samw propname, SCF_TYPE_ASTRING) == 0 || 2025331Samw scf_transaction_property_new(handle->scf_trans, entry, 2035331Samw propname, SCF_TYPE_ASTRING) == 0) { 2045331Samw if (scf_value_set_astring(value, valstr) == 0) { 2055331Samw if (scf_entry_add_value(entry, value) != 0) { 2065331Samw ret = SMBD_SMF_SYSTEM_ERR; 2075331Samw scf_value_destroy(value); 2085331Samw } 2095331Samw /* the value is in the transaction */ 2105331Samw value = NULL; 2115331Samw } else { 2125331Samw /* value couldn't be constructed */ 2135331Samw ret = SMBD_SMF_SYSTEM_ERR; 2145331Samw } 2155331Samw /* the entry is in the transaction */ 2165331Samw entry = NULL; 2175331Samw } else { 2185331Samw ret = SMBD_SMF_SYSTEM_ERR; 2195331Samw } 2205331Samw } else { 2215331Samw ret = SMBD_SMF_SYSTEM_ERR; 2225331Samw } 2235331Samw if (ret == SMBD_SMF_SYSTEM_ERR) { 2245331Samw switch (scf_error()) { 2255331Samw case SCF_ERROR_PERMISSION_DENIED: 2265331Samw ret = SMBD_SMF_NO_PERMISSION; 2275331Samw break; 2285331Samw } 2295331Samw } 2305331Samw 2315331Samw /* 2325331Samw * cleanup if there were any errors that didn't leave these 2335331Samw * values where they would be cleaned up later. 2345331Samw */ 2355331Samw if (value != NULL) 2365331Samw scf_value_destroy(value); 2375331Samw if (entry != NULL) 2385331Samw scf_entry_destroy(entry); 2395331Samw return (ret); 2405331Samw } 2415331Samw 2425331Samw /* 2435331Samw * Gets string property value.upto sz size. 2445331Samw * Caller is responsible to have enough memory allocated. 2455331Samw */ 2465331Samw int 2475331Samw smb_smf_get_string_property(smb_scfhandle_t *handle, char *propname, 2485331Samw char *valstr, size_t sz) 2495331Samw { 2505331Samw int ret = SMBD_SMF_OK; 2515331Samw scf_value_t *value; 2525331Samw scf_property_t *prop; 2535331Samw 2545331Samw if (handle == NULL) 2555331Samw return (SMBD_SMF_SYSTEM_ERR); 2565331Samw 2575331Samw value = scf_value_create(handle->scf_handle); 2585331Samw prop = scf_property_create(handle->scf_handle); 2595331Samw if (value && prop && 2605331Samw (scf_pg_get_property(handle->scf_pg, propname, prop) == 0)) { 2615331Samw if (scf_property_get_value(prop, value) == 0) { 2625331Samw if (scf_value_get_astring(value, valstr, sz) < 0) { 2635331Samw ret = SMBD_SMF_SYSTEM_ERR; 2645331Samw } 2655331Samw } else { 2665331Samw ret = SMBD_SMF_SYSTEM_ERR; 2675331Samw } 2685331Samw } else { 2695331Samw ret = SMBD_SMF_SYSTEM_ERR; 2705331Samw } 2715331Samw if (value != NULL) 2725331Samw scf_value_destroy(value); 2735331Samw if (prop != NULL) 2745331Samw scf_property_destroy(prop); 2755331Samw return (ret); 2765331Samw } 2775331Samw 2785331Samw /* 2795331Samw * Set integer value of property. 2805331Samw * The value is returned as int64_t value 2815331Samw * Caller ensures appropriate translation. 2825331Samw */ 2835331Samw int 2845331Samw smb_smf_set_integer_property(smb_scfhandle_t *handle, char *propname, 2855331Samw int64_t valint) 2865331Samw { 2875331Samw int ret = SMBD_SMF_OK; 2885331Samw scf_value_t *value = NULL; 2895331Samw scf_transaction_entry_t *entry = NULL; 2905331Samw 2915331Samw if (handle == NULL) 2925331Samw return (SMBD_SMF_SYSTEM_ERR); 2935331Samw 2945331Samw /* 2955331Samw * properties must be set in transactions and don't take 2965331Samw * effect until the transaction has been ended/committed. 2975331Samw */ 2985331Samw value = scf_value_create(handle->scf_handle); 2995331Samw entry = scf_entry_create(handle->scf_handle); 3005331Samw if (value != NULL && entry != NULL) { 3015331Samw if (scf_transaction_property_change(handle->scf_trans, entry, 3025331Samw propname, SCF_TYPE_INTEGER) == 0 || 3035331Samw scf_transaction_property_new(handle->scf_trans, entry, 3045331Samw propname, SCF_TYPE_INTEGER) == 0) { 3055331Samw scf_value_set_integer(value, valint); 3065331Samw if (scf_entry_add_value(entry, value) != 0) { 3075331Samw ret = SMBD_SMF_SYSTEM_ERR; 3085331Samw scf_value_destroy(value); 3095331Samw } 3105331Samw /* the value is in the transaction */ 3115331Samw value = NULL; 3125331Samw } 3135331Samw /* the entry is in the transaction */ 3145331Samw entry = NULL; 3155331Samw } else { 3165331Samw ret = SMBD_SMF_SYSTEM_ERR; 3175331Samw } 3185331Samw if (ret == SMBD_SMF_SYSTEM_ERR) { 3195331Samw switch (scf_error()) { 3205331Samw case SCF_ERROR_PERMISSION_DENIED: 3215331Samw ret = SMBD_SMF_NO_PERMISSION; 3225331Samw break; 3235331Samw } 3245331Samw } 3255331Samw /* 3265331Samw * cleanup if there were any errors that didn't leave these 3275331Samw * values where they would be cleaned up later. 3285331Samw */ 3295331Samw if (value != NULL) 3305331Samw scf_value_destroy(value); 3315331Samw if (entry != NULL) 3325331Samw scf_entry_destroy(entry); 3335331Samw return (ret); 3345331Samw } 3355331Samw 3365331Samw /* 3375331Samw * Gets integer property value. 3385331Samw * Caller is responsible to have enough memory allocated. 3395331Samw */ 3405331Samw int 3415331Samw smb_smf_get_integer_property(smb_scfhandle_t *handle, char *propname, 3425331Samw int64_t *valint) 3435331Samw { 3445331Samw int ret = SMBD_SMF_OK; 3455331Samw scf_value_t *value = NULL; 3465331Samw scf_property_t *prop = NULL; 3475331Samw 3485331Samw if (handle == NULL) 3495331Samw return (SMBD_SMF_SYSTEM_ERR); 3505331Samw 3515331Samw value = scf_value_create(handle->scf_handle); 3525331Samw prop = scf_property_create(handle->scf_handle); 3535331Samw if ((prop) && (value) && 3545331Samw (scf_pg_get_property(handle->scf_pg, propname, prop) == 0)) { 3555331Samw if (scf_property_get_value(prop, value) == 0) { 3565331Samw if (scf_value_get_integer(value, 3575331Samw valint) != 0) { 3585331Samw ret = SMBD_SMF_SYSTEM_ERR; 3595331Samw } 3605331Samw } else { 3615331Samw ret = SMBD_SMF_SYSTEM_ERR; 3625331Samw } 3635331Samw } else { 3645331Samw ret = SMBD_SMF_SYSTEM_ERR; 3655331Samw } 3665331Samw if (value != NULL) 3675331Samw scf_value_destroy(value); 3685331Samw if (prop != NULL) 3695331Samw scf_property_destroy(prop); 3705331Samw return (ret); 3715331Samw } 3725331Samw 3735331Samw /* 3745331Samw * Set boolean value of property. 3755331Samw * The value is returned as int64_t value 3765331Samw * Caller ensures appropriate translation. 3775331Samw */ 3785331Samw int 3795331Samw smb_smf_set_boolean_property(smb_scfhandle_t *handle, char *propname, 3805331Samw uint8_t valbool) 3815331Samw { 3825331Samw int ret = SMBD_SMF_OK; 3835331Samw scf_value_t *value = NULL; 3845331Samw scf_transaction_entry_t *entry = NULL; 3855331Samw 3865331Samw if (handle == NULL) 3875331Samw return (SMBD_SMF_SYSTEM_ERR); 3885331Samw 3895331Samw /* 3905331Samw * properties must be set in transactions and don't take 3915331Samw * effect until the transaction has been ended/committed. 3925331Samw */ 3935331Samw value = scf_value_create(handle->scf_handle); 3945331Samw entry = scf_entry_create(handle->scf_handle); 3955331Samw if (value != NULL && entry != NULL) { 3965331Samw if (scf_transaction_property_change(handle->scf_trans, entry, 3975331Samw propname, SCF_TYPE_BOOLEAN) == 0 || 3985331Samw scf_transaction_property_new(handle->scf_trans, entry, 3995331Samw propname, SCF_TYPE_BOOLEAN) == 0) { 4005331Samw scf_value_set_boolean(value, valbool); 4015331Samw if (scf_entry_add_value(entry, value) != 0) { 4025331Samw ret = SMBD_SMF_SYSTEM_ERR; 4035331Samw scf_value_destroy(value); 4045331Samw } 4055331Samw /* the value is in the transaction */ 4065331Samw value = NULL; 4075331Samw } 4085331Samw /* the entry is in the transaction */ 4095331Samw entry = NULL; 4105331Samw } else { 4115331Samw ret = SMBD_SMF_SYSTEM_ERR; 4125331Samw } 4135331Samw if (ret == SMBD_SMF_SYSTEM_ERR) { 4145331Samw switch (scf_error()) { 4155331Samw case SCF_ERROR_PERMISSION_DENIED: 4165331Samw ret = SMBD_SMF_NO_PERMISSION; 4175331Samw break; 4185331Samw } 4195331Samw } 4205331Samw /* 4215331Samw * cleanup if there were any errors that didn't leave these 4225331Samw * values where they would be cleaned up later. 4235331Samw */ 4245331Samw if (value != NULL) 4255331Samw scf_value_destroy(value); 4265331Samw if (entry != NULL) 4275331Samw scf_entry_destroy(entry); 4285331Samw return (ret); 4295331Samw } 4305331Samw 4315331Samw /* 4325331Samw * Gets boolean property value. 4335331Samw * Caller is responsible to have enough memory allocated. 4345331Samw */ 4355331Samw int 4365331Samw smb_smf_get_boolean_property(smb_scfhandle_t *handle, char *propname, 4375331Samw uint8_t *valbool) 4385331Samw { 4395331Samw int ret = SMBD_SMF_OK; 4405331Samw scf_value_t *value = NULL; 4415331Samw scf_property_t *prop = NULL; 4425331Samw 4435331Samw if (handle == NULL) 4445331Samw return (SMBD_SMF_SYSTEM_ERR); 4455331Samw 4465331Samw value = scf_value_create(handle->scf_handle); 4475331Samw prop = scf_property_create(handle->scf_handle); 4485331Samw if ((prop) && (value) && 4495331Samw (scf_pg_get_property(handle->scf_pg, propname, prop) == 0)) { 4505331Samw if (scf_property_get_value(prop, value) == 0) { 4515331Samw if (scf_value_get_boolean(value, 4525331Samw valbool) != 0) { 4535331Samw ret = SMBD_SMF_SYSTEM_ERR; 4545331Samw } 4555331Samw } else { 4565331Samw ret = SMBD_SMF_SYSTEM_ERR; 4575331Samw } 4585331Samw } else { 4595331Samw ret = SMBD_SMF_SYSTEM_ERR; 4605331Samw } 4615331Samw if (value != NULL) 4625331Samw scf_value_destroy(value); 4635331Samw if (prop != NULL) 4645331Samw scf_property_destroy(prop); 4655331Samw return (ret); 4665331Samw } 4675331Samw 4685331Samw /* 4695331Samw * Sets a blob property value. 4705331Samw */ 4715331Samw int 4725331Samw smb_smf_set_opaque_property(smb_scfhandle_t *handle, char *propname, 4735331Samw void *voidval, size_t sz) 4745331Samw { 4755331Samw int ret = SMBD_SMF_OK; 4765331Samw scf_value_t *value; 4775331Samw scf_transaction_entry_t *entry; 4785331Samw 4795331Samw if (handle == NULL) 4805331Samw return (SMBD_SMF_SYSTEM_ERR); 4815331Samw 4825331Samw /* 4835331Samw * properties must be set in transactions and don't take 4845331Samw * effect until the transaction has been ended/committed. 4855331Samw */ 4865331Samw value = scf_value_create(handle->scf_handle); 4875331Samw entry = scf_entry_create(handle->scf_handle); 4885331Samw if (value != NULL && entry != NULL) { 4895331Samw if (scf_transaction_property_change(handle->scf_trans, entry, 4905331Samw propname, SCF_TYPE_OPAQUE) == 0 || 4915331Samw scf_transaction_property_new(handle->scf_trans, entry, 4925331Samw propname, SCF_TYPE_OPAQUE) == 0) { 4935331Samw if (scf_value_set_opaque(value, voidval, sz) == 0) { 4945331Samw if (scf_entry_add_value(entry, value) != 0) { 4955331Samw ret = SMBD_SMF_SYSTEM_ERR; 4965331Samw scf_value_destroy(value); 4975331Samw } 4985331Samw /* the value is in the transaction */ 4995331Samw value = NULL; 5005331Samw } else { 5015331Samw /* value couldn't be constructed */ 5025331Samw ret = SMBD_SMF_SYSTEM_ERR; 5035331Samw } 5045331Samw /* the entry is in the transaction */ 5055331Samw entry = NULL; 5065331Samw } else { 5075331Samw ret = SMBD_SMF_SYSTEM_ERR; 5085331Samw } 5095331Samw } else { 5105331Samw ret = SMBD_SMF_SYSTEM_ERR; 5115331Samw } 5125331Samw if (ret == SMBD_SMF_SYSTEM_ERR) { 5135331Samw switch (scf_error()) { 5145331Samw case SCF_ERROR_PERMISSION_DENIED: 5155331Samw ret = SMBD_SMF_NO_PERMISSION; 5165331Samw break; 5175331Samw } 5185331Samw } 5195331Samw /* 5205331Samw * cleanup if there were any errors that didn't leave these 5215331Samw * values where they would be cleaned up later. 5225331Samw */ 5235331Samw if (value != NULL) 5245331Samw scf_value_destroy(value); 5255331Samw if (entry != NULL) 5265331Samw scf_entry_destroy(entry); 5275331Samw return (ret); 5285331Samw } 5295331Samw 5305331Samw /* 5315331Samw * Gets a blob property value. 5325331Samw * Caller is responsible to have enough memory allocated. 5335331Samw */ 5345331Samw int 5355331Samw smb_smf_get_opaque_property(smb_scfhandle_t *handle, char *propname, 5365331Samw void *v, size_t sz) 5375331Samw { 5385331Samw int ret = SMBD_SMF_OK; 5395331Samw scf_value_t *value = NULL; 5405331Samw scf_property_t *prop = NULL; 5415331Samw 5425331Samw if (handle == NULL) 5435331Samw return (SMBD_SMF_SYSTEM_ERR); 5445331Samw 5455331Samw value = scf_value_create(handle->scf_handle); 5465331Samw prop = scf_property_create(handle->scf_handle); 5475331Samw if ((prop) && (value) && 5485331Samw (scf_pg_get_property(handle->scf_pg, propname, prop) == 0)) { 5495331Samw if (scf_property_get_value(prop, value) == 0) { 5505331Samw if (scf_value_get_opaque(value, (char *)v, sz) != sz) { 5515331Samw ret = SMBD_SMF_SYSTEM_ERR; 5525331Samw } 5535331Samw } else { 5545331Samw ret = SMBD_SMF_SYSTEM_ERR; 5555331Samw } 5565331Samw } else { 5575331Samw ret = SMBD_SMF_SYSTEM_ERR; 5585331Samw } 5595331Samw if (value != NULL) 5605331Samw scf_value_destroy(value); 5615331Samw if (prop != NULL) 5625331Samw scf_property_destroy(prop); 5635331Samw return (ret); 5645331Samw } 5655331Samw 5665331Samw /* 567*7348SJose.Borrego@Sun.COM * smb_smf_restart_service() 568*7348SJose.Borrego@Sun.COM * 569*7348SJose.Borrego@Sun.COM * Restarts SMB SMF service. 570*7348SJose.Borrego@Sun.COM */ 571*7348SJose.Borrego@Sun.COM int 572*7348SJose.Borrego@Sun.COM smb_smf_restart_service(void) 573*7348SJose.Borrego@Sun.COM { 574*7348SJose.Borrego@Sun.COM return (smf_restart_instance(SMBD_DEFAULT_INSTANCE_FMRI)); 575*7348SJose.Borrego@Sun.COM } 576*7348SJose.Borrego@Sun.COM 577*7348SJose.Borrego@Sun.COM /* 5785331Samw * smb_smf_scf_init() 5795331Samw * 5805331Samw * must be called before using any of the SCF functions. 5815331Samw * Returns smb_scfhandle_t pointer if success. 5825331Samw */ 5835331Samw smb_scfhandle_t * 5845331Samw smb_smf_scf_init(char *svc_name) 5855331Samw { 5865331Samw smb_scfhandle_t *handle; 5875331Samw 5885331Samw handle = malloc(sizeof (smb_scfhandle_t)); 5895331Samw if (handle != NULL) { 5905331Samw bzero((char *)handle, sizeof (smb_scfhandle_t)); 5915331Samw handle->scf_state = SCH_STATE_INITIALIZING; 5925331Samw handle->scf_handle = scf_handle_create(SCF_VERSION); 5935331Samw if (handle->scf_handle != NULL) { 5945331Samw if (scf_handle_bind(handle->scf_handle) == 0) { 5955331Samw handle->scf_scope = 5965331Samw scf_scope_create(handle->scf_handle); 5976030Sjb150015 5986030Sjb150015 if (handle->scf_scope == NULL) 5996030Sjb150015 goto err; 6006030Sjb150015 6015331Samw if (scf_handle_get_local_scope( 6025331Samw handle->scf_handle, handle->scf_scope) != 0) 6035331Samw goto err; 6045331Samw 6055331Samw handle->scf_service = 6065331Samw scf_service_create(handle->scf_handle); 6075331Samw 6086030Sjb150015 if (handle->scf_service == NULL) 6096030Sjb150015 goto err; 6106030Sjb150015 6115331Samw if (scf_scope_get_service(handle->scf_scope, 6125331Samw svc_name, handle->scf_service) 6135331Samw != SCF_SUCCESS) { 6145331Samw goto err; 6155331Samw } 6165331Samw handle->scf_pg = 6175331Samw scf_pg_create(handle->scf_handle); 6186030Sjb150015 6196030Sjb150015 if (handle->scf_pg == NULL) 6206030Sjb150015 goto err; 6216030Sjb150015 6225331Samw handle->scf_state = SCH_STATE_INIT; 6235331Samw } else { 6245331Samw goto err; 6255331Samw } 6265331Samw } else { 6275331Samw free(handle); 6285331Samw handle = NULL; 6295331Samw smb_smf_scf_log_error("Could not access SMF " 6305331Samw "repository: %s\n"); 6315331Samw } 6325331Samw } 6335331Samw return (handle); 6345331Samw 6355331Samw /* error handling/unwinding */ 6365331Samw err: 6375331Samw (void) smb_smf_scf_fini(handle); 6385331Samw (void) smb_smf_scf_log_error("SMF initialization problem: %s\n"); 6395331Samw return (NULL); 6405331Samw } 6415331Samw 6425331Samw /* 6435331Samw * smb_smf_scf_fini(handle) 6445331Samw * 6455331Samw * must be called when done. Called with the handle allocated in 6465331Samw * smb_smf_scf_init(), it cleans up the state and frees any SCF resources 6475331Samw * still in use. 6485331Samw */ 6495331Samw void 6505331Samw smb_smf_scf_fini(smb_scfhandle_t *handle) 6515331Samw { 6525331Samw if (handle != NULL) { 6535331Samw int unbind = 0; 6545331Samw scf_iter_destroy(handle->scf_pg_iter); 6555331Samw handle->scf_pg_iter = NULL; 6565331Samw 6575331Samw scf_iter_destroy(handle->scf_inst_iter); 6585331Samw handle->scf_inst_iter = NULL; 6595331Samw 6605331Samw unbind = 1; 6615331Samw scf_scope_destroy(handle->scf_scope); 6625331Samw handle->scf_scope = NULL; 6635331Samw 6645331Samw scf_instance_destroy(handle->scf_instance); 6655331Samw handle->scf_instance = NULL; 6665331Samw 6675331Samw scf_service_destroy(handle->scf_service); 6685331Samw handle->scf_service = NULL; 6695331Samw 6705331Samw scf_pg_destroy(handle->scf_pg); 6715331Samw handle->scf_pg = NULL; 6725331Samw 6735331Samw handle->scf_state = SCH_STATE_UNINIT; 6745331Samw if (unbind) 6755331Samw (void) scf_handle_unbind(handle->scf_handle); 6765331Samw scf_handle_destroy(handle->scf_handle); 6775331Samw handle->scf_handle = NULL; 6785331Samw 6795331Samw free(handle); 6805331Samw } 6815331Samw } 682