Limit Login Attempts - Version 1.2

Version Description

Download this release

Release Info

Developer johanee
Plugin Icon wp plugin Limit Login Attempts
Version 1.2
Comparing to
See all releases

Code changes from version 1.1 to 1.2

limit-login-attempts-sv_SE.mo CHANGED
Binary file
limit-login-attempts-sv_SE.po CHANGED
@@ -1,14 +1,14 @@
1
  # Limit Login Attempts Swedish Translation
2
  # Copyright (C) 2009 Johan Eenfeldt
3
- # This file is distributed under the same license as the PACKAGE package.
4
  # Johan Eenfeldt <johan.eenfeldt@kostdoktorn.se>, 2009.
5
  #
6
  #, fuzzy
7
  msgid ""
8
  msgstr ""
9
- "Project-Id-Version: limit-login-attempts 1.1\n"
10
  "Report-Msgid-Bugs-To: http://wordpress.org/tag/limit-login-attempts\n"
11
- "POT-Creation-Date: 2009-01-15 20:21+0000\n"
12
  "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
13
  "Last-Translator: Johan Eenfeldt <johan.eenfeldt@kostdoktorn.se>\n"
14
  "Language-Team: Swedish\n"
@@ -17,222 +17,217 @@ msgstr ""
17
  "Content-Transfer-Encoding: 8bit\n"
18
  "Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n"
19
 
20
- #: limit-login-attempts.php:315
21
  #, php-format
22
  msgid "%d hour"
23
  msgid_plural "%d hours"
24
  msgstr[0] "%d timme"
25
  msgstr[1] "%d timmar"
26
 
27
- #: limit-login-attempts.php:320
28
  #, php-format
29
  msgid "%d minute"
30
  msgid_plural "%d minutes"
31
  msgstr[0] "%d minut"
32
  msgstr[1] "%d minuter"
33
 
34
- #: limit-login-attempts.php:323
35
  #, php-format
36
  msgid "[%s] Too many failed login attempts"
37
- msgstr "[%s] F&ouml;r m&aring;nga misslyckade inloggningar"
38
 
39
- #: limit-login-attempts.php:325
40
  #, php-format
41
  msgid ""
42
  "%d failed login attempts (%d lockout(s)) from IP: %s\r\n"
43
  "\r\n"
44
  msgstr ""
45
- "%d misslyckade inloggningar (blockad %d g&aring;ng(er)) fr&aring;n IP: %s\r\n"
46
  "\r\n"
47
 
48
- #: limit-login-attempts.php:329
49
  #, php-format
50
  msgid ""
51
  "Last user attempted: %s\r\n"
52
  "\r\n"
53
  msgstr ""
54
- "Senast misslyckades med anv&auml;ndare : %s\r\n"
55
  "\r\n"
56
 
57
- #: limit-login-attempts.php:332
58
  #, php-format
59
  msgid "IP was blocked for %s"
60
- msgstr "IP har blockerats i %s"
61
 
62
- #: limit-login-attempts.php:389
63
  msgid "<strong>ERROR</strong>: Too many failed login attempts."
64
  msgstr "<strong>Fel</strong>: F&ouml;r m&aring;nga misslyckade f&ouml;rs&ouml;k."
65
 
66
- #: limit-login-attempts.php:393
67
  msgid "Please try again later."
68
  msgstr "F&ouml;rs&ouml;k igen senare."
69
 
70
- #: limit-login-attempts.php:400
71
  #, php-format
72
  msgid "Please try again in %d hour."
73
  msgid_plural "Please try again in %d hours."
74
  msgstr[0] "F&ouml;rs&ouml;k igen om %d timme."
75
  msgstr[1] "F&ouml;rs&ouml;k igen om %d timmar."
76
 
77
- #: limit-login-attempts.php:402
78
  #, php-format
79
  msgid "Please try again in %d minute."
80
  msgid_plural "Please try again in %d minutes."
81
  msgstr[0] "F&ouml;rs&ouml;k igen om %d minut."
82
  msgstr[1] "F&ouml;rs&ouml;k igen om %d minuter."
83
 
84
- #: limit-login-attempts.php:440
85
  #, php-format
86
  msgid "<strong>%d</strong> attempt remaining."
87
  msgid_plural "<strong>%d</strong> attempts remaining."
88
  msgstr[0] "<strong>%d</strong> f&ouml;rs&ouml;k &aring;terst&aring;r."
89
  msgstr[1] "<strong>%d</strong> f&ouml;rs&ouml;k &aring;terst&aring;r."
90
 
91
- #: limit-login-attempts.php:527
92
- #, php-format
93
- msgid ""
94
- "%s is unable to replace function wp_get_current_user(). Disable plugin "
95
- "cookie login handling, or competing plugin."
96
- msgstr ""
97
- "%s kan inte ers&auml;tta funktionen wp_get_current_user(). St&auml;ng av "
98
- "inloggningshantering f&ouml;r kakor, eller eller inkompatibelt till&auml;gg."
99
 
100
- #: limit-login-attempts.php:546
101
  msgid "IP|Internet address"
102
  msgstr "IP"
103
 
104
- #: limit-login-attempts.php:546
105
  msgid "Tried to log in as"
106
  msgstr "F&ouml;rs&ouml;kte logga in som"
107
 
108
- #: limit-login-attempts.php:551
109
  #, php-format
110
  msgid "%d lockout"
111
  msgid_plural "%d lockouts"
112
  msgstr[0] "%d blockering"
113
  msgstr[1] "%d blockeringar"
114
 
115
- #: limit-login-attempts.php:577
116
  msgid "Cleared IP log"
117
  msgstr "Rensade IP loggen"
118
 
119
- #: limit-login-attempts.php:585
120
  msgid "Reset lockout count"
121
  msgstr "Nollst&auml;llde r&auml;knaren f&ouml;r blockeringar"
122
 
123
- #: limit-login-attempts.php:593
124
  msgid "Cleared current lockouts"
125
  msgstr "Tog bort aktuella blockeringar"
126
 
127
- #: limit-login-attempts.php:620
128
  msgid "Options changed"
129
  msgstr "Inst&auml;llningar &auml;ndrade"
130
 
131
- #: limit-login-attempts.php:631
132
- msgid "<strong>NOTE:</strong> Only works on Wordpress 2.7 or later"
133
- msgstr "<strong>OBS:</strong> Fungerar endast med WordPress 2.7 eller senare"
134
 
135
- #: limit-login-attempts.php:644
136
  msgid "Limit Login Attempts Settings"
137
  msgstr "Limit Login Attempts Inst&auml;llningar"
138
 
139
- #: limit-login-attempts.php:645
140
  msgid "Statistics"
141
  msgstr "Statistik"
142
 
143
- #: limit-login-attempts.php:649
144
  msgid "Total lockouts"
145
  msgstr "Antal blockeringar"
146
 
147
- #: limit-login-attempts.php:652
148
  msgid "Reset Counter"
149
  msgstr "Nollst&auml;ll r&auml;knare"
150
 
151
- #: limit-login-attempts.php:653
152
  #, php-format
153
  msgid "%d lockout since last reset"
154
  msgid_plural "%d lockouts since last reset"
155
  msgstr[0] "%d blockering sedan r&auml;knaren nollst&auml;lldes"
156
  msgstr[1] "%d blockeringar sedan r&auml;knaren nollst&auml;lldes"
157
 
158
- #: limit-login-attempts.php:654
159
  msgid "No lockouts yet"
160
  msgstr "Inga blockeringar har skett &auml;nnu"
161
 
162
- #: limit-login-attempts.php:659
163
  msgid "Active lockouts"
164
  msgstr "Aktiva blockeringar"
165
 
166
- #: limit-login-attempts.php:661
167
  msgid "Restore Lockouts"
168
  msgstr "Ta bort blockeringar"
169
 
170
- #: limit-login-attempts.php:662
171
  #, php-format
172
  msgid "%d IP is currently blocked from trying to log in"
173
  msgstr "%d IP &auml;r f&ouml;r n&auml;rvarande blockerade fr&aring;n att logga in"
174
 
175
- #: limit-login-attempts.php:672
176
  msgid "Lockout"
177
  msgstr "Blockering"
178
 
179
- #: limit-login-attempts.php:674
180
  msgid "allowed retries"
181
  msgstr "till&aring;tna misslyckanden"
182
 
183
- #: limit-login-attempts.php:675
184
  msgid "minutes lockout"
185
  msgstr "minuters blockering"
186
 
187
- #: limit-login-attempts.php:676
188
  msgid "lockouts increase lockout time to"
189
  msgstr "blockeringar &ouml;kar tiden till"
190
 
191
- #: limit-login-attempts.php:676
192
  msgid "hours"
193
  msgstr "timmar"
194
 
195
- #: limit-login-attempts.php:677
196
  msgid "hours until retries are reset"
197
  msgstr "timmar tills misslyckanden nollst&auml;lls"
198
 
199
- #: limit-login-attempts.php:681
200
  msgid "Handle cookie login"
201
  msgstr "Hantera inloggning med kakor"
202
 
203
- #: limit-login-attempts.php:683
204
  msgid "Yes"
205
  msgstr "Ja"
206
 
207
- #: limit-login-attempts.php:683
208
  msgid "No"
209
  msgstr "Nej"
210
 
211
- #: limit-login-attempts.php:688
212
  msgid "Notify on lockout"
213
  msgstr "Notifiera om blockering"
214
 
215
- #: limit-login-attempts.php:690
216
  msgid "Log IP"
217
  msgstr "Logga IP"
218
 
219
- #: limit-login-attempts.php:691
220
  msgid "Email to admin after"
221
  msgstr "E-post till administrat&ouml;r efter"
222
 
223
- #: limit-login-attempts.php:691
224
  msgid "lockouts"
225
  msgstr "blockeringar"
226
 
227
- #: limit-login-attempts.php:696
228
  msgid "Change Options"
229
  msgstr "&Auml;ndra Inst&auml;llningar"
230
 
231
- #: limit-login-attempts.php:704
232
  msgid "Lockout log"
233
  msgstr "Log &ouml;ver blockeringar"
234
 
235
- #: limit-login-attempts.php:708
236
  msgid "Clear Log"
237
  msgstr "Rensa Log"
238
 
1
  # Limit Login Attempts Swedish Translation
2
  # Copyright (C) 2009 Johan Eenfeldt
3
+ # This file is distributed under the same license as the Wordpress package.
4
  # Johan Eenfeldt <johan.eenfeldt@kostdoktorn.se>, 2009.
5
  #
6
  #, fuzzy
7
  msgid ""
8
  msgstr ""
9
+ "Project-Id-Version: limit-login-attempts 1.2\n"
10
  "Report-Msgid-Bugs-To: http://wordpress.org/tag/limit-login-attempts\n"
11
+ "POT-Creation-Date: 2009-01-20 12:47+0000\n"
12
  "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
13
  "Last-Translator: Johan Eenfeldt <johan.eenfeldt@kostdoktorn.se>\n"
14
  "Language-Team: Swedish\n"
17
  "Content-Transfer-Encoding: 8bit\n"
18
  "Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n"
19
 
20
+ #: limit-login-attempts.php:319
21
  #, php-format
22
  msgid "%d hour"
23
  msgid_plural "%d hours"
24
  msgstr[0] "%d timme"
25
  msgstr[1] "%d timmar"
26
 
27
+ #: limit-login-attempts.php:325
28
  #, php-format
29
  msgid "%d minute"
30
  msgid_plural "%d minutes"
31
  msgstr[0] "%d minut"
32
  msgstr[1] "%d minuter"
33
 
34
+ #: limit-login-attempts.php:328
35
  #, php-format
36
  msgid "[%s] Too many failed login attempts"
37
+ msgstr "[%s] För många misslyckade inloggningar"
38
 
39
+ #: limit-login-attempts.php:330
40
  #, php-format
41
  msgid ""
42
  "%d failed login attempts (%d lockout(s)) from IP: %s\r\n"
43
  "\r\n"
44
  msgstr ""
45
+ "%d misslyckade inloggningar (blockad %d gång(er)) från IP: %s\r\n"
46
  "\r\n"
47
 
48
+ #: limit-login-attempts.php:334
49
  #, php-format
50
  msgid ""
51
  "Last user attempted: %s\r\n"
52
  "\r\n"
53
  msgstr ""
54
+ "Senast misslyckades med användare : %s\r\n"
55
  "\r\n"
56
 
57
+ #: limit-login-attempts.php:337
58
  #, php-format
59
  msgid "IP was blocked for %s"
60
+ msgstr "IP blockerades i %s"
61
 
62
+ #: limit-login-attempts.php:394
63
  msgid "<strong>ERROR</strong>: Too many failed login attempts."
64
  msgstr "<strong>Fel</strong>: F&ouml;r m&aring;nga misslyckade f&ouml;rs&ouml;k."
65
 
66
+ #: limit-login-attempts.php:398
67
  msgid "Please try again later."
68
  msgstr "F&ouml;rs&ouml;k igen senare."
69
 
70
+ #: limit-login-attempts.php:405
71
  #, php-format
72
  msgid "Please try again in %d hour."
73
  msgid_plural "Please try again in %d hours."
74
  msgstr[0] "F&ouml;rs&ouml;k igen om %d timme."
