// Copyright 1997 The Open Group Research Institute.  All rights reserved.

package krb4.lib;

import java.io.*;
import krb4.lib.crypto.des;

public class Krb4ASRep {
	public byte pvno;
	public byte msgType;
	boolean littleEndian;
	public String cname;
	public String cinst;
	public String crealm;
	public long timestamp;
	public byte numberOfTickets;
	public long exptime;
	public byte keyVersion;
	public byte[] encCreds;
	public Krb4Creds creds;

	public Krb4ASRep(byte[] data) throws Krb4Exception {
		Krb4Encode ref = new Krb4Encode(data);
		pvno = ref.getByte();
		if (pvno != Krb4.KRB_PROT_VERSION)
			throw new Krb4Exception(Krb4.RD_AP_VERSION);
		byte temp = ref.getByte();
		msgType = (byte)(temp >>> 1);
		if (msgType != Krb4.AUTH_MSG_KDC_REPLY)
			throw new Krb4Exception(Krb4.RD_AP_MSG_TYPE);
		littleEndian = (temp & 1) == 1;
		ref.setByteOrder(littleEndian);
		cname = ref.getString();
		cinst = ref.getString();
		crealm = ref.getString();
		timestamp = (long)ref.getInt() * 1000L;
		numberOfTickets = ref.getByte();
		exptime = (long)ref.getInt() * 1000L;
		keyVersion = ref.getByte();
		int encCredsLength = ref.getShort();
		encCreds = ref.getBytes(encCredsLength);
	}

	public Krb4Creds getCreds(byte[] key) throws Krb4Exception {
		byte[] credsBytes = new byte[encCreds.length];
		long[] key_sched = new long[16];
		des.des_set_key(key, key_sched);
		byte[] ivec = new byte[key.length];
		System.arraycopy(key, 0, ivec, 0, key.length);
		des.pcbc_encrypt(encCreds, credsBytes, key_sched,
			ivec, false);
		try {
			creds = new Krb4Creds(credsBytes, littleEndian);
		} catch (Krb4Exception e) {
			if (e.returnCode() == Krb4.REP_OVERRUN)
				throw new Krb4Exception( Krb4.RD_AP_UNDEC);
			else
				throw e;
		}
		return creds;
	}

}
