001: /*
002: * JBoss, Home of Professional Open Source.
003: * Copyright 2006, Red Hat Middleware LLC, and individual contributors
004: * as indicated by the @author tags. See the copyright.txt file in the
005: * distribution for a full listing of individual contributors.
006: *
007: * This is free software; you can redistribute it and/or modify it
008: * under the terms of the GNU Lesser General Public License as
009: * published by the Free Software Foundation; either version 2.1 of
010: * the License, or (at your option) any later version.
011: *
012: * This software is distributed in the hope that it will be useful,
013: * but WITHOUT ANY WARRANTY; without even the implied warranty of
014: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015: * Lesser General Public License for more details.
016: *
017: * You should have received a copy of the GNU Lesser General Public
018: * License along with this software; if not, write to the Free
019: * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020: * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
021: */
022: package org.jboss.security.test;
023:
024: import java.math.BigInteger;
025: import java.rmi.RemoteException;
026: import java.security.KeyException;
027: import java.security.NoSuchAlgorithmException;
028:
029: import org.apache.log4j.Category;
030: import org.apache.log4j.ConsoleAppender;
031: import org.apache.log4j.NDC;
032: import org.apache.log4j.PatternLayout;
033:
034: import org.jboss.logging.XLevel;
035: import org.jboss.logging.Logger;
036: import org.jboss.security.Util;
037: import org.jboss.security.srp.SRPConf;
038: import org.jboss.security.srp.SRPServerInterface;
039: import org.jboss.security.srp.SRPClientSession;
040: import org.jboss.security.srp.SRPParameters;
041: import org.jboss.security.srp.SRPServerSession;
042:
043: /** Test of the SRP protocol msg exchange sequence.
044:
045: @author Scott.Stark@jboss.org
046: @version $Revision: 57210 $
047: */
048: public class TestProtocol extends junit.framework.TestCase {
049: static Logger log = Logger.getLogger(TestProtocol.class);
050: String username = "jduke";
051: char[] password = "theduke".toCharArray();
052: SRPServerInterface server;
053:
054: /** A simple hard coded implementation of SRPServerInterface that validates
055: any given username to the password and salt provided to its constructor.
056: */
057: static class TstImpl implements SRPServerInterface {
058: SRPParameters params;
059: SRPServerSession session;
060: char[] password;
061:
062: public Object[] getSRPParameters(String username,
063: boolean mutipleSessions) throws KeyException,
064: RemoteException {
065: return new Object[0];
066: }
067:
068: public byte[] init(String username, byte[] A, int sessionID)
069: throws SecurityException, NoSuchAlgorithmException,
070: RemoteException {
071: return new byte[0];
072: }
073:
074: public byte[] verify(String username, byte[] M1, int sessionID)
075: throws SecurityException, RemoteException {
076: return new byte[0];
077: }
078:
079: public byte[] verify(String username, byte[] M1,
080: Object auxChallenge) throws SecurityException,
081: RemoteException {
082: return new byte[0];
083: }
084:
085: public byte[] verify(String username, byte[] M1,
086: Object auxChallenge, int sessionID)
087: throws SecurityException, RemoteException {
088: return new byte[0];
089: }
090:
091: public void close(String username, int sessionID)
092: throws SecurityException, RemoteException {
093: }
094:
095: TstImpl(char[] password, String salt) {
096: BigInteger N = SRPConf.getDefaultParams().N();
097: log.trace("N: " + Util.tob64(N.toByteArray()));
098: BigInteger g = SRPConf.getDefaultParams().g();
099: log.trace("g: " + Util.tob64(g.toByteArray()));
100: byte[] Nb = SRPConf.getDefaultParams().Nbytes();
101: log.trace("N': " + Util.tob64(params.N));
102: byte[] gb = SRPConf.getDefaultParams().gbytes();
103: log.trace("g': " + Util.tob64(params.g));
104: byte[] hn = Util.newDigest().digest(params.N);
105: log.trace("H(N): " + Util.tob64(hn));
106: byte[] hg = Util.newDigest().digest(params.g);
107: log.trace("H(g): " + Util.tob64(hg));
108: byte[] sb = Util.fromb64(salt);
109: this .password = password;
110: params = new SRPParameters(Nb, gb, sb);
111: }
112:
113: public SRPParameters getSRPParameters(String username)
114: throws KeyException, RemoteException {
115: return params;
116: }
117:
118: public byte[] init(String username, byte[] A)
119: throws SecurityException, NoSuchAlgorithmException,
120: RemoteException {
121: // Calculate the password verfier v
122: byte[] v = Util.calculateVerifier(username, password,
123: params.s, params.N, params.g);
124: // Create an SRP session
125: session = new SRPServerSession(username, v, params);
126: byte[] B = session.exponential();
127: session.buildSessionKey(A);
128:
129: return B;
130: }
131:
132: public byte[] verify(String username, byte[] M1)
133: throws SecurityException, RemoteException {
134: if (session.verify(M1) == false)
135: throw new SecurityException("Failed to verify M1");
136: return session.getServerResponse();
137: }
138:
139: /** Close the SRP session for the given username.
140: */
141: public void close(String username) throws SecurityException,
142: RemoteException {
143: }
144:
145: }
146:
147: public TestProtocol(String name) {
148: super (name);
149: }
150:
151: protected void setUp() throws Exception {
152: // Set up a simple configuration that logs on the console.
153: Category root = Category.getRoot();
154: root.setLevel(XLevel.TRACE);
155: root.addAppender(new ConsoleAppender(
156: new PatternLayout("%x%m%n")));
157: Util.init();
158: NDC.push("S,");
159: server = new TstImpl(password, "123456");
160: NDC.pop();
161: NDC.remove();
162: }
163:
164: public void testProtocol() throws Exception {
165: SRPParameters params = server.getSRPParameters(username);
166: NDC.push("C,");
167: SRPClientSession client = new SRPClientSession(username,
168: password, params);
169: byte[] A = client.exponential();
170: NDC.pop();
171: NDC.push("S,");
172: byte[] B = server.init(username, A);
173: NDC.pop();
174: NDC.push("C,");
175: byte[] M1 = client.response(B);
176: NDC.pop();
177: NDC.push("S,");
178: byte[] M2 = server.verify(username, M1);
179: NDC.pop();
180: NDC.push("C,");
181: if (client.verify(M2) == false)
182: throw new SecurityException(
183: "Failed to validate server reply");
184: NDC.pop();
185: NDC.remove();
186: }
187:
188: /**
189: * @param args the command line arguments
190: */
191: public static void main(String args[]) {
192: long start = System.currentTimeMillis();
193: try {
194: TestProtocol tst = new TestProtocol("main");
195: tst.setUp();
196: tst.testProtocol();
197: } catch (Exception e) {
198: e.printStackTrace(System.out);
199: } finally {
200: long end = System.currentTimeMillis();
201: System.out.println("Elapsed time = " + (end - start));
202: }
203: }
204:
205: }
|