75
  msgstr[1] "F&ouml;rs&ouml;k igen om %d timmar."
76
 
77
+ #: limit-login-attempts.php:407
78
  #, php-format
79
  msgid "Please try again in %d minute."
80
  msgid_plural "Please try again in %d minutes."
81
  msgstr[0] "F&ouml;rs&ouml;k igen om %d minut."
82
  msgstr[1] "F&ouml;rs&ouml;k igen om %d minuter."
83
 
84
+ #: limit-login-attempts.php:439
85
  #, php-format
86
  msgid "<strong>%d</strong> attempt remaining."
87
  msgid_plural "<strong>%d</strong> attempts remaining."
88
  msgstr[0] "<strong>%d</strong> f&ouml;rs&ouml;k &aring;terst&aring;r."
89
  msgstr[1] "<strong>%d</strong> f&ouml;rs&ouml;k &aring;terst&aring;r."
90
 
91
+ #: limit-login-attempts.php:503
92
+ msgid "<strong>ERROR</strong>: Incorrect username or password."
93
+ msgstr "<strong>Fel</strong>: Felaktigt anv&auml;ndarnamn eller l&ouml;senord."
 
 
 
 
 
94
 
95
+ #: limit-login-attempts.php:643
96
  msgid "IP|Internet address"
97
  msgstr "IP"
98
 
99
+ #: limit-login-attempts.php:643
100
  msgid "Tried to log in as"
101
  msgstr "F&ouml;rs&ouml;kte logga in som"
102
 
103
+ #: limit-login-attempts.php:648
104
  #, php-format
105
  msgid "%d lockout"
106
  msgid_plural "%d lockouts"
107
  msgstr[0] "%d blockering"
108
  msgstr[1] "%d blockeringar"
109
 
110
+ #: limit-login-attempts.php:674
111
  msgid "Cleared IP log"
112
  msgstr "Rensade IP loggen"
113
 
114
+ #: limit-login-attempts.php:682
115
  msgid "Reset lockout count"
116
  msgstr "Nollst&auml;llde r&auml;knaren f&ouml;r blockeringar"
117
 
118
+ #: limit-login-attempts.php:690
119
  msgid "Cleared current lockouts"
120
  msgstr "Tog bort aktuella blockeringar"
121
 
122
+ #: limit-login-attempts.php:717
123
  msgid "Options changed"
124
  msgstr "Inst&auml;llningar &auml;ndrade"
125
 
126
+ #: limit-login-attempts.php:728
127
+ msgid "<strong>NOTE:</strong> Only works in Wordpress 2.7 or later"
128
+ msgstr "<strong>OBS:</strong> Fungerar endast i WordPress 2.7 eller senare"
129
 
130
+ #: limit-login-attempts.php:741
131
  msgid "Limit Login Attempts Settings"
132
  msgstr "Limit Login Attempts Inst&auml;llningar"
133
 
134
+ #: limit-login-attempts.php:742
135
  msgid "Statistics"
136
  msgstr "Statistik"
137
 
138
+ #: limit-login-attempts.php:746
139
  msgid "Total lockouts"
140
  msgstr "Antal blockeringar"
141
 
142
+ #: limit-login-attempts.php:749
143
  msgid "Reset Counter"
144
  msgstr "Nollst&auml;ll r&auml;knare"
145
 
146
+ #: limit-login-attempts.php:750
147
  #, php-format
148
  msgid "%d lockout since last reset"
149
  msgid_plural "%d lockouts since last reset"
150
  msgstr[0] "%d blockering sedan r&auml;knaren nollst&auml;lldes"
151
  msgstr[1] "%d blockeringar sedan r&auml;knaren nollst&auml;lldes"
152
 
153
+ #: limit-login-attempts.php:751
154
  msgid "No lockouts yet"
155
  msgstr "Inga blockeringar har skett &auml;nnu"
156
 
157
+ #: limit-login-attempts.php:756
158
  msgid "Active lockouts"
159
  msgstr "Aktiva blockeringar"
160
 
161
+ #: limit-login-attempts.php:758
162
  msgid "Restore Lockouts"
163
  msgstr "Ta bort blockeringar"
164
 
165
+ #: limit-login-attempts.php:759
166
  #, php-format
167
  msgid "%d IP is currently blocked from trying to log in"
168
  msgstr "%d IP &auml;r f&ouml;r n&auml;rvarande blockerade fr&aring;n att logga in"
169
 
170
+ #: limit-login-attempts.php:769
171
  msgid "Lockout"
172
  msgstr "Blockering"
173
 
174
+ #: limit-login-attempts.php:771
175
  msgid "allowed retries"
176
  msgstr "till&aring;tna misslyckanden"
177
 
178
+ #: limit-login-attempts.php:772
179
  msgid "minutes lockout"
180
  msgstr "minuters blockering"
181
 
182
+ #: limit-login-attempts.php:773
183
  msgid "lockouts increase lockout time to"
184
  msgstr "blockeringar &ouml;kar tiden till"
185
 
186
+ #: limit-login-attempts.php:773
187
  msgid "hours"
188
  msgstr "timmar"
189
 
190
+ #: limit-login-attempts.php:774
191
  msgid "hours until retries are reset"
192
  msgstr "timmar tills misslyckanden nollst&auml;lls"
193
 
194
+ #: limit-login-attempts.php:778
195
  msgid "Handle cookie login"
196
  msgstr "Hantera inloggning med kakor"
197
 
198
+ #: limit-login-attempts.php:780
199
  msgid "Yes"
200
  msgstr "Ja"
201
 
202
+ #: limit-login-attempts.php:780
203
  msgid "No"
204
  msgstr "Nej"
205
 
206
+ #: limit-login-attempts.php:785
207
  msgid "Notify on lockout"
208
  msgstr "Notifiera om blockering"
209
 
210
+ #: limit-login-attempts.php:787
211
  msgid "Log IP"
212
  msgstr "Logga IP"
213
 
214
+ #: limit-login-attempts.php:788
215
  msgid "Email to admin after"
216
  msgstr "E-post till administrat&ouml;r efter"
217
 
218
+ #: limit-login-attempts.php:788
219
  msgid "lockouts"
220
  msgstr "blockeringar"
221
 
222
+ #: limit-login-attempts.php:793
223
  msgid "Change Options"
224
  msgstr "&Auml;ndra Inst&auml;llningar"
225
 
226
+ #: limit-login-attempts.php:801
227
  msgid "Lockout log"
228
  msgstr "Log &ouml;ver blockeringar"
229
 
230
+ #: limit-login-attempts.php:805
231
  msgid "Clear Log"
232
  msgstr "Rensa Log"
233
 
