#if !defined(lint) && !defined(__INSIGHT__)
static char sos__rcsid[] = "alice_bob.c,v 1.1.1.1 1995/06/16 17:42:40 seth Exp";
static char sos__copyright[] = "Copyright (c) 1994, 1995 SOS Corporation";
static char sos__contact[] = "SOS Corporation <sos-info@soscorp.com> +1 800 SOS UNIX";
#endif /* not lint */

/*
 * ++Copyright Released Product++
 *
 * Copyright (c) 1994, 1995 Sources of Supply Corporation ("SOS").
 * All rights reserved.
 *
 * The SOS Released Product License Agreement specifies the terms and
 * conditions for redistribution.  You may find the License Agreement
 * in the file LICENSE.
 *
 * SOS Corporation
 * 461 5th Ave.; 16th floor
 * New York, NY 10017
 *
 * +1 800 SOS UNIX
 * <sos-info@soscorp.com>
 *
 * --Copyright Released Product--
 */

#include "sos.h"
#include "md5.h"


/* 
 * Randomly determine an identity. Quite useful when you want to use a
 * cryptographic protocols which are not inherently symetric, but which would
 * you would like to make so.  Most protocols have two peers, so this 
 * routine simply generates a random number, sends it, reads the peer's,
 * compares the two, and assigns an identity according to the ordering of the
 * numbers. Now obviously the peer can cheat the routine with ease, but 
 * the assumption is that you know what your doing and cheating (ie allowing
 * you peer to choose ALICE or BOB) will not by her/him anything.
 *
 * input: readpeer, writepeer: file descriptors open on peer connection
 * 	  rfun, wfun: read and write functions to use on connection.
 *
 * output: SOS_IDENT_ALICE, SOS_IDENT_BOB, or -1
 */
 

int
sos_alice_bob(int readpeer,
	      int (*rfun) (int, caddr_t,  __SIZE_TYPE__ ),
	      int writepeer,
	      int (*wfun) (int, caddr_t, __SIZE_TYPE__ ) )
{
  long  localidentrand;		/* Random number used for identity  */
  long  peeridentrand;		/* Random number used for identity  */

    /* Exchange numbers until the numbers are different */
  do
    {
      sos_get_rand((unsigned char *)&localidentrand, sizeof(localidentrand));
      
      if ( sos_xdr_wencode (writepeer, wfun, "l",  localidentrand) <=0 )
	{
	  return -1;
	}
      
      if ( sos_xdr_wdecode (readpeer, rfun, "l", &peeridentrand) != 1 )
	{
	  return -1;
	}
    } while (localidentrand == peeridentrand );

  /* Determine Alice/Bob Roles */
  if ( localidentrand < peeridentrand )
    return SOS_IDENT_ALICE;
  else 
    return SOS_IDENT_BOB;


}
