Beispiel #1
0
struct rx_securityClass *
get_sc(char *cellname)
{
#if 0
    char realm[REALM_SZ];
    CREDENTIALS c;
#endif

    return rxnull_NewClientSecurityObject();
#if 0

    ucstring(realm, cellname, REALM_SZ);

    if (krb_get_cred("afs", "", realm, &c)) {
	if (get_ad_tkt("afs", "", realm, DEFAULT_TKT_LIFE)) {
	    return NULL;
	} else {
	    if (krb_get_cred("afs", "", realm, &c)) {
		return NULL;
	    }
	}
    }

    return rxkad_NewClientSecurityObject(rxkad_clear, c.session, c.kvno,
					 c.ticket_st.length, c.ticket_st.dat);
#endif
}
Beispiel #2
0
int
krb_mk_req(KTEXT authent,
	   char *service, char *instance, char *realm, 
	   int32_t checksum)

#endif
{
    CREDENTIALS cr;
    KTEXT_ST req;
    krb5_storage *sp;
    int code;
    /* XXX get user realm */
    const char *myrealm = realm;
    krb5_data a;

    code = krb_get_cred(service, instance, realm, &cr);
    if(code || time(NULL) > krb_life_to_time(cr.issue_date, cr.lifetime)){
	code = get_ad_tkt((char *)service,
			  (char *)instance, (char *)realm, lifetime);
	if(code == KSUCCESS)
	    code = krb_get_cred(service, instance, realm, &cr);
    }

    if(code)
	return code;

    sp = krb5_storage_emem();

    krb5_store_int8(sp, KRB_PROT_VERSION);
    krb5_store_int8(sp, AUTH_MSG_APPL_REQUEST);
    
    krb5_store_int8(sp, cr.kvno);
    krb5_store_stringz(sp, realm);
    krb5_store_int8(sp, cr.ticket_st.length);

    build_request(&req, cr.pname, cr.pinst, myrealm, checksum);
    encrypt_ktext(&req, &cr.session, DES_ENCRYPT);

    krb5_store_int8(sp, req.length);

    krb5_storage_write(sp, cr.ticket_st.dat, cr.ticket_st.length);
    krb5_storage_write(sp, req.dat, req.length);
    krb5_storage_to_data(sp, &a);
    krb5_storage_free(sp);
    memcpy(authent->dat, a.data, a.length);
    authent->length = a.length;
    krb5_data_free(&a);

    memset(&cr, 0, sizeof(cr));
    memset(&req, 0, sizeof(req));

    return KSUCCESS;
}
Beispiel #3
0
static int get_cred(char *name, char *inst, char *realm, CREDENTIALS *c)
{
  int status;

  status = krb_get_cred(name, inst, realm, c);
  if (status != KSUCCESS)
    {
      status = get_ad_tkt(name, inst, realm, 255);
      if (status == KSUCCESS)
	status = krb_get_cred(name, inst, realm, c);
    }

  return (status);
}
Beispiel #4
0
int
kerberos4_forward(Authenticator *ap)
{
    CREDENTIALS cred;
    char *realm;
    des_key_schedule ks;
    int len;
    unsigned char netcred[sizeof(CREDENTIALS)];
    int ret;

    realm = krb_realmofhost(RemoteHostName);
    if(realm == NULL)
	return -1;
    memset(&cred, 0, sizeof(cred));
    ret = krb_get_cred(KRB_TICKET_GRANTING_TICKET,
		       realm,
		       realm, 
		       &cred);
    if(ret)
	return ret;
    des_set_key(&session_key, ks);
    len = pack_cred(&cred, netcred);
    des_pcbc_encrypt((void*)netcred, (void*)netcred, len,
		     ks, &session_key, DES_ENCRYPT);
    memset(ks, 0, sizeof(ks));
    Data(ap, KRB_FORWARD, netcred, len);
    memset(netcred, 0, sizeof(netcred));
    return 0;
}
Beispiel #5
0
static int
kvno4(krb5_context ctx, const char *host, krb5_principal sprinc)
{
	krb5_error_code	kerr;
	KTEXT_ST	req;
	CREDENTIALS	creds;
	int		err = 0;
	char		name[ANAME_SZ];
	char		instance[INST_SZ];
	char		realm[REALM_SZ];

	VERBOSE(1, (stderr, "initiating kvno4/udp ping to %s\n", host));

	kerr = krb5_524_conv_principal(ctx, sprinc, name, instance, realm);
	if (kerr) {
		fail_msg("kvno4", SOCK_DGRAM, host, error_message(kerr));
		goto bail;
	}

	err = krb_mk_req(&req, name, instance, realm, 0);
	if (err)
		goto bail;

        err = krb_get_cred(name, instance, realm, &creds);
        if (err)
		goto bail;

	VERBOSE(2, (stderr, "%s.%s@%s kvno = %d\n", name, instance, realm,
	    creds.kvno));

bail:
	if (err)
		fail_msg("kvno4", SOCK_DGRAM, host, krb_get_err_text(err));
	return err;
}
Beispiel #6
0
static int
get_cred(struct kafs_data *data, const char *name, const char *inst, 
	 const char *realm, uid_t uid, struct kafs_token *kt)
{
    CREDENTIALS c;
    KTEXT_ST tkt;
    int ret = krb_get_cred((char*)name, (char*)inst, (char*)realm, &c);
    
    if (ret) {
	ret = krb_mk_req(&tkt, (char*)name, (char*)inst, (char*)realm, 0);
	if (ret == KSUCCESS)
	    ret = krb_get_cred((char*)name, (char*)inst, (char*)realm, &c);
    }
    if (ret == 0)
	ret = _kafs_v4_to_kt(&c, uid, kt);
    return ret;
}
Beispiel #7
0
static int get_cred(char *name, char *inst, char *realm, CREDENTIALS *c)
{
    int status;

    status = krb_get_cred(name, inst, realm, c);
    if (status != KSUCCESS)
    {
#ifdef DONT_HAVE_GET_AD_TKT
        KTEXT_ST ticket;
        status = krb_mk_req(&ticket, name, inst, realm, 0);
#else
        status = get_ad_tkt(name, inst, realm, 255);
#endif
        if (status == KSUCCESS)
            status = krb_get_cred(name, inst, realm, c);
    }       

    return (status);
}
Beispiel #8
0
/*
 * 
 * K4_auth_send - gets authentication bits we need to send to KDC.
 * 
 * Result is left in auth
 *
 * Returns: 0 on failure, 1 on success
 */
