Exemplo n.º 1
0
/// Update packet data from the frame
FSTATIC void
_seqnoframe_updatedata(Frame* fself,		///< object whose data will be put into FrameSet packet
                       gpointer tlvptr,		///< pointer to our current TLV entry
                       gconstpointer pktend,	///< end of packet
                       FrameSet* fs)		///< FrameSet that we're doing this for
{
    SeqnoFrame* self = CASTTOCLASS(SeqnoFrame, fself);
    // NOTE - this gets rid of the "const" coming out of get_generic_tlv_value...
    ///@todo add a new get_generic_nonconst_tlv_value() function.
    guint8* pktpos = get_generic_tlv_nonconst_value(tlvptr, pktend);
    (void)fs;
    g_return_if_fail(NULL != pktpos);

    tlv_set_guint32(pktpos,                                self->_sessionid, pktend);
    tlv_set_guint64(pktpos+sizeof(guint32),                self->_reqid, pktend);
    tlv_set_guint16(pktpos+sizeof(guint32)+sizeof(guint64),self->_qid, pktend);
}
Exemplo n.º 2
0
///
/// We update the data in the packet from our CryptCurve25519 object with the
/// side-effect of encrypting all the frames already put into the packet.  Note that
/// this only works because we always construct the packet from the end back to the
/// beginning.  We do this in-place - fortunately the algorithms allow that...
/// We effectively suck all the remaining frames into a single encrypted frame...
FSTATIC void	
_cryptcurve25519_updatedata(Frame* f,			///< Frame to marshall
			    gpointer tlvstart,		///< Start of our Frame in the packet
			    gconstpointer pktend,	///< Last byte in the allocated packet
			    FrameSet* unused_fs)	///< Pointer to our containing frameset
{
	CryptCurve25519*self		= CASTTOCLASS(CryptCurve25519, f);
	const guint8*	pktend8		= pktend;
	//guint8*	tlvstart8	= tlvstart;
	guint8*		tlvval;
	guint8*		valptr;
	guint32		plaintextoffset;
	guint32		plaintextsize;
	guint32		cyphertextoffset;
	guint32		nonceoffset;
	guint32		tlvsize;
	unsigned char*	nonce;
	int		j;

	(void)unused_fs;
	
	// [key1, key2, nonce, MAC, plaintext]

	DUMP3(__FUNCTION__, &f->baseclass, " is CryptCurve25519 Frame being processed.");
	DEBUGMSG3("%s.%d: tlvstart:%p, pktend:%p", __FUNCTION__, __LINE__, tlvstart, pktend);
	// The plain text starts immediately after our (incoming) frame
	plaintextoffset = f->length;					// Plain text starts here
	cyphertextoffset = plaintextoffset - crypto_box_MACBYTES;	// Preceded by MAC
	nonceoffset = cyphertextoffset - crypto_box_NONCEBYTES;		// Preceded by nonce
	// Our (outgoing) frame consists of the original incoming frame plus all other frames after ours
	tlvval = get_generic_tlv_nonconst_value(tlvstart, pktend);
	tlvsize = pktend8 - tlvval;
	plaintextsize = (tlvsize - plaintextoffset);

	// Generate a "nonce" as part of the packet - make known plaintext attacks harder
	// ... lots of our plaintext is easy to figure out ...
	nonce = tlvval + nonceoffset;
	DEBUGMSG3("%s.%d: generating random nonce (%p, %d, %p)", __FUNCTION__, __LINE__
	,	nonce, (int)crypto_box_NONCEBYTES, nonce+crypto_box_NONCEBYTES);
	randombytes_buf(nonce, crypto_box_NONCEBYTES);
	DEBUGMSG3("%s.%d: random nonce generated.", __FUNCTION__, __LINE__);

	DEBUGMSG3("%s.%d: public->key_id: [%s], private_key->key_id: [%s]", __FUNCTION__, __LINE__
	,	self->public_key->key_id, self->private_key->key_id);
	DEBUGMSG3("%s.%d: calling crypto_box_easy(%p,%p,%d,%p,%p,%p)", __FUNCTION__, __LINE__
	,	tlvval+cyphertextoffset, tlvval+plaintextoffset, plaintextsize
	,	nonce, self->public_key->public_key, self->private_key->private_key);
	DEBUGCKSUM4("plain text cksum:", tlvval+plaintextoffset, plaintextsize);
	DEBUGCKSUM4("receiver public key cksum:",self->public_key -> public_key, crypto_box_PUBLICKEYBYTES);
	DEBUGCKSUM4("sender  private key cksum:", self->private_key->private_key, crypto_box_SECRETKEYBYTES);
	DEBUGCKSUM4("nonce cksum:", nonce, crypto_box_NONCEBYTES);
	// Encrypt in-place [we previously allocated enough space for authentication info]
	crypto_box_easy(tlvval+cyphertextoffset, tlvval+plaintextoffset, plaintextsize
	,	nonce, self->public_key->public_key, self->private_key->private_key);
	DEBUGMSG4("cypher offset versus tlvstart: %ld", (long)(tlvval+cyphertextoffset-(guint8*)tlvstart));
	DEBUGCKSUM4("cypher text checksum:", tlvval+cyphertextoffset, plaintextsize+crypto_box_MACBYTES);
	set_generic_tlv_type(tlvstart, self->baseclass.baseclass.type, pktend);
	set_generic_tlv_len(tlvstart, tlvsize, pktend);
	// Put in the frame type, length, key name length, and key name for both keys
	// We're the sender - our [private] key name goes first, then the receiver's [public] key name
	valptr = get_generic_tlv_nonconst_value(tlvstart, pktend);
	for (j=0; j < 2; ++j) {
		char *	key_id = (j == 0 ? self->baseclass.sender_key_id : self->baseclass.receiver_key_id);
		int	keylen = strlen(key_id)+1;
		tlv_set_guint8(valptr, keylen, pktend);
		valptr += 1;
		g_strlcpy((char *)valptr, key_id, keylen);
		valptr += keylen;
	}
	DEBUGMSG3("%s.%d: returning after next assert (tlvval:%p, tlvsize%d, pktend:%p"
	,	__FUNCTION__, __LINE__, tlvval, (int)tlvsize, pktend);
	g_assert((tlvval + tlvsize) == pktend);
	DEBUGMSG3("%s.%d: returning (assert passed).", __FUNCTION__, __LINE__);
}
Exemplo n.º 3
0
/// Given marshalled packet data corresponding to an CryptCurve25519 frame
/// return the corresponding Frame
/// In other words, un-marshall the data...
/// In our case, this means we decrypt it in-place into many other frames...
WINEXPORT Frame*
cryptcurve25519_tlvconstructor(gpointer tlvstart,	///<[in/out] Start of marshalled CStringFrame data
			  gconstpointer pktend,		///<[in] Pointer to first invalid byte past 'tlvstart'
		          gpointer* ignorednewpkt,	///<[ignored] replacement packet
		          gpointer* ignoredpktend)	///<[ignored] end of replacement packet
{
	guint8*			valptr = get_generic_tlv_nonconst_value(tlvstart, pktend);
	guint8*			nonce;
	guint8*			cyphertext;
	const guint8*		tlvend8 = valptr + get_generic_tlv_len(tlvstart, pktend);
	guint8*			plaintext;
	CryptCurve25519*	ret;
	guint			namelen;
	gsize			cypherlength;
				// The first key name is in sender's key name
				// The second key name is in receiver's key name
	CryptFramePublicKey *	sender_public_key = NULL;
	CryptFramePrivateKey*	receiver_secret_key = NULL;
	const char*		sender_pubkey_id = NULL;
	const char*		rcvr_seckey_id = NULL;
	int			j;

	(void)ignorednewpkt; (void)ignoredpktend;
	valptr = get_generic_tlv_nonconst_value(tlvstart, pktend);
	for (j=0; j < 2; ++j) {
		char *	key_id;
		g_return_val_if_fail((gpointer)(valptr+2) <= pktend, NULL);
		namelen = tlv_get_guint8(valptr, pktend);
		valptr += 1;
		g_return_val_if_fail((gpointer)(valptr+namelen) <= pktend, NULL);
		key_id = (char *)valptr;
		g_return_val_if_fail (strnlen(key_id, namelen) == namelen -1, NULL);
		g_return_val_if_fail(_is_valid_curve25519_key_id(key_id
		, 	0 == j ? PUBLICKEY : PRIVATEKEY), NULL);
		if (0 == j) {
			sender_public_key = cryptframe_public_key_by_id(key_id);
			sender_pubkey_id = key_id;
		}else{
			receiver_secret_key = cryptframe_private_key_by_id(key_id);
			rcvr_seckey_id = key_id;
		}
		g_return_val_if_fail(key_id != NULL, NULL);
		valptr += namelen;
	}
	if (NULL == sender_public_key) {
		g_warning("%s.%d: No access to sender %s public key"
		,	__FUNCTION__, __LINE__, sender_pubkey_id);
		return NULL;
	}
	if (NULL == receiver_secret_key) {
		g_warning("%s.%d: No access to receiver %s private key"
		,	__FUNCTION__, __LINE__, rcvr_seckey_id);
		return NULL;
	}
	g_return_val_if_fail((gpointer)(valptr + (crypto_box_NONCEBYTES+crypto_box_MACBYTES)) <= pktend, NULL);
	nonce = valptr;
	cyphertext = nonce + crypto_box_NONCEBYTES;
	plaintext = cyphertext + crypto_box_MACBYTES;
	cypherlength = tlvend8 - cyphertext;
	DEBUGCKSUM4("nonce:", nonce, crypto_box_NONCEBYTES);
	DEBUGCKSUM4("sender   public key :", sender_public_key -> public_key,  crypto_box_PUBLICKEYBYTES);
	DEBUGCKSUM4("receiver private key:", receiver_secret_key->private_key, crypto_box_SECRETKEYBYTES);
	DEBUGMSG4("cypher offset versus tlvstart: %ld", (long)(cyphertext-(guint8*)tlvstart));
	DEBUGCKSUM4("cypher text:", cyphertext, cypherlength);
	if (crypto_box_open_easy(plaintext, cyphertext, cypherlength, nonce
	,	sender_public_key->public_key, receiver_secret_key->private_key) != 0) {
		g_warning("%s.%d: could not decrypt %d byte message encrypted with key pair [pub:%s, sec:%s]"
		,	__FUNCTION__, __LINE__, (int)cypherlength, sender_pubkey_id, rcvr_seckey_id);
		return NULL;
	}
	DEBUGCKSUM4("plain text:", plaintext, cypherlength-crypto_box_MACBYTES);
	// Note that our return value's size will determine where the beginning of the
	// decrypted data is (according to it's dataspace() member function)
	ret = cryptcurve25519_new(get_generic_tlv_type(tlvstart, pktend)
	,	(const char *)sender_pubkey_id
	,	rcvr_seckey_id, FALSE, 0);
	return (ret ? &(ret->baseclass.baseclass) : NULL);
}