/* * smb_smf_scf_init() * * must be called before using any of the SCF functions. * Returns smb_scfhandle_t pointer if success. */ smb_scfhandle_t * smb_smf_scf_init(char *svc_name) { smb_scfhandle_t *handle; handle = malloc(sizeof (smb_scfhandle_t)); if (handle != NULL) { bzero((char *)handle, sizeof (smb_scfhandle_t)); handle->scf_state = SCH_STATE_INITIALIZING; handle->scf_handle = scf_handle_create(SCF_VERSION); if (handle->scf_handle != NULL) { if (scf_handle_bind(handle->scf_handle) == 0) { handle->scf_scope = scf_scope_create(handle->scf_handle); if (handle->scf_scope == NULL) goto err; if (scf_handle_get_local_scope( handle->scf_handle, handle->scf_scope) != 0) goto err; handle->scf_service = scf_service_create(handle->scf_handle); if (handle->scf_service == NULL) goto err; if (scf_scope_get_service(handle->scf_scope, svc_name, handle->scf_service) != SCF_SUCCESS) { goto err; } handle->scf_pg = scf_pg_create(handle->scf_handle); if (handle->scf_pg == NULL) goto err; handle->scf_state = SCH_STATE_INIT; } else { goto err; } } else { free(handle); handle = NULL; smb_smf_scf_log_error("Could not access SMF " "repository: %s\n"); } } return (handle); /* error handling/unwinding */ err: (void) smb_smf_scf_fini(handle); (void) smb_smf_scf_log_error("SMF initialization problem: %s\n"); return (NULL); }
fs_smfhandle_t * fs_smf_init(char *fmri, char *instance) { fs_smfhandle_t *handle = NULL; char *svcname, srv[MAXPATHLEN]; /* * svc name is of the form svc://network/fs/server:instance1 * FMRI portion is /network/fs/server */ snprintf(srv, MAXPATHLEN, "%s", fmri + strlen("svc:/")); svcname = strrchr(srv, ':'); if (svcname != NULL) *svcname = '\0'; svcname = srv; handle = calloc(1, sizeof (fs_smfhandle_t)); if (handle != NULL) { handle->fs_handle = scf_handle_create(SCF_VERSION); if (handle->fs_handle == NULL) goto out; if (scf_handle_bind(handle->fs_handle) != 0) goto out; handle->fs_service = scf_service_create(handle->fs_handle); handle->fs_scope = scf_scope_create(handle->fs_handle); if (scf_handle_get_local_scope(handle->fs_handle, handle->fs_scope) != 0) goto out; if (scf_scope_get_service(handle->fs_scope, svcname, handle->fs_service) != SCF_SUCCESS) { goto out; } handle->fs_pg = scf_pg_create(handle->fs_handle); handle->fs_instance = scf_instance_create(handle->fs_handle); handle->fs_property = scf_property_create(handle->fs_handle); handle->fs_value = scf_value_create(handle->fs_handle); } else { fprintf(stderr, gettext("Cannot access SMF repository: %s\n"), fmri); } return (handle); out: fs_smf_fini(handle); fprintf(stderr, gettext("SMF Initialization problems..%s\n"), fmri); return (NULL); }
targ_scf_t * mgmt_handle_init(void) { targ_scf_t *h; h = calloc(1, sizeof (targ_scf_t)); if (h == NULL) return (NULL); h->t_handle = scf_handle_create(SCF_VERSION); if (h->t_handle != NULL) { if (scf_handle_bind(h->t_handle) == 0) { h->t_scope = scf_scope_create(h->t_handle); h->t_service = scf_service_create(h->t_handle); h->t_pg = scf_pg_create(h->t_handle); h->t_instance = scf_instance_create(h->t_handle); if (scf_handle_get_scope(h->t_handle, SCF_SCOPE_LOCAL, h->t_scope) == 0) { if (scf_scope_get_service(h->t_scope, SA_TARGET_SVC_NAME, h->t_service) != 0) goto error; } else { syslog(LOG_ERR, "Got local scope which is wrong\n"); goto error; } } else goto error; } else { free(h); h = NULL; syslog(LOG_ERR, "iscsitgt could not access SMF repository: %s\n", scf_strerror(scf_error())); } return (h); error: mgmt_handle_fini(h); free(h); syslog(LOG_ERR, "iscsitgt SMF initialization problem: %s\n", scf_strerror(scf_error())); return (NULL); }
static int create_service(const char *instance_name, const char *kssl_entry, const char *command, const char *username, char *inaddr_any_name) { int status = FAILURE; scf_scope_t *scope; scf_service_t *svc; scf_handle_t *handle; boolean_t errflag = B_TRUE; handle = scf_handle_create(SCF_VERSION); if (handle == NULL) { KSSL_DEBUG("scf_handle_create failed: %s\n", scf_strerror(scf_error())); goto out1; } KSSL_DEBUG("scf_handle_create succeeded\n"); if (scf_handle_bind(handle) == -1) { KSSL_DEBUG("scf_handle_bind failed: %s\n", scf_strerror(scf_error())); goto out1; } KSSL_DEBUG("scf_handle_bind succeeded\n"); if ((scope = scf_scope_create(handle)) == NULL) { KSSL_DEBUG("scf_scope_create failed: %s\n", scf_strerror(scf_error())); goto out2; } KSSL_DEBUG("scf_scope_create succeeded\n"); if ((svc = scf_service_create(handle)) == NULL) { KSSL_DEBUG("scf_service_create failed: %s\n", scf_strerror(scf_error())); goto out3; } KSSL_DEBUG("scf_service_create succeeded\n"); if (scf_handle_decode_fmri(handle, SERVICE_NAME, NULL, svc, NULL, NULL, NULL, SCF_DECODE_FMRI_EXACT) != 0) { KSSL_DEBUG("scf_handle_decode_fmri failed: %s\n", scf_strerror(scf_error())); if (scf_error() == SCF_ERROR_NOT_FOUND) { (void) fprintf(stderr, gettext( "service %s not found in the repository." " Exiting.\n"), SERVICE_NAME); errflag = B_FALSE; } goto out4; } status = create_instance(handle, svc, instance_name, kssl_entry, command, username, inaddr_any_name); out4: scf_service_destroy(svc); out3: scf_scope_destroy(scope); out2: (void) scf_handle_unbind(handle); out1: if (handle != NULL) scf_handle_destroy(handle); if (status != SUCCESS && status != INSTANCE_OTHER_EXISTS && status != INSTANCE_ANY_EXISTS && errflag) (void) fprintf(stderr, gettext( "Unexpected fatal libscf error: %s. Exiting.\n"), scf_strerror(scf_error())); return (status); }
int delete_instance(const char *instance_name) { int status = FAILURE; char *buf; boolean_t errflag = B_FALSE; ssize_t max_fmri_len; scf_scope_t *scope; scf_service_t *svc; scf_handle_t *handle; scf_instance_t *instance; handle = scf_handle_create(SCF_VERSION); if (handle == NULL) { errflag = B_TRUE; KSSL_DEBUG("scf_handle_create failed: %s\n", scf_strerror(scf_error())); goto out1; } KSSL_DEBUG("scf_handle_create succeeded\n"); if (scf_handle_bind(handle) == -1) { errflag = B_TRUE; KSSL_DEBUG("scf_handle_bind failed: %s\n", scf_strerror(scf_error())); goto out1; } KSSL_DEBUG("scf_handle_bind succeeded\n"); if ((scope = scf_scope_create(handle)) == NULL) { errflag = B_TRUE; KSSL_DEBUG("scf_scope_create failed: %s\n", scf_strerror(scf_error())); goto out2; } KSSL_DEBUG("scf_scope_create succeeded\n"); if ((svc = scf_service_create(handle)) == NULL) { errflag = B_TRUE; KSSL_DEBUG("scf_service_create failed: %s\n", scf_strerror(scf_error())); goto out3; } KSSL_DEBUG("scf_service_create succeeded\n"); if (scf_handle_get_scope(handle, SCF_SCOPE_LOCAL, scope) == -1) { errflag = B_TRUE; KSSL_DEBUG("scf_handle_get_scope failed: %s\n", scf_strerror(scf_error())); goto out4; } KSSL_DEBUG("scf_handle_get_scope succeeded\n"); if (scf_scope_get_service(scope, SERVICE_NAME, svc) < 0) { scf_error_t scf_errnum = scf_error(); if (scf_errnum != SCF_ERROR_NOT_FOUND) { errflag = B_TRUE; KSSL_DEBUG( "ERROR scf_scope_get_service failed: %s\n", scf_strerror(scf_errnum)); } goto out4; } else { KSSL_DEBUG("scf_scope_get_service succeeded\n"); } instance = scf_instance_create(handle); if (instance == NULL) { errflag = B_TRUE; KSSL_DEBUG("scf_instance_create failed: %s\n", scf_strerror(scf_error())); goto out4; } if (scf_service_get_instance(svc, instance_name, instance) != 0) { scf_error_t scf_errnum = scf_error(); if (scf_errnum == SCF_ERROR_NOT_FOUND) { status = SUCCESS; } else { errflag = B_TRUE; KSSL_DEBUG( "ERROR scf_scope_get_service failed: %s\n", scf_strerror(scf_errnum)); } scf_instance_destroy(instance); goto out4; } max_fmri_len = scf_limit(SCF_LIMIT_MAX_FMRI_LENGTH); if ((buf = malloc(max_fmri_len + 1)) == NULL) goto out4; if (scf_instance_to_fmri(instance, buf, max_fmri_len + 1) > 0) { char *state; KSSL_DEBUG("instance_fmri=%s\n", buf); state = smf_get_state(buf); if (state) KSSL_DEBUG("state=%s\n", state); if (state && strcmp(state, "online") == 0) { if (smf_disable_instance(buf, 0) != 0) { errflag = B_TRUE; KSSL_DEBUG( "smf_disable_instance failed: %s\n", scf_strerror(scf_error())); } else { /* * Wait for some time till timeout to avoid * a race with scf_instance_delete() below. */ wait_till_to(buf); } } } if (scf_instance_delete(instance) != 0) { errflag = B_TRUE; KSSL_DEBUG( "ERROR scf_instance_delete failed: %s\n", scf_strerror(scf_error())); goto out4; } else { KSSL_DEBUG("deleted %s\n", instance_name); } status = SUCCESS; out4: scf_service_destroy(svc); out3: scf_scope_destroy(scope); out2: (void) scf_handle_unbind(handle); out1: if (handle != NULL) scf_handle_destroy(handle); if (errflag) (void) fprintf(stderr, gettext( "Unexpected fatal libscf error: %s. Exiting.\n"), scf_strerror(scf_error())); return (status); }
void read_scf_proto_cfg(const char *proto, scf_cfg_t *cfg) { scf_handle_t *handle = NULL; scf_scope_t *sc = NULL; scf_service_t *svc = NULL; scf_propertygroup_t *pg = NULL; scf_property_t *prop = NULL; scf_value_t *value = NULL; scf_iter_t *value_iter = NULL; uint64_t val; char *str; size_t slen; int i; handle = scf_handle_create(SCF_VERSION); sc = scf_scope_create(handle); svc = scf_service_create(handle); pg = scf_pg_create(handle); prop = scf_property_create(handle); value = scf_value_create(handle); value_iter = scf_iter_create(handle); if (handle == NULL || sc == NULL || svc == NULL || pg == NULL || prop == NULL || value == NULL || value_iter == NULL) { DMSG(D_OP, "%s: unable to create smf(5) handles.", proto); goto done; } if (scf_handle_bind(handle) != 0) { DMSG(D_OP, "%s: unable to bind smf(5) handle: %s", proto, scf_strerror(scf_error())); goto done; } if (scf_handle_decode_fmri(handle, fmri, sc, svc, NULL, NULL, NULL, 0) != 0) { DMSG(D_OP, "%s: unable to decode fmri '%s': %s", fmri, scf_strerror(scf_error())); goto done; } if (scf_service_get_pg(svc, proto, pg) != 0 && scf_error() != SCF_ERROR_NOT_FOUND) { DMSG(D_OP, "%s: unable to read '%s' property group: %s", proto, proto, scf_strerror(scf_error())); goto done; } for (i = 0; cfg[i].name != NULL; i++) { scf_cfg_t *c = &cfg[i]; if (scf_pg_get_property(pg, c->name, prop) != 0) { if (scf_error() != SCF_ERROR_NOT_FOUND) DMSG(D_OP, "%s: unable to read %s/%s from " "smf: %s", proto, proto, c->name, scf_strerror(scf_error())); continue; } if (scf_property_is_type(prop, c->type) != 0) { scf_type_t type; if (scf_error() != SCF_ERROR_TYPE_MISMATCH) { DMSG(D_OP, "%s: unable to validate " "type of '%s/%s' smf property: %s", proto, proto, c->name, scf_strerror(scf_error())); continue; } if (scf_property_type(prop, &type) != 0) { DMSG(D_OP, "%s: unable to obtain " "type of '%s/%s' smf property: %s", proto, proto, c->name, scf_strerror(scf_error())); continue; } DMSG(D_OP, "%s: property '%s/%s' has an unexpected " "type:\n" " expected type: %s\n" " actual type: %s\n", proto, proto, c->name, scf_type_to_string(c->type), scf_type_to_string(type)); continue; } if (scf_property_get_value(prop, value) != 0) { if (scf_error() != SCF_ERROR_NOT_SET) DMSG(D_OP, "%s: unable to get value of " "'%s/%s' smf property: %s", proto, proto, c->name, scf_strerror(scf_error())); continue; } switch (c->type) { case SCF_TYPE_COUNT: if (scf_value_get_count(value, &val) != 0) { DMSG(D_OP, "%s: unable to read value of " "'%s/%s' smf property: %s", proto, proto, c->name, scf_strerror(scf_error())); continue; } if (val > c->max) { DMSG(D_OP, "%s: value of '%s/%s' smf property " "(%'llu) is out of range (0 - %'zu).", proto, proto, c->name, val, c->max); continue; } *((uint32_t *)c->val) = (uint32_t)val; break; case SCF_TYPE_ASTRING: { char **valp = (char **)c->val; ssize_t len; slen = c->max + 1; if ((str = malloc(slen)) == NULL) { /* XXX message */ continue; } if ((len = scf_value_get_astring(value, str, slen)) >= slen) DMSG(D_OP, "%s: length of '%s/%s' " "(%'zd bytes) exceeds maximum " "allowable length (%zu bytes). The string" " will be truncated.", proto, proto, c->name, len, c->max); free(*valp); *valp = str; break; } default: VERIFY(0); } } done: scf_iter_destroy(value_iter); scf_value_destroy(value); scf_property_destroy(prop); scf_pg_destroy(pg); scf_service_destroy(svc); scf_scope_destroy(sc); scf_handle_destroy(handle); }