1
14
15 package com.liferay.portal.servlet.filters.sso.ntlm;
16
17 import com.liferay.portal.kernel.exception.SystemException;
18 import com.liferay.portal.kernel.log.Log;
19 import com.liferay.portal.kernel.log.LogFactoryUtil;
20 import com.liferay.portal.kernel.servlet.HttpHeaders;
21 import com.liferay.portal.kernel.util.GetterUtil;
22 import com.liferay.portal.kernel.util.PropsKeys;
23 import com.liferay.portal.kernel.util.Validator;
24 import com.liferay.portal.security.ldap.LDAPSettingsUtil;
25 import com.liferay.portal.security.ntlm.NtlmManager;
26 import com.liferay.portal.security.ntlm.NtlmUserAccount;
27 import com.liferay.portal.servlet.filters.BasePortalFilter;
28 import com.liferay.portal.util.PortalInstances;
29 import com.liferay.portal.util.PrefsPropsUtil;
30 import com.liferay.portal.util.PropsUtil;
31 import com.liferay.portal.util.PropsValues;
32 import com.liferay.portal.util.WebKeys;
33
34 import java.security.SecureRandom;
35
36 import java.util.Iterator;
37 import java.util.Map;
38 import java.util.Properties;
39 import java.util.concurrent.ConcurrentHashMap;
40
41 import javax.servlet.FilterChain;
42 import javax.servlet.FilterConfig;
43 import javax.servlet.http.HttpServletRequest;
44 import javax.servlet.http.HttpServletResponse;
45 import javax.servlet.http.HttpSession;
46
47 import jcifs.Config;
48
49 import jcifs.http.NtlmHttpFilter;
50
51 import jcifs.util.Base64;
52
53
62 public class NtlmFilter extends BasePortalFilter {
63
64 public void init(FilterConfig filterConfig) {
65 try {
66 NtlmHttpFilter ntlmFilter = new NtlmHttpFilter();
67
68 ntlmFilter.init(filterConfig);
69
70 Properties properties = PropsUtil.getProperties("jcifs.", false);
71
72 Iterator<Map.Entry<Object, Object>> itr =
73 properties.entrySet().iterator();
74
75 while (itr.hasNext()) {
76 Map.Entry<Object, Object> entry = itr.next();
77
78 String key = (String)entry.getKey();
79 String value = (String)entry.getValue();
80
81 Config.setProperty(key, value);
82 }
83 }
84 catch (Exception e) {
85 _log.error(e, e);
86 }
87 }
88
89 protected Log getLog() {
90 return _log;
91 }
92
93 protected NtlmManager getNtlmManager(long companyId)
94 throws SystemException {
95
96 String domain = PrefsPropsUtil.getString(
97 companyId, PropsKeys.NTLM_DOMAIN, PropsValues.NTLM_DOMAIN);
98 String domainController = PrefsPropsUtil.getString(
99 companyId, PropsKeys.NTLM_DOMAIN_CONTROLLER,
100 PropsValues.NTLM_DOMAIN_CONTROLLER);
101 String domainControllerName = PrefsPropsUtil.getString(
102 companyId, PropsKeys.NTLM_DOMAIN_CONTROLLER_NAME,
103 PropsValues.NTLM_DOMAIN_CONTROLLER_NAME);
104 String serviceAccount = PrefsPropsUtil.getString(
105 companyId, PropsKeys.NTLM_SERVICE_ACCOUNT,
106 PropsValues.NTLM_SERVICE_ACCOUNT);
107 String servicePassword = PrefsPropsUtil.getString(
108 companyId, PropsKeys.NTLM_SERVICE_PASSWORD,
109 PropsValues.NTLM_SERVICE_PASSWORD);
110
111 NtlmManager ntlmManager = _ntlmManagers.get(companyId);
112
113 if (ntlmManager == null) {
114 ntlmManager = new NtlmManager(
115 domain, domainController, domainControllerName, serviceAccount,
116 servicePassword);
117
118 _ntlmManagers.put(companyId, ntlmManager);
119 }
120 else {
121 if (!Validator.equals(ntlmManager.getDomain(), domain) ||
122 !Validator.equals(
123 ntlmManager.getDomainController(), domainController) ||
124 !Validator.equals(
125 ntlmManager.getDomainControllerName(),
126 domainControllerName) ||
127 !Validator.equals(
128 ntlmManager.getServiceAccount(), serviceAccount) ||
129 !Validator.equals(
130 ntlmManager.getServicePassword(), servicePassword)) {
131
132 ntlmManager.setConfiguration(
133 domain, domainController, domainControllerName,
134 serviceAccount, servicePassword);
135 }
136 }
137
138 return ntlmManager;
139 }
140
141 protected void processFilter(
142 HttpServletRequest request, HttpServletResponse response,
143 FilterChain filterChain)
144 throws Exception {
145
146 long companyId = PortalInstances.getCompanyId(request);
147
148 if (LDAPSettingsUtil.isNtlmEnabled(companyId)) {
149
150
155 HttpSession session = request.getSession(false);
156
157 String authorization = GetterUtil.getString(
158 request.getHeader(HttpHeaders.AUTHORIZATION));
159
160 if (authorization.startsWith("NTLM")) {
161 NtlmManager ntlmManager = getNtlmManager(companyId);
162
163 byte[] src = Base64.decode(authorization.substring(5));
164
165 if (src[8] == 1) {
166 byte[] serverChallenge = new byte[8];
167
168 _secureRandom.nextBytes(serverChallenge);
169
170 byte[] challengeMessage = ntlmManager.negotiate(
171 src, serverChallenge);
172
173 authorization = Base64.encode(challengeMessage);
174
175 response.setHeader(
176 HttpHeaders.WWW_AUTHENTICATE, "NTLM " + authorization);
177 response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
178 response.setContentLength(0);
179
180 response.flushBuffer();
181
182 _serverChallenges.put(
183 request.getRemoteAddr(), serverChallenge);
184
185
188 return;
189 }
190 else {
191 byte[] serverChallenge = _serverChallenges.get(
192 request.getRemoteAddr());
193
194 NtlmUserAccount ntlmUserAccount = ntlmManager.authenticate(
195 src, serverChallenge);
196
197 if (ntlmUserAccount == null) {
198 return;
199 }
200
201 if (_log.isDebugEnabled()) {
202 _log.debug(
203 "NTLM remote user " +
204 ntlmUserAccount.getUserName());
205 }
206
207 _serverChallenges.remove(request.getRemoteAddr());
208
209 request.setAttribute(
210 WebKeys.NTLM_REMOTE_USER,
211 ntlmUserAccount.getUserName());
212
213 if (session != null) {
214 session.setAttribute(
215 WebKeys.NTLM_USER_ACCOUNT, ntlmUserAccount);
216 }
217 }
218 }
219
220 String path = request.getPathInfo();
221
222 if ((path != null) && path.endsWith("/login")) {
223 NtlmUserAccount ntlmUserAccount = null;
224
225 if (session != null) {
226 ntlmUserAccount = (NtlmUserAccount)session.getAttribute(
227 WebKeys.NTLM_USER_ACCOUNT);
228 }
229
230 if (ntlmUserAccount == null) {
231 response.setHeader(HttpHeaders.WWW_AUTHENTICATE, "NTLM");
232 response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
233 response.setContentLength(0);
234
235 response.flushBuffer();
236
237 return;
238 }
239 }
240 }
241
242 processFilter(NtlmPostFilter.class, request, response, filterChain);
243 }
244
245 private static Log _log = LogFactoryUtil.getLog(NtlmFilter.class);
246
247 private Map<Long, NtlmManager> _ntlmManagers =
248 new ConcurrentHashMap<Long, NtlmManager>();
249 private SecureRandom _secureRandom = new SecureRandom();
250 private Map<String, byte[]> _serverChallenges =
251 new ConcurrentHashMap<String, byte[]>();
252
253 }