static int
k4_auth_send(kstream ks)
{
  int r;                                      /* Return value */
  char instance[INST_SZ];
  char *realm;
  char buf[256];

  memset(instance, 0, sizeof(instance));

  if (realm = krb_get_phost(szHostName))
    lstrcpy(instance, realm);

  realm = krb_realmofhost(szHostName);

  if (!realm) {
    strcpy(buf, "Can't find realm for host \"");
    strncat(buf, szHostName, sizeof(buf) - 1 - strlen(buf));
    strncat(buf, "\"", sizeof(buf) - 1 - strlen(buf));
    auth_abort(ks, buf, 0);
    return KFAILURE;
  }

  r = krb_mk_req(&auth, KRB_SERVICE_NAME, instance, realm, 0);

  if (r == 0)
    r = krb_get_cred(KRB_SERVICE_NAME, instance, realm, &cred);

  if (r) {
    strcpy(buf, "Can't get \"");
    strncat(buf, KRB_SERVICE_NAME, sizeof(buf) - 1 - strlen(buf));
    if (instance[0] != 0) {
      strncat(buf, ".", sizeof(buf) - 1 - strlen(buf));
      lstrcat(buf, instance);
    }
    strncat(buf, "@", sizeof(buf) - 1 - strlen(buf));
    lstrcat(buf, realm);
    strncat(buf, "\" ticket", sizeof(buf) - 1 - strlen(buf));
    auth_abort(ks, buf, r);

    return r;
  }

  if (!szUserName[0])			/* Copy if not there */
    strcpy(szUserName, cred.pname);

  return(1);
}
Beispiel #9
0
/*
 * Function: Save the credentials for later restoration.
 *
 * Parameters:
 *	c - Returned pointer to saved credential cache.
 *
 *	pname - Returned as principal name of session.
 *
 *	pinstance - Returned as principal instance of session.
 *
 *	ncred - Returned number of credentials saved.
 */