limit-login-attempts.php CHANGED
@@ -1,782 +1,835 @@
1
- <?php
2
- /*
3
- Plugin Name: Limit Login Attempts
4
- Plugin URI: http://devel.kostdoktorn.se/limit-login-attempts
5
- Description: Limit rate of login attempts, including by way of cookies, for each IP.
6
- Author: Johan Eenfeldt
7
- Author URI: http://devel.kostdoktorn.se
8
- Version: 1.1
9
-
10
- Copyright 2008 Johan Eenfeldt
11
-
12
- Licenced under the GNU GPL:
13
-
14
- This program is free software; you can redistribute it and/or modify
15
- it under the terms of the GNU General Public License as published by
16
- the Free Software Foundation; either version 2 of the License, or
17
- (at your option) any later version.
18
-
19
- This program is distributed in the hope that it will be useful,
20
- but WITHOUT ANY WARRANTY; without even the implied warranty of
21
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22
- GNU General Public License for more details.
23
-
24
- You should have received a copy of the GNU General Public License
25
- along with this program; if not, write to the Free Software
26
- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27
- */
28
-
29
-
30
- /*
31
- * Variables
32
- *
33
- * Assignments are for default value -- change in admin page.
34
- */
35
-
36
- /* Lock out after this many tries */
37
- $limit_login_allowed_retries = 4;
38
-
39
- /* Lock out for this many seconds */
40
- $limit_login_lockout_duration = 1200; // 20 minutes
41
-
42
- /* Long lock out after this many lockouts */
43
- $limit_login_allowed_lockouts = 4;
44
-
45
- /* Long lock out for this many seconds */
46
- $limit_login_long_duration = 86400; // 24 hours
47
-
48
- /* Reset failed attempts after this many seconds */
49
- $limit_login_valid_duration = 86400; // 24 hours
50
-
51
- /* Also limit malformed/forged cookies?
52
- *
53
- * NOTE1: Only works in WP 2.7+, as necessary actions were added then.
54
- *
55
- * NOTE2: Overrides the pluggable function wp_get_current_user(). Will not
56
- * co-exist peacefully with anyone doing the same (know any such?).
57
- */
58
- $limit_login_cookies = true;
59
-
60
- /* Notify on lockout. Values: '', 'log', 'email', 'log,email' */
61
- $limit_login_lockout_notify = 'log';
62
-
63
- /* Notify value checked against these in limit_login_sanitize_variables() */
64
- $limit_login_lockout_notify_allowed = 'log,email';
65
-
66
- /* If notify by email, do so after this number of lockouts */
67
- $limit_login_notify_email_after = 4;
68
-
69
- $limit_login_my_error_shown = false; /* have we shown our stuff? */
70
- $limit_login_error_fn_exist = false; /* error replacing function */
71
- $limit_login_just_lockedout = false; /* started this pageload??? */
72
-
73
-
74
- /*
75
- * Startup
76
- */
77
-
78
- limit_login_setup();
79
-
80
- /* Replace wp_get_current_user() to handle login cookie lockout */
81
- if ($limit_login_cookies && !function_exists('wp_get_current_user') ) {
82
- /*
83
- * NOTE: overrides wp_get_current_user() when activated
84
- *
85
- * Unfortunately there is no nice filter like wp_authenticate_user when
86
- * handling the auth cookies.
87
- */
88
- function wp_get_current_user() {
89
- global $current_user;
90
-
91
- if (is_limit_login_ok()) {
92
- get_currentuserinfo();
93
- } else {
94
- if ($current_user > 0) {
95
- wp_set_current_user(0);
96
- }
97
- }
98
-
99
- return $current_user;
100
- }
101
- }
102
-
103
-
104
- /*
105
- * Functions start here
106
- */
107
-
108
- /* Get options and setup filters & actions */
109
- function limit_login_setup() {
110
- global $limit_login_cookies;
111
-
112
- load_plugin_textdomain('limit-login-attempts'
113
- , PLUGINDIR.'/'.dirname(plugin_basename(__FILE__)));
114
-
115
- limit_login_setup_options();
116
-
117
- if ($limit_login_cookies && function_exists('wp_get_current_user') ) {
118
- add_action('admin_notices', 'limit_login_pluggable_warning');
119
- $limit_login_cookies = false;
120
- $limit_login_error_fn_exist = true;
121
- }
122
-
123
- /* Filters and actions */
124
- add_action('wp_login_failed', 'limit_login_failed');
125
- if ($limit_login_cookies) {
126
- /* These are WP2.7+ */
127
- add_action('auth_cookie_bad_hash', 'limit_login_failed_cookie');
128
- add_action('auth_cookie_bad_username', 'limit_login_failed_cookie');
129
- }
130
- add_filter('wp_authenticate_user', 'limit_login_wp_authenticate_user', 99999, 2);
131
- add_action('login_head', 'limit_login_add_error_message');
132
- add_action('login_errors', 'limit_login_fixup_error_messages');
133
- add_action('admin_menu', 'limit_login_admin_menu');
134
- }
135
-
136
-
137
- /* Check if it is ok to login */
138
- function is_limit_login_ok() {
139
- $index = $_SERVER['REMOTE_ADDR'];
140
-
141
- /* lockout active? */
142
- $lockouts = get_option('limit_login_lockouts');
143
- return (!is_array($lockouts) || !isset($lockouts[$index]) || time() >= $lockouts[$index]);
144
- }
145
-
146
-
147
- /* Filter: allow login attempt? (called from wp_authenticate()) */
148
- function limit_login_wp_authenticate_user($user, $password) {
149
- if (is_wp_error($user) || is_limit_login_ok() ) {
150
- return $user;
151
- }
152
-
153
- global $limit_login_my_error_shown;
154
- $limit_login_my_error_shown = true;
155
-
156
- $error = new WP_Error();
157
- $error->add('too_many_retries', limit_login_error_msg());
158
- return $error;
159
- }
160
-
161
-
162
- /* Action: failed cookie login wrapper for limit_login_failed() */
163
- function limit_login_failed_cookie($arg) {
164
- limit_login_failed($arg);
165
- wp_clear_auth_cookie();
166
- }
167
-
168
- /*
169
- * Action when login attempt failed
170
- *
171
- * Increase nr of retries (if necessary). Reset valid value. Setup
172
- * lockout if nr of retries are above threshold. And more!
173
- */
174
- function limit_login_failed($arg) {
175
- global $limit_login_allowed_retries, $limit_login_valid_duration, $limit_login_last_user, $limit_login_allowed_lockouts, $limit_login_long_duration;
176
-
177
- $index = $_SERVER['REMOTE_ADDR'];
178
-
179
- /* if currently locked-out, do not add to retries */
180
- $lockouts = get_option('limit_login_lockouts');
181
- if(is_array($lockouts) && isset($lockouts[$index]) && time() < $lockouts[$index]) {
182
- return;
183
- } elseif (!is_array($lockouts)) {
184
- $lockouts = array();
185
- }
186
-
187
- /* Get the arrays with retries and retries-valid information */
188
- $retries = get_option('limit_login_retries');
189
- $valid = get_option('limit_login_retries_valid');
190
- if ($retries === false) {
191
- $retries = array();
192
- add_option('limit_login_retries', $retries, '', 'no');
193
- }
194
- if ($valid === false) {
195
- $valid = array();
196
- add_option('limit_login_retries_valid', $valid, '', 'no');
197
- }
198
-
199
- /* Check validity and add one to retries */
200
- if (isset($retries[$index]) && isset($valid[$index]) && time() < $valid[$index]) {
201
- $retries[$index] ++;
202
- } else {
203
- $retries[$index] = 1;
204
- }
205
- $valid[$index] = time() + $limit_login_valid_duration;
206
-
207
- /* lockout? */
208
- if($retries[$index] % $limit_login_allowed_retries == 0) {
209
- global $limit_login_lockout_duration, $limit_login_just_lockedout;
210
-
211
- $limit_login_just_lockedout = true;
212
-
213
- /* setup lockout, reset retries as needed */
214
- if ($retries[$index] >= $limit_login_allowed_retries * $limit_login_allowed_lockouts) {
215
- /* long lockout */
216
- $lockouts[$index] = time() + $limit_login_long_duration;
217
- unset($retries[$index]);
218
- unset($valid[$index]);
219
- } else {
220
- /* normal lockout */
221
- $lockouts[$index] = time() + $limit_login_lockout_duration;
222
- }
223
-
224
- /* try to find username which failed */
225
- $user = '';
226
- if (is_string($arg)) {
227
- /* action: wp_login_failed */
228
- $user = $arg;
229
- } elseif (is_array($arg) && array_key_exists('username', $arg)) {
230
- /* action: auth_cookie_bad_* */
231
- $user = $arg['username'];
232
- }
233
-
234
- /* do housecleaning and save values */
235
- limit_login_cleanup($retries, $lockouts, $valid);
236
-
237
- /* do any notification */
238
- limit_login_notify($user);
239
-
240
- /* increase statistics */
241
- $total = get_option('limit_login_lockouts_total');
242
- if ($total === false) {
243
- add_option('limit_login_lockouts_total', 1, '', 'no');
244
- } else {
245
- update_option('limit_login_lockouts_total', $total + 1);
246
- }
247
- } else {
248
- /* do not lockout (yet!) */
249
- update_option('limit_login_retries', $retries);
250
- update_option('limit_login_retries_valid', $valid);
251
- }
252
- }
253
-
254
-
255
- /* Clean up any old lockouts and old retries */
256
- function limit_login_cleanup($retries = null, $lockouts = null, $valid = null) {
257
- global $limit_login_lockout_duration, $limit_login_allowed_retries, $limit_login_valid_duration;
258
-
259
- $now = time();
260
-
261
- $lockouts = !is_null($lockouts) ? $lockouts : get_option('limit_login_lockouts');
262
-
263
- /* remove old lockouts */
264
- if (is_array($lockouts)) {
265
- foreach ($lockouts as $ip => $lockout) {
266
- if ($lockout < $now) {
267
- unset($lockouts[$ip]);
268
- }
269
- }
270
- update_option('limit_login_lockouts', $lockouts);
271
- }
272
-
273
- /* remove retries that are no longer valid */
274
- $valid = !is_null($valid) ? $valid : get_option('limit_login_retries_valid');
275
- $retries = !is_null($retries) ? $retries : get_option('limit_login_retries');
276
- if (is_array($valid) && is_array($retries)) {
277
- foreach ($valid as $ip => $lockout) {
278
- if ($lockout < $now) {
279
- unset($valid[$ip]);
280
- unset($retries[$ip]);
281
- }
282
- }
283
-
284
- /* go through retries directly, if for some reason they've gone out of sync */
285
- foreach ($retries as $ip => $retry) {
286
- if (!isset($valid[$ip])) {
287
- unset($retries[$ip]);
288
- }
289
- }
290
-
291
- update_option('limit_login_retries', $retries);
292
- update_option('limit_login_retries_valid', $valid);
293
- }
294
- }
295
-
296
-
297
- /* Email notification of lockout to admin (if configured) */
298
- function limit_login_notify_email($user) {
299
- global $limit_login_allowed_retries, $limit_login_allowed_lockouts, $limit_login_lockout_duration, $limit_login_notify_email_after, $limit_login_long_duration;
300
-
301
- $index = $_SERVER['REMOTE_ADDR'];
302
- $retries = get_option('limit_login_retries');
303
-
304
- if (!is_array($retries)) {
305
- $retries = array();
306
- }
307
-
308
- /* check if we are at the right nr to do notification */
309
- if ( isset($retries[$index])
310
- && ( ($retries[$index] / $limit_login_allowed_retries)
311
- % $limit_login_notify_email_after ) != 0 ) {
312
- return;
313
- }
314
-
315
- if (!isset($retries[$index])) {
316
- $count = $limit_login_allowed_retries * $limit_login_allowed_lockouts;
317
- $lockouts = $limit_login_allowed_lockouts;
318
- $time = round($limit_login_long_duration / 3600);
319
- $when = sprintf(__ngettext('%d hour', '%d hours', $time, 'limit-login-attempts'), $time);
320
- } else {
321
- $count = $retries[$index];
322
- $lockouts = floor($count / $limit_login_allowed_retries);
323
- $time = round($limit_login_lockout_duration / 60);
324
- $when = sprintf(__ngettext('%d minute', '%d minutes', $time, 'limit-login-attempts'), $time);
325
- }
326
-
327
- $subject = sprintf(__("[%s] Too many failed login attempts", 'limit-login-attempts')
328
- , get_option('blogname'));
329
- $message = sprintf(__("%d failed login attempts (%d lockout(s)) from IP: %s\r\n\r\n"
330
- , 'limit-login-attempts')
331
- , $count, $lockouts, $index);
332
- if ($user != '') {
333
- $message .= sprintf(__("Last user attempted: %s\r\n\r\n", 'limit-login-attempts')
334
- , $user);
335
- }
336
- $message .= sprintf(__("IP was blocked for %s", 'limit-login-attempts'), $when);
337
-
338
- @wp_mail(get_option('admin_email'), $subject, $message);
339
- }
340
-
341
-
342
- /* Logging of lockout (if configured) */
343
- function limit_login_notify_log($user) {
344
- $log = get_option('limit_login_logged');
345
- if ($log === false) {
346
- $log = array($_SERVER['REMOTE_ADDR'] => array($user => 1));
347
- add_option('limit_login_logged', $log, '', 'no'); /* no autoload */
348
- } else {
349
- if (isset($log[$_SERVER['REMOTE_ADDR']])) {
350
- if (isset($log[$_SERVER['REMOTE_ADDR']][$user])) {
351
- $log[$_SERVER['REMOTE_ADDR']][$user]++;
352
- } else {
353
- $log[$_SERVER['REMOTE_ADDR']][$user] = 1;
354
- }
355
- } else {
356
- $log[$_SERVER['REMOTE_ADDR']] = array($user => 1);
357
- }
358
- update_option('limit_login_logged', $log);
359
- }
360
- }
361
-
362
-
363
- /* Handle notification in event of lockout */
364
- function limit_login_notify($user) {
365
- global $limit_login_lockout_notify;
366
-
367
- $args = explode(',', $limit_login_lockout_notify);
368
-
369
- if (empty($args)) {
370
- return;
371
- }
372
-
373
- foreach ($args as $mode) {
374
- switch (trim($mode)) {
375
- case 'email':
376
- limit_login_notify_email($user);
377
- break;
378
- case 'log':
379
- limit_login_notify_log($user);
380
- break;
381
- }
382
- }
383
- }
384
-
385
-
386
- /* Construct informative error message */
387
- function limit_login_error_msg() {
388
- $index = $_SERVER['REMOTE_ADDR'];
389
-
390
- $lockouts = get_option('limit_login_lockouts');
391
-
392
-
393
- $msg = __('<strong>ERROR</strong>: Too many failed login attempts.', 'limit-login-attempts') . ' ';
394
-
395
- if (!is_array($lockouts) || !isset($lockouts[$index]) || time() >= $lockouts[$index]) {
396
- /* Huh? No timeout active? */
397
- $msg .= __('Please try again later.', 'limit-login-attempts');
398
- return $msg;
399
- }
400
-
401
- $when = ceil(($lockouts[$index] - time()) / 60);
402
- if ($when > 60) {
403
- $when = ceil($when / 60);
404
- $msg .= sprintf(__ngettext('Please try again in %d hour.', 'Please try again in %d hours.', $when, 'limit-login-attempts'), $when);
405
- } else {
406
- $msg .= sprintf(__ngettext('Please try again in %d minute.', 'Please try again in %d minutes.', $when, 'limit-login-attempts'), $when);
407
- }
408
-
409
- return $msg;
410
- }
411
-
412
-
413
- /* Fix up the error message before showing it */
414
- function limit_login_fixup_error_messages($content) {
415
- global $limit_login_just_lockedout;
416
-
417
- /*
418
- * During lockout we do not want to show any other error messages (like
419
- * unknown user or empty password).
420
- */
421
- if (!is_limit_login_ok() && !$limit_login_just_lockedout) {
422
- return limit_login_error_msg();
423
- }
424
-
425
- /*
426
- * If more than one error message, put an extra <br /> tag between them.
427
- */
428
- $msgs = explode("<br />\n", $content);
429
-
430
- if (strlen(end($msgs)) == 0) {
431
- /* remove last entry empty string */
432
- array_pop($msgs);
433
- }
434
-
435
- $count = count($msgs);
436
-
437
- if ($count == 1) {
438
- return $content;
439
- }
440
-
441
- $new = '';
442
- while ($count-- > 0) {
443
- $new .= array_shift($msgs) . "<br />\n";
444
- if ($count > 0) {
445
- $new .= "<br />\n";
446
- }
447
- }
448
-
449
- return $new;
450
- }
451
-
452
-
453
- /* Add a message to login page when necessary */
454
- function limit_login_add_error_message() {
455
- global $error, $limit_login_my_error_shown, $limit_login_allowed_retries;
456
-
457
- if ($limit_login_my_error_shown) {
458
- return;
459
- }
460
-
461
- if (!is_limit_login_ok()) {
462
- $error .= limit_login_error_msg();
463
- return;
464
- }
465
-
466
- $index = $_SERVER['REMOTE_ADDR'];
467
-
468
- $retries = get_option('limit_login_retries');
469
- $valid = get_option('limit_login_retries_valid');
470
-
471
- if (!is_array($retries) || !is_array($valid)) {
472
- return;
473
- }
474
- if (!isset($retries[$index]) || !isset($valid[$index]) || time() > $valid[$index]) {
475
- /* no valid retries */
476
- return;
477
- }
478
- if (($retries[$index] % $limit_login_allowed_retries) == 0 ) {
479
- /* already been locked out for these retries */
480
- return;
481
- }
482
-
483
- $remaining = max(($limit_login_allowed_retries - ($retries[$index] % $limit_login_allowed_retries)), 0);
484
- $error .= sprintf(__ngettext("<strong>%d</strong> attempt remaining.", "<strong>%d</strong> attempts remaining.", $remaining, 'limit-login-attempts'), $remaining);
485
- }
486
-
487
-
488
- /*
489
- * Admin stuff
490
- */
491
-
492
- /* Does wordpress version support cookie option? */
493
- function limit_login_support_cookie_option() {
494
- global $wp_version;
495
- return (version_compare($wp_version, '2.7', '>='));
496
- }
497
-
498
-
499
- /* Only change var if option exists */
500
- function limit_login_get_option($option, &$var) {
501
- $a = get_option($option);
502
-
503
- if ($a !== false) {
504
- $var = $a;
505
- }
506
- }
507
-
508
-
509
- /* Setup global variables from options */
510
- function limit_login_setup_options() {
511
- global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_notify_email_after;
512
-
513
- limit_login_get_option('limit_login_allowed_retries', $limit_login_allowed_retries);
514
- limit_login_get_option('limit_login_lockout_duration', $limit_login_lockout_duration);
515
- limit_login_get_option('limit_login_valid_duration', $limit_login_valid_duration);
516
- limit_login_get_option('limit_login_cookies', $limit_login_cookies);
517
- limit_login_get_option('limit_login_lockout_notify', $limit_login_lockout_notify);
518
- limit_login_get_option('limit_login_allowed_lockouts', $limit_login_allowed_lockouts);
519
- limit_login_get_option('limit_login_long_duration', $limit_login_long_duration);
520
- limit_login_get_option('limit_login_notify_email_after', $limit_login_notify_email_after);
521
-
522
- limit_login_sanitize_variables();
523
- }
524
-
525
-
526
- /* Update options in db from global variables */
527
- function limit_login_update_options() {
528
- global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_notify_email_after;
529
-
530
- update_option('limit_login_allowed_retries', $limit_login_allowed_retries);
531
- update_option('limit_login_lockout_duration', $limit_login_lockout_duration);
532
- update_option('limit_login_allowed_lockouts', $limit_login_allowed_lockouts);
533
- update_option('limit_login_long_duration', $limit_login_long_duration);
534
- update_option('limit_login_valid_duration', $limit_login_valid_duration);
535
- update_option('limit_login_lockout_notify', $limit_login_lockout_notify);
536
- update_option('limit_login_notify_email_after', $limit_login_notify_email_after);
537
- update_option('limit_login_cookies', $limit_login_cookies ? '1' : '0');
538
- }
539
-
540
-
541
- /* Make sure the variables make sense */
542
- function limit_login_sanitize_variables() {
543
- global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_lockout_notify_allowed, $limit_login_notify_email_after;
544
-
545
- $limit_login_allowed_retries = max(1, intval($limit_login_allowed_retries));
546
- $limit_login_lockout_duration = max(1, intval($limit_login_lockout_duration));
547
- $limit_login_valid_duration = max(1, intval($limit_login_valid_duration));
548
- $limit_login_allowed_lockouts = max(1, intval($limit_login_allowed_lockouts));
549
- $limit_login_long_duration = max(1, intval($limit_login_long_duration));
550
-
551
- $limit_login_notify_email_after = max(1, intval($limit_login_notify_email_after));
552
- $limit_login_notify_email_after = min($limit_login_allowed_lockouts, $limit_login_notify_email_after);
553
-
554
- $args = explode(',', $limit_login_lockout_notify);
555
- $args_allowed = explode(',', $limit_login_lockout_notify_allowed);
556
- $new_args = array();
557
- foreach ($args as $a) {
558
- if (in_array($a, $args_allowed)) {
559
- $new_args[] = $a;
560
- }
561
- }
562
- $limit_login_lockout_notify = implode(',', $new_args);
563
-
564
- $limit_login_cookies = $limit_login_cookies && limit_login_support_cookie_option() ? true : false;
565
- }
566
-
567
-
568
- /* Warning msg if unable to replace pluggable function (used by another plugin?) */
569
- function limit_login_pluggable_warning() {
570
- $msg = '<div id="message" class="error fade"><p>';
571
- $msg .= sprintf(__('%s is unable to replace function wp_get_current_user(). Disable plugin cookie login handling, or competing plugin.','limit-login-attempts'), '<a href=\"options-general.php?page=limit-login-attempts\">Limit Login Attempts</a> ');
572
- $msg .= '</p></div>';
573
-
574
- echo($msg);
575
- }
576
-
577
-
578
- /* Add admin options page */
579
- function limit_login_admin_menu() {
580
- add_options_page('Limit Login Attempts', 'Limit Login Attempts', 8, 'limit-login-attempts', 'limit_login_option_page');
581
- }
582
-
583
-
584
- /* Show log on admin page */
585
- function limit_login_show_log($log) {
586
- if (!is_array($log) || count($log) == 0) {
587
- return;
588
- }
589
-
590
- echo('<tr><th scope="col">' . _c("IP|Internet address", 'limit-login-attempts') . '</th><th scope="col">' . __('Tried to log in as', 'limit-login-attempts') . '</th></tr>');
591
- foreach ($log as $ip => $arr) {
592
- echo('<tr><td class="limit-login-ip">' . $ip . '</td><td class="limit-login-max">');
593
- $first = true;
594
- foreach($arr as $user => $count) {
595
- $count_desc = sprintf(__ngettext('%d lockout', '%d lockouts', $count, 'limit-login-attempts'), $count);
596
- if (!$first) {
597
- echo(', ' . $user . ' (' . $count_desc . ')');
598
- } else {
599
- echo($user . ' (' . $count_desc . ')');
600
- }
601
- $first = false;
602
- }
603
- echo('</td></tr>');
604
- }
605
- }
606
-
607
- /* Actual admin page */
608
- function limit_login_option_page() {
609
- global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_lockout_notify_allowed, $limit_login_notify_email_after;
610
-
611
- limit_login_cleanup();
612
-
613
- if (!current_user_can('manage_options')) {
614
- wp_die('Sorry, but you do not have permissions to change settings.');
615
- }
616
-
617
- /* Should we clear log? */
618
- if (isset($_POST['clear_log'])) {
619
- update_option('limit_login_logged', '');
620
- echo '<div id="message" class="updated fade"><p>'
621
- . __('Cleared IP log', 'limit-login-attempts')
622
- . '</p></div>';
623
- }
624
-
625
- /* Should we reset counter? */
626
- if (isset($_POST['reset_total'])) {
627
- update_option('limit_login_lockouts_total', 0);
628
- echo '<div id="message" class="updated fade"><p>'
629
- . __('Reset lockout count', 'limit-login-attempts')
630
- . '</p></div>';
631
- }
632
-
633
- /* Should we restore current lockouts? */
634
- if (isset($_POST['reset_current'])) {
635
- update_option('limit_login_lockouts', array());
636
- echo '<div id="message" class="updated fade"><p>'
637
- . __('Cleared current lockouts', 'limit-login-attempts')
638
- . '</p></div>';
639
- }
640
-
641
- /* Should we update options */
642
- if (isset($_POST['update_options'])) {
643
- $limit_login_allowed_retries = $_POST['allowed_retries'];
644
- $limit_login_lockout_duration = $_POST['lockout_duration'] * 60;
645
- $limit_login_valid_duration = $_POST['valid_duration'] * 3600;
646
- $limit_login_allowed_lockouts = $_POST['allowed_lockouts'];
647
- $limit_login_long_duration = $_POST['long_duration'] * 3600;
648
- $limit_login_notify_email_after = $_POST['email_after'];
649
-
650
- $limit_login_cookies = (isset($_POST['cookies']) && $_POST['cookies'] == '1');
651
-
652
- $v = array();
653
- if (isset($_POST['lockout_notify_log'])) {
654
- $v[] = 'log';
655
- }
656
- if (isset($_POST['lockout_notify_email'])) {
657
- $v[] = 'email';
658
- }
659
- $limit_login_lockout_notify = implode(',', $v);
660
-
661
- limit_login_sanitize_variables();
662
- limit_login_update_options();
663
- echo '<div id="message" class="updated fade"><p>'
664
- . __('Options changed', 'limit-login-attempts')
665
- . '</p></div>';
666
- }
667
-
668
- $lockouts_total = get_option('limit_login_lockouts_total', 0);
669
- $lockouts = get_option('limit_login_lockouts');
670
- $lockouts_now = is_array($lockouts) ? count($lockouts) : 0;
671
-
672
- if (!limit_login_support_cookie_option()) {
673
- $cookies_disabled = ' DISABLED ';
674
- $cookies_note = ' <br /> '
675
- . __('<strong>NOTE:</strong> Only works on Wordpress 2.7 or later', 'limit-login-attempts');
676
- } else {
677
- $cookies_disabled = '';
678
- $cookies_note = '';
679
- }
680
- $cookies_yes = $limit_login_cookies ? ' checked ' : '';
681
- $cookies_no = $limit_login_cookies ? '' : ' checked ';
682
-
683
- $v = explode(',', $limit_login_lockout_notify);
684
- $log_checked = in_array('log', $v) ? ' checked ' : '';
685
- $email_checked = in_array('email', $v) ? ' checked ' : '';
686
- ?>
687
- <div class="wrap">
688
- <h2><?php echo __('Limit Login Attempts Settings','limit-login-attempts'); ?></h2>
689
- <h3><?php echo __('Statistics','limit-login-attempts'); ?></h3>
690
- <form action="options-general.php?page=limit-login-attempts" method="post">
691
- <table class="form-table">
692
- <tr>
693
- <th scope="row" valign="top"><?php echo __('Total lockouts','limit-login-attempts'); ?></th>
694
- <td>
695
- <?php if ($lockouts_total > 0) { ?>
696
- <input name="reset_total" value="<?php echo __('Reset Counter','limit-login-attempts'); ?>" type="submit" />
697
- <?php echo sprintf(__ngettext('%d lockout since last reset', '%d lockouts since last reset', $lockouts_total, 'limit-login-attempts'), $lockouts_total); ?>
698
- <?php } else { echo __('No lockouts yet','limit-login-attempts'); } ?>
699
- </td>
700
- </tr>
701
- <?php if ($lockouts_now > 0) { ?>
702
- <tr>
703
- <th scope="row" valign="top"><?php echo __('Active lockouts','limit-login-attempts'); ?></th>
704
- <td>
705
- <input name="reset_current" value="<?php echo __('Restore Lockouts','limit-login-attempts'); ?>" type="submit" />
706
- <?php echo sprintf(__('%d IP is currently blocked from trying to log in','limit-login-attempts'), $lockouts_now); ?>
707
- </td>
708
- </tr>
709
- <?php } ?>
710
- </table>
711
- </form>
712
- <h3>Options</h3>
713
- <form action="options-general.php?page=limit-login-attempts" method="post">
714
- <table class="form-table">
715
- <tr>
716
- <th scope="row" valign="top"><?php echo __('Lockout','limit-login-attempts'); ?></th>
717
- <td>
718
- <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_allowed_retries); ?>" name="allowed_retries" /> <?php echo __('allowed retries','limit-login-attempts'); ?> <br />
719
- <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_lockout_duration/60); ?>" name="lockout_duration" /> <?php echo __('minutes lockout','limit-login-attempts'); ?> <br />
720
- <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_allowed_lockouts); ?>" name="allowed_lockouts" /> <?php echo __('lockouts increase lockout time to','limit-login-attempts'); ?> <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_long_duration/3600); ?>" name="long_duration" /> <?php echo __('hours','limit-login-attempts'); ?> <br />
721
- <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_valid_duration/3600); ?>" name="valid_duration" /> <?php echo __('hours until retries are reset','limit-login-attempts'); ?>
722
- </td>
723
- </tr>
724
- <tr>
725
- <th scope="row" valign="top"><?php echo __('Handle cookie login','limit-login-attempts'); ?></th>
726
- <td>
727
- <input type="radio" name="cookies" <?php echo $cookies_disabled . $cookies_yes; ?> value="1" /> <?php echo __('Yes','limit-login-attempts'); ?> <input type="radio" name="cookies" <?php echo $cookies_disabled . $cookies_no; ?> value="0" /> <?php echo __('No','limit-login-attempts'); ?>
728
- <?php echo $cookies_note ?>
729
- </td>
730
- </tr>
731
- <tr>
732
- <th scope="row" valign="top"><?php echo __('Notify on lockout','limit-login-attempts'); ?></th>
733
- <td>
734
- <input type="checkbox" name="lockout_notify_log" <?php echo $log_checked; ?> value="log" /> <?php echo __('Log IP','limit-login-attempts'); ?><br />
735
- <input type="checkbox" name="lockout_notify_email" <?php echo $email_checked; ?> value="email" /> <?php echo __('Email to admin after','limit-login-attempts'); ?> <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_notify_email_after); ?>" name="email_after" /> <?php echo __('lockouts','limit-login-attempts'); ?>
736
- </td>
737
- </tr>
738
- </table>
739
- <p class="submit">
740
- <input name="update_options" value="<?php echo __('Change Options','limit-login-attempts'); ?>" type="submit" />
741
- </p>
742
- </form>
743
- <?php
744
- $log = get_option('limit_login_logged');
745
-
746
- if (is_array($log) && count($log) > 0) {
747
- ?>
748
- <h3><?php echo __('Lockout log','limit-login-attempts'); ?></h3>
749
- <form action="options-general.php?page=limit-login-attempts" method="post">
750
- <input type="hidden" value="true" name="clear_log" />
751
- <p class="submit">
752
- <input name="submit" value="<?php echo __('Clear Log','limit-login-attempts'); ?>" type="submit" />
753
- </p>
754
- </form>
755
- <style type="text/css" media="screen">
756
- .limit-login-log th {
757
- font-weight: bold;
758
- }
759
- .limit-login-log td, .limit-login-log th {
760
- padding: 1px 5px 1px 5px;
761
- }
762
- td.limit-login-ip {
763
- font-family: "Courier New", Courier, monospace;
764
- vertical-align: top;
765
- }
766
- td.limit-login-max {
767
- width: 100%;
768
- }
769
- </style>
770
- <div class="limit-login-log">
771
- <table class="form-table">
772
- <?php limit_login_show_log($log); ?>
773
- </table>
774
- </div>
775
- <?php
776
- } /* if showing $log */
777
- ?>
778
-
779
- </div>
780
- <?php
781
- }
782
- ?>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /*
3
+ Plugin Name: Limit Login Attempts
4
+ Plugin URI: http://devel.kostdoktorn.se/limit-login-attempts
5
+ Description: Limit rate of login attempts, including by way of cookies, for each IP.
6
+ Author: Johan Eenfeldt
7
+ Author URI: http://devel.kostdoktorn.se
8
+ Version: 1.2
9
+
10
+ Copyright 2008, 2009 Johan Eenfeldt
11
+
12
+ Licenced under the GNU GPL:
13
+
14
+ This program is free software; you can redistribute it and/or modify
15
+ it under the terms of the GNU General Public License as published by
16
+ the Free Software Foundation; either version 2 of the License, or
17
+ (at your option) any later version.
18
+
19
+ This program is distributed in the hope that it will be useful,
20
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
21
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22
+ GNU General Public License for more details.
23
+
24
+ You should have received a copy of the GNU General Public License
25
+ along with this program; if not, write to the Free Software
26
+ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27
+ */
28
+
29
+
30
+ /*
31
+ * Variables
32
+ *
33
+ * Assignments are for default value -- change in admin page.
34
+ */
35
+
36
+ /* Lock out after this many tries */
37
+ $limit_login_allowed_retries = 4;
38
+
39
+ /* Lock out for this many seconds */
40
+ $limit_login_lockout_duration = 1200; // 20 minutes
41
+
42
+ /* Long lock out after this many lockouts */
43
+ $limit_login_allowed_lockouts = 4;
44
+
45
+ /* Long lock out for this many seconds */
46
+ $limit_login_long_duration = 86400; // 24 hours
47
+
48
+ /* Reset failed attempts after this many seconds */
49
+ $limit_login_valid_duration = 86400; // 24 hours
50
+
51
+ /* Also limit malformed/forged cookies?
52
+ *
53
+ * NOTE: Only works in WP 2.7+, as necessary actions were added then.
54
+ */
55
+ $limit_login_cookies = true;
56
+
57
+ /* Notify on lockout. Values: '', 'log', 'email', 'log,email' */
58
+ $limit_login_lockout_notify = 'log';
59
+
60
+ /* Notify value checked against these in limit_login_sanitize_variables() */
61
+ $limit_login_lockout_notify_allowed = 'log,email';
62
+
63
+ /* If notify by email, do so after this number of lockouts */
64
+ $limit_login_notify_email_after = 4;
65
+
66
+ $limit_login_my_error_shown = false; /* have we shown our stuff? */
67
+ $limit_login_just_lockedout = false; /* started this pageload??? */
68
+ $limit_login_nonempty_credentials = false; /* user and pwd nonempty */
69
+
70
+
71
+ /*
72
+ * Startup
73
+ */
74
+
75
+ limit_login_setup();
76
+
77
+
78
+ /*
79
+ * Functions start here
80
+ */
81
+
82
+ /* Get options and setup filters & actions */
83
+ function limit_login_setup() {
84
+ global $limit_login_cookies;
85
+
86
+ load_plugin_textdomain('limit-login-attempts'
87
+ , PLUGINDIR.'/'.dirname(plugin_basename(__FILE__)));
88
+
89
+ limit_login_setup_options();
90
+
91
+ /* Filters and actions */
92
+ add_action('wp_login_failed', 'limit_login_failed');
93
+ if ($limit_login_cookies) {
94
+ add_action('plugins_loaded', 'limit_login_handle_cookies', 99999);
95
+ add_action('auth_cookie_bad_hash', 'limit_login_failed_cookie');
96
+ add_action('auth_cookie_bad_username', 'limit_login_failed_cookie');
97
+ }
98
+ add_filter('wp_authenticate_user', 'limit_login_wp_authenticate_user', 99999, 2);
99
+ add_action('wp_authenticate', 'limit_login_track_credentials', 10, 2);
100
+ add_action('login_head', 'limit_login_add_error_message');
101
+ add_action('login_errors', 'limit_login_fixup_error_messages');
102
+ add_action('admin_menu', 'limit_login_admin_menu');
103
+ }
104
+
105
+
106
+ /* Check if it is ok to login */
107
+ function is_limit_login_ok() {
108
+ $index = $_SERVER['REMOTE_ADDR'];
109
+
110
+ /* lockout active? */
111
+ $lockouts = get_option('limit_login_lockouts');
112
+ return (!is_array($lockouts) || !isset($lockouts[$index]) || time() >= $lockouts[$index]);
113
+ }
114
+
115
+
116
+ /* Filter: allow login attempt? (called from wp_authenticate()) */
117
+ function limit_login_wp_authenticate_user($user, $password) {
118
+ if (is_wp_error($user) || is_limit_login_ok() ) {
119
+ return $user;
120
+ }
121
+
122
+ global $limit_login_my_error_shown;
123
+ $limit_login_my_error_shown = true;
124
+
125
+ $error = new WP_Error();
126
+ $error->add('too_many_retries', limit_login_error_msg());
127
+ return $error;
128
+ }
129
+
130
+
131
+ /*
132
+ * Action: called in plugin_loaded (really early) to make sure we do not allow
133
+ * auth cookies while locked out.
134
+ */
135
+ function limit_login_handle_cookies() {
136
+ if (is_limit_login_ok()) {
137
+ return;
138
+ }
139
+
140
+ if (empty($_COOKIE[AUTH_COOKIE]) && empty($_COOKIE[SECURE_AUTH_COOKIE])
141
+ && empty($_COOKIE[LOGGED_IN_COOKIE])) {
142
+ return;
143
+ }
144
+
145
+ wp_clear_auth_cookie();
146
+
147
+ if (!empty($_COOKIE[AUTH_COOKIE])) {
148
+ $_COOKIE[AUTH_COOKIE] = '';
149
+ }
150
+ if (!empty($_COOKIE[SECURE_AUTH_COOKIE])) {
151
+ $_COOKIE[SECURE_AUTH_COOKIE] = '';
152
+ }
153
+ if (!empty($_COOKIE[LOGGED_IN_COOKIE])) {
154
+ $_COOKIE[LOGGED_IN_COOKIE] = '';
155
+ }
156
+ }
157
+
158
+
159
+ /* Action: failed cookie login wrapper for limit_login_failed() */
160
+ function limit_login_failed_cookie($arg) {
161
+ limit_login_failed($arg);
162
+ wp_clear_auth_cookie();
163
+ }
164
+
165
+ /*
166
+ * Action when login attempt failed
167
+ *
168
+ * Increase nr of retries (if necessary). Reset valid value. Setup
169
+ * lockout if nr of retries are above threshold. And more!
170
+ */
171
+ function limit_login_failed($arg) {
172
+ global $limit_login_allowed_retries, $limit_login_valid_duration, $limit_login_last_user, $limit_login_allowed_lockouts, $limit_login_long_duration;
173
+
174
+ $index = $_SERVER['REMOTE_ADDR'];
175
+
176
+ /* if currently locked-out, do not add to retries */
177
+ $lockouts = get_option('limit_login_lockouts');
178
+ if(is_array($lockouts) && isset($lockouts[$index]) && time() < $lockouts[$index]) {
179
+ return;
180
+ } elseif (!is_array($lockouts)) {
181
+ $lockouts = array();
182
+ }
183
+
184
+ /* Get the arrays with retries and retries-valid information */
185
+ $retries = get_option('limit_login_retries');
186
+ $valid = get_option('limit_login_retries_valid');
187
+ if ($retries === false) {
188
+ $retries = array();
189
+ add_option('limit_login_retries', $retries, '', 'no');
190
+ }
191
+ if ($valid === false) {
192
+ $valid = array();
193
+ add_option('limit_login_retries_valid', $valid, '', 'no');
194
+ }
195
+
196
+ /* Check validity and add one to retries */
197
+ if (isset($retries[$index]) && isset($valid[$index]) && time() < $valid[$index]) {
198
+ $retries[$index] ++;
199
+ } else {
200
+ $retries[$index] = 1;
201
+ }
202
+ $valid[$index] = time() + $limit_login_valid_duration;
203
+
204
+ /* lockout? */
205
+ if($retries[$index] % $limit_login_allowed_retries == 0) {
206
+ global $limit_login_lockout_duration, $limit_login_just_lockedout;
207
+
208
+ $limit_login_just_lockedout = true;
209
+
210
+ /* setup lockout, reset retries as needed */
211
+ if ($retries[$index] >= $limit_login_allowed_retries * $limit_login_allowed_lockouts) {
212
+ /* long lockout */
213
+ $lockouts[$index] = time() + $limit_login_long_duration;
214
+ unset($retries[$index]);
215
+ unset($valid[$index]);
216
+ } else {
217
+ /* normal lockout */
218
+ $lockouts[$index] = time() + $limit_login_lockout_duration;
219
+ }
220
+
221
+ /* try to find username which failed */
222
+ $user = '';
223
+ if (is_string($arg)) {
224
+ /* action: wp_login_failed */
225
+ $user = $arg;
226
+ } elseif (is_array($arg) && array_key_exists('username', $arg)) {
227
+ /* action: auth_cookie_bad_* */
228
+ $user = $arg['username'];
229
+ }
230
+
231
+ /* do housecleaning and save values */
232
+ limit_login_cleanup($retries, $lockouts, $valid);
233
+
234
+ /* do any notification */
235
+ limit_login_notify($user);
236
+
237
+ /* increase statistics */
238
+ $total = get_option('limit_login_lockouts_total');
239
+ if ($total === false) {
240
+ add_option('limit_login_lockouts_total', 1, '', 'no');
241
+ } else {
242
+ update_option('limit_login_lockouts_total', $total + 1);
243
+ }
244
+ } else {
245
+ /* not lockout (yet!), do housecleaning and save values */
246
+ limit_login_cleanup($retries, null, $valid);
247
+ }
248
+ }
249
+
250
+
251
+ /* Clean up any old lockouts and old retries */
252
+ function limit_login_cleanup($retries = null, $lockouts = null, $valid = null) {
253
+ global $limit_login_lockout_duration, $limit_login_allowed_retries, $limit_login_valid_duration;
254
+
255
+ $now = time();
256
+
257
+ $lockouts = !is_null($lockouts) ? $lockouts : get_option('limit_login_lockouts');
258
+
259
+ /* remove old lockouts */
260
+ if (is_array($lockouts)) {
261
+ foreach ($lockouts as $ip => $lockout) {
262
+ if ($lockout < $now) {
263
+ unset($lockouts[$ip]);
264
+ }
265
+ }
266
+ update_option('limit_login_lockouts', $lockouts);
267
+ }
268
+
269
+ /* remove retries that are no longer valid */
270
+ $valid = !is_null($valid) ? $valid : get_option('limit_login_retries_valid');
271
+ $retries = !is_null($retries) ? $retries : get_option('limit_login_retries');
272
+ if (!is_array($valid) || !is_array($retries)) {
273
+ return;
274
+ }
275
+
276
+ foreach ($valid as $ip => $lockout) {
277
+ if ($lockout < $now) {
278
+ unset($valid[$ip]);
279
+ unset($retries[$ip]);
280
+ }
281
+ }
282
+
283
+ /* go through retries directly, if for some reason they've gone out of sync */
284
+ foreach ($retries as $ip => $retry) {
285
+ if (!isset($valid[$ip])) {
286
+ unset($retries[$ip]);
287
+ }
288
+ }
289
+
290
+ update_option('limit_login_retries', $retries);
291
+ update_option('limit_login_retries_valid', $valid);
292
+ }
293
+
294
+
295
+ /* Email notification of lockout to admin (if configured) */
296
+ function limit_login_notify_email($user) {
297
+ global $limit_login_allowed_retries, $limit_login_allowed_lockouts, $limit_login_lockout_duration, $limit_login_notify_email_after, $limit_login_long_duration;
298
+
299
+ $index = $_SERVER['REMOTE_ADDR'];
300
+ $retries = get_option('limit_login_retries');
301
+
302
+ if (!is_array($retries)) {
303
+ $retries = array();
304
+ }
305
+
306
+ /* check if we are at the right nr to do notification */
307
+ if ( isset($retries[$index])
308
+ && ( ($retries[$index] / $limit_login_allowed_retries)
309
+ % $limit_login_notify_email_after ) != 0 ) {
310
+ return;
311
+ }
312
+
313
+ /* Format message. First current lockout duration */
314
+ if (!isset($retries[$index])) {
315
+ /* longer lockout */
316
+ $count = $limit_login_allowed_retries * $limit_login_allowed_lockouts;
317
+ $lockouts = $limit_login_allowed_lockouts;
318
+ $time = round($limit_login_long_duration / 3600);
319
+ $when = sprintf(__ngettext('%d hour', '%d hours', $time, 'limit-login-attempts'), $time);
320
+ } else {
321
+ /* normal lockout */
322
+ $count = $retries[$index];
323
+ $lockouts = floor($count / $limit_login_allowed_retries);
324
+ $time = round($limit_login_lockout_duration / 60);
325
+ $when = sprintf(__ngettext('%d minute', '%d minutes', $time, 'limit-login-attempts'), $time);
326
+ }
327
+
328
+ $subject = sprintf(__("[%s] Too many failed login attempts", 'limit-login-attempts')
329
+ , get_option('blogname'));
330
+ $message = sprintf(__("%d failed login attempts (%d lockout(s)) from IP: %s\r\n\r\n"
331
+ , 'limit-login-attempts')
332
+ , $count, $lockouts, $index);
333
+ if ($user != '') {
334
+ $message .= sprintf(__("Last user attempted: %s\r\n\r\n", 'limit-login-attempts')
335
+ , $user);
336
+ }
337
+ $message .= sprintf(__("IP was blocked for %s", 'limit-login-attempts'), $when);
338
+
339
+ @wp_mail(get_option('admin_email'), $subject, $message);
340
+ }
341
+
342
+
343
+ /* Logging of lockout (if configured) */
344
+ function limit_login_notify_log($user) {
345
+ $log = get_option('limit_login_logged');
346
+ if ($log === false) {
347
+ $log = array($_SERVER['REMOTE_ADDR'] => array($user => 1));
348
+ add_option('limit_login_logged', $log, '', 'no'); /* no autoload */
349
+ } else {
350
+ /* can be written much simpler, if you do not mind php warnings */
351
+ if (isset($log[$_SERVER['REMOTE_ADDR']])) {
352
+ if (isset($log[$_SERVER['REMOTE_ADDR']][$user])) {
353
+ $log[$_SERVER['REMOTE_ADDR']][$user]++;
354
+ } else {
355
+ $log[$_SERVER['REMOTE_ADDR']][$user] = 1;
356
+ }
357
+ } else {
358
+ $log[$_SERVER['REMOTE_ADDR']] = array($user => 1);
359
+ }
360
+ update_option('limit_login_logged', $log);
361
+ }
362
+ }
363
+
364
+
365
+ /* Handle notification in event of lockout */
366
+ function limit_login_notify($user) {
367
+ global $limit_login_lockout_notify;
368
+
369
+ $args = explode(',', $limit_login_lockout_notify);
370
+
371
+ if (empty($args)) {
372
+ return;
373
+ }
374
+
375
+ foreach ($args as $mode) {
376
+ switch (trim($mode)) {
377
+ case 'email':
378
+ limit_login_notify_email($user);
379
+ break;
380
+ case 'log':
381
+ limit_login_notify_log($user);
382
+ break;
383
+ }
384
+ }
385
+ }
386
+
387
+
388
+ /* Construct informative error message */
389
+ function limit_login_error_msg() {
390
+ $index = $_SERVER['REMOTE_ADDR'];
391
+
392
+ $lockouts = get_option('limit_login_lockouts');
393
+
394
+ $msg = __('<strong>ERROR</strong>: Too many failed login attempts.', 'limit-login-attempts') . ' ';
395
+
396
+ if (!is_array($lockouts) || !isset($lockouts[$index]) || time() >= $lockouts[$index]) {
397
+ /* Huh? No timeout active? */
398
+ $msg .= __('Please try again later.', 'limit-login-attempts');
399
+ return $msg;
400
+ }
401
+
402
+ $when = ceil(($lockouts[$index] - time()) / 60);
403
+ if ($when > 60) {
404
+ $when = ceil($when / 60);
405
+ $msg .= sprintf(__ngettext('Please try again in %d hour.', 'Please try again in %d hours.', $when, 'limit-login-attempts'), $when);
406
+ } else {
407
+ $msg .= sprintf(__ngettext('Please try again in %d minute.', 'Please try again in %d minutes.', $when, 'limit-login-attempts'), $when);
408
+ }
409
+
410
+ return $msg;
411
+ }
412
+
413
+
414
+ /* Construct retries remaining message */
415
+ function limit_login_retries_remaining_msg() {
416
+ global $limit_login_allowed_retries;
417
+
418
+ $index = $_SERVER['REMOTE_ADDR'];
419
+
420
+ $retries = get_option('limit_login_retries');
421
+ $valid = get_option('limit_login_retries_valid');
422
+
423
+ /* Should we show retries remaining? */
424
+
425
+ if (!is_array($retries) || !is_array($valid)) {
426
+ /* no retries at all */
427
+ return '';
428
+ }
429
+ if (!isset($retries[$index]) || !isset($valid[$index]) || time() > $valid[$index]) {
430
+ /* no: no valid retries */
431
+ return '';
432
+ }
433
+ if (($retries[$index] % $limit_login_allowed_retries) == 0 ) {
434
+ /* no: already been locked out for these retries */
435
+ return '';
436
+ }
437
+
438
+ $remaining = max(($limit_login_allowed_retries - ($retries[$index] % $limit_login_allowed_retries)), 0);
439
+ return sprintf(__ngettext("<strong>%d</strong> attempt remaining.", "<strong>%d</strong> attempts remaining.", $remaining, 'limit-login-attempts'), $remaining);
440
+ }
441
+
442
+
443
+ /* Return current (error) message to show, if any */
444
+ function limit_login_get_message() {
445
+ if (!is_limit_login_ok()) {
446
+ return limit_login_error_msg();
447
+ }
448
+
449
+ return limit_login_retries_remaining_msg();
450
+ }
451
+
452
+
453
+ /* Should we show errors and messages on this page? */
454
+ function should_limit_login_show_msg() {
455
+ if (isset($_GET['key'])) {
456
+ /* reset password */
457
+ return false;
458
+ }
459
+
460
+ $action = isset($_REQUEST['action']) ? $_REQUEST['action'] : '';
461
+
462
+ return ( $action != 'lostpassword' && $action != 'retrievepassword'
463
+ && $action != 'resetpass' && $action != 'rp'
464
+ && $action != 'register' );
465
+ }
466
+
467
+
468
+ /* Fix up the error message before showing it */
469
+ function limit_login_fixup_error_messages($content) {
470
+ global $limit_login_just_lockedout, $limit_login_nonempty_credentials, $limit_login_my_error_shown;
471
+
472
+ if (!should_limit_login_show_msg()) {
473
+ return $content;
474
+ }
475
+
476
+ /*
477
+ * During lockout we do not want to show any other error messages (like
478
+ * unknown user or empty password).
479
+ */
480
+ if (!is_limit_login_ok() && !$limit_login_just_lockedout) {
481
+ return limit_login_error_msg();
482
+ }
483
+
484
+ /*
485
+ * We want to filter the messages 'Invalid username' and 'Invalid password'
486
+ * as that is an information leak regarding user account names.
487
+ *
488
+ * Also, if more than one error message, put an extra <br /> tag between
489
+ * them.
490
+ */
491
+ $msgs = explode("<br />\n", $content);
492
+
493
+ if (strlen(end($msgs)) == 0) {
494
+ /* remove last entry empty string */
495
+ array_pop($msgs);
496
+ }
497
+
498
+ $count = count($msgs);
499
+ $my_warn_count = $limit_login_my_error_shown ? 1 : 0;
500
+
501
+ if ($limit_login_nonempty_credentials && $count > $my_warn_count) {
502
+ /* Replace error message, including ours if necessary */
503
+ $content = __('<strong>ERROR</strong>: Incorrect username or password.', 'limit-login-attempts') . "<br />\n";
504
+ if ($limit_login_my_error_shown) {
505
+ $content .= "<br />\n" . limit_login_get_message() . "<br />\n";
506
+ }
507
+ return $content;
508
+ } elseif ($count <= 1) {
509
+ return $content;
510
+ }
511
+
512
+ $new = '';
513
+ while ($count-- > 0) {
514
+ $new .= array_shift($msgs) . "<br />\n";
515
+ if ($count > 0) {
516
+ $new .= "<br />\n";
517
+ }
518
+ }
519
+
520
+ return $new;
521
+ }
522
+
523
+
524
+ /* Add a message to login page when necessary */
525
+ function limit_login_add_error_message() {
526
+ global $error, $limit_login_my_error_shown, $limit_login_allowed_retries;
527
+
528
+ if (!should_limit_login_show_msg() || $limit_login_my_error_shown) {
529
+ return;
530
+ }
531
+
532
+ $msg = limit_login_get_message();
533
+
534
+ if ($msg != '') {
535
+ $limit_login_my_error_shown = true;
536
+ $error .= $msg;
537
+ }
538
+
539
+ return;
540
+ }
541
+
542
+
543
+ /* Keep track of if user or password are empty, to filter errors correctly */
544
+ function limit_login_track_credentials($user, $password) {
545
+ global $limit_login_nonempty_credentials;
546
+
547
+ $limit_login_nonempty_credentials = (!empty($user) && !empty($password));
548
+ }
549
+
550
+
551
+ /*
552
+ * Admin stuff
553
+ */
554
+
555
+ /* Does wordpress version support cookie option? */
556
+ function limit_login_support_cookie_option() {
557
+ global $wp_version;
558
+ return (version_compare($wp_version, '2.7', '>='));
559
+ }
560
+
561
+
562
+ /* Only change var if option exists */
563
+ function limit_login_get_option($option, &$var) {
564
+ $a = get_option($option);
565
+
566
+ if ($a !== false) {
567
+ $var = $a;
568
+ }
569
+ }
570
+
571
+
572
+ /* Setup global variables from options */
573
+ function limit_login_setup_options() {
574
+ global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_notify_email_after;
575
+
576
+ limit_login_get_option('limit_login_allowed_retries', $limit_login_allowed_retries);
577
+ limit_login_get_option('limit_login_lockout_duration', $limit_login_lockout_duration);
578
+ limit_login_get_option('limit_login_valid_duration', $limit_login_valid_duration);
579
+ limit_login_get_option('limit_login_cookies', $limit_login_cookies);
580
+ limit_login_get_option('limit_login_lockout_notify', $limit_login_lockout_notify);
581
+ limit_login_get_option('limit_login_allowed_lockouts', $limit_login_allowed_lockouts);
582
+ limit_login_get_option('limit_login_long_duration', $limit_login_long_duration);
583
+ limit_login_get_option('limit_login_notify_email_after', $limit_login_notify_email_after);
584
+
585
+ limit_login_sanitize_variables();
586
+ }
587
+
588
+
589
+ /* Update options in db from global variables */
590
+ function limit_login_update_options() {
591
+ global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_notify_email_after;
592
+
593
+ update_option('limit_login_allowed_retries', $limit_login_allowed_retries);
594
+ update_option('limit_login_lockout_duration', $limit_login_lockout_duration);
595
+ update_option('limit_login_allowed_lockouts', $limit_login_allowed_lockouts);
596
+ update_option('limit_login_long_duration', $limit_login_long_duration);
597
+ update_option('limit_login_valid_duration', $limit_login_valid_duration);
598
+ update_option('limit_login_lockout_notify', $limit_login_lockout_notify);
599
+ update_option('limit_login_notify_email_after', $limit_login_notify_email_after);
600
+ update_option('limit_login_cookies', $limit_login_cookies ? '1' : '0');
601
+ }
602
+
603
+
604
+ /* Make sure the variables make sense */
605
+ function limit_login_sanitize_variables() {
606
+ global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_lockout_notify_allowed, $limit_login_notify_email_after;
607
+
608
+ $limit_login_allowed_retries = max(1, intval($limit_login_allowed_retries));
609
+ $limit_login_lockout_duration = max(1, intval($limit_login_lockout_duration));
610
+ $limit_login_valid_duration = max(1, intval($limit_login_valid_duration));
611
+ $limit_login_allowed_lockouts = max(1, intval($limit_login_allowed_lockouts));
612
+ $limit_login_long_duration = max(1, intval($limit_login_long_duration));
613
+
614
+ $limit_login_notify_email_after = max(1, intval($limit_login_notify_email_after));
615
+ $limit_login_notify_email_after = min($limit_login_allowed_lockouts, $limit_login_notify_email_after);
616
+
617
+ $args = explode(',', $limit_login_lockout_notify);
618
+ $args_allowed = explode(',', $limit_login_lockout_notify_allowed);
619
+ $new_args = array();
620
+ foreach ($args as $a) {
621
+ if (in_array($a, $args_allowed)) {
622
+ $new_args[] = $a;
623
+ }
624
+ }
625
+ $limit_login_lockout_notify = implode(',', $new_args);
626
+
627
+ $limit_login_cookies = $limit_login_cookies && limit_login_support_cookie_option() ? true : false;
628
+ }
629
+
630
+
631
+ /* Add admin options page */
632
+ function limit_login_admin_menu() {
633
+ add_options_page('Limit Login Attempts', 'Limit Login Attempts', 8, 'limit-login-attempts', 'limit_login_option_page');
634
+ }
635
+
636
+
637
+ /* Show log on admin page */
638
+ function limit_login_show_log($log) {
639
+ if (!is_array($log) || count($log) == 0) {
640
+ return;
641
+ }
642
+
643
+ echo('<tr><th scope="col">' . _c("IP|Internet address", 'limit-login-attempts') . '</th><th scope="col">' . __('Tried to log in as', 'limit-login-attempts') . '</th></tr>');
644
+ foreach ($log as $ip => $arr) {
645
+ echo('<tr><td class="limit-login-ip">' . $ip . '</td><td class="limit-login-max">');
646
+ $first = true;
647
+ foreach($arr as $user => $count) {
648
+ $count_desc = sprintf(__ngettext('%d lockout', '%d lockouts', $count, 'limit-login-attempts'), $count);
649
+ if (!$first) {
650
+ echo(', ' . $user . ' (' . $count_desc . ')');
651
+ } else {
652
+ echo($user . ' (' . $count_desc . ')');
653
+ }
654
+ $first = false;
655
+ }
656
+ echo('</td></tr>');
657
+ }
658
+ }
659
+
660
+ /* Actual admin page */
661
+ function limit_login_option_page() {
662
+ global $limit_login_allowed_retries, $limit_login_lockout_duration, $limit_login_valid_duration, $limit_login_cookies, $limit_login_lockout_notify, $limit_login_allowed_lockouts, $limit_login_long_duration, $limit_login_lockout_notify_allowed, $limit_login_notify_email_after;
663
+
664
+ limit_login_cleanup();
665
+
666
+ if (!current_user_can('manage_options')) {
667
+ wp_die('Sorry, but you do not have permissions to change settings.');
668
+ }
669
+
670
+ /* Should we clear log? */
671
+ if (isset($_POST['clear_log'])) {
672
+ update_option('limit_login_logged', '');
673
+ echo '<div id="message" class="updated fade"><p>'
674
+ . __('Cleared IP log', 'limit-login-attempts')
675
+ . '</p></div>';
676
+ }
677
+
678
+ /* Should we reset counter? */
679
+ if (isset($_POST['reset_total'])) {
680
+ update_option('limit_login_lockouts_total', 0);
681
+ echo '<div id="message" class="updated fade"><p>'
682
+ . __('Reset lockout count', 'limit-login-attempts')
683
+ . '</p></div>';
684
+ }
685
+
686
+ /* Should we restore current lockouts? */
687
+ if (isset($_POST['reset_current'])) {
688
+ update_option('limit_login_lockouts', array());
689
+ echo '<div id="message" class="updated fade"><p>'
690
+ . __('Cleared current lockouts', 'limit-login-attempts')
691
+ . '</p></div>';
692
+ }
693
+
694
+ /* Should we update options? */
695
+ if (isset($_POST['update_options'])) {
696
+ $limit_login_allowed_retries = $_POST['allowed_retries'];
697
+ $limit_login_lockout_duration = $_POST['lockout_duration'] * 60;
698
+ $limit_login_valid_duration = $_POST['valid_duration'] * 3600;
699
+ $limit_login_allowed_lockouts = $_POST['allowed_lockouts'];
700
+ $limit_login_long_duration = $_POST['long_duration'] * 3600;
701
+ $limit_login_notify_email_after = $_POST['email_after'];
702
+
703
+ $limit_login_cookies = (isset($_POST['cookies']) && $_POST['cookies'] == '1');
704
+
705
+ $v = array();
706
+ if (isset($_POST['lockout_notify_log'])) {
707
+ $v[] = 'log';
708
+ }
709
+ if (isset($_POST['lockout_notify_email'])) {
710
+ $v[] = 'email';
711
+ }
712
+ $limit_login_lockout_notify = implode(',', $v);
713
+
714
+ limit_login_sanitize_variables();
715
+ limit_login_update_options();
716
+ echo '<div id="message" class="updated fade"><p>'
717
+ . __('Options changed', 'limit-login-attempts')
718
+ . '</p></div>';
719
+ }
720
+
721
+ $lockouts_total = get_option('limit_login_lockouts_total', 0);
722
+ $lockouts = get_option('limit_login_lockouts');
723
+ $lockouts_now = is_array($lockouts) ? count($lockouts) : 0;
724
+
725
+ if (!limit_login_support_cookie_option()) {
726
+ $cookies_disabled = ' DISABLED ';
727
+ $cookies_note = ' <br /> '
728
+ . __('<strong>NOTE:</strong> Only works in Wordpress 2.7 or later', 'limit-login-attempts');
729
+ } else {
730
+ $cookies_disabled = '';
731
+ $cookies_note = '';
732
+ }
733
+ $cookies_yes = $limit_login_cookies ? ' checked ' : '';
734
+ $cookies_no = $limit_login_cookies ? '' : ' checked ';
735
+
736
+ $v = explode(',', $limit_login_lockout_notify);
737
+ $log_checked = in_array('log', $v) ? ' checked ' : '';
738
+ $email_checked = in_array('email', $v) ? ' checked ' : '';
739
+ ?>
740
+ <div class="wrap">
741
+ <h2><?php echo __('Limit Login Attempts Settings','limit-login-attempts'); ?></h2>
742
+ <h3><?php echo __('Statistics','limit-login-attempts'); ?></h3>
743
+ <form action="options-general.php?page=limit-login-attempts" method="post">
744
+ <table class="form-table">
745
+ <tr>
746
+ <th scope="row" valign="top"><?php echo __('Total lockouts','limit-login-attempts'); ?></th>
747
+ <td>
748
+ <?php if ($lockouts_total > 0) { ?>
749
+ <input name="reset_total" value="<?php echo __('Reset Counter','limit-login-attempts'); ?>" type="submit" />
750
+ <?php echo sprintf(__ngettext('%d lockout since last reset', '%d lockouts since last reset', $lockouts_total, 'limit-login-attempts'), $lockouts_total); ?>
751
+ <?php } else { echo __('No lockouts yet','limit-login-attempts'); } ?>
752
+ </td>
753
+ </tr>
754
+ <?php if ($lockouts_now > 0) { ?>
755
+ <tr>
756
+ <th scope="row" valign="top"><?php echo __('Active lockouts','limit-login-attempts'); ?></th>
757
+ <td>
758
+ <input name="reset_current" value="<?php echo __('Restore Lockouts','limit-login-attempts'); ?>" type="submit" />
759
+ <?php echo sprintf(__('%d IP is currently blocked from trying to log in','limit-login-attempts'), $lockouts_now); ?>
760
+ </td>
761
+ </tr>
762
+ <?php } ?>
763
+ </table>
764
+ </form>
765
+ <h3>Options</h3>
766
+ <form action="options-general.php?page=limit-login-attempts" method="post">
767
+ <table class="form-table">
768
+ <tr>
769
+ <th scope="row" valign="top"><?php echo __('Lockout','limit-login-attempts'); ?></th>
770
+ <td>
771
+ <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_allowed_retries); ?>" name="allowed_retries" /> <?php echo __('allowed retries','limit-login-attempts'); ?> <br />
772
+ <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_lockout_duration/60); ?>" name="lockout_duration" /> <?php echo __('minutes lockout','limit-login-attempts'); ?> <br />
773
+ <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_allowed_lockouts); ?>" name="allowed_lockouts" /> <?php echo __('lockouts increase lockout time to','limit-login-attempts'); ?> <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_long_duration/3600); ?>" name="long_duration" /> <?php echo __('hours','limit-login-attempts'); ?> <br />
774
+ <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_valid_duration/3600); ?>" name="valid_duration" /> <?php echo __('hours until retries are reset','limit-login-attempts'); ?>
775
+ </td>
776
+ </tr>
777
+ <tr>
778
+ <th scope="row" valign="top"><?php echo __('Handle cookie login','limit-login-attempts'); ?></th>
779
+ <td>
780
+ <input type="radio" name="cookies" <?php echo $cookies_disabled . $cookies_yes; ?> value="1" /> <?php echo __('Yes','limit-login-attempts'); ?> <input type="radio" name="cookies" <?php echo $cookies_disabled . $cookies_no; ?> value="0" /> <?php echo __('No','limit-login-attempts'); ?>
781
+ <?php echo $cookies_note ?>
782
+ </td>
783
+ </tr>
784
+ <tr>
785
+ <th scope="row" valign="top"><?php echo __('Notify on lockout','limit-login-attempts'); ?></th>
786
+ <td>
787
+ <input type="checkbox" name="lockout_notify_log" <?php echo $log_checked; ?> value="log" /> <?php echo __('Log IP','limit-login-attempts'); ?><br />
788
+ <input type="checkbox" name="lockout_notify_email" <?php echo $email_checked; ?> value="email" /> <?php echo __('Email to admin after','limit-login-attempts'); ?> <input type="text" size="3" maxlength="4" value="<?php echo($limit_login_notify_email_after); ?>" name="email_after" /> <?php echo __('lockouts','limit-login-attempts'); ?>
789
+ </td>
790
+ </tr>
791
+ </table>
792
+ <p class="submit">
793
+ <input name="update_options" value="<?php echo __('Change Options','limit-login-attempts'); ?>" type="submit" />
794
+ </p>
795
+ </form>
796
+ <?php
797
+ $log = get_option('limit_login_logged');
798
+
799
+ if (is_array($log) && count($log) > 0) {
800
+ ?>
801
+ <h3><?php echo __('Lockout log','limit-login-attempts'); ?></h3>
802
+ <form action="options-general.php?page=limit-login-attempts" method="post">
803
+ <input type="hidden" value="true" name="clear_log" />
804
+ <p class="submit">
805
+ <input name="submit" value="<?php echo __('Clear Log','limit-login-attempts'); ?>" type="submit" />
806
+ </p>
807
+ </form>
808
+ <style type="text/css" media="screen">
809
+ .limit-login-log th {
810
+ font-weight: bold;
811
+ }
812
+ .limit-login-log td, .limit-login-log th {
813
+ padding: 1px 5px 1px 5px;
814
+ }
815
+ td.limit-login-ip {
816
+ font-family: "Courier New", Courier, monospace;
817
+ vertical-align: top;
818
+ }
819
+ td.limit-login-max {
820
+ width: 100%;
821
+ }
822
+ </style>
823
+ <div class="limit-login-log">
824
+ <table class="form-table">
825
+ <?php limit_login_show_log($log); ?>
826
+ </table>
827
+ </div>
828
+ <?php
829
+ } /* if showing $log */
830
+ ?>
831
+
832
+ </div>
833
+ <?php
834
+ }
835
+ ?>
limit-login-attempts.pot CHANGED
@@ -8,7 +8,7 @@ msgid ""
8
  msgstr ""
