#include "includes.h"
#include "dbutil.h"
#include "buffer.h"
#include "ecdsa.h"
#include "genrsa.h"
#include "gendss.h"
#include "signkey.h"
#include "dbrandom.h"

#define RSA_DEFAULT_SIZE 2048
#define DSS_DEFAULT_SIZE 1024

/* Returns DROPBEAR_SUCCESS or DROPBEAR_FAILURE */
static int buf_writefile(buffer * buf, const char * filename) {
	int ret = DROPBEAR_FAILURE;
	int fd = -1;

	fd = open(filename, O_RDWR | O_CREAT | O_EXCL, S_IRUSR | S_IWUSR);
	if (fd < 0) {
		dropbear_log(LOG_ERR, "Couldn't create new file %s: %s",
			filename, strerror(errno));
		goto out;
	}

	/* write the file now */
	while (buf->pos != buf->len) {
		int len = write(fd, buf_getptr(buf, buf->len - buf->pos),
				buf->len - buf->pos);
		if (len == -1 && errno == EINTR) {
			continue;
		}
		if (len <= 0) {
			dropbear_log(LOG_ERR, "Failed writing file %s: %s",
				filename, strerror(errno));
			goto out;
		}
		buf_incrpos(buf, len);
	}

	ret = DROPBEAR_SUCCESS;

out:
	if (fd >= 0) {
		if (fsync(fd) != 0) {
			dropbear_log(LOG_ERR, "fsync of %s failed: %s", filename, strerror(errno));
		}
		m_close(fd);
	}
	return ret;
}

/* returns 0 on failure */
static int get_default_bits(enum signkey_type keytype)
{
	switch (keytype) {
#if DROPBEAR_RSA
		case DROPBEAR_SIGNKEY_RSA:
			return RSA_DEFAULT_SIZE;
#endif
#if DROPBEAR_DSS
		case DROPBEAR_SIGNKEY_DSS:
			return DSS_DEFAULT_SIZE;
#endif
#if DROPBEAR_ECDSA
		case DROPBEAR_SIGNKEY_ECDSA_KEYGEN:
			return ECDSA_DEFAULT_SIZE;
		case DROPBEAR_SIGNKEY_ECDSA_NISTP521:
			return 521;
		case DROPBEAR_SIGNKEY_ECDSA_NISTP384:
			return 384;
		case DROPBEAR_SIGNKEY_ECDSA_NISTP256:
			return 256;
#endif
		default:
			return 0;
	}
}

int signkey_generate(enum signkey_type keytype, int bits, const char* filename)
{
	sign_key * key = NULL;
	buffer *buf = NULL;
	int ret = DROPBEAR_FAILURE;
	if (bits == 0)
	{
		bits = get_default_bits(keytype);
	}

	/* now we can generate the key */
	key = new_sign_key();

	seedrandom();

	switch(keytype) {
#if DROPBEAR_RSA
		case DROPBEAR_SIGNKEY_RSA:
			key->rsakey = gen_rsa_priv_key(bits);
			break;
#endif
#if DROPBEAR_DSS
		case DROPBEAR_SIGNKEY_DSS:
			key->dsskey = gen_dss_priv_key(bits);
			break;
#endif
#if DROPBEAR_ECDSA
		case DROPBEAR_SIGNKEY_ECDSA_KEYGEN:
		case DROPBEAR_SIGNKEY_ECDSA_NISTP521:
		case DROPBEAR_SIGNKEY_ECDSA_NISTP384:
		case DROPBEAR_SIGNKEY_ECDSA_NISTP256:
			{
				ecc_key *ecckey = gen_ecdsa_priv_key(bits);
				keytype = ecdsa_signkey_type(ecckey);
				*signkey_key_ptr(key, keytype) = ecckey;
			}
			break;
#endif
		default:
			dropbear_exit("Internal error");
	}

	seedrandom();

	buf = buf_new(MAX_PRIVKEY_SIZE); 

	buf_put_priv_key(buf, key, keytype);
	sign_key_free(key);
	key = NULL;
	buf_setpos(buf, 0);
	ret = buf_writefile(buf, filename);

	buf_burn(buf);
	buf_free(buf);
	buf = NULL;
	return ret;
}