static void
push_credentials(CREDENTIALS **cp, char *pname, char *pinstance, int *ncred)
{
#ifdef KRB4
  int i;
  char service[ANAME_SZ];
  char instance[INST_SZ];
  char realm[REALM_SZ];
  CREDENTIALS *c;

  if (krb_get_tf_fullname(NULL, pname, pinstance, NULL) != KSUCCESS) {
    pname[0] = 0;

    pinstance[0] = 0;
  }

  *ncred = krb_get_num_cred();
  if (*ncred <= 0)
    return;

  c= malloc(*ncred * sizeof(CREDENTIALS));
  assert(c != NULL);
  if (c == NULL) {
    *ncred = 0;

    return;
  }

  for (i = 0; i < *ncred; i++) {
    krb_get_nth_cred(service, instance, realm, i + 1);
    krb_get_cred(service, instance, realm, &c[i]);
  }

  *cp = c;
#endif

#ifdef KRB5     /* FIXME */
  return;
#endif
}
Beispiel #10
0
static int
mk_auth(struct krb4_data *d, KTEXT adat, 
	char *service, char *host, int checksum)
{
    int ret;
    CREDENTIALS cred;
    char sname[SNAME_SZ], inst[INST_SZ], realm[REALM_SZ];

    strlcpy(sname, service, sizeof(sname));
    strlcpy(inst, krb_get_phost(host), sizeof(inst));
    strlcpy(realm, krb_realmofhost(host), sizeof(realm));
    ret = krb_mk_req(adat, sname, inst, realm, checksum);
    if(ret)
	return ret;
    strlcpy(sname, service, sizeof(sname));
    strlcpy(inst, krb_get_phost(host), sizeof(inst));
    strlcpy(realm, krb_realmofhost(host), sizeof(realm));
    ret = krb_get_cred(sname, inst, realm, &cred);
    memmove(&d->key, &cred.session, sizeof(des_cblock));
    des_key_sched(&d->key, d->schedule);
    memset(&cred, 0, sizeof(cred));
    return ret;
}
Beispiel #11
0
int krb_sendauth_udp(long options, int fd, KTEXT_FP ticket,
	const LPSTR service, const LPSTR inst, LPSTR realm, LONG checksum,
	MSG_DAT *msg_data, CREDENTIALS *cred, Key_schedule *schedule,
	struct sockaddr_in *laddr, struct sockaddr_in *faddr, LPSTR version,
	LPSTR buffer, int sz)
{
	int rem, i, cc;
	char srv_inst[INST_SZ];
	char krb_realm[REALM_SZ];
	char buf[BUFSIZ];
	long tkt_len;
	u_char priv_buf[1024];
	u_long cksum;
	
	rem = KSUCCESS;
	
	/* get current realm if not passed in */
	if (!realm) {
		rem = krb_get_lrealm(krb_realm,1);
		if (rem != KSUCCESS)
			return (rem);
		realm = krb_realm;
	}
	
	/* Copy instance into local storage, canonicalizing if desired */
	if (options & KOPT_DONT_CANON)
		(void) strncpy(srv_inst, inst, INST_SZ);
	else
		(void) strncpy((LPSTR)srv_inst, (LPSTR)krb_get_phost(inst), INST_SZ);
		
	/* Get the ticket if desired */
	if (!(options & KOPT_DONT_MK_REQ)) {
		rem = krb_mk_req(ticket, service, srv_inst, realm, checksum);
		if (rem != KSUCCESS)
			return (rem);
	}
	
#ifdef ATHENA_COMPAT
	/* this is only for compatibility with old servers */
	if (options & KOPT_DO_OLDSTYLE) {
		(void) sprintf(buf, "%d ", ticket->length);
		(void) write(fd, buf, strlen(buf));
		(void) write(fd, (char *) ticket->dat, ticket->length);
		return (rem);
	}
#endif /* ATHENA_COMPAT */
	/* if the mutual auth, get credentials so we have service session
	 * keys for decryption below
	 */
	if (options & KOPT_DO_MUTUAL)
	{
		/*if (cc == 1)
		 *{
		 *      krb_get_cred(service, srv_inst, realm, cred);
		 *      return (cc);
		 *}
		 */
		krb_get_cred(service, srv_inst, realm, cred);
	}
			
	/* Zero the buffer */
	(void) bzero(buf, BUFSIZ);
	
	/* insert version strings */
	(void) strncpy(buf, KRB_SENDAUTH_VERS, KRB_SENDAUTH_VLEN);
	
	/* increment past version strings */
	i = 2*KRB_SENDAUTH_VLEN;
	
	/* put ticket length into buffer */
	tkt_len = htonl((unsigned long) ticket->length);
	(void) bcopy((char *) &tkt_len, buf+i, ticket->length);
	i += ticket->length;
	
	/* Normally, we write the request to the server
	** For udp, esp. TechNotify type protocols, we
	** just return the buffer.  
	*/
	if (sz < i)
		return HEY_PAUL_WHAT_ERROR;     /* Buffer not big enough */
	bcopy(buf, buffer, i);
	return (KSUCCESS);
}
Beispiel #12
0
static int
try_krb4_authentication(void)
{
	KTEXT_ST auth;		/* Kerberos data */
	char *reply;
	char inst[INST_SZ];
	char *realm;
	CREDENTIALS cred;
	int r, type;
	socklen_t slen;
	Key_schedule schedule;
	u_long checksum, cksum;
	MSG_DAT msg_data;
	struct sockaddr_in local, foreign;
	struct stat st;

	/* Don't do anything if we don't have any tickets. */
	if (stat(tkt_string(), &st) < 0)
		return 0;

	strlcpy(inst, (char *)krb_get_phost(get_canonical_hostname(1)),
	    INST_SZ);

	realm = (char *)krb_realmofhost(get_canonical_hostname(1));
	if (!realm) {
		debug("Kerberos v4: no realm for %s", get_canonical_hostname(1));
		return 0;
	}
	/* This can really be anything. */
	checksum = (u_long)getpid();

	r = krb_mk_req(&auth, KRB4_SERVICE_NAME, inst, realm, checksum);
	if (r != KSUCCESS) {
		debug("Kerberos v4 krb_mk_req failed: %s", krb_err_txt[r]);
		return 0;
	}
	/* Get session key to decrypt the server's reply with. */
	r = krb_get_cred(KRB4_SERVICE_NAME, inst, realm, &cred);
	if (r != KSUCCESS) {
		debug("get_cred failed: %s", krb_err_txt[r]);
		return 0;
	}
	des_key_sched((des_cblock *) cred.session, schedule);

	/* Send authentication info to server. */
	packet_start(SSH_CMSG_AUTH_KERBEROS);
	packet_put_string((char *) auth.dat, auth.length);
	packet_send();
	packet_write_wait();

	/* Zero the buffer. */
	(void) memset(auth.dat, 0, MAX_KTXT_LEN);

	slen = sizeof(local);
	memset(&local, 0, sizeof(local));
	if (getsockname(packet_get_connection_in(),
	    (struct sockaddr *)&local, &slen) < 0)
		debug("getsockname failed: %s", strerror(errno));

	slen = sizeof(foreign);
	memset(&foreign, 0, sizeof(foreign));
	if (getpeername(packet_get_connection_in(),
	    (struct sockaddr *)&foreign, &slen) < 0) {
		debug("getpeername failed: %s", strerror(errno));
		cleanup_exit(255);
	}
	/* Get server reply. */
	type = packet_read();
	switch (type) {
	case SSH_SMSG_FAILURE:
		/* Should really be SSH_SMSG_AUTH_KERBEROS_FAILURE */
		debug("Kerberos v4 authentication failed.");
		return 0;
		break;

	case SSH_SMSG_AUTH_KERBEROS_RESPONSE:
		/* SSH_SMSG_AUTH_KERBEROS_SUCCESS */
		debug("Kerberos v4 authentication accepted.");

		/* Get server's response. */
		reply = packet_get_string((u_int *) &auth.length);
		if (auth.length >= MAX_KTXT_LEN)
			fatal("Kerberos v4: Malformed response from server");
		memcpy(auth.dat, reply, auth.length);
		free(reply);

		packet_check_eom();

		/*
		 * If his response isn't properly encrypted with the session
		 * key, and the decrypted checksum fails to match, he's
		 * bogus. Bail out.
		 */
		r = krb_rd_priv(auth.dat, auth.length, (void *)schedule,
		    &cred.session, &foreign, &local, &msg_data);
		if (r != KSUCCESS) {
			debug("Kerberos v4 krb_rd_priv failed: %s",
			    krb_err_txt[r]);
			packet_disconnect("Kerberos v4 challenge failed!");
		}
		/* Fetch the (incremented) checksum that we supplied in the request. */
		memcpy((char *)&cksum, (char *)msg_data.app_data,
		    sizeof(cksum));
		cksum = ntohl(cksum);

		/* If it matches, we're golden. */
		if (cksum == checksum + 1) {
			debug("Kerberos v4 challenge successful.");
			return 1;
		} else
			packet_disconnect("Kerberos v4 challenge failed!");
		break;

	default:
		packet_disconnect("Protocol error on Kerberos v4 response: %d", type);
	}
	return 0;
}
Beispiel #13
0
/*
 * Function: Process WM_TIMER messages
 */