9
  "Project-Id-Version: PACKAGE VERSION\n"
10
  "Report-Msgid-Bugs-To: http://wordpress.org/tag/limit-login-attempts\n"
11
- "POT-Creation-Date: 2009-01-16 00:37+0000\n"
12
  "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
13
  "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
14
  "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -17,216 +17,213 @@ msgstr ""
17
  "Content-Transfer-Encoding: 8bit\n"
18
  "Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n"
19
 
20
- #: limit-login-attempts.php:315
21
  #, php-format
22
  msgid "%d hour"
23
  msgid_plural "%d hours"
24
  msgstr[0] ""
25
  msgstr[1] ""
26
 
27
- #: limit-login-attempts.php:320
28
  #, php-format
29
  msgid "%d minute"
30
  msgid_plural "%d minutes"
31
  msgstr[0] ""
32
  msgstr[1] ""
33
 
34
- #: limit-login-attempts.php:323
35
  #, php-format
36
  msgid "[%s] Too many failed login attempts"
37
  msgstr ""
38
 
39
- #: limit-login-attempts.php:325
40
  #, php-format
41
  msgid ""
42
  "%d failed login attempts (%d lockout(s)) from IP: %s\r\n"
43
  "\r\n"
44
  msgstr ""
45
 
46
- #: limit-login-attempts.php:329
47
  #, php-format
