Skip to content

Commit 49424df

Browse files
authored
waf lock utility integration with Modsec (microsoft#35)
change permission, alignment issue, revet to original api revert owner back, will remove later change to snake style
1 parent c71425a commit 49424df

File tree

13 files changed

+175
-209
lines changed

13 files changed

+175
-209
lines changed

apache2/apache2_config.c

100644100755
File mode changed.

apache2/apache2_util.c

100644100755
Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919

2020
#ifdef WAF_JSON_LOGGING_ENABLE
2121
#include "waf_log_util_external.h"
22+
#include "waf_lock_external.h"
2223
#include "string.h"
2324
#endif
2425

@@ -289,24 +290,24 @@ static void get_ruleset_type_version(char* waf_ruleset_info, char* waf_ruleset_t
289290
}
290291
}
291292

292-
static int write_file_with_lock(apr_global_mutex_t* lock, apr_file_t* fd, char* str) {
293+
static int write_file_with_lock(struct waf_lock* lock, apr_file_t* fd, char* str) {
293294
int rc;
294295
apr_size_t nbytes, nbytes_written;
295296

296297
if (lock == NULL || fd == NULL || str == NULL) {
297298
return WAF_LOG_UTIL_FAILED;
298299
}
299300

300-
rc = apr_global_mutex_lock(lock);
301-
if (rc != APR_SUCCESS) {
301+
rc = waf_get_exclusive_lock(lock);
302+
if (waf_lock_is_error(rc)) {
302303
return WAF_LOG_UTIL_FAILED;
303304
}
304305

305306
nbytes = strlen(str);
306307
apr_file_write_full(fd, str, nbytes, &nbytes_written);
307308

308-
rc = apr_global_mutex_unlock(lock);
309-
if (rc != APR_SUCCESS) {
309+
rc = waf_free_exclusive_lock(lock);
310+
if (waf_lock_is_error(rc)) {
310311
return WAF_LOG_UTIL_FAILED;
311312
}
312313

@@ -316,7 +317,7 @@ static int write_file_with_lock(apr_global_mutex_t* lock, apr_file_t* fd, char*
316317
/**
317318
* send all waf fields in json format to a file.
318319
*/
319-
static void send_waf_log(apr_global_mutex_t* lock, apr_file_t* fd, const char* str1, const char* ip_port, const char* uri, int mode, const char* hostname, request_rec *r) {
320+
static void send_waf_log(struct waf_lock* lock, apr_file_t* fd, const char* str1, const char* ip_port, const char* uri, int mode, const char* hostname, request_rec *r) {
320321
int rc = 0;
321322
char* json_str;
322323
char waf_filename[1024] = "";

apache2/mod_security2.c

100644100755
File mode changed.

apache2/modsecurity.c

100644100755
Lines changed: 84 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -135,13 +135,47 @@ msc_engine *modsecurity_create(apr_pool_t *mp, int processing_mode) {
135135
return msce;
136136
}
137137

138+
static void set_lock_args(struct waf_lock_args *lock_args, int lock_id) {
139+
if (lock_args == NULL) {
140+
return;
141+
}
142+
143+
#ifdef _WIN32
144+
switch(lock_id) {
145+
case AUDITLOG_LOCK_ID:
146+
lock_args->lock_name = AUDITLOG_LOCK_NAME;
147+
lock_args->lock_name_length = strlen(AUDITLOG_LOCK_NAME);
148+
break;
149+
case WAFJSONLOG_LOCK_ID:
150+
lock_args->lock_name = WAFJSONLOG_LOCK_NAME;
151+
lock_args->lock_name_length = strlen(WAFJSONLOG_LOCK_NAME);
152+
break;
153+
case GEO_LOCK_ID:
154+
lock_args->lock_name = GEO_LOCK_NAME;
155+
lock_args->lock_name_length = strlen(GEO_LOCK_NAME);
156+
break;
157+
case DBM_LOCK_ID:
158+
lock_args->lock_name = DBM_LOCK_NAME;
159+
lock_args->lock_name_length = strlen(DBM_LOCK_NAME);
160+
break;
161+
default:
162+
break;
163+
}
164+
165+
#else
166+
lock_args->lock_id = lock_id;
167+
#endif
168+
}
169+
138170
/**
139171
* Initialise the modsecurity engine. This function must be invoked
140172
* after configuration processing is complete as Apache needs to know the
141173
* username it is running as.
142174
*/
143175
int modsecurity_init(msc_engine *msce, apr_pool_t *mp) {
144176
apr_status_t rc;
177+
struct waf_lock_args *lock_args;
178+
char *lock_name;
145179

146180
/**
147181
* Notice that curl is initialized here but never cleaned up. First version
@@ -153,85 +187,51 @@ int modsecurity_init(msc_engine *msce, apr_pool_t *mp) {
153187
#ifdef WITH_CURL
154188
curl_global_init(CURL_GLOBAL_ALL);
155189
#endif
190+
lock_args = apr_pcalloc(mp, sizeof(struct waf_lock_args));
191+
156192
/* Serial audit log mutext */
157-
rc = apr_global_mutex_create(&msce->auditlog_lock, NULL, APR_LOCK_DEFAULT, mp);
158-
if (rc != APR_SUCCESS) {
193+
set_lock_args(lock_args, AUDITLOG_LOCK_ID);
194+
195+
msce->auditlog_lock = apr_pcalloc(mp, sizeof(struct waf_lock));
196+
rc = waf_create_lock(msce->auditlog_lock, lock_args);
197+
if (waf_lock_is_error(rc)) {
159198
//ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, "mod_security: Could not create modsec_auditlog_lock");
160199
//return HTTP_INTERNAL_SERVER_ERROR;
161200
return -1;
162201
}
163202

164203
#ifdef WAF_JSON_LOGGING_ENABLE
165204
/* Serial wafjson log mutext */
166-
rc = apr_global_mutex_create(&msce->wafjsonlog_lock, NULL, APR_LOCK_DEFAULT, mp);
167-
if (rc != APR_SUCCESS) {
205+
set_lock_args(lock_args, WAFJSONLOG_LOCK_ID);
206+
207+
msce->wafjsonlog_lock = apr_pcalloc(mp, sizeof(struct waf_lock));
208+
rc = waf_create_lock(msce->wafjsonlog_lock, lock_args);
209+
if (waf_lock_is_error(rc)) {
168210
//ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, "mod_security: Could not create modsec_wafjsonlog_lock");
169211
//return HTTP_INTERNAL_SERVER_ERROR;
170212
return -1;
171213
}
172214
#endif
173215

174-
#if !defined(MSC_TEST)
175-
#ifdef __SET_MUTEX_PERMS
176-
#if AP_SERVER_MAJORVERSION_NUMBER > 1 && AP_SERVER_MINORVERSION_NUMBER > 2
177-
rc = ap_unixd_set_global_mutex_perms(msce->auditlog_lock);
178-
#else
179-
rc = unixd_set_global_mutex_perms(msce->auditlog_lock);
180-
#endif
181-
if (rc != APR_SUCCESS) {
182-
// ap_log_error(APLOG_MARK, APLOG_ERR, rc, s, "mod_security: Could not set permissions on modsec_auditlog_lock; check User and Group directives");
183-
// return HTTP_INTERNAL_SERVER_ERROR;
184-
return -1;
185-
}
186-
#endif /* SET_MUTEX_PERMS */
187-
188-
#ifdef WAF_JSON_LOGGING_ENABLE
189-
#ifdef __SET_MUTEX_PERMS
190-
#if AP_SERVER_MAJORVERSION_NUMBER > 1 && AP_SERVER_MINORVERSION_NUMBER > 2
191-
rc = ap_unixd_set_global_mutex_perms(msce->wafjsonlog_lock);
192-
#else
193-
rc = unixd_set_global_mutex_perms(msce->wafjsonlog_lock);
194-
#endif
195-
if (rc != APR_SUCCESS) {
196-
// ap_log_error(APLOG_MARK, APLOG_ERR, rc, s, "mod_security: Could not set permissions on modsec_wafjsonlog_lock; check User and Group directives");
197-
// return HTTP_INTERNAL_SERVER_ERROR;
198-
return -1;
199-
}
200-
#endif /* SET_MUTEX_PERMS */
201-
#endif
216+
// Have removed all the lock permission related code since we implment in different way now
202217

203-
rc = apr_global_mutex_create(&msce->geo_lock, NULL, APR_LOCK_DEFAULT, mp);
204-
if (rc != APR_SUCCESS) {
205-
return -1;
206-
}
218+
#if !defined(MSC_TEST)
219+
set_lock_args(lock_args, GEO_LOCK_ID);
207220

208-
#ifdef __SET_MUTEX_PERMS
209-
#if AP_SERVER_MAJORVERSION_NUMBER > 1 && AP_SERVER_MINORVERSION_NUMBER > 2
210-
rc = ap_unixd_set_global_mutex_perms(msce->geo_lock);
211-
#else
212-
rc = unixd_set_global_mutex_perms(msce->geo_lock);
213-
#endif
214-
if (rc != APR_SUCCESS) {
221+
msce->geo_lock = apr_pcalloc(mp, sizeof(struct waf_lock));
222+
rc = waf_create_lock(msce->geo_lock, lock_args);
223+
if (waf_lock_is_error(rc)) {
215224
return -1;
216225
}
217-
#endif /* SET_MUTEX_PERMS */
218226

219227
#ifdef GLOBAL_COLLECTION_LOCK
220-
rc = apr_global_mutex_create(&msce->dbm_lock, NULL, APR_LOCK_DEFAULT, mp);
221-
if (rc != APR_SUCCESS) {
222-
return -1;
223-
}
228+
set_lock_args(lock_args, DBM_LOCK_ID);
224229

225-
#ifdef __SET_MUTEX_PERMS
226-
#if AP_SERVER_MAJORVERSION_NUMBER > 1 && AP_SERVER_MINORVERSION_NUMBER > 2
227-
rc = ap_unixd_set_global_mutex_perms(msce->dbm_lock);
228-
#else
229-
rc = unixd_set_global_mutex_perms(msce->dbm_lock);
230-
#endif
231-
if (rc != APR_SUCCESS) {
230+
msce->dbm_lock = apr_pcalloc(mp, sizeof(struct waf_lock));
231+
rc = waf_create_lock(msce->dbm_lock, lock_args);
232+
if (waf_lock_is_error(rc)) {
232233
return -1;
233234
}
234-
#endif /* SET_MUTEX_PERMS */
235235
#endif
236236
#endif
237237

@@ -242,39 +242,47 @@ int modsecurity_init(msc_engine *msce, apr_pool_t *mp) {
242242
* Performs per-child (new process) initialisation.
243243
*/
244244
void modsecurity_child_init(msc_engine *msce) {
245+
struct waf_lock_args *lock_args;
246+
char *lock_name;
247+
245248
/* Need to call this once per process before any other XML calls. */
246249
xmlInitParser();
250+
lock_args = apr_pcalloc(msce->mp, sizeof(struct waf_lock_args));
247251

248-
if (msce->auditlog_lock != NULL) {
249-
apr_status_t rc = apr_global_mutex_child_init(&msce->auditlog_lock, NULL, msce->mp);
250-
if (rc != APR_SUCCESS) {
251-
// ap_log_error(APLOG_MARK, APLOG_ERR, rs, s, "Failed to child-init auditlog mutex");
252-
}
252+
if (msce->auditlog_lock == NULL) {
253+
msce->auditlog_lock = apr_pcalloc(msce->mp, sizeof(struct waf_lock));
253254
}
254255

256+
set_lock_args(lock_args, AUDITLOG_LOCK_ID);
257+
258+
waf_create_lock(msce->auditlog_lock, lock_args);
259+
255260
#ifdef WAF_JSON_LOGGING_ENABLE
256-
if (msce->wafjsonlog_lock != NULL) {
257-
apr_status_t rc = apr_global_mutex_child_init(&msce->wafjsonlog_lock, NULL, msce->mp);
258-
if (rc != APR_SUCCESS) {
259-
// ap_log_error(APLOG_MARK, APLOG_ERR, rs, s, "Failed to child-init auditlog mutex");
260-
}
261+
if (msce->wafjsonlog_lock == NULL) {
262+
msce->wafjsonlog_lock = apr_pcalloc(msce->mp, sizeof(struct waf_lock));
261263
}
264+
265+
set_lock_args(lock_args, WAFJSONLOG_LOCK_ID);
266+
267+
waf_create_lock(msce->wafjsonlog_lock, lock_args);
262268
#endif
263269

264-
if (msce->geo_lock != NULL) {
265-
apr_status_t rc = apr_global_mutex_child_init(&msce->geo_lock, NULL, msce->mp);
266-
if (rc != APR_SUCCESS) {
267-
// ap_log_error(APLOG_MARK, APLOG_ERR, rs, s, "Failed to child-init geo mutex");
268-
}
270+
if (msce->geo_lock == NULL) {
271+
msce->geo_lock = apr_pcalloc(msce->mp, sizeof(struct waf_lock));
269272
}
270273

274+
set_lock_args(lock_args, GEO_LOCK_ID);
275+
276+
waf_create_lock(msce->geo_lock, lock_args);
277+
271278
#ifdef GLOBAL_COLLECTION_LOCK
272-
if (msce->dbm_lock != NULL) {
273-
apr_status_t rc = apr_global_mutex_child_init(&msce->dbm_lock, NULL, msce->mp);
274-
if (rc != APR_SUCCESS) {
275-
// ap_log_error(APLOG_MARK, APLOG_ERR, rs, s, "Failed to child-init dbm mutex");
276-
}
279+
if (msce->dbm_lock == NULL) {
280+
msce->dbm_lock = apr_pcalloc(msce->mp, sizeof(struct waf_lock));
277281
}
282+
283+
set_lock_args(lock_args, DBM_LOCK_ID);
284+
285+
waf_create_lock(msce->dbm_lock, lock_args);
278286
#endif
279287

280288
}

apache2/modsecurity.h

100644100755
Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ typedef struct msc_parm msc_parm;
5656
#include "http_config.h"
5757
#include "http_log.h"
5858
#include "http_protocol.h"
59+
#include "waf_lock_external.h"
5960

6061
#if defined(WITH_LUA)
6162
#include "msc_lua.h"
@@ -173,6 +174,16 @@ extern DSOLOCAL char *msc_waf_instanceId;
173174
extern DSOLOCAL char *msc_waf_lock_owner;
174175
#endif
175176

177+
#define AUDITLOG_LOCK_ID 1
178+
#define WAFJSONLOG_LOCK_ID 2
179+
#define GEO_LOCK_ID 3
180+
#define DBM_LOCK_ID 4
181+
182+
#define AUDITLOG_LOCK_NAME "Global\\auditlog_lock"
183+
#define WAFJSONLOG_LOCK_NAME "Global\\wafjsonlog_lock"
184+
#define GEO_LOCK_NAME "Global\\geo_lock"
185+
#define DBM_LOCK_NAME "Global\\dbm_lock"
186+
176187
#define RESBODY_STATUS_NOT_READ 0 /* we were not configured to read the body */
177188
#define RESBODY_STATUS_ERROR 1 /* error occured while we were reading the body */
178189
#define RESBODY_STATUS_PARTIAL 2 /* partial body content available in the brigade */
@@ -674,13 +685,13 @@ struct error_message_t {
674685

675686
struct msc_engine {
676687
apr_pool_t *mp;
677-
apr_global_mutex_t *auditlog_lock;
688+
struct waf_lock *auditlog_lock;
678689
#ifdef WAF_JSON_LOGGING_ENABLE
679-
apr_global_mutex_t *wafjsonlog_lock;
690+
struct waf_lock *wafjsonlog_lock;
680691
#endif
681-
apr_global_mutex_t *geo_lock;
692+
struct waf_lock *geo_lock;
682693
#ifdef GLOBAL_COLLECTION_LOCK
683-
apr_global_mutex_t *dbm_lock;
694+
struct waf_lock *dbm_lock;
684695
#endif
685696
msre_engine *msre;
686697
unsigned int processing_mode;

apache2/msc_geo.c

100644100755
Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
*/
1414

1515
#include "msc_geo.h"
16+
#include "waf_lock_external.h"
1617

1718

1819
/* -- Lookup Tables -- */
@@ -315,8 +316,8 @@ int geo_lookup(modsec_rec *msr, geo_rec *georec, const char *target, char **erro
315316
msr_log(msr, 9, "GEO: Using address \"%s\" (0x%08lx). %lu", targetip, ipnum, ipnum);
316317
}
317318

318-
ret = apr_global_mutex_lock(msr->modsecurity->geo_lock);
319-
if (ret != APR_SUCCESS) {
319+
ret = waf_get_exclusive_lock(msr->modsecurity->geo_lock);
320+
if (waf_lock_is_error(ret)) {
320321
msr_log(msr, 1, "Geo Lookup: Failed to lock proc mutex: %s",
321322
get_apr_error(msr->mp, ret));
322323
}
@@ -352,8 +353,8 @@ int geo_lookup(modsec_rec *msr, geo_rec *georec, const char *target, char **erro
352353
*error_msg = apr_psprintf(msr->mp, "No geo data for \"%s\").", log_escape(msr->mp, target));
353354
msr_log(msr, 4, "%s", *error_msg);
354355

355-
ret = apr_global_mutex_unlock(msr->modsecurity->geo_lock);
356-
if (ret != APR_SUCCESS) {
356+
ret = waf_free_exclusive_lock(msr->modsecurity->geo_lock);
357+
if (waf_lock_is_error(ret)) {
357358
msr_log(msr, 1, "Geo Lookup: Failed to lock proc mutex: %s",
358359
get_apr_error(msr->mp, ret));
359360
}
@@ -368,8 +369,8 @@ int geo_lookup(modsec_rec *msr, geo_rec *georec, const char *target, char **erro
368369
*error_msg = apr_psprintf(msr->mp, "No geo data for \"%s\" (country %d).", log_escape(msr->mp, target), country);
369370
msr_log(msr, 4, "%s", *error_msg);
370371

371-
ret = apr_global_mutex_unlock(msr->modsecurity->geo_lock);
372-
if (ret != APR_SUCCESS) {
372+
ret = waf_free_exclusive_lock(msr->modsecurity->geo_lock);
373+
if (waf_lock_is_error(ret)) {
373374
msr_log(msr, 1, "Geo Lookup: Failed to lock proc mutex: %s",
374375
get_apr_error(msr->mp, ret));
375376
}
@@ -399,8 +400,8 @@ int geo_lookup(modsec_rec *msr, geo_rec *georec, const char *target, char **erro
399400
*error_msg = apr_psprintf(msr->mp, "No geo data for \"%s\" (country %d).", log_escape(msr->mp, target), country);
400401
msr_log(msr, 4, "%s", *error_msg);
401402

402-
ret = apr_global_mutex_unlock(msr->modsecurity->geo_lock);
403-
if (ret != APR_SUCCESS) {
403+
ret = waf_free_exclusive_lock(msr->modsecurity->geo_lock);
404+
if (waf_lock_is_error(ret)) {
404405
msr_log(msr, 1, "Geo Lookup: Failed to lock proc mutex: %s",
405406
get_apr_error(msr->mp, ret));
406407
}
@@ -494,8 +495,8 @@ int geo_lookup(modsec_rec *msr, geo_rec *georec, const char *target, char **erro
494495

495496
*error_msg = apr_psprintf(msr->mp, "Geo lookup for \"%s\" succeeded.", log_escape(msr->mp, target));
496497

497-
ret = apr_global_mutex_unlock(msr->modsecurity->geo_lock);
498-
if (ret != APR_SUCCESS) {
498+
ret = waf_free_exclusive_lock(msr->modsecurity->geo_lock);
499+
if (waf_lock_is_error(ret)) {
499500
msr_log(msr, 1, "Geo Lookup: Failed to lock proc mutex: %s",
500501
get_apr_error(msr->mp, ret));
501502
}

0 commit comments

Comments
 (0)