static void
kwin_timer(HWND hwnd, UINT timer_id)
{
  HWND hwndfocus;
  time_t t;
  time_t expiration;
  BOOL expired;
#ifdef KRB4
  CREDENTIALS c;
  int ncred;
  int i;
  char service[ANAME_SZ];
  char instance[INST_SZ];
  char realm[REALM_SZ];
#endif
#ifdef KRB5
  krb5_error_code code;
  krb5_cc_cursor cursor;
  krb5_creds cred;
  int n;
  char *s;
#endif

  if (timer_id != 1) {
    FORWARD_WM_TIMER(hwnd, timer_id, DefDlgProc);
    return;
  }

  expired = FALSE;
  ticket_init_list(GetDlgItem(hwnd, IDD_TICKET_LIST));

  if (alerted) {
    if (IsIconic(hwnd))
      InvalidateRect(hwnd, NULL, TRUE);

    return;
  }

#ifdef KRB4
  ncred = krb_get_num_cred();
  for (i = 1; i <= ncred; i++) {
    krb_get_nth_cred(service, instance, realm, i);

    if (_stricmp(service, "krbtgt") == 0) {
      /* Warn if ticket will expire w/i TIME_BUFFER seconds */
      krb_get_cred(service, instance, realm, &c);
      expiration = c.issue_date + (long)c.lifetime * 5L * 60L;
      t = TIME_BUFFER + time(NULL);

      if (t >= expiration) {
	expired = TRUE;
	/* Don't alert because of stale tickets */
	if (t >= expiration + KWIN_UPDATE_PERIOD / 1000) {
	  alerted = TRUE;

	  if (IsIconic(hwnd))
	    InvalidateRect(hwnd, NULL, TRUE);
	  return;
	}
	break;
      }
    }
  }
#endif

#ifdef KRB5
  code = krb5_cc_start_seq_get(k5_context, k5_ccache, &cursor);

  while (code == 0) {
    code = krb5_cc_next_cred(k5_context, k5_ccache, &cursor, &cred);
    if (code)
      break;
    n = krb5_princ_component(k5_context, cred.server, 0)->length;
    s = krb5_princ_component(k5_context, cred.server, 0)->data;
    if (n != KRB5_TGS_NAME_SIZE)
      continue;
    if (memcmp(KRB5_TGS_NAME, s, KRB5_TGS_NAME_SIZE))
      continue;

    /* Warn if ticket will expire w/i TIME_BUFFER seconds */
    expiration = cred.times.endtime;
    t = TIME_BUFFER + time(NULL);

    if (t >= expiration) {
      expired = TRUE;
      /* Don't alert because of stale tickets */
      if (t >= expiration + KWIN_UPDATE_PERIOD / 1000) {
	alerted = TRUE;

	if (IsIconic(hwnd))
	  InvalidateRect(hwnd, NULL, TRUE);
	return;
      }
      break;
    }
  }
  if (code == 0 || code == KRB5_CC_END)
    krb5_cc_end_seq_get(k5_context, k5_ccache, &cursor);

#endif

  if (!expired) {
    if (IsIconic(hwnd))
      InvalidateRect(hwnd, NULL, TRUE);

    return;
  }

  alerted = TRUE;

  if (beep)
    MessageBeep(MB_ICONEXCLAMATION);

  if (alert) {
    if (IsIconic(hwnd)) {
      hwndfocus = GetFocus();
      ShowWindow(hwnd, SW_RESTORE);
      SetWindowPos(hwnd, HWND_TOP, 0, 0, 0, 0,
		   SWP_NOACTIVATE | SWP_SHOWWINDOW | SWP_NOMOVE | SWP_NOSIZE);
      SetFocus(hwndfocus);
    }

    SetWindowPos(hwnd, HWND_TOP, 0, 0, 0, 0,
		 SWP_NOACTIVATE | SWP_SHOWWINDOW | SWP_NOMOVE | SWP_NOSIZE);

    return;
  }

  if (IsIconic(hwnd))
    InvalidateRect(hwnd, NULL, TRUE);
}
Beispiel #14
0
/*
 * Function: Process WM_PAINT messages by displaying an
 *	informative icon when we are iconic.
 */