48
  msgid ""
49
  "Last user attempted: %s\r\n"
50
  "\r\n"
51
  msgstr ""
52
 
53
- #: limit-login-attempts.php:332
54
  #, php-format
55
  msgid "IP was blocked for %s"
56
  msgstr ""
57
 
58
- #: limit-login-attempts.php:389
59
  msgid "<strong>ERROR</strong>: Too many failed login attempts."
60
  msgstr ""
61
 
62
- #: limit-login-attempts.php:393
63
  msgid "Please try again later."
64
  msgstr ""
65
 
66
- #: limit-login-attempts.php:400
67
  #, php-format
68
  msgid "Please try again in %d hour."
69
  msgid_plural "Please try again in %d hours."
70
  msgstr[0] ""
71
  msgstr[1] ""
72
 
73
- #: limit-login-attempts.php:402
74
  #, php-format
75
  msgid "Please try again in %d minute."
76
  msgid_plural "Please try again in %d minutes."
77
  msgstr[0] ""
78
  msgstr[1] ""
79
 
80
- #: limit-login-attempts.php:440
81
  #, php-format
82
  msgid "<strong>%d</strong> attempt remaining."
83
  msgid_plural "<strong>%d</strong> attempts remaining."
84
  msgstr[0] ""
85
  msgstr[1] ""
