2 * @(#)Token.java 1.2 05/06/2002
4 * Copyright (c) 2001 International Business Machines Corp.
7 * This software has been released under the terms of the IBM Public
8 * License. For details, see the LICENSE file in the top-level source
9 * directory or online at http://www.openafs.org/dl/license10.html
11 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
12 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
13 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
14 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR
15 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
16 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
17 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
18 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
19 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
20 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
21 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 package org
.openafs
.jafs
;
26 import java
.io
.Serializable
;
29 * An abstract representation of an AFS authentication token. It conveniently
30 * maintains the handle associated with token and the cell to which the token
34 * Constructing a <code>Token</code> object results in an immediate attempt to
35 * authenticate the user within the specified cell. If this attempt fails, an
36 * <code>{@link AFSException}</code> will be thrown. Therefore, if the
37 * construction of the object succeeds without an exception, then the
38 * <code>Token</code> is considered authenticated.
40 * The construction of a <code>Token</code> object acts as an entry point
41 * for authentication into the AFS system. Thus, when you construct a
42 * <code>{@link Cell}</code> object, you must pass in an instance of a
43 * <code>Token</code> that has been authenticated within the AFS cell that
44 * <code><I>Cell</I></code> is intended to represent. You will only be
45 * allowed to perform actions that the user, used to authenticate
46 * <code>Token</code>, is authorized to perform. You must construct a
47 * <code>Token</code> object before constructing a <code>Cell</code> object,
48 * which is required by all other objects within this package either directly
49 * or indirectly.<BR><BR>
51 * If an error occurs during a method call, an
52 * <code>AFSException</code> will be thrown. This class is the Java
53 * equivalent of errors thrown by AFS; see {@link AFSException}
54 * for a complete description.<BR><BR>
56 * <!--Example of how to use class-->
57 * The following is a simple example of how to construct and use a
58 * <code>Token</code> object. It shows how to construct a <code>Cell</code>
59 * using a <code>Token</code>. See {@link Cell} for a more detailed example
60 * of constructing and using a <code>Cell</code> object.<BR><BR>
63 * import org.openafs.jafs.AFSException;
64 * import org.openafs.jafs.Cell;
65 * import org.openafs.jafs.Token;
71 * private Token token;
73 * public static void main(String[] args) throws Exception
75 * String username = arg[0];
76 * String password = arg[1];
77 * String cellName = arg[2];
78 * String serverName = arg[3];
80 * token = new Token(username, password, cellName);
81 * cell = new Cell(token);
90 public class Token
implements Serializable
, Comparable
92 public static int ANYUSER_PAG_ID
;
94 protected long tokenHandle
;
95 protected int pagID
= -1;
98 protected String cellName
;
99 protected String username
;
100 private String password
;
102 private boolean hasInitialized
= false;
105 * Load the native libraries <code>libjafs</code> and
106 * <code>libjafs</code>.
111 Class
.forName("org.openafs.jafs.AFSLibraryLoader");
113 initializeAdminClient();
114 } catch (Exception e
) {
115 System
.err
.println(e
);
117 } catch (ClassNotFoundException e
) {
118 /* Most likely running on a client, do nothing */
123 * Constructs a new <CODE>Token</CODE> object instance given
124 * the name of the AFS cell it represents and the username and password
125 * of the user to be Tokend for
126 * administrative access.
128 * @param username the name of the user to Token with
129 * @param password the password of that user
130 * @param cellName the name of the cell to Token into
131 * @param login if true, automatically login upon construction
132 * @exception AFSException If an error occurs in the native code
134 protected Token( String username
, String password
, String cellName
,
135 boolean automaticallyLogin
)
138 this.username
= username
;
139 this.password
= password
;
140 this.cellName
= cellName
;
142 /* By default lets authenticate the user using libafsauthent.a */
143 if (automaticallyLogin
) login();
147 * Constructs a new <CODE>Token</CODE> object instance given the
148 * name of the AFS cell it represents; the token for administrative
149 * access will be extracted from the kernel cache manager if possible.
151 * @param cellName the name of the cell to Token into
152 * @exception AFSException If an error occurs in the native code
154 public Token(String cellName
)
157 this(null, null, cellName
);
161 * Constructs a new <CODE>Token</CODE> object instance given
162 * the name of the AFS cell it represents and the username and password
163 * of the user to be Tokend for
164 * administrative access.
166 * @param username the name of the user to Token with
167 * @param password the password of that user
168 * @param cellName the name of the cell to Token into
169 * @exception AFSException If an error occurs in the native code
171 public Token( String username
, String password
, String cellName
)
174 this.username
= username
;
175 this.password
= password
;
176 this.cellName
= cellName
;
178 //System.out.println(username + ", " + cellName);
179 /* By default lets authenticate the user using libafsauthent.a */
184 * Returns the name of the AFS cell that this <code>Token</code> was
185 * authenticated against.
187 * @exception AFSException If an error occurs in the native code
188 * @return the name of the AFS cell associated with this <code>Token</code>.
190 public String
getCellName()
196 * Returns the username of user to whom this token belongs.
198 * @exception AFSException If an error occurs in the native code
199 * @return the username of the user represented by this Token
201 public String
getUsername()
207 * Returns a token handle that can be used to prove this authentication
210 * @exception AFSException If an error occurs in the native code
211 * @return a token representing the authentication
213 protected long getHandle()
219 * Closes the given currently open token.
221 * @exception AFSException If an error occurs in the native code
223 public void close() throws AFSException
229 * Gets the expiration time for a given token.
231 * @return a long representing the UTC time for the token expiration
232 * @exception AFSException If an error occurs in the native code
234 public long getExpiration() throws AFSException
236 return getExpiration(tokenHandle
);
240 * Authenticates a user in kas, and binds that authentication
241 * to the current process.
243 * @exception AFSException If an error occurs in the native code
245 public void klog() throws AFSException
247 if (!hasInitialized
) {
248 initializeUserSpace();
249 hasInitialized
= true;
254 pagID
= klog(username
, password
, cellName
, pagID
);
259 * Authenticates a user in KAS, and binds that authentication
260 * to the current process.
262 * @exception AFSException If an error occurs in the native code
264 public void login() throws AFSException
266 this.tokenHandle
= this.getToken(cellName
, username
, password
);
267 //System.out.println("Token handle -> " + tokenHandle);
271 * Initialize the user space AFS client (libjafs).
273 * <P> The user space client must be initialized prior to any
274 * user space related methods, including: klog, unlog, relog,
277 * @exception AFSException If an error occurs in the native code
279 protected static void initializeUserSpace() throws AFSException
282 Token
.initUserSpace();
283 } catch (AFSException e
) {
284 System
.err
.println(e
.getMessage());
287 Runtime
.getRuntime().addShutdownHook(new AFSShutdownHandler());
288 } catch (Exception e
) {
289 System
.err
.println("Could not register shutdown hook: " + e
.toString());
293 /////////////// custom override methods ////////////////////
296 * Compares two ACL objects respective to their paths and does not
297 * factor any other attribute. Alphabetic case is significant in
300 * @param acl The ACL object to be compared to this ACL
303 * @return Zero if the argument is equal to this ACL's path, a
304 * value less than zero if this ACL's path is
305 * lexicographically less than the argument, or a value greater
306 * than zero if this ACL's path is lexicographically
307 * greater than the argument
309 public int compareTo(Token token
)
311 return this.toString().compareTo(token
.toString());
315 * Comparable interface method.
317 * @see #compareTo(Token)
319 public int compareTo(Object obj
)
321 return compareTo((Token
)obj
);
325 * Tests whether two <code>Cell</code> objects are equal, based on their
326 * names. Does not test whether the objects are actually the same
327 * representational instance of the AFS cell.
329 * @param otherCell the <code>Cell</code> to test
330 * @return whether the specifed user is the same as this user
332 public boolean equals( Token token
)
334 return this.toString().equals( token
.toString() );
338 * Returns the name of this <CODE>Cell</CODE>
340 * @return the name of this <CODE>Cell</CODE>
342 public String
toString()
344 return username
+ "@" + cellName
+ ":" + tokenHandle
;
347 /////////////// native methods found in *Token.c ////////////////////
350 * Initialize the user space library.
352 * @exception AFSException If an error occurs in the native code
354 private static native void initUserSpace() throws AFSException
;
357 * Initialize the administrative library.
359 * @exception AFSException If an error occurs in the native code
361 protected static native void initializeAdminClient() throws AFSException
;
364 * Returns a token handle that can be used to prove this authentication
367 * @param cellName the name of the cell in which to Token this user
368 * @param userName the name of the user to Token
369 * @param password the password of the user
370 * @exception AFSException If an error occurs in the native code
371 * @return a token representing the authentication
373 protected native long getToken( String cellName
, String username
,
378 * Closes the given currently open token.
380 * @param tokenHandle the token to close
381 * @exception AFSException If an error occurs in the native code
383 protected native void close( long tokenHandle
) throws AFSException
;
386 * Gets the expiration time for a given token.
388 * @param tokenHandle a token handle previously returned by a call
389 * to {@link #getToken}
391 * @return a long representing the UTC time for the token expiration
392 * @exception AFSException If an error occurs in the native code
394 protected native long getExpiration( long tokenHandle
)
398 * Authenticates a user in KAS, and binds that authentication
399 * to the current thread or native process.
401 * @param username the login to authenticate
402 * (expected as username@cellname)
403 * @param password the password of the login
404 * @param cellName the name of the cell to authenticate into
405 * @param id the existing pag (or 0)
407 * @return the assigned pag
408 * @exception AFSException If an error occurs in the native code
410 protected native int klog(String username
, String password
,
411 String cellName
, int id
)
415 * Authenticates a user in KAS by a previously acquired PAG ID, and binds
416 * that authentication to the current thread or native process.
418 * <P> This method does not require the user's username and password to
419 * fully authenticate their request. Rather it utilizes the user's PAG ID
420 * to recapture the user's existing credentials.
422 * <P> This method is called by the public <code>klog</code> method, which
423 * internally manages the PAG ID. Additionally, an application needs only
424 * call <code>klog</code>, this reduces the amount of complexity and ensures
425 * that <code>relog</code> is never called before a <code>klog</code>.
427 * @param int User's current PAG (process authentication group) ID
428 * @exception AFSException If an error occurs in the native code
430 protected native void relog(int id
) throws AFSException
;
433 * Manually discards all AFS credentials associated with the bound user.
435 * @exception AFSException If an error occurs in the native code
437 public native void unlog() throws AFSException
;
440 * Inform the native library that the application is
441 * shutting down and will be unloading.
443 * <p> The library will make a call informing the file server that it will
444 * no longer be available for callbacks.
446 protected static native void shutdown();
449 * Reclaims all memory being saved by the authentication portion of
450 * the native library.
451 * This method should be called when no more authentications are expected.
453 protected static native void reclaimAuthMemory();
456 /*=======================================================================*/
458 * Class that loads the native libraries required for direct communication with
459 * AFS. Since the Token class is serializable the function of loading the
460 * native libraries must be performed in a non-serialized class, one that will
461 * not be included in any client side application packages.
463 * @version 1.0, 06/13/2001
465 class AFSLibraryLoader
469 System
.loadLibrary("jafs");
470 System
.loadLibrary("jafsadm");
473 /*=======================================================================*/
475 * Class that handles graceful AFS application shutdown procedures by
476 * instructing the native library to inform the file system server that
477 * it is shutting down.
479 * @version 1.0, 06/13/2001
481 class AFSShutdownHandler
extends Thread
483 public AFSShutdownHandler() {}
486 * This is the execution method satisfying the interface requirement as a
487 * stand alone runnable thread.
489 * <p> This method will automatically be invoked by the Thread instantiator.
491 * @see Token#shutdown()
495 System
.out
.println("Shutting down Java AFS library...");
496 org
.openafs
.jafs
.Token
.shutdown();
499 /*=======================================================================*/