/* crypto/engine/eng_ctrl.c */
/* ====================================================================
 * Copyright (c) 1999-2001 The OpenSSL Project.  All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer. 
 *
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *
 * 3. All advertising materials mentioning features or use of this
 *    software must display the following acknowledgment:
 *    "This product includes software developed by the OpenSSL Project
 *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 *
 * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
 *    endorse or promote products derived from this software without
 *    prior written permission. For written permission, please contact
 *    licensing@OpenSSL.org.
 *
 * 5. Products derived from this software may not be called "OpenSSL"
 *    nor may "OpenSSL" appear in their names without prior written
 *    permission of the OpenSSL Project.
 *
 * 6. Redistributions of any form whatsoever must retain the following
 *    acknowledgment:
 *    "This product includes software developed by the OpenSSL Project
 *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 *
 * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
 * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
 * OF THE POSSIBILITY OF SUCH DAMAGE.
 * ====================================================================
 *
 * This product includes cryptographic software written by Eric Young
 * (eay@cryptsoft.com).  This product includes software written by Tim
 * Hudson (tjh@cryptsoft.com).
 *
 */

#include <openssl/crypto.h>
#include "cryptlib.h"
#include "eng_int.h"
#include <openssl/engine.h>

/* When querying a ENGINE-specific control command's 'description', this string
 * is used if the ENGINE_CMD_DEFN has cmd_desc set to NULL. */
static const char *int_no_description = "";

/* These internal functions handle 'CMD'-related control commands when the
 * ENGINE in question has asked us to take care of it (ie. the ENGINE did not
 * set the ENGINE_FLAGS_MANUAL_CMD_CTRL flag. */

static int int_ctrl_cmd_is_null(const ENGINE_CMD_DEFN *defn)
	{
	if((defn->cmd_num == 0) || (defn->cmd_name == NULL))
		return 1;
	return 0;
	}

static int int_ctrl_cmd_by_name(const ENGINE_CMD_DEFN *defn, const char *s)
	{
	int idx = 0;
	while(!int_ctrl_cmd_is_null(defn) && (strcmp(defn->cmd_name, s) != 0))
		{
		idx++;
		defn++;
		}
	if(int_ctrl_cmd_is_null(defn))
		/* The given name wasn't found */
		return -1;
	return idx;
	}

static int int_ctrl_cmd_by_num(const ENGINE_CMD_DEFN *defn, unsigned int num)
	{
	int idx = 0;
	/* NB: It is stipulated that 'cmd_defn' lists are ordered by cmd_num. So
	 * our searches don't need to take any longer than necessary. */
	while(!int_ctrl_cmd_is_null(defn) && (defn->cmd_num < num))
		{
		idx++;
		defn++;
		}
	if(defn->cmd_num == num)
		return idx;
	/* The given cmd_num wasn't found */
	return -1;
	}

static int int_ctrl_helper(ENGINE *e, int cmd, long i, void *p, void (*f)())
	{
	int idx;
	char *s = (char *)p;
	/* Take care of the easy one first (eg. it requires no searches) */
	if(cmd == ENGINE_CTRL_GET_FIRST_CMD_TYPE)
		{
		if((e->cmd_defns == NULL) || int_ctrl_cmd_is_null(e->cmd_defns))
			return 0;
		return e->cmd_defns->cmd_num;
		}
	/* One or two commands require that "p" be a valid string buffer */
	if((cmd == ENGINE_CTRL_GET_CMD_FROM_NAME) ||
			(cmd == ENGINE_CTRL_GET_NAME_FROM_CMD) ||
			(cmd == ENGINE_CTRL_GET_DESC_FROM_CMD))
		{
		if(s == NULL)
			{
			ENGINEerr(ENGINE_F_INT_CTRL_HELPER,
				ERR_R_PASSED_NULL_PARAMETER);
			return -1;
			}
		}
	/* Now handle cmd_name -> cmd_num conversion */
	if(cmd == ENGINE_CTRL_GET_CMD_FROM_NAME)
		{
		if((e->cmd_defns == NULL) || ((idx = int_ctrl_cmd_by_name(
						e->cmd_defns, s)) < 0))
			{
			ENGINEerr(ENGINE_F_INT_CTRL_HELPER,
				ENGINE_R_INVALID_CMD_NAME);
			return -1;
			}
		return e->cmd_defns[idx].cmd_num;
		}
	/* For the rest of the commands, the 'long' argument must specify a
	 * valie command number - so we need to conduct a search. */
	if((e->cmd_defns == NULL) || ((idx = int_ctrl_cmd_by_num(e->cmd_defns,
					(unsigned int)i)) < 0))
		{
		ENGINEerr(ENGINE_F_INT_CTRL_HELPER,
			ENGINE_R_INVALID_CMD_NUMBER);
		return -1;
		}
	/* Now the logic splits depending on command type */
	switch(cmd)
		{
	case ENGINE_CTRL_GET_NEXT_CMD_TYPE:
		idx++;
		if(int_ctrl_cmd_is_null(e->cmd_defns + idx))
			/* end-of-list */
			return 0;
		else
			return e->cmd_defns[idx].cmd_num;
	case ENGINE_CTRL_GET_NAME_LEN_FROM_CMD:
		return strlen(e->cmd_defns[idx].cmd_name);
	case ENGINE_CTRL_GET_NAME_FROM_CMD:
		return sprintf(s, "%s", e->cmd_defns[idx].cmd_name);
	case ENGINE_CTRL_GET_DESC_LEN_FROM_CMD:
		if(e->cmd_defns[idx].cmd_desc)
			return strlen(e->cmd_defns[idx].cmd_desc);
		return strlen(int_no_description);
	case ENGINE_CTRL_GET_DESC_FROM_CMD:
		if(e->cmd_defns[idx].cmd_desc)
			return sprintf(s, "%s", e->cmd_defns[idx].cmd_desc);
		return sprintf(s, "%s", int_no_description);
	case ENGINE_CTRL_GET_CMD_FLAGS:
		return e->cmd_defns[idx].cmd_flags;
		}
	/* Shouldn't really be here ... */
	ENGINEerr(ENGINE_F_INT_CTRL_HELPER,ENGINE_R_INTERNAL_LIST_ERROR);
	return -1;
	}