86
 
87
- #: limit-login-attempts.php:527
88
- #, php-format
89
- msgid ""
90
- "%s is unable to replace function wp_get_current_user(). Disable plugin "
91
- "cookie login handling, or competing plugin."
92
  msgstr ""
93
 
94
- #: limit-login-attempts.php:546
95
  msgid "IP|Internet address"
96
  msgstr ""
97
 
98
- #: limit-login-attempts.php:546
99
  msgid "Tried to log in as"
100
  msgstr ""
101
 
102
- #: limit-login-attempts.php:551
103
  #, php-format
104
  msgid "%d lockout"
105
  msgid_plural "%d lockouts"
106
  msgstr[0] ""
107
  msgstr[1] ""
108
 
109
- #: limit-login-attempts.php:577
110
  msgid "Cleared IP log"
111
  msgstr ""
112
 
113
- #: limit-login-attempts.php:585
114
  msgid "Reset lockout count"
115
  msgstr ""
116
 
117
- #: limit-login-attempts.php:593
118
  msgid "Cleared current lockouts"
119
  msgstr ""
120
 
121
- #: limit-login-attempts.php:620
122
  msgid "Options changed"
123
  msgstr ""
124
 
125
- #: limit-login-attempts.php:631
126
- msgid "<strong>NOTE:</strong> Only works on Wordpress 2.7 or later"
127
  msgstr ""
