summaryrefslogtreecommitdiff
path: root/usr/src
diff options
context:
space:
mode:
authorjeanm <none@none>2007-07-27 08:24:13 -0700
committerjeanm <none@none>2007-07-27 08:24:13 -0700
commit76cf44ab96bdcdc3cbfa2f528bc2094df8743fde (patch)
treec9b4029ff92f21b2d949b067c6cf25e09c6c5d02 /usr/src
parent670251a0e454576c55927103f27beadb19c3cf5b (diff)
downloadillumos-joyent-76cf44ab96bdcdc3cbfa2f528bc2094df8743fde.tar.gz
6254363 svccfg validate returns incorrect diagnostics
6268011 Maintenance mode login and a shell fight for console input when the repository is corrupt 6287024 Determine which libscf functions can fail with SCF_ERROR_NO_RESOURCES 6316785 scf_snapshot_update() should abort if svc.configd returns _BAD_REQUEST
Diffstat (limited to 'usr/src')
-rw-r--r--usr/src/cmd/svc/startd/fork.c23
-rw-r--r--usr/src/cmd/svc/svccfg/svccfg_xml.c33
-rw-r--r--usr/src/lib/libscf/common/lowlevel.c139
3 files changed, 177 insertions, 18 deletions
diff --git a/usr/src/cmd/svc/startd/fork.c b/usr/src/cmd/svc/startd/fork.c
index 8968095008..c7d0670fa2 100644
--- a/usr/src/cmd/svc/startd/fork.c
+++ b/usr/src/cmd/svc/startd/fork.c
@@ -2,9 +2,8 @@
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License"). You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -53,11 +52,14 @@
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
+#include <utmpx.h>
#include "configd_exit.h"
#include "protocol.h"
#include "startd.h"
+static struct utmpx *utmpp; /* pointer for getutxent() */
+
pid_t
startd_fork1(int *forkerr)
{
@@ -267,6 +269,16 @@ fork_sulogin(boolean_t immediate, const char *format, ...)
(void) close(fd_console);
}
+ setutxent();
+ while ((utmpp = getutxent()) != NULL) {
+ if (strcmp(utmpp->ut_user, "LOGIN") != 0) {
+ if (strcmp(utmpp->ut_line, "console") == 0) {
+ (void) kill(utmpp->ut_pid, 9);
+ break;
+ }
+ }
+ }
+
(void) execl("/sbin/sulogin", "sulogin", NULL);
uu_warn("Could not exec() sulogin");
@@ -604,7 +616,8 @@ fork_rc_script(char rl, const char *arg, boolean_t wait)
if (wait) {
do
err = waitpid(pid, &stat, 0);
- while (err != 0 && errno == EINTR);
+ while (err != 0 && errno == EINTR)
+ ;
if (!WIFEXITED(stat)) {
log_framework(LOG_INFO,
diff --git a/usr/src/cmd/svc/svccfg/svccfg_xml.c b/usr/src/cmd/svc/svccfg/svccfg_xml.c
index 477c49f90b..09f4c66dfc 100644
--- a/usr/src/cmd/svc/svccfg/svccfg_xml.c
+++ b/usr/src/cmd/svc/svccfg/svccfg_xml.c
@@ -2,9 +2,8 @@
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License"). You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -37,6 +36,10 @@
#include <stdlib.h>
#include <string.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+
#include "svccfg.h"
/*
@@ -1187,8 +1190,10 @@ lxml_get_loctext(entity_t *service, pgroup_t *pg, xmlNodePtr loctext)
if ((stripped = strdup((const char *)cursor->content)) == NULL)
uu_die(gettext("Out of memory\n"));
- for (; isspace(*stripped); stripped++);
- for (cp = stripped + strlen(stripped) - 1; isspace(*cp); cp--);
+ for (; isspace(*stripped); stripped++)
+ ;
+ for (cp = stripped + strlen(stripped) - 1; isspace(*cp); cp--)
+ ;
*(cp + 1) = '\0';
p = internal_property_create((const char *)val, SCF_TYPE_USTRING, 1,
@@ -1794,9 +1799,18 @@ lxml_get_bundle_file(bundle_t *bundle, const char *filename, int apply)
xmlValidCtxtPtr vcp;
boolean_t do_validate;
char *dtdpath = NULL;
+ struct stat st;
int r;
/*
+ * Verify we can read the file before we try to parse it.
+ */
+ if (access(filename, R_OK | F_OK) == -1) {
+ semerr(gettext("unable to open file: %s\n"), strerror(errno));
+ return (-1);
+ }
+
+ /*
* Until libxml2 addresses DTD-based validation with XInclude, we don't
* validate service profiles (i.e. the apply path).
*/
@@ -1807,8 +1821,7 @@ lxml_get_bundle_file(bundle_t *bundle, const char *filename, int apply)
if (dtdpath != NULL)
xmlLoadExtDtdDefaultValue = 0;
- if ((document = xmlReadFile(filename, NULL,
- XML_PARSE_NOERROR | XML_PARSE_NOWARNING)) == NULL) {
+ if ((document = xmlReadFile(filename, NULL, 0)) == NULL) {
semerr(gettext("couldn't parse document\n"));
return (-1);
}
@@ -1853,9 +1866,9 @@ lxml_get_bundle_file(bundle_t *bundle, const char *filename, int apply)
document->extSubset = dtd;
}
- if (xmlXIncludeProcessFlags(document, XML_PARSE_XINCLUDE) == -1) {;
+ if (xmlXIncludeProcessFlags(document, XML_PARSE_XINCLUDE) == -1) {
semerr(gettext("couldn't handle XInclude statements "
- "in document\n"));
+ "in document\n"));
return (-1);
}
diff --git a/usr/src/lib/libscf/common/lowlevel.c b/usr/src/lib/libscf/common/lowlevel.c
index 198603f084..cd1c9a1459 100644
--- a/usr/src/lib/libscf/common/lowlevel.c
+++ b/usr/src/lib/libscf/common/lowlevel.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -1604,7 +1604,7 @@ datael_get_parent(const scf_datael_t *dp, scf_datael_t *pp)
* too big, bad id, iter already exists, element cannot have children of type,
* type is invalid, iter was reset, sequence was bad, iter walks values, iter
* does not walk type entities), _NOT_SET, _DELETED, _NO_RESOURCES,
- * _BACKEND_ACCESS.
+ * _BACKEND_ACCESS, _NOT_FOUND.
*/
static int
datael_get_child_composed_locked(const scf_datael_t *dp, const char *name,
@@ -1732,6 +1732,14 @@ datael_get_child_locked(const scf_datael_t *dp, const char *name,
return (0);
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT (out does not have type type,
+ * name is invalid), _NOT_BOUND, _CONNECTION_BROKEN, _INTERNAL (server response
+ * too big, bad id, iter already exists, element cannot have children of type,
+ * type is invalid, iter was reset, sequence was bad, iter walks values, iter
+ * does not walk type entities), _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
static int
datael_get_child(const scf_datael_t *dp, const char *name, uint32_t type,
scf_datael_t *out, boolean_t composed)
@@ -2557,6 +2565,22 @@ scf_service_create(scf_handle_t *handle)
return (ret);
}
+
+/*
+ * Fails with
+ * _HANDLE_MISMATCH
+ * _INVALID_ARGUMENT
+ * _NOT_BOUND
+ * _CONNECTION_BROKEN
+ * _INTERNAL
+ * _EXISTS
+ * _DELETED
+ * _NOT_SET
+ * _NO_RESOURCES
+ * _PERMISSION_DENIED
+ * _BACKEND_ACCESS
+ * _BACKEND_READONLY
+ */
int
scf_scope_add_service(const scf_scope_t *scope, const char *name,
scf_service_t *svc)
@@ -2565,6 +2589,11 @@ scf_scope_add_service(const scf_scope_t *scope, const char *name,
REP_PROTOCOL_ENTITY_SERVICE, (svc != NULL)? &svc->rd_d : NULL));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_scope_get_service(const scf_scope_t *s, const char *name,
scf_service_t *svc)
@@ -2603,6 +2632,21 @@ _scf_snapshot_delete(scf_snapshot_t *snap)
return (datael_delete(&snap->rd_d));
}
+/*
+ * Fails with
+ * _HANDLE_MISMATCH
+ * _INVALID_ARGUMENT
+ * _NOT_BOUND
+ * _CONNECTION_BROKEN
+ * _INTERNAL
+ * _EXISTS
+ * _DELETED
+ * _NOT_SET
+ * _NO_RESOURCES
+ * _PERMISSION_DENIED
+ * _BACKEND_ACCESS
+ * _BACKEND_READONLY
+ */
int
scf_service_add_instance(const scf_service_t *svc, const char *name,
scf_instance_t *instance)
@@ -2612,6 +2656,12 @@ scf_service_add_instance(const scf_service_t *svc, const char *name,
(instance != NULL)? &instance->rd_d : NULL));
}
+
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_service_get_instance(const scf_service_t *svc, const char *name,
scf_instance_t *inst)
@@ -2628,6 +2678,11 @@ scf_service_add_pg(const scf_service_t *svc, const char *name,
(pg != NULL)?&pg->rd_d : NULL));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_service_get_pg(const scf_service_t *svc, const char *name,
scf_propertygroup_t *pg)
@@ -2644,6 +2699,11 @@ scf_instance_add_pg(const scf_instance_t *inst, const char *name,
(pg != NULL)?&pg->rd_d : NULL));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_instance_get_snapshot(const scf_instance_t *inst, const char *name,
scf_snapshot_t *pg)
@@ -2652,6 +2712,11 @@ scf_instance_get_snapshot(const scf_instance_t *inst, const char *name,
REP_PROTOCOL_ENTITY_SNAPSHOT, pg ? &pg->rd_d : NULL, 0));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_instance_get_pg(const scf_instance_t *inst, const char *name,
scf_propertygroup_t *pg)
@@ -2660,6 +2725,11 @@ scf_instance_get_pg(const scf_instance_t *inst, const char *name,
REP_PROTOCOL_ENTITY_PROPERTYGRP, pg ? &pg->rd_d : NULL, 0));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_instance_get_pg_composed(const scf_instance_t *inst,
const scf_snapshot_t *snap, const char *name, scf_propertygroup_t *pg)
@@ -2671,6 +2741,11 @@ scf_instance_get_pg_composed(const scf_instance_t *inst,
REP_PROTOCOL_ENTITY_PROPERTYGRP, pg ? &pg->rd_d : NULL, 1));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_pg_get_property(const scf_propertygroup_t *pg, const char *name,
scf_property_t *prop)
@@ -2847,6 +2922,11 @@ scf_snaplevel_get_instance_name(const scf_snaplevel_t *rep, char *out,
RP_ENTITY_NAME_SNAPLEVEL_INSTANCE));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _NOT_FOUND.
+ */
int
scf_snaplevel_get_pg(const scf_snaplevel_t *snap, const char *name,
scf_propertygroup_t *pg)
@@ -3015,6 +3095,13 @@ datael_update(scf_datael_t *dp)
if (r < 0)
DOOR_ERRORS_BLOCK(r);
+ /*
+ * This should never happen but if it does something has
+ * gone terribly wrong and we should abort.
+ */
+ if (response.rpr_response == REP_PROTOCOL_FAIL_BAD_REQUEST)
+ abort();
+
if (response.rpr_response != REP_PROTOCOL_SUCCESS &&
response.rpr_response != REP_PROTOCOL_DONE) {
return (scf_set_error(proto_error(response.rpr_response)));
@@ -3564,6 +3651,11 @@ entry_destroy_locked(scf_transaction_entry_t *entry)
uu_free(entry);
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _IN_USE, _NOT_FOUND, _EXISTS, _TYPE_MISMATCH.
+ */
static int
transaction_add(scf_transaction_t *tran, scf_transaction_entry_t *entry,
enum rep_protocol_transaction_action action,
@@ -3672,6 +3764,11 @@ error:
return (scf_set_error(error));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _IN_USE, _NOT_FOUND, _EXISTS, _TYPE_MISMATCH.
+ */
int
scf_transaction_property_new(scf_transaction_t *tx,
scf_transaction_entry_t *entry, const char *prop, scf_type_t type)
@@ -3680,6 +3777,11 @@ scf_transaction_property_new(scf_transaction_t *tx,
prop, scf_type_to_protocol_type(type)));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _IN_USE, _NOT_FOUND, _EXISTS, _TYPE_MISMATCH.
+ */
int
scf_transaction_property_change(scf_transaction_t *tx,
scf_transaction_entry_t *entry, const char *prop, scf_type_t type)
@@ -3688,6 +3790,11 @@ scf_transaction_property_change(scf_transaction_t *tx,
prop, scf_type_to_protocol_type(type)));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _IN_USE, _NOT_FOUND, _EXISTS, _TYPE_MISMATCH.
+ */
int
scf_transaction_property_change_type(scf_transaction_t *tx,
scf_transaction_entry_t *entry, const char *prop, scf_type_t type)
@@ -3696,6 +3803,11 @@ scf_transaction_property_change_type(scf_transaction_t *tx,
prop, scf_type_to_protocol_type(type)));
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _NOT_BOUND,
+ * _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED, _NO_RESOURCES,
+ * _BACKEND_ACCESS, _IN_USE, _NOT_FOUND, _EXISTS, _TYPE_MISMATCH.
+ */
int
scf_transaction_property_delete(scf_transaction_t *tx,
scf_transaction_entry_t *entry, const char *prop)
@@ -5100,7 +5212,7 @@ scf_parse_fmri(char *fmri, int *type, const char **scope, const char **service,
if (type)
*type = SCF_FMRI_TYPE_SVC;
return (scf_parse_svc_fmri(fmri, scope, service, instance,
- propertygroup, property));
+ propertygroup, property));
} else if (strncmp(fmri, SCF_FMRI_FILE_PREFIX,
sizeof (SCF_FMRI_FILE_PREFIX) - 1) == 0) {
if (type)
@@ -5169,6 +5281,11 @@ scf_canonify_fmri(const char *fmri, char *buf, size_t bufsz)
return (len);
}
+/*
+ * Fails with _HANDLE_MISMATCH, _INVALID_ARGUMENT, _CONSTRAINT_VIOLATED,
+ * _NOT_FOUND, _NOT_BOUND, _CONNECTION_BROKEN, _INTERNAL, _NOT_SET, _DELETED,
+ * _NO_RESOURCES, _BACKEND_ACCESS.
+ */
int
scf_handle_decode_fmri(scf_handle_t *h, const char *fmri, scf_scope_t *sc,
scf_service_t *svc, scf_instance_t *inst, scf_propertygroup_t *pg,
@@ -5664,6 +5781,16 @@ scf_property_to_fmri(const scf_property_t *prop, char *out, size_t sz)
return (len);
}
+/*
+ * Fails with _HANDLE_MISMATCH, _NOT_BOUND, _CONNECTION_BROKEN, _INTERNAL
+ * (server response too big, bad entity id, request not applicable to entity,
+ * name too long for buffer, bad element id, iter already exists, element
+ * cannot have children of type, type is invalid, iter was reset, sequence
+ * was bad, iter walks values, iter does not walk type entities),
+ * _NOT_SET, _DELETED, or _CONSTRAINT_VIOLATED,
+ * _NOT_FOUND (scope has no parent), _INVALID_ARGUMENT, _NO_RESOURCES,
+ * _BACKEND_ACCESS.
+ */
int
scf_pg_get_underlying_pg(const scf_propertygroup_t *pg,
scf_propertygroup_t *out)
@@ -5984,6 +6111,12 @@ scf_pattern_match(scf_matchkey_t **htable, char *fmri, const char *legacy,
return (0);
}
+/*
+ * Fails with _INVALID_ARGUMENT, _HANDLE_DESTROYED, _INTERNAL (bad server
+ * response or id in use), _NO_MEMORY, _HANDLE_MISMATCH, _CONSTRAINT_VIOLATED,
+ * _NOT_FOUND, _NOT_BOUND, _CONNECTION_BROKEN, _NOT_SET, _DELETED,
+ * _NO_RESOURCES, _BACKEND_ACCESS, _TYPE_MISMATCH.
+ */
scf_error_t
scf_walk_fmri(scf_handle_t *h, int argc, char **argv, int flags,
scf_walk_callback callback, void *data, int *err,