int ENGINE_ctrl(ENGINE *e, int cmd, long i, void *p, void (*f)())
	{
	int ctrl_exists, ref_exists;
	if(e == NULL)
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL,ERR_R_PASSED_NULL_PARAMETER);
		return 0;
		}
	CRYPTO_w_lock(CRYPTO_LOCK_ENGINE);
	ref_exists = ((e->struct_ref > 0) ? 1 : 0);
	CRYPTO_w_unlock(CRYPTO_LOCK_ENGINE);
	ctrl_exists = ((e->ctrl == NULL) ? 0 : 1);
	if(!ref_exists)
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL,ENGINE_R_NO_REFERENCE);
		return 0;
		}
	/* Intercept any "root-level" commands before trying to hand them on to
	 * ctrl() handlers. */
	switch(cmd)
		{
	case ENGINE_CTRL_HAS_CTRL_FUNCTION:
		return ctrl_exists;
	case ENGINE_CTRL_GET_FIRST_CMD_TYPE:
	case ENGINE_CTRL_GET_NEXT_CMD_TYPE:
	case ENGINE_CTRL_GET_CMD_FROM_NAME:
	case ENGINE_CTRL_GET_NAME_LEN_FROM_CMD:
	case ENGINE_CTRL_GET_NAME_FROM_CMD:
	case ENGINE_CTRL_GET_DESC_LEN_FROM_CMD:
	case ENGINE_CTRL_GET_DESC_FROM_CMD:
	case ENGINE_CTRL_GET_CMD_FLAGS:
		if(ctrl_exists && !(e->flags & ENGINE_FLAGS_MANUAL_CMD_CTRL))
			return int_ctrl_helper(e,cmd,i,p,f);
		if(!ctrl_exists)
			{
			ENGINEerr(ENGINE_F_ENGINE_CTRL,ENGINE_R_NO_CONTROL_FUNCTION);
			/* For these cmd-related functions, failure is indicated
			 * by a -1 return value (because 0 is used as a valid
			 * return in some places). */
			return -1;
			}
	default:
		break;
		}
	/* Anything else requires a ctrl() handler to exist. */
	if(!ctrl_exists)
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL,ENGINE_R_NO_CONTROL_FUNCTION);
		return 0;
		}
	return e->ctrl(e, cmd, i, p, f);
	}

int ENGINE_cmd_is_executable(ENGINE *e, int cmd)
	{
	int flags;
	if((flags = ENGINE_ctrl(e, ENGINE_CTRL_GET_CMD_FLAGS, cmd, NULL, NULL)) < 0)
		{
		ENGINEerr(ENGINE_F_ENGINE_CMD_IS_EXECUTABLE,
			ENGINE_R_INVALID_CMD_NUMBER);
		return 0;
		}
	if(!(flags & ENGINE_CMD_FLAG_NO_INPUT) &&
			!(flags & ENGINE_CMD_FLAG_NUMERIC) &&
			!(flags & ENGINE_CMD_FLAG_STRING))
		return 0;
	return 1;
	}