128
 
129
- #: limit-login-attempts.php:644
130
  msgid "Limit Login Attempts Settings"
131
  msgstr ""
132
 
133
- #: limit-login-attempts.php:645
134
  msgid "Statistics"
135
  msgstr ""
136
 
137
- #: limit-login-attempts.php:649
138
  msgid "Total lockouts"
139
  msgstr ""
140
 
141
- #: limit-login-attempts.php:652
142
  msgid "Reset Counter"
143
  msgstr ""
144
 
145
- #: limit-login-attempts.php:653
146
  #, php-format
147
  msgid "%d lockout since last reset"
148
  msgid_plural "%d lockouts since last reset"
149
  msgstr[0] ""
150
  msgstr[1] ""
151
 
152
- #: limit-login-attempts.php:654
153
  msgid "No lockouts yet"
154
  msgstr ""
155
 
156
- #: limit-login-attempts.php:659
157
  msgid "Active lockouts"
158
  msgstr ""
159
 
160
- #: limit-login-attempts.php:661
161
  msgid "Restore Lockouts"
162
  msgstr ""
163
 
164
- #: limit-login-attempts.php:662
165
  #, php-format
166
  msgid "%d IP is currently blocked from trying to log in"
167
  msgstr ""
168
 
169
- #: limit-login-attempts.php:672
170
  msgid "Lockout"
