View Javadoc
1   /**
2    * Waffle (https://github.com/dblock/waffle)
3    *
4    * Copyright (c) 2010 - 2015 Application Security, Inc.
5    *
6    * All rights reserved. This program and the accompanying materials
7    * are made available under the terms of the Eclipse Public License v1.0
8    * which accompanies this distribution, and is available at
9    * http://www.eclipse.org/legal/epl-v10.html
10   *
11   * Contributors:
12   *     Application Security, Inc.
13   */
14  package waffle.windows.auth.impl;
15  
16  import java.util.ArrayList;
17  import java.util.List;
18  
19  import waffle.windows.auth.IWindowsAccount;
20  import waffle.windows.auth.IWindowsIdentity;
21  import waffle.windows.auth.IWindowsImpersonationContext;
22  
23  import com.sun.jna.platform.win32.Advapi32Util;
24  import com.sun.jna.platform.win32.Kernel32;
25  import com.sun.jna.platform.win32.Advapi32Util.Account;
26  import com.sun.jna.platform.win32.WinNT.HANDLE;
27  import com.sun.jna.platform.win32.WinNT.WELL_KNOWN_SID_TYPE;
28  
29  /**
30   * Windows Identity.
31   * 
32   * @author dblock[at]dblock[dot]org
33   */
34  public class WindowsIdentityImpl implements IWindowsIdentity {
35  
36      /** The windows identity. */
37      private final HANDLE    windowsIdentity;
38      
39      /** The user groups. */
40      private Account[] userGroups;
41      
42      /** The windows account. */
43      private Account   windowsAccount;
44  
45      /**
46       * Instantiates a new windows identity impl.
47       *
48       * @param newWindowsIdentity
49       *            the new windows identity
50       */
51      public WindowsIdentityImpl(final HANDLE newWindowsIdentity) {
52          this.windowsIdentity = newWindowsIdentity;
53      }
54  
55      /**
56       * Gets the windows account.
57       *
58       * @return the windows account
59       */
60      private Account getWindowsAccount() {
61          if (this.windowsAccount == null) {
62              this.windowsAccount = Advapi32Util.getTokenAccount(this.windowsIdentity);
63          }
64          return this.windowsAccount;
65      }
66  
67      /**
68       * Gets the user groups.
69       *
70       * @return the user groups
71       */
72      private Account[] getUserGroups() {
73          if (this.userGroups == null) {
74              this.userGroups = Advapi32Util.getTokenGroups(this.windowsIdentity);
75          }
76          return this.userGroups.clone();
77      }
78  
79      /* (non-Javadoc)
80       * @see waffle.windows.auth.IWindowsIdentity#getFqn()
81       */
82      @Override
83      public String getFqn() {
84          return this.getWindowsAccount().fqn;
85      }
86  
87      /* (non-Javadoc)
88       * @see waffle.windows.auth.IWindowsIdentity#getGroups()
89       */
90      @Override
91      public IWindowsAccount[] getGroups() {
92  
93          final Account[] groups = this.getUserGroups();
94  
95          final List<IWindowsAccount> result = new ArrayList<IWindowsAccount>(groups.length);
96          for (final Account userGroup : groups) {
97              final WindowsAccountImpl account = new WindowsAccountImpl(userGroup);
98              result.add(account);
99          }
100 
101         return result.toArray(new IWindowsAccount[0]);
102     }
103 
104     /* (non-Javadoc)
105      * @see waffle.windows.auth.IWindowsIdentity#getSid()
106      */
107     @Override
108     public byte[] getSid() {
109         return this.getWindowsAccount().sid;
110     }
111 
112     /* (non-Javadoc)
113      * @see waffle.windows.auth.IWindowsIdentity#getSidString()
114      */
115     @Override
116     public String getSidString() {
117         return this.getWindowsAccount().sidString;
118     }
119 
120     /* (non-Javadoc)
121      * @see waffle.windows.auth.IWindowsIdentity#dispose()
122      */
123     @Override
124     public void dispose() {
125         if (this.windowsIdentity != null) {
126             Kernel32.INSTANCE.CloseHandle(this.windowsIdentity);
127         }
128     }
129 
130     /* (non-Javadoc)
131      * @see waffle.windows.auth.IWindowsIdentity#impersonate()
132      */
133     @Override
134     public IWindowsImpersonationContext impersonate() {
135         return new WindowsIdentityImpersonationContextImpl(this.windowsIdentity);
136     }
137 
138     /* (non-Javadoc)
139      * @see waffle.windows.auth.IWindowsIdentity#isGuest()
140      */
141     @Override
142     public boolean isGuest() {
143         for (final Account userGroup : this.getUserGroups()) {
144             if (Advapi32Util.isWellKnownSid(userGroup.sid, WELL_KNOWN_SID_TYPE.WinBuiltinGuestsSid)) {
145                 return true;
146             }
147             if (Advapi32Util.isWellKnownSid(userGroup.sid, WELL_KNOWN_SID_TYPE.WinAccountDomainGuestsSid)) {
148                 return true;
149             }
150             if (Advapi32Util.isWellKnownSid(userGroup.sid, WELL_KNOWN_SID_TYPE.WinAccountGuestSid)) {
151                 return true;
152             }
153         }
154 
155         if (Advapi32Util.isWellKnownSid(this.getSid(), WELL_KNOWN_SID_TYPE.WinAnonymousSid)) {
156             return true;
157         }
158 
159         return false;
160     }
161 }