static void
kwin_paint(HWND hwnd)
{
  HDC hdc;
  PAINTSTRUCT ps;
  HICON hicon;
  time_t expiration = 0;
  time_t dt;
  char buf[20];
  RECT r;
#ifdef KRB4
  int i;
  int ncred;
  char service[ANAME_SZ];
  char instance[INST_SZ];
  char realm[REALM_SZ];
  CREDENTIALS c;
#endif
#ifdef KRB5
  krb5_error_code code;
  krb5_cc_cursor cursor;
  krb5_creds c;
  int n;
  char *service;
#endif

  if (!IsIconic(hwnd)) {
    FORWARD_WM_PAINT(hwnd, DefDlgProc);
    return;
  }

#ifdef KRB4
  ncred = krb_get_num_cred();

  for (i = 1; i <= ncred; i++) {
    krb_get_nth_cred(service, instance, realm, i);
    krb_get_cred(service, instance, realm, &c);
    if (_stricmp(c.service, "krbtgt") == 0) {
      expiration = c.issue_date - kwin_get_epoch()
	+ (long)c.lifetime * 5L * 60L;
      break;
    }
  }
#endif

#ifdef KRB5
  code = krb5_cc_start_seq_get(k5_context, k5_ccache, &cursor);

  while (code == 0) {
    code = krb5_cc_next_cred(k5_context, k5_ccache, &cursor, &c);
    if (code)
      break;
    n = krb5_princ_component(k5_context, c.server, 0)->length;
    service = krb5_princ_component(k5_context, c.server, 0)->data;
    if (n != KRB5_TGS_NAME_SIZE)
      continue;
    if (memcmp(KRB5_TGS_NAME, service, KRB5_TGS_NAME_SIZE))
      continue;
    expiration = c.times.endtime;
    break;

  }
  if (code == 0 || code == KRB5_CC_END)
    krb5_cc_end_seq_get(k5_context, k5_ccache, &cursor);
#endif

  hdc = BeginPaint(hwnd, &ps);
  GetClientRect(hwnd, &r);
  DefWindowProc(hwnd, WM_ICONERASEBKGND, (WPARAM)hdc, 0);

  if (expiration == 0) {
    strcpy(buf, KWIN_DIALOG_NAME);
    hicon = LoadIcon(hinstance, MAKEINTRESOURCE(IDI_KWIN));
  }
  else {
    hicon = kwin_get_icon(expiration);
    dt = (expiration - time(NULL)) / 60;

    if (dt <= 0)
      sprintf(buf, "%s - %s", KWIN_DIALOG_NAME, "Expired");
    else if (dt < 60) {
      dt %= 60;
      sprintf(buf, "%s - %ld min", KWIN_DIALOG_NAME, dt);
    }
    else {
      dt /= 60;
      sprintf(buf, "%s - %ld hr", KWIN_DIALOG_NAME, dt);
    }

    buf[sizeof(buf) - 1] = '\0';
    if (dt > 1)
      strncat(buf, "s", sizeof(buf) - 1 - strlen(buf));
  }

  DrawIcon(hdc, r.left, r.top, hicon);
  EndPaint(hwnd, &ps);
  SetWindowText(hwnd, buf);
}
Beispiel #15
0
int
krb_mk_req(KTEXT authent, char *service, char *instance, char *realm, 
	   int32_t checksum)
{
    KTEXT_ST req_st;
    KTEXT req_id = &req_st;

    CREDENTIALS cr;             /* Credentials used by retr */
    KTEXT ticket = &(cr.ticket_st); /* Pointer to tkt_st */
    int retval;                 /* Returned by krb_get_cred */

    char myrealm[REALM_SZ];

    unsigned char *p = authent->dat;
    int rem = sizeof(authent->dat);
    int tmp;

    tmp = krb_put_int(KRB_PROT_VERSION, p, rem, 1);
    if (tmp < 0)
	return KFAILURE;
    p += tmp;
    rem -= tmp;

    tmp = krb_put_int(AUTH_MSG_APPL_REQUEST, p, rem, 1);
    if (tmp < 0)
	return KFAILURE;
    p += tmp;
    rem -= tmp;

    /* Get the ticket and move it into the authenticator */
    if (krb_ap_req_debug)
        krb_warning("Realm: %s\n", realm);

    retval = krb_get_cred(service,instance,realm,&cr);

    if (retval == RET_NOTKT) {
	retval = get_ad_tkt(service, instance, realm, lifetime);
	if (retval == KSUCCESS)
	    retval = krb_get_cred(service, instance, realm, &cr);
    }

    if (retval != KSUCCESS)
	return retval;


    /*
     * With multi realm ticket files either find a matching TGT or
     * else use the first TGT for inter-realm authentication.
     *
     * In myrealm hold the realm of the principal "owning" the
     * corresponding ticket-granting-ticket.
     */

    retval = krb_get_cred(KRB_TICKET_GRANTING_TICKET, realm, realm, 0);
    if (retval == KSUCCESS) {
      strcpy_truncate(myrealm, realm, REALM_SZ);
    } else
      retval = krb_get_tf_realm(TKT_FILE, myrealm);
    
    if (retval != KSUCCESS)
	return retval;
    
    if (krb_ap_req_debug)
        krb_warning("serv=%s.%s@%s princ=%s.%s@%s\n", service, instance, realm,
		    cr.pname, cr.pinst, myrealm);

    tmp = krb_put_int(cr.kvno, p, rem, 1);
    if (tmp < 0)
	return KFAILURE;
    p += tmp;
    rem -= tmp;

    tmp = krb_put_string(realm, p, rem);
    if (tmp < 0)
	return KFAILURE;
    p += tmp;
    rem -= tmp;

    tmp = krb_put_int(ticket->length, p, rem, 1);
    if (tmp < 0)
	return KFAILURE;
    p += tmp;
    rem -= tmp;

    retval = build_request(req_id, cr.pname, cr.pinst, myrealm, checksum);
    if (retval != KSUCCESS)
	return retval;
    
    encrypt_ktext(req_id, &cr.session, DES_ENCRYPT);

    tmp = krb_put_int(req_id->length, p, rem, 1);
    if (tmp < 0)
	return KFAILURE;
    p += tmp;
    rem -= tmp;

    if (rem < ticket->length + req_id->length)
	return KFAILURE;

    memcpy(p, ticket->dat, ticket->length);
    p += ticket->length;
    rem -= ticket->length;
    memcpy(p, req_id->dat, req_id->length);
    p += req_id->length;
    rem -= req_id->length;

    authent->length = p - authent->dat;
    
    memset(&cr, 0, sizeof(cr));
    memset(&req_st, 0, sizeof(req_st));

    if (krb_ap_req_debug)
        krb_warning("Authent->length = %d\n", authent->length);

    return KSUCCESS;
}
Beispiel #16
0
int do_GetSecret(char *hostname, const char **identity, int *ilen, 
                 const char **secret, int *slen)
{
    struct ktext *authenticator = NULL;
    struct credentials *cred = NULL;
    char *host = NULL;
    int rc = -1;

    host = krb_canonicalize_host(hostname);
    if (!host) return -1;

    cred = malloc(sizeof(struct credentials));
    if (!cred) {
	fprintf(stderr, "krb4: malloc(credentials) failed\n");
	goto out;
    }

    authenticator = malloc(sizeof(struct ktext));
    if (!authenticator) {
	fprintf(stderr, "krb4: malloc(ktext) failed\n");
	goto out;
    }

    /* construct a new authenticator, or find an old one */
    rc = krb_mk_req(authenticator, kerberos4service, host, kerberos4realm, 0);
    if (rc) {
	fprintf(stderr, "krb4: %s (%d)\n", krb_err_txt[rc], rc);
	rc = 1;
	goto out;
    }

    /* authenticator now contains authenticator */
    /* pull out the shared secret for RPC2 to use in the bind */

    rc = krb_get_cred(kerberos4service, host, kerberos4realm, cred);
    if (rc) {
	fprintf(stderr, "krb4: %s (%d)\n", krb_err_txt[rc], rc);
	rc = 1;
	goto out;
    }

    /* we now have the key in session_key */
    HashSecret(cred->session, 8, *secret);
    *slen = RPC2_KEYSIZE;

    *identity = (char *)authenticator;
    *ilen = sizeof(struct ktext);

    rc = 0;

    authenticator = NULL; /* XXX ok, who is supposed to be freeing the
			     authenticator now? -JH */
out:
    if (host)
	free(host);

    if (authenticator)
	free(authenticator);

    if (cred)
	free(cred);

    return rc;
}
Beispiel #17
0
static int
kerberos4_send(char *name, Authenticator *ap)
{
    KTEXT_ST auth;
    char instance[INST_SZ];
    char *realm;
    CREDENTIALS cred;
    int r;

    printf("[ Trying %s ... ]\r\n", name);
    if (!UserNameRequested) {
	if (auth_debug_mode) {
	    printf("Kerberos V4: no user name supplied\r\n");
	}
	return(0);
    }

    memset(instance, 0, sizeof(instance));

    if ((realm = krb_get_phost(RemoteHostName)))
	strncpy(instance, realm, sizeof(instance));

    instance[sizeof(instance)-1] = '\0';

    realm = dest_realm ? dest_realm : krb_realmofhost(RemoteHostName);

    if (!realm) {
	printf("Kerberos V4: no realm for %s\r\n", RemoteHostName);
	return(0);
    }
    r = krb_mk_req(&auth, KRB_SERVICE_NAME, instance, realm, 0L);
    if (r) {
	printf("mk_req failed: %s\r\n", krb_get_err_text(r));
	return(0);
    }
    r = krb_get_cred(KRB_SERVICE_NAME, instance, realm, &cred);
    if (r) {
	printf("get_cred failed: %s\r\n", krb_get_err_text(r));
	return(0);
    }
    if (!auth_sendname(UserNameRequested, strlen(UserNameRequested))) {
	if (auth_debug_mode)
	    printf("Not enough room for user name\r\n");
	return(0);
    }
    if (auth_debug_mode)
	printf("Sent %d bytes of authentication data\r\n", auth.length);
    if (!Data(ap, KRB_AUTH, (void *)auth.dat, auth.length)) {
	if (auth_debug_mode)
	    printf("Not enough room for authentication data\r\n");
	return(0);
    }
#ifdef ENCRYPTION
    /* create challenge */
    if ((ap->way & AUTH_HOW_MASK)==AUTH_HOW_MUTUAL) {
	int i;

	des_key_sched(&cred.session, sched);
	des_init_random_number_generator(&cred.session);
	des_new_random_key(&session_key);
	des_ecb_encrypt(&session_key, &session_key, sched, 0);
	des_ecb_encrypt(&session_key, &challenge, sched, 0);

	/*
	  old code
	  Some CERT Advisory thinks this is a bad thing...
	    
	  des_init_random_number_generator(&cred.session);
	  des_new_random_key(&challenge);
	  des_ecb_encrypt(&challenge, &session_key, sched, 1);
	  */
	  
	/*
	 * Increment the challenge by 1, and encrypt it for
	 * later comparison.
	 */
	for (i = 7; i >= 0; --i) 
	    if(++challenge[i] != 0) /* No carry! */
		break;
	des_ecb_encrypt(&challenge, &challenge, sched, 1);
    }

#endif

    if (auth_debug_mode) {
	printf("CK: %d:", kerberos4_cksum(auth.dat, auth.length));
	printd(auth.dat, auth.length);
	printf("\r\n");
	printf("Sent Kerberos V4 credentials to server\r\n");
    }
    return(1);
}
Beispiel #18
0
Code_t
ZMakeAuthentication(register ZNotice_t *notice,
		    char *buffer,
		    int buffer_len,
		    int *len)
{
#ifdef HAVE_KRB5
    return ZMakeZcodeAuthentication(notice, buffer, buffer_len, len/*?XXX*/);
#else
#ifdef HAVE_KRB4
    int result;
    KTEXT_ST authent;
    char *cstart, *cend;
    ZChecksum_t checksum;
    CREDENTIALS cred;
    C_Block *session;

    result = krb_mk_req(&authent, SERVER_SERVICE,
			SERVER_INSTANCE, __Zephyr_realm, 0);
    if (result != MK_AP_OK)
	return (result+krb_err_base);
    result = krb_get_cred(SERVER_SERVICE, SERVER_INSTANCE,
			  __Zephyr_realm, &cred);
    if (result != KSUCCESS)
	return (result+krb_err_base);

    session = (C_Block *)cred.session;

    notice->z_auth = 1;
    notice->z_authent_len = authent.length;
    notice->z_ascii_authent = (char *)malloc((unsigned)authent.length*3);
    /* zero length authent is an error, so malloc(0) is not a problem */
    if (!notice->z_ascii_authent)
	return (ENOMEM);
    if ((result = ZMakeAscii(notice->z_ascii_authent,
			     authent.length*3,
			     authent.dat,
			     authent.length)) != ZERR_NONE) {
	free(notice->z_ascii_authent);
	return (result);
    }
    result = Z_FormatRawHeader(notice, buffer, buffer_len, len, &cstart,
			       &cend);
    free(notice->z_ascii_authent);
    notice->z_authent_len = 0;
    if (result)
	return(result);

    /* Compute a checksum over the header and message. */
    checksum = des_quad_cksum((unsigned char *)buffer, NULL, cstart - buffer, 0, session);
    checksum ^= des_quad_cksum((unsigned char *)cend, NULL, buffer + *len - cend, 0,
			       session);
    checksum ^= des_quad_cksum((unsigned char *)notice->z_message, NULL, notice->z_message_len,
			       0, session);
    notice->z_checksum = checksum;
    ZMakeAscii32(cstart, buffer + buffer_len - cstart, checksum);

    return (ZERR_NONE);
#else
    notice->z_checksum = 0;
    notice->z_auth = 1;
    notice->z_authent_len = 0;
    notice->z_ascii_authent = "";
    return (Z_FormatRawHeader(notice, buffer, buffer_len, len, NULL, NULL));
#endif
#endif
}