171
  msgstr ""
172
 
173
- #: limit-login-attempts.php:674
174
  msgid "allowed retries"
175
  msgstr ""
176
 
177
- #: limit-login-attempts.php:675
178
  msgid "minutes lockout"
179
  msgstr ""
180
 
181
- #: limit-login-attempts.php:676
182
  msgid "lockouts increase lockout time to"
183
  msgstr ""
184
 
185
- #: limit-login-attempts.php:676
186
  msgid "hours"
187
  msgstr ""
188
 
189
- #: limit-login-attempts.php:677
190
  msgid "hours until retries are reset"
191
  msgstr ""
192
 
193
- #: limit-login-attempts.php:681
194
  msgid "Handle cookie login"
195
  msgstr ""
196
 
197
- #: limit-login-attempts.php:683
198
  msgid "Yes"
199
  msgstr ""
200
 
201
- #: limit-login-attempts.php:683
202
  msgid "No"
203
  msgstr ""
204
 
205
- #: limit-login-attempts.php:688
206
  msgid "Notify on lockout"
207
  msgstr ""
208
 
209
- #: limit-login-attempts.php:690
210
  msgid "Log IP"
211
  msgstr ""
212
 
213
- #: limit-login-attempts.php:691
214
  msgid "Email to admin after"
215
  msgstr ""
216
 
217
- #: limit-login-attempts.php:691
218
  msgid "lockouts"
219
  msgstr ""
220
 
221
- #: limit-login-attempts.php:696
222
  msgid "Change Options"
223
  msgstr ""
224
 
225
- #: limit-login-attempts.php:704
226
  msgid "Lockout log"
227
  msgstr ""
228
 
229
- #: limit-login-attempts.php:708
230
  msgid "Clear Log"
231
  msgstr ""
232
 
8
  msgstr ""
9
  "Project-Id-Version: PACKAGE VERSION\n"
10
  "Report-Msgid-Bugs-To: http://wordpress.org/tag/limit-login-attempts\n"
11
+ "POT-Creation-Date: 2009-01-20 12:47+0000\n"
12
  "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
13
  "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
14
  "Language-Team: LANGUAGE <LL@li.org>\n"
17
  "Content-Transfer-Encoding: 8bit\n"
18
  "Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n"
19
 
20
+ #: limit-login-attempts.php:319
21
  #, php-format
22
  msgid "%d hour"
23
  msgid_plural "%d hours"
24
  msgstr[0] ""
25
  msgstr[1] ""
26
 
27
+ #: limit-login-attempts.php:325
28
  #, php-format
29
  msgid "%d minute"
30
  msgid_plural "%d minutes"
31
  msgstr[0] ""
32
  msgstr[1] ""
33
 
34
+ #: limit-login-attempts.php:328
35
  #, php-format
36
  msgid "[%s] Too many failed login attempts"
37
  msgstr ""
38
 
39
+ #: limit-login-attempts.php:330
40
  #, php-format
41
  msgid ""
42
  "%d failed login attempts (%d lockout(s)) from IP: %s\r\n"
43
  "\r\n"
44
  msgstr ""
45
 
46
+ #: limit-login-attempts.php:334
47
  #, php-format
48
  msgid ""
49
  "Last user attempted: %s\r\n"
50
  "\r\n"
51
  msgstr ""
52
 
53
+ #: limit-login-attempts.php:337
54
  #, php-format
55
  msgid "IP was blocked for %s"
56
  msgstr ""
57
 
58
+ #: limit-login-attempts.php:394
59
  msgid "<strong>ERROR</strong>: Too many failed login attempts."
60
  msgstr ""
61
 
62
+ #: limit-login-attempts.php:398
63
  msgid "Please try again later."
64
  msgstr ""
65
 
66
+ #: limit-login-attempts.php:405
67
  #, php-format
68
  msgid "Please try again in %d hour."
69
  msgid_plural "Please try again in %d hours."
70
  msgstr[0] ""
71
  msgstr[1] ""
72
 
73
+ #: limit-login-attempts.php:407
74
  #, php-format
75
  msgid "Please try again in %d minute."
76
  msgid_plural "Please try again in %d minutes."
77
  msgstr[0] ""
78
  msgstr[1] ""
79
 
80
+ #: limit-login-attempts.php:439
81
  #, php-format
82
  msgid "<strong>%d</strong> attempt remaining."
83
  msgid_plural "<strong>%d</strong> attempts remaining."
84
  msgstr[0] ""
85
  msgstr[1] ""
86
 
87
+ #: limit-login-attempts.php:503
88
+ msgid "<strong>ERROR</strong>: Incorrect username or password."
 
 
 
89
  msgstr ""
90
 
91
+ #: limit-login-attempts.php:643
92
  msgid "IP|Internet address"
93
  msgstr ""
94
 
95
+ #: limit-login-attempts.php:643
96
  msgid "Tried to log in as"
97
  msgstr ""
98
 
99
+ #: limit-login-attempts.php:648
100
  #, php-format
101
  msgid "%d lockout"
102
  msgid_plural "%d lockouts"
103
  msgstr[0] ""
104
  msgstr[1] ""
105
 
106
+ #: limit-login-attempts.php:674
107
  msgid "Cleared IP log"
108
  msgstr ""
109
 
110
+ #: limit-login-attempts.php:682
111
  msgid "Reset lockout count"
112
  msgstr ""
113
 
114
+ #: limit-login-attempts.php:690
115
  msgid "Cleared current lockouts"
116
  msgstr ""
117
 
118
+ #: limit-login-attempts.php:717
119
  msgid "Options changed"
120
  msgstr ""
121
 
122
+ #: limit-login-attempts.php:728
123
+ msgid "<strong>NOTE:</strong> Only works in Wordpress 2.7 or later"
124
  msgstr ""
125
 
126
+ #: limit-login-attempts.php:741
127
  msgid "Limit Login Attempts Settings"
128
  msgstr ""
129
 
130
+ #: limit-login-attempts.php:742
131
  msgid "Statistics"
132
  msgstr ""
133
 
134
+ #: limit-login-attempts.php:746
135
  msgid "Total lockouts"
136
  msgstr ""
137
 
138
+ #: limit-login-attempts.php:749
139
  msgid "Reset Counter"
140
  msgstr ""
141
 
142
+ #: limit-login-attempts.php:750
143
  #, php-format
144
  msgid "%d lockout since last reset"
145
  msgid_plural "%d lockouts since last reset"
146
  msgstr[0] ""
147
  msgstr[1] ""
148
 
149
+ #: limit-login-attempts.php:751
150
  msgid "No lockouts yet"
151
  msgstr ""
152
 
153
+ #: limit-login-attempts.php:756
154
  msgid "Active lockouts"
155
  msgstr ""
156
 
157
+ #: limit-login-attempts.php:758
158
  msgid "Restore Lockouts"
159
  msgstr ""
160
 
161
+ #: limit-login-attempts.php:759
162
  #, php-format
163
  msgid "%d IP is currently blocked from trying to log in"
164
  msgstr ""
165
 
166
+ #: limit-login-attempts.php:769
167
  msgid "Lockout"
168
  msgstr ""
169
 
170
+ #: limit-login-attempts.php:771
171
  msgid "allowed retries"
172
  msgstr ""
173
 
174
+ #: limit-login-attempts.php:772
175
  msgid "minutes lockout"
176
  msgstr ""
177
 
178
+ #: limit-login-attempts.php:773
179
  msgid "lockouts increase lockout time to"
180
  msgstr ""
181
 
182
+ #: limit-login-attempts.php:773
183
  msgid "hours"
184
  msgstr ""
185
 
186
+ #: limit-login-attempts.php:774
187
  msgid "hours until retries are reset"
188
  msgstr ""
189
 
190
+ #: limit-login-attempts.php:778
191
  msgid "Handle cookie login"
192
  msgstr ""
193
 
194
+ #: limit-login-attempts.php:780
195
  msgid "Yes"
196
  msgstr ""
197
 
198
+ #: limit-login-attempts.php:780
199
  msgid "No"
200
  msgstr ""
201
 
202
+ #: limit-login-attempts.php:785
203
  msgid "Notify on lockout"
204
  msgstr ""
205
 
206
+ #: limit-login-attempts.php:787
207
  msgid "Log IP"
208
  msgstr ""
209
 
210
+ #: limit-login-attempts.php:788
211
  msgid "Email to admin after"
212
  msgstr ""
213
 
214
+ #: limit-login-attempts.php:788
215
  msgid "lockouts"
216
  msgstr ""
217
 
218
+ #: limit-login-attempts.php:793
219
  msgid "Change Options"
220
  msgstr ""
221
 
222
+ #: limit-login-attempts.php:801
223
  msgid "Lockout log"
224
  msgstr ""
225
 
226
+ #: limit-login-attempts.php:805
227
  msgid "Clear Log"
228
  msgstr ""
229
 
readme.txt CHANGED
@@ -3,7 +3,7 @@ Contributors: johanee
3
  Tags: login, security, authentication
4
  Requires at least: 2.5
5
  Tested up to: 2.7
6
- Stable tag: 1.1
7
 
8
  Limit rate of login attempts, including by way of cookies, for each IP.
9
 
@@ -22,7 +22,7 @@ Features
22
  * Informs user about remaining retries or lockout time on login page
23
  * Optional logging, optional email notification
24
 
25
- Of possible note: when cookie login handling is activated plugin overrides the pluggable function wp_get_current_user, which might collide with others wanting to do the same. If you know of any such plugins please contact me.
26
 
27
  == Installation ==
28
 
@@ -30,26 +30,26 @@ Of possible note: when cookie login handling is activated plugin overrides the p
30
  2. Activate the plugin through the WordPress admin interface.
31
  3. Customize the settings from the options page, if desired.
32
 
33
- == Frequently Asked Questions ==
34
-
35
- = What do I do if I get a notice that it was unable to replace wp_get_current_user()? =
36
-
37
- This means another plugin or modification is already replacing this pluggable function (I do not yet know of any that do). Mail me with details about your plugins and we'll sort it out.
38
 
39
  == Screenshots ==
40
 
41
  1. Loginscreen after failed login with retries remaining
42
- 2. Loginscreen after failed login during lockout
43
  3. Administration interface in WordPress 2.7
44
  4. Administration interface in WordPress 2.5
45
 
46
-
47
  == Version History ==
48
 
 
 
 
 
 
49
  * Version 1.1
50
  * Added translation support
51
  * Added Swedish translation
52
- * During lockout, filter out all other login errors.
53
  * Minor cleanups
54
  * Version 1.0
55
  * Initial version
3
  Tags: login, security, authentication
4
  Requires at least: 2.5
5
  Tested up to: 2.7
6
+ Stable tag: 1.2
7
 
8
  Limit rate of login attempts, including by way of cookies, for each IP.
9
 
22
  * Informs user about remaining retries or lockout time on login page
23
  * Optional logging, optional email notification
24
 
25
+ Note: Cookie handling reimplemented without replacing pluggable function. Plugin now using standard actions and filters only.
26
 
27
  == Installation ==
28
 
30
  2. Activate the plugin through the WordPress admin interface.
31
  3. Customize the settings from the options page, if desired.
32
 
33
+ If you have any questions or problems please make a post here: http://wordpress.org/tags/limit-login-attempts
 
 
 
 
34
 
35
  == Screenshots ==
36
 
37
  1. Loginscreen after failed login with retries remaining
38
+ 2. Loginscreen during lockout
39
  3. Administration interface in WordPress 2.7
40
  4. Administration interface in WordPress 2.5
41
 
 
42
  == Version History ==
43
 
44
+ * Version 1.2
45
+ * No longer replaces pluggable function when cookie handling active. Re-implemented using available actions and filters
46
+ * Filter error messages during login to avoid information leak regarding available usernames
47
+ * Do not show retries or lockout messages except for login (registration, lost password pages). No change in actual enforcement
48
+ * Slightly more aggressive in trimming old retries data
49
  * Version 1.1
50
  * Added translation support
51
  * Added Swedish translation
52
+ * During lockout, filter out all other login errors
53
  * Minor cleanups
54
  * Version 1.0
55
  * Initial version
screenshot-1.gif CHANGED
Binary file
screenshot-4.gif CHANGED
Binary file