int ENGINE_ctrl_cmd(ENGINE *e, const char *cmd_name,
        long i, void *p, void (*f)(), int cmd_optional)
        {
	int num;

	if((e == NULL) || (cmd_name == NULL))
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ERR_R_PASSED_NULL_PARAMETER);
		return 0;
		}
	if((e->ctrl == NULL) || ((num = ENGINE_ctrl(e,
					ENGINE_CTRL_GET_CMD_FROM_NAME,
					0, (void *)cmd_name, NULL)) <= 0))
		{
		/* If the command didn't *have* to be supported, we fake
		 * success. This allows certain settings to be specified for
		 * multiple ENGINEs and only require a change of ENGINE id
		 * (without having to selectively apply settings). Eg. changing
		 * from a hardware device back to the regular software ENGINE
		 * without editing the config file, etc. */
		if(cmd_optional)
			{
			ERR_clear_error();
			return 1;
			}
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD,
			ENGINE_R_INVALID_CMD_NAME);
		return 0;
		}
	/* Force the result of the control command to 0 or 1, for the reasons
	 * mentioned before. */
        if (ENGINE_ctrl(e, num, i, p, f))
                return 1;
        return 0;
        }

int ENGINE_ctrl_cmd_string(ENGINE *e, const char *cmd_name, const char *arg,
				int cmd_optional)
	{
	int num, flags;
	long l;
	char *ptr;
	if((e == NULL) || (cmd_name == NULL))
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ERR_R_PASSED_NULL_PARAMETER);
		return 0;
		}
	if((e->ctrl == NULL) || ((num = ENGINE_ctrl(e,
					ENGINE_CTRL_GET_CMD_FROM_NAME,
					0, (void *)cmd_name, NULL)) <= 0))
		{
		/* If the command didn't *have* to be supported, we fake
		 * success. This allows certain settings to be specified for
		 * multiple ENGINEs and only require a change of ENGINE id
		 * (without having to selectively apply settings). Eg. changing
		 * from a hardware device back to the regular software ENGINE
		 * without editing the config file, etc. */
		if(cmd_optional)
			{
			ERR_clear_error();
			return 1;
			}
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ENGINE_R_INVALID_CMD_NAME);
		return 0;
		}
	if(!ENGINE_cmd_is_executable(e, num))
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ENGINE_R_CMD_NOT_EXECUTABLE);
		return 0;
		}
	if((flags = ENGINE_ctrl(e, ENGINE_CTRL_GET_CMD_FLAGS, num, NULL, NULL)) < 0)
		{
		/* Shouldn't happen, given that ENGINE_cmd_is_executable()
		 * returned success. */
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ENGINE_R_INTERNAL_LIST_ERROR);
		return 0;
		}
	/* If the command takes no input, there must be no input. And vice
	 * versa. */
	if(flags & ENGINE_CMD_FLAG_NO_INPUT)
		{
		if(arg != NULL)
			{
			ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
				ENGINE_R_COMMAND_TAKES_NO_INPUT);
			return 0;
			}
		/* We deliberately force the result of ENGINE_ctrl() to 0 or 1
		 * rather than returning it as "return data". This is to ensure
		 * usage of these commands is consistent across applications and
		 * that certain applications don't understand it one way, and
		 * others another. */
		if(ENGINE_ctrl(e, num, 0, (void *)arg, NULL))
			return 1;
		return 0;
		}
	/* So, we require input */
	if(arg == NULL)
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ENGINE_R_COMMAND_TAKES_INPUT);
		return 0;
		}
	/* If it takes string input, that's easy */
	if(flags & ENGINE_CMD_FLAG_STRING)
		{
		/* Same explanation as above */
		if(ENGINE_ctrl(e, num, 0, (void *)arg, NULL))
			return 1;
		return 0;
		}
	/* If it doesn't take numeric either, then it is unsupported for use in
	 * a config-setting situation, which is what this function is for. This
	 * should never happen though, because ENGINE_cmd_is_executable() was
	 * used. */
	if(!(flags & ENGINE_CMD_FLAG_NUMERIC))
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ENGINE_R_INTERNAL_LIST_ERROR);
		return 0;
		}
	l = strtol(arg, &ptr, 10);
	if((arg == ptr) || (*ptr != '\0'))
		{
		ENGINEerr(ENGINE_F_ENGINE_CTRL_CMD_STRING,
			ENGINE_R_ARGUMENT_IS_NOT_A_NUMBER);
		return 0;
		}
	/* Force the result of the control command to 0 or 1, for the reasons
	 * mentioned before. */
	if(ENGINE_ctrl(e, num, l, NULL, NULL))
		return 1;
	return 0;
	}
