control.c revision d2ef84e07b67e72a4bd9c729c6b8228067d17584
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews/*
7d32c065c7bb56f281651ae3dd2888f32ce4f1d9Bob Halley * Copyright (C) 2004, 2005 Internet Systems Consortium, Inc. ("ISC")
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence * Copyright (C) 2001-2003 Internet Software Consortium.
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews *
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * Permission to use, copy, modify, and distribute this software for any
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * purpose with or without fee is hereby granted, provided that the above
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence * copyright notice and this permission notice appear in all copies.
15a44745412679c30a6d022733925af70a38b715David Lawrence *
15a44745412679c30a6d022733925af70a38b715David Lawrence * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
15a44745412679c30a6d022733925af70a38b715David Lawrence * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
15a44745412679c30a6d022733925af70a38b715David Lawrence * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
15a44745412679c30a6d022733925af70a38b715David Lawrence * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
15a44745412679c30a6d022733925af70a38b715David Lawrence * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
15a44745412679c30a6d022733925af70a38b715David Lawrence * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
15a44745412679c30a6d022733925af70a38b715David Lawrence * PERFORMANCE OF THIS SOFTWARE.
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews */
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
b589e90689c6e87bf9608424ca8d99571c18bc61Mark Andrews/* $Id: control.c,v 1.27 2006/03/09 23:39:00 marka Exp $ */
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
542deb20c44666a870855bf755a100d254db074dAndreas Gustafsson/*! \file */
542deb20c44666a870855bf755a100d254db074dAndreas Gustafsson
542deb20c44666a870855bf755a100d254db074dAndreas Gustafsson#include <config.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
854d0238dbc2908490197984b3b9d558008a53dfMark Andrews#include <string.h>
854d0238dbc2908490197984b3b9d558008a53dfMark Andrews
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#include <isc/app.h>
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff#include <isc/event.h>
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff#include <isc/mem.h>
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff#include <isc/timer.h>
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#include <isc/util.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence#include <dns/result.h>
0bd044c2afee944d93879a7de82cd2ccc0635798David Lawrence
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#include <isccc/alist.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#include <isccc/cc.h>
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff#include <isccc/result.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#include <named/control.h>
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson#include <named/log.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#include <named/os.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#include <named/server.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#ifdef HAVE_LIBSCF
542deb20c44666a870855bf755a100d254db074dAndreas Gustafsson#include <named/ns_smf_globals.h>
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#endif
34b394b43e2207e8f8f3703f0402422121455638David Lawrence
34b394b43e2207e8f8f3703f0402422121455638David Lawrencestatic isc_boolean_t
34b394b43e2207e8f8f3703f0402422121455638David Lawrencecommand_compare(const char *text, const char *command) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews unsigned int commandlen = strlen(command);
542deb20c44666a870855bf755a100d254db074dAndreas Gustafsson if (strncasecmp(text, command, commandlen) == 0 &&
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff (text[commandlen] == '\0' ||
0bd044c2afee944d93879a7de82cd2ccc0635798David Lawrence text[commandlen] == ' ' ||
0bd044c2afee944d93879a7de82cd2ccc0635798David Lawrence text[commandlen] == '\t'))
34b394b43e2207e8f8f3703f0402422121455638David Lawrence return (ISC_TRUE);
5d15501996f597d9bbb734d88d4549828e28000bMark Andrews return (ISC_FALSE);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews}
0bd044c2afee944d93879a7de82cd2ccc0635798David Lawrence
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews/*%
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * This function is called to process the incoming command
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * when a control channel message is received.
34b394b43e2207e8f8f3703f0402422121455638David Lawrence */
34b394b43e2207e8f8f3703f0402422121455638David Lawrenceisc_result_t
34b394b43e2207e8f8f3703f0402422121455638David Lawrencens_control_docommand(isccc_sexpr_t *message, isc_buffer_t *text) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isccc_sexpr_t *data;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson char *command;
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews isc_result_t result;
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#ifdef HAVE_LIBSCF
34b394b43e2207e8f8f3703f0402422121455638David Lawrence ns_smf_want_disable = 0;
34b394b43e2207e8f8f3703f0402422121455638David Lawrence#endif
34b394b43e2207e8f8f3703f0402422121455638David Lawrence
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews data = isccc_alist_lookup(message, "_data");
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews if (data == NULL) {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence /*
ea8651059209b96fa005e06a0b9b33ae5a8eacd4David Lawrence * No data section.
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews */
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews return (ISC_R_FAILURE);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence }
34b394b43e2207e8f8f3703f0402422121455638David Lawrence
34b394b43e2207e8f8f3703f0402422121455638David Lawrence result = isccc_cc_lookupstring(data, "type", &command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews if (result != ISC_R_SUCCESS) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews /*
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * We have no idea what this is.
34b394b43e2207e8f8f3703f0402422121455638David Lawrence */
34b394b43e2207e8f8f3703f0402422121455638David Lawrence return (result);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence }
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson isc_log_write(ns_g_lctx, NS_LOGCATEGORY_GENERAL,
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson NS_LOGMODULE_CONTROL, ISC_LOG_DEBUG(1),
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews "received control channel command '%s'",
34b394b43e2207e8f8f3703f0402422121455638David Lawrence command);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence
34b394b43e2207e8f8f3703f0402422121455638David Lawrence /*
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * Compare the 'command' parameter against all known control commands.
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson */
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson if (command_compare(command, NS_COMMAND_RELOAD)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_reloadcommand(ns_g_server, command, text);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_RECONFIG)) {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence result = ns_server_reconfigcommand(ns_g_server, command);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_REFRESH)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_refreshcommand(ns_g_server, command, text);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_RETRANSFER)) {
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence result = ns_server_retransfercommand(ns_g_server, command);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_HALT)) {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence#ifdef HAVE_LIBSCF
34b394b43e2207e8f8f3703f0402422121455638David Lawrence /*
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * If we are managed by smf(5), AND in chroot, then
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * we cannot connect to the smf repository, so just
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence * return with an appropriate message back to rndc.
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews */
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews if (ns_smf_got_instance == 1 && ns_smf_chroot == 1) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_smf_add_message(text);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence return (result);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence }
34b394b43e2207e8f8f3703f0402422121455638David Lawrence /*
822f6cdabb1edd44472c7a758b5cae71376fa9beBrian Wellington * If we are managed by smf(5) but not in chroot,
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * try to disable ourselves the smf way.
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews */
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff if (ns_smf_got_instance == 1 && ns_smf_chroot == 0)
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence ns_smf_want_disable = 1;
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews /*
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * If ns_smf_got_instance = 0, ns_smf_chroot
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * is not relevant and we fall through to
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews * isc_app_shutdown below.
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews */
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#endif
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews ns_server_flushonshutdown(ns_g_server, ISC_FALSE);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews ns_os_shutdownmsg(command, text);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews isc_app_shutdown();
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ISC_R_SUCCESS;
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_STOP)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#ifdef HAVE_LIBSCF
b589e90689c6e87bf9608424ca8d99571c18bc61Mark Andrews if (ns_smf_got_instance == 1 && ns_smf_chroot == 1) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_smf_add_message(text);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews return (result);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews }
34b394b43e2207e8f8f3703f0402422121455638David Lawrence if (ns_smf_got_instance == 1 && ns_smf_chroot == 0)
34b394b43e2207e8f8f3703f0402422121455638David Lawrence ns_smf_want_disable = 1;
34b394b43e2207e8f8f3703f0402422121455638David Lawrence#endif
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews ns_server_flushonshutdown(ns_g_server, ISC_TRUE);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews ns_os_shutdownmsg(command, text);
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson isc_app_shutdown();
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson result = ISC_R_SUCCESS;
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson } else if (command_compare(command, NS_COMMAND_DUMPSTATS)) {
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson result = ns_server_dumpstats(ns_g_server);
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson } else if (command_compare(command, NS_COMMAND_QUERYLOG)) {
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson result = ns_server_togglequerylog(ns_g_server);
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson } else if (command_compare(command, NS_COMMAND_DUMPDB)) {
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson ns_server_dumpdb(ns_g_server, command);
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson result = ISC_R_SUCCESS;
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson } else if (command_compare(command, NS_COMMAND_TRACE)) {
1ac4b2a1da88e574319b374bc733eccf8ac45327Andreas Gustafsson result = ns_server_setdebuglevel(ns_g_server, command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_NOTRACE)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews ns_g_debuglevel = 0;
34b394b43e2207e8f8f3703f0402422121455638David Lawrence isc_log_setdebuglevel(ns_g_lctx, ns_g_debuglevel);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence result = ISC_R_SUCCESS;
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_FLUSH)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_flushcache(ns_g_server, command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_FLUSHNAME)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_flushname(ns_g_server, command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_STATUS)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_status(ns_g_server, text);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_FREEZE)) {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence result = ns_server_freeze(ns_g_server, ISC_TRUE, command);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_UNFREEZE) ||
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews command_compare(command, NS_COMMAND_THAW)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_freeze(ns_g_server, ISC_FALSE, command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_RECURSING)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_dumprecursing(ns_g_server);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_TIMERPOKE)) {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence result = ISC_R_SUCCESS;
34b394b43e2207e8f8f3703f0402422121455638David Lawrence isc_timermgr_poke(ns_g_timermgr);
34b394b43e2207e8f8f3703f0402422121455638David Lawrence } else if (command_compare(command, NS_COMMAND_NULL)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ISC_R_SUCCESS;
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_NOTIFY)) {
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence result = ns_server_notifycommand(ns_g_server, command, text);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else if (command_compare(command, NS_COMMAND_VALIDATION)) {
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = ns_server_validation(ns_g_server, command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews } else {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence isc_log_write(ns_g_lctx, NS_LOGCATEGORY_GENERAL,
34b394b43e2207e8f8f3703f0402422121455638David Lawrence NS_LOGMODULE_CONTROL, ISC_LOG_WARNING,
34b394b43e2207e8f8f3703f0402422121455638David Lawrence "unknown control channel command '%s'",
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews command);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews result = DNS_R_UNKNOWNCOMMAND;
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson }
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
fad44a20eede1bbc66716241dede225500c91caaAndreas Gustafsson return (result);
fad44a20eede1bbc66716241dede225500c91caaAndreas Gustafsson}
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson