ruby-lsapi 4.4 → 5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/ext/lsapi/lsapidef.h +13 -13
- data/ext/lsapi/lsapilib.c +838 -197
- data/ext/lsapi/lsapilib.h +61 -16
- data/ext/lsapi/lsruby.c +35 -4
- data/lsapi.gemspec +2 -2
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: d4a6919e0d321057af7cf14393996e0363f79078d81f7246bc763c6111f9b4fa
|
4
|
+
data.tar.gz: fb8fbce714f668d4b974bccce18f48b384a491011d4e2172f3c8635e00f10cbf
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 673a3a93b519d8d54171ff6430970669c8ad23fa023ff8f1a3f774b446b54f171a8027a89c2f6c4acd5d0a7c00f394d225d8d58736accb5b528f731a50b285be
|
7
|
+
data.tar.gz: bc5907c83c66ed42af04b60ef5977dc01603e2c210fb5d36b8904303193a6ae537213ae9a1c92ada2a9f89efb873bf470525ae2357edf215d8f2db308b1d80cb
|
data/ext/lsapi/lsapidef.h
CHANGED
@@ -1,21 +1,21 @@
|
|
1
1
|
/*
|
2
|
-
Copyright (c) 2002-
|
2
|
+
Copyright (c) 2002-2018, Lite Speed Technologies Inc.
|
3
3
|
All rights reserved.
|
4
4
|
|
5
5
|
Redistribution and use in source and binary forms, with or without
|
6
6
|
modification, are permitted provided that the following conditions are
|
7
|
-
met:
|
7
|
+
met:
|
8
8
|
|
9
9
|
* Redistributions of source code must retain the above copyright
|
10
|
-
notice, this list of conditions and the following disclaimer.
|
10
|
+
notice, this list of conditions and the following disclaimer.
|
11
11
|
* Redistributions in binary form must reproduce the above
|
12
12
|
copyright notice, this list of conditions and the following
|
13
13
|
disclaimer in the documentation and/or other materials provided
|
14
|
-
with the distribution.
|
14
|
+
with the distribution.
|
15
15
|
* Neither the name of the Lite Speed Technologies Inc nor the
|
16
16
|
names of its contributors may be used to endorse or promote
|
17
17
|
products derived from this software without specific prior
|
18
|
-
written permission.
|
18
|
+
written permission.
|
19
19
|
|
20
20
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
21
21
|
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
@@ -27,7 +27,7 @@ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
27
27
|
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
28
28
|
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
29
29
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
30
|
-
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
30
|
+
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
31
31
|
*/
|
32
32
|
|
33
33
|
|
@@ -76,7 +76,7 @@ enum
|
|
76
76
|
|
77
77
|
/* Values for m_flag in lsapi_packet_header */
|
78
78
|
#define LSAPI_ENDIAN_LITTLE 0
|
79
|
-
#define LSAPI_ENDIAN_BIG 1
|
79
|
+
#define LSAPI_ENDIAN_BIG 1
|
80
80
|
#define LSAPI_ENDIAN_BIT 1
|
81
81
|
|
82
82
|
#if defined(__i386__)||defined( __x86_64 )||defined( __x86_64__ )
|
@@ -119,7 +119,7 @@ struct lsapi_packet_header
|
|
119
119
|
|
120
120
|
/*
|
121
121
|
LSAPI request header packet
|
122
|
-
|
122
|
+
|
123
123
|
1. struct lsapi_req_header
|
124
124
|
2. struct lsapi_http_header_index
|
125
125
|
3. lsapi_header_offset * unknownHeaders
|
@@ -130,7 +130,7 @@ struct lsapi_packet_header
|
|
130
130
|
struct lsapi_req_header
|
131
131
|
{
|
132
132
|
struct lsapi_packet_header m_pktHeader;
|
133
|
-
|
133
|
+
|
134
134
|
int32_t m_httpHeaderLen;
|
135
135
|
int32_t m_reqBodyLen;
|
136
136
|
int32_t m_scriptFileOff; /* path to the script file. */
|
@@ -144,11 +144,11 @@ struct lsapi_req_header
|
|
144
144
|
|
145
145
|
|
146
146
|
struct lsapi_http_header_index
|
147
|
-
{
|
148
|
-
|
147
|
+
{
|
148
|
+
uint16_t m_headerLen[H_TRANSFER_ENCODING+1];
|
149
149
|
int32_t m_headerOff[H_TRANSFER_ENCODING+1];
|
150
|
-
} ;
|
151
|
-
|
150
|
+
} ;
|
151
|
+
|
152
152
|
struct lsapi_header_offset
|
153
153
|
{
|
154
154
|
int32_t nameOff;
|
data/ext/lsapi/lsapilib.c
CHANGED
@@ -1,5 +1,6 @@
|
|
1
|
+
//#define LSAPI_DEBUG
|
1
2
|
/*
|
2
|
-
Copyright (c) 2002-
|
3
|
+
Copyright (c) 2002-2018, Lite Speed Technologies Inc.
|
3
4
|
All rights reserved.
|
4
5
|
|
5
6
|
Redistribution and use in source and binary forms, with or without
|
@@ -37,9 +38,11 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
37
38
|
#include <fcntl.h>
|
38
39
|
#include <limits.h>
|
39
40
|
#include <sys/stat.h>
|
41
|
+
#include <sched.h>
|
40
42
|
#include <signal.h>
|
41
43
|
#include <stdlib.h>
|
42
44
|
#include <stdio.h>
|
45
|
+
#include <stdarg.h>
|
43
46
|
#include <string.h>
|
44
47
|
#include <sys/mman.h>
|
45
48
|
#include <sys/resource.h>
|
@@ -94,18 +97,26 @@ typedef struct lsapi_MD5Context lsapi_MD5_CTX;
|
|
94
97
|
#define LSAPI_ST_REQ_BODY 2
|
95
98
|
#define LSAPI_ST_RESP_HEADER 4
|
96
99
|
#define LSAPI_ST_RESP_BODY 8
|
100
|
+
#define LSAPI_ST_BACKGROUND 16
|
97
101
|
|
98
102
|
#define LSAPI_RESP_BUF_SIZE 8192
|
99
103
|
#define LSAPI_INIT_RESP_HEADER_LEN 4096
|
100
104
|
|
101
|
-
|
105
|
+
enum
|
106
|
+
{
|
107
|
+
LSAPI_STATE_IDLE,
|
108
|
+
LSAPI_STATE_CONNECTED,
|
109
|
+
LSAPI_STATE_ACCEPTING,
|
110
|
+
};
|
111
|
+
|
112
|
+
typedef struct lsapi_child_status
|
102
113
|
{
|
103
114
|
int m_pid;
|
104
115
|
long m_tmStart;
|
105
116
|
|
106
117
|
volatile short m_iKillSent;
|
107
118
|
volatile char m_inProcess;
|
108
|
-
volatile char
|
119
|
+
volatile char m_state;
|
109
120
|
volatile int m_iReqCounter;
|
110
121
|
|
111
122
|
volatile long m_tmWaitBegin;
|
@@ -114,28 +125,43 @@ typedef struct _lsapi_child_status
|
|
114
125
|
}
|
115
126
|
lsapi_child_status;
|
116
127
|
|
117
|
-
static lsapi_child_status *
|
128
|
+
static lsapi_child_status * s_worker_status = NULL;
|
118
129
|
|
119
130
|
static int g_inited = 0;
|
120
131
|
static int g_running = 1;
|
121
132
|
static int s_ppid;
|
133
|
+
static int s_restored_ppid = 0;
|
134
|
+
static int s_pid = 0;
|
122
135
|
static int s_slow_req_msecs = 0;
|
123
136
|
static int s_keepListener = 0;
|
124
137
|
static int s_dump_debug_info = 0;
|
125
138
|
static int s_pid_dump_debug_info = 0;
|
139
|
+
static int s_req_processed = 0;
|
140
|
+
static int s_skip_write = 0;
|
141
|
+
static int (*pthread_atfork_func)(void (*prepare)(void), void (*parent)(void),
|
142
|
+
void (*child)(void)) = NULL;
|
126
143
|
|
127
144
|
static int *s_busy_workers = NULL;
|
128
|
-
static int
|
129
|
-
|
130
|
-
|
145
|
+
static int *s_accepting_workers = NULL;
|
146
|
+
static int *s_global_counter = &s_req_processed;
|
147
|
+
static int s_max_busy_workers = -1;
|
148
|
+
static char *s_stderr_log_path = NULL;
|
149
|
+
static int s_stderr_is_pipe = 0;
|
150
|
+
static int s_ignore_pid = -1;
|
151
|
+
static size_t s_total_pages = 1;
|
152
|
+
static size_t s_min_avail_pages = 256 * 1024;
|
153
|
+
static size_t *s_avail_pages = &s_total_pages;
|
154
|
+
|
155
|
+
LSAPI_Request g_req =
|
156
|
+
{ .m_fdListen = -1, .m_fd = -1 };
|
131
157
|
|
132
158
|
static char s_secret[24];
|
133
|
-
|
159
|
+
|
160
|
+
static LSAPI_On_Timer_pf s_proc_group_timer_cb = NULL;
|
134
161
|
|
135
162
|
void Flush_RespBuf_r( LSAPI_Request * pReq );
|
136
163
|
static int lsapi_reopen_stderr(const char *p);
|
137
164
|
|
138
|
-
|
139
165
|
static const char *CGI_HEADERS[H_TRANSFER_ENCODING+1] =
|
140
166
|
{
|
141
167
|
"HTTP_ACCEPT", "HTTP_ACCEPT_CHARSET",
|
@@ -188,9 +214,95 @@ static int HTTP_HEADER_LEN[H_TRANSFER_ENCODING+1] =
|
|
188
214
|
13,17, 8, 13, 8, 19, 10, 5, 15, 3, 17
|
189
215
|
};
|
190
216
|
|
217
|
+
|
218
|
+
static const char *s_log_level_names[8] =
|
219
|
+
{
|
220
|
+
"", "DEBUG","INFO", "NOTICE", "WARN", "ERROR", "CRIT", "FATAL"
|
221
|
+
};
|
222
|
+
|
223
|
+
|
224
|
+
void LSAPI_Log(int flag, const char * fmt, ...)
|
225
|
+
{
|
226
|
+
char buf[1024];
|
227
|
+
char *p = buf;
|
228
|
+
if ((flag & LSAPI_LOG_TIMESTAMP_BITS) &&
|
229
|
+
!((flag & LSAPI_LOG_TIMESTAMP_STDERR) && s_stderr_is_pipe))
|
230
|
+
{
|
231
|
+
struct timeval tv;
|
232
|
+
struct tm tm;
|
233
|
+
gettimeofday(&tv, NULL);
|
234
|
+
localtime_r(&tv.tv_sec, &tm);
|
235
|
+
if (flag & LSAPI_LOG_TIMESTAMP_FULL)
|
236
|
+
{
|
237
|
+
p += snprintf(p, 1024, "%04d-%02d-%02d %02d:%02d:%02d.%06d ",
|
238
|
+
tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday,
|
239
|
+
tm.tm_hour, tm.tm_min, tm.tm_sec, (int)tv.tv_usec);
|
240
|
+
}
|
241
|
+
else if (flag & LSAPI_LOG_TIMESTAMP_HMS)
|
242
|
+
{
|
243
|
+
p += snprintf(p, 1024, "%02d:%02d:%02d ",
|
244
|
+
tm.tm_hour, tm.tm_min, tm.tm_sec);
|
245
|
+
}
|
246
|
+
}
|
247
|
+
|
248
|
+
int level = flag & LSAPI_LOG_LEVEL_BITS;
|
249
|
+
if (level && level <= LSAPI_LOG_FLAG_FATAL)
|
250
|
+
{
|
251
|
+
p += snprintf(p, 100, "[%s] ", s_log_level_names[level]);
|
252
|
+
}
|
253
|
+
|
254
|
+
if (flag & LSAPI_LOG_PID)
|
255
|
+
{
|
256
|
+
p += snprintf(p, 100, "[%d] ", s_pid);
|
257
|
+
}
|
258
|
+
|
259
|
+
if (p > buf)
|
260
|
+
fprintf(stderr, "%.*s", (int)(p - buf), buf);
|
261
|
+
va_list ap;
|
262
|
+
va_start(ap, fmt);
|
263
|
+
vfprintf(stderr, fmt, ap);
|
264
|
+
va_end(ap);
|
265
|
+
}
|
266
|
+
|
267
|
+
#ifdef LSAPI_DEBUG
|
268
|
+
|
269
|
+
#define DBGLOG_FLAG (LSAPI_LOG_TIMESTAMP_FULL|LSAPI_LOG_FLAG_DEBUG|LSAPI_LOG_PID)
|
270
|
+
#define lsapi_dbg(...) LSAPI_Log(DBGLOG_FLAG, __VA_ARGS__)
|
271
|
+
|
272
|
+
#else
|
273
|
+
|
274
|
+
#define lsapi_dbg(...)
|
275
|
+
|
276
|
+
#endif
|
277
|
+
|
278
|
+
#define lsapi_log(...) LSAPI_Log(LSAPI_LOG_TIMESTAMP_FULL|LSAPI_LOG_TIMESTAMP_STDERR|LSAPI_LOG_PID, __VA_ARGS__)
|
279
|
+
|
280
|
+
|
281
|
+
static int lsapi_parent_dead()
|
282
|
+
{
|
283
|
+
// Return non-zero if the parent is dead. 0 if still alive.
|
284
|
+
if (!s_ppid) {
|
285
|
+
// not checking, so not dead
|
286
|
+
return(0);
|
287
|
+
}
|
288
|
+
if (s_restored_ppid) {
|
289
|
+
if (kill(s_restored_ppid,0) == -1) {
|
290
|
+
if (errno == EPERM) {
|
291
|
+
return(0); // no permission, but it's still there.
|
292
|
+
}
|
293
|
+
return(1); // Dead
|
294
|
+
}
|
295
|
+
return(0); // it worked, so it's not dead
|
296
|
+
}
|
297
|
+
return(s_ppid != getppid());
|
298
|
+
}
|
299
|
+
|
300
|
+
|
191
301
|
static void lsapi_sigpipe( int sig )
|
192
302
|
{
|
193
303
|
}
|
304
|
+
|
305
|
+
|
194
306
|
static void lsapi_siguser1( int sig )
|
195
307
|
{
|
196
308
|
g_running = 0;
|
@@ -254,6 +366,7 @@ static inline void lsapi_buildPacketHeader( struct lsapi_packet_header * pHeader
|
|
254
366
|
pHeader->m_packetLen.m_iLen = len;
|
255
367
|
}
|
256
368
|
|
369
|
+
|
257
370
|
static int lsapi_set_nblock( int fd, int nonblock )
|
258
371
|
{
|
259
372
|
int val = fcntl( fd, F_GETFL, 0 );
|
@@ -274,6 +387,7 @@ static int lsapi_set_nblock( int fd, int nonblock )
|
|
274
387
|
return 0;
|
275
388
|
}
|
276
389
|
|
390
|
+
|
277
391
|
static int lsapi_close( int fd )
|
278
392
|
{
|
279
393
|
int ret;
|
@@ -295,9 +409,9 @@ static void lsapi_close_connection(LSAPI_Request *pReq)
|
|
295
409
|
pReq->m_fd = -1;
|
296
410
|
if (s_busy_workers)
|
297
411
|
__sync_fetch_and_sub(s_busy_workers, 1);
|
298
|
-
if (
|
299
|
-
|
300
|
-
}
|
412
|
+
if (s_worker_status)
|
413
|
+
__sync_lock_test_and_set(&s_worker_status->m_state, LSAPI_STATE_IDLE);
|
414
|
+
}
|
301
415
|
|
302
416
|
|
303
417
|
static inline ssize_t lsapi_read( int fd, void * pBuf, size_t len )
|
@@ -312,6 +426,7 @@ static inline ssize_t lsapi_read( int fd, void * pBuf, size_t len )
|
|
312
426
|
}
|
313
427
|
}
|
314
428
|
|
429
|
+
|
315
430
|
/*
|
316
431
|
static int lsapi_write( int fd, const void * pBuf, int len )
|
317
432
|
{
|
@@ -334,11 +449,16 @@ static int lsapi_write( int fd, const void * pBuf, int len )
|
|
334
449
|
}
|
335
450
|
*/
|
336
451
|
|
452
|
+
|
337
453
|
static int lsapi_writev( int fd, struct iovec ** pVec, int count, int totalLen )
|
338
454
|
{
|
339
455
|
int ret;
|
340
456
|
int left = totalLen;
|
341
457
|
int n = count;
|
458
|
+
|
459
|
+
if (s_skip_write)
|
460
|
+
return totalLen;
|
461
|
+
|
342
462
|
while(( left > 0 )&&g_running )
|
343
463
|
{
|
344
464
|
ret = writev( fd, *pVec, n );
|
@@ -378,6 +498,7 @@ static int lsapi_writev( int fd, struct iovec ** pVec, int count, int totalLen )
|
|
378
498
|
return totalLen - left;
|
379
499
|
}
|
380
500
|
|
501
|
+
|
381
502
|
/*
|
382
503
|
static int getTotalLen( struct iovec * pVec, int count )
|
383
504
|
{
|
@@ -392,6 +513,7 @@ static int getTotalLen( struct iovec * pVec, int count )
|
|
392
513
|
}
|
393
514
|
*/
|
394
515
|
|
516
|
+
|
395
517
|
static inline int allocateBuf( LSAPI_Request * pReq, int size )
|
396
518
|
{
|
397
519
|
char * pBuf = (char *)realloc( pReq->m_pReqBuf, size );
|
@@ -419,6 +541,7 @@ static int allocateIovec( LSAPI_Request * pReq, int n )
|
|
419
541
|
return 0;
|
420
542
|
}
|
421
543
|
|
544
|
+
|
422
545
|
static int allocateRespHeaderBuf( LSAPI_Request * pReq, int size )
|
423
546
|
{
|
424
547
|
char * p = (char *)realloc( pReq->m_pRespHeaderBuf, size );
|
@@ -450,6 +573,7 @@ static inline int verifyHeader( struct lsapi_packet_header * pHeader, char pktTy
|
|
450
573
|
return pHeader->m_packetLen.m_iLen;
|
451
574
|
}
|
452
575
|
|
576
|
+
|
453
577
|
static int allocateEnvList( struct LSAPI_key_value_pair ** pEnvList,
|
454
578
|
int *curSize, int newSize )
|
455
579
|
{
|
@@ -471,6 +595,7 @@ static int allocateEnvList( struct LSAPI_key_value_pair ** pEnvList,
|
|
471
595
|
|
472
596
|
}
|
473
597
|
|
598
|
+
|
474
599
|
static inline int isPipe( int fd )
|
475
600
|
{
|
476
601
|
char achPeer[128];
|
@@ -482,6 +607,7 @@ static inline int isPipe( int fd )
|
|
482
607
|
return 1;
|
483
608
|
}
|
484
609
|
|
610
|
+
|
485
611
|
static int parseEnv( struct LSAPI_key_value_pair * pEnvList, int count,
|
486
612
|
char **pBegin, char * pEnd )
|
487
613
|
{
|
@@ -518,6 +644,7 @@ static int parseEnv( struct LSAPI_key_value_pair * pEnvList, int count,
|
|
518
644
|
return 0;
|
519
645
|
}
|
520
646
|
|
647
|
+
|
521
648
|
static inline void swapIntEndian( int * pInteger )
|
522
649
|
{
|
523
650
|
char * p = (char *)pInteger;
|
@@ -531,6 +658,7 @@ static inline void swapIntEndian( int * pInteger )
|
|
531
658
|
|
532
659
|
}
|
533
660
|
|
661
|
+
|
534
662
|
static inline void fixEndian( LSAPI_Request * pReq )
|
535
663
|
{
|
536
664
|
struct lsapi_req_header *p= pReq->m_pHeader;
|
@@ -545,6 +673,7 @@ static inline void fixEndian( LSAPI_Request * pReq )
|
|
545
673
|
swapIntEndian( &p->m_cntSpecialEnv );
|
546
674
|
}
|
547
675
|
|
676
|
+
|
548
677
|
static void fixHeaderIndexEndian( LSAPI_Request * pReq )
|
549
678
|
{
|
550
679
|
int i;
|
@@ -633,7 +762,7 @@ static int (*fp_lve_leave)(struct liblve *, uint32_t *) = NULL;
|
|
633
762
|
static int (*fp_lve_jail)( struct passwd *, char *) = NULL;
|
634
763
|
static int lsapi_load_lve_lib(void)
|
635
764
|
{
|
636
|
-
s_liblve = dlopen("liblve.so.0",
|
765
|
+
s_liblve = dlopen("liblve.so.0", RTLD_NOW | RTLD_GLOBAL);
|
637
766
|
if (s_liblve)
|
638
767
|
{
|
639
768
|
fp_lve_is_available = dlsym(s_liblve, "lve_is_available");
|
@@ -644,10 +773,10 @@ static int lsapi_load_lve_lib(void)
|
|
644
773
|
int uid = getuid();
|
645
774
|
if ( uid )
|
646
775
|
{
|
647
|
-
setreuid( s_uid, uid );
|
776
|
+
if (setreuid( s_uid, uid )) {};
|
648
777
|
if ( !(*fp_lve_is_available)() )
|
649
778
|
s_enable_lve = 0;
|
650
|
-
setreuid( uid, s_uid );
|
779
|
+
if (setreuid( uid, s_uid )) {};
|
651
780
|
}
|
652
781
|
}
|
653
782
|
}
|
@@ -659,6 +788,7 @@ static int lsapi_load_lve_lib(void)
|
|
659
788
|
return (s_liblve)? 0 : -1;
|
660
789
|
}
|
661
790
|
|
791
|
+
|
662
792
|
static int init_lve_ex(void)
|
663
793
|
{
|
664
794
|
int rc;
|
@@ -698,32 +828,32 @@ static int readSecret( const char * pSecretFile )
|
|
698
828
|
int fd = open( pSecretFile, O_RDONLY , 0600 );
|
699
829
|
if ( fd == -1 )
|
700
830
|
{
|
701
|
-
|
831
|
+
lsapi_log("LSAPI: failed to open secret file: %s!\n", pSecretFile );
|
702
832
|
return -1;
|
703
833
|
}
|
704
834
|
if ( fstat( fd, &st ) == -1 )
|
705
835
|
{
|
706
|
-
|
836
|
+
lsapi_log("LSAPI: failed to check state of file: %s!\n", pSecretFile );
|
707
837
|
close( fd );
|
708
838
|
return -1;
|
709
839
|
}
|
710
840
|
/*
|
711
841
|
if ( st.st_uid != s_uid )
|
712
842
|
{
|
713
|
-
|
843
|
+
lsapi_log("LSAPI: file owner check failure: %s!\n", pSecretFile );
|
714
844
|
close( fd );
|
715
845
|
return -1;
|
716
846
|
}
|
717
847
|
*/
|
718
848
|
if ( st.st_mode & 0077 )
|
719
849
|
{
|
720
|
-
|
850
|
+
lsapi_log("LSAPI: file permission check failure: %s\n", pSecretFile );
|
721
851
|
close( fd );
|
722
852
|
return -1;
|
723
853
|
}
|
724
854
|
if ( read( fd, s_secret, 16 ) < 16 )
|
725
855
|
{
|
726
|
-
|
856
|
+
lsapi_log("LSAPI: failed to read secret from secret file: %s\n", pSecretFile );
|
727
857
|
close( fd );
|
728
858
|
return -1;
|
729
859
|
}
|
@@ -731,6 +861,7 @@ static int readSecret( const char * pSecretFile )
|
|
731
861
|
return 0;
|
732
862
|
}
|
733
863
|
|
864
|
+
|
734
865
|
int LSAPI_is_suEXEC_Daemon(void)
|
735
866
|
{
|
736
867
|
if (( !s_uid )&&( s_secret[0] ))
|
@@ -739,20 +870,22 @@ int LSAPI_is_suEXEC_Daemon(void)
|
|
739
870
|
return 0;
|
740
871
|
}
|
741
872
|
|
873
|
+
|
742
874
|
static int LSAPI_perror_r( LSAPI_Request * pReq, const char * pErr1, const char *pErr2 )
|
743
875
|
{
|
744
876
|
char achError[4096];
|
745
877
|
int n = snprintf(achError, sizeof(achError), "[%d] %s:%s: %s\n", getpid(),
|
746
878
|
pErr1, (pErr2)?pErr2:"", strerror(errno));
|
747
|
-
if (n > sizeof(achError))
|
879
|
+
if (n > (int)sizeof(achError))
|
748
880
|
n = sizeof(achError);
|
749
881
|
if ( pReq )
|
750
882
|
LSAPI_Write_Stderr_r( pReq, achError, n );
|
751
883
|
else
|
752
|
-
write( STDERR_FILENO, achError, n );
|
884
|
+
if (write( STDERR_FILENO, achError, n )) {};
|
753
885
|
return 0;
|
754
886
|
}
|
755
887
|
|
888
|
+
|
756
889
|
static int lsapi_lve_error( LSAPI_Request * pReq )
|
757
890
|
{
|
758
891
|
static const char * headers[] =
|
@@ -776,6 +909,7 @@ static int lsapi_lve_error( LSAPI_Request * pReq )
|
|
776
909
|
return 0;
|
777
910
|
}
|
778
911
|
|
912
|
+
|
779
913
|
static int lsapi_enterLVE( LSAPI_Request * pReq, uid_t uid )
|
780
914
|
{
|
781
915
|
#if defined(linux) || defined(__linux) || defined(__linux__) || defined(__gnu_linux__)
|
@@ -786,7 +920,7 @@ static int lsapi_enterLVE( LSAPI_Request * pReq, uid_t uid )
|
|
786
920
|
ret = (*fp_lve_enter)(s_lve, uid, -1, -1, &cookie);
|
787
921
|
if ( ret < 0 )
|
788
922
|
{
|
789
|
-
|
923
|
+
//lsapi_log("enter LVE (%d) : ressult: %d !\n", uid, ret );
|
790
924
|
LSAPI_perror_r(pReq, "LSAPI: lve_enter() failure, reached resource limit.", NULL );
|
791
925
|
lsapi_lve_error( pReq );
|
792
926
|
return -1;
|
@@ -797,6 +931,7 @@ static int lsapi_enterLVE( LSAPI_Request * pReq, uid_t uid )
|
|
797
931
|
return 0;
|
798
932
|
}
|
799
933
|
|
934
|
+
|
800
935
|
static int lsapi_jailLVE( LSAPI_Request * pReq, uid_t uid, struct passwd * pw )
|
801
936
|
{
|
802
937
|
int ret = 0;
|
@@ -805,8 +940,8 @@ static int lsapi_jailLVE( LSAPI_Request * pReq, uid_t uid, struct passwd * pw )
|
|
805
940
|
ret = (*fp_lve_jail)( pw, error_msg );
|
806
941
|
if ( ret < 0 )
|
807
942
|
{
|
808
|
-
|
809
|
-
|
943
|
+
lsapi_log("LSAPI: LVE jail(%d) ressult: %d, error: %s !\n",
|
944
|
+
uid, ret, error_msg );
|
810
945
|
LSAPI_perror_r( pReq, "LSAPI: jail() failure.", NULL );
|
811
946
|
return -1;
|
812
947
|
}
|
@@ -973,11 +1108,11 @@ static int lsapi_changeUGid( LSAPI_Request * pReq )
|
|
973
1108
|
--pReq->m_pHeader->m_cntSpecialEnv;
|
974
1109
|
uid = *(uint32_t *)pEnv->pValue;
|
975
1110
|
gid = *(((uint32_t *)pEnv->pValue) + 1 );
|
976
|
-
//
|
1111
|
+
//lsapi_log("LSAPI: SUEXEC_UGID set UID: %d, GID: %d\n", uid, gid );
|
977
1112
|
}
|
978
1113
|
else
|
979
1114
|
{
|
980
|
-
|
1115
|
+
lsapi_log("LSAPI: missing SUEXEC_UGID env, use default user!\n" );
|
981
1116
|
pEnv = NULL;
|
982
1117
|
}
|
983
1118
|
if ( pEnv&& lsapi_suexec_auth( pReq, pAuth->pValue, pAuth->valLen, pEnv->pValue, pEnv->valLen ) == 0 )
|
@@ -988,13 +1123,13 @@ static int lsapi_changeUGid( LSAPI_Request * pReq )
|
|
988
1123
|
else
|
989
1124
|
{
|
990
1125
|
//authentication error
|
991
|
-
|
1126
|
+
lsapi_log("LSAPI: SUEXEC_AUTH authentication failed, use default user!\n" );
|
992
1127
|
uid = 0;
|
993
1128
|
}
|
994
1129
|
}
|
995
1130
|
else
|
996
1131
|
{
|
997
|
-
//
|
1132
|
+
//lsapi_log("LSAPI: no SUEXEC_AUTH env, use default user!\n" );
|
998
1133
|
}
|
999
1134
|
}
|
1000
1135
|
|
@@ -1012,7 +1147,13 @@ static int lsapi_changeUGid( LSAPI_Request * pReq )
|
|
1012
1147
|
}
|
1013
1148
|
|
1014
1149
|
s_uid = uid;
|
1015
|
-
|
1150
|
+
|
1151
|
+
if ( pReq->m_fdListen != -1 )
|
1152
|
+
{
|
1153
|
+
close( pReq->m_fdListen );
|
1154
|
+
pReq->m_fdListen = -1;
|
1155
|
+
}
|
1156
|
+
|
1016
1157
|
pStderrLog = LSAPI_GetEnv_r( pReq, "LSAPI_STDERR_LOG");
|
1017
1158
|
if (pStderrLog)
|
1018
1159
|
lsapi_reopen_stderr(pStderrLog);
|
@@ -1021,6 +1162,7 @@ static int lsapi_changeUGid( LSAPI_Request * pReq )
|
|
1021
1162
|
|
1022
1163
|
}
|
1023
1164
|
|
1165
|
+
|
1024
1166
|
static int parseContentLenFromHeader(LSAPI_Request * pReq)
|
1025
1167
|
{
|
1026
1168
|
const char * pContentLen = LSAPI_GetHeader_r( pReq, H_CONTENT_LENGTH );
|
@@ -1067,7 +1209,7 @@ static int parseRequest( LSAPI_Request * pReq, int totalLen )
|
|
1067
1209
|
|| pReq->m_pHeader->m_requestMethodOff < 0
|
1068
1210
|
|| pReq->m_pHeader->m_requestMethodOff >= totalLen)
|
1069
1211
|
{
|
1070
|
-
|
1212
|
+
lsapi_log("Bad request header - ERROR#1\n");
|
1071
1213
|
return -1;
|
1072
1214
|
}
|
1073
1215
|
pReq->m_pScriptFile = pReq->m_pReqBuf + pReq->m_pHeader->m_scriptFileOff;
|
@@ -1087,8 +1229,8 @@ static int parseRequest( LSAPI_Request * pReq, int totalLen )
|
|
1087
1229
|
pBegin += pReq->m_pHeader->m_httpHeaderLen;
|
1088
1230
|
if ( pBegin != pEnd )
|
1089
1231
|
{
|
1090
|
-
|
1091
|
-
|
1232
|
+
lsapi_log("Request header does match total size, total: %d, "
|
1233
|
+
"real: %ld\n", totalLen, pBegin - pReq->m_pReqBuf );
|
1092
1234
|
return -1;
|
1093
1235
|
}
|
1094
1236
|
if ( shouldFixEndian )
|
@@ -1098,7 +1240,7 @@ static int parseRequest( LSAPI_Request * pReq, int totalLen )
|
|
1098
1240
|
|
1099
1241
|
if (validateHeaders(pReq) == -1)
|
1100
1242
|
{
|
1101
|
-
|
1243
|
+
lsapi_log("Bad request header - ERROR#2\n");
|
1102
1244
|
return -1;
|
1103
1245
|
}
|
1104
1246
|
|
@@ -1111,6 +1253,7 @@ static int parseRequest( LSAPI_Request * pReq, int totalLen )
|
|
1111
1253
|
return 0;
|
1112
1254
|
}
|
1113
1255
|
|
1256
|
+
|
1114
1257
|
//OPTIMIZATION
|
1115
1258
|
static char s_accept_notify = 0;
|
1116
1259
|
static char s_schedule_notify = 0;
|
@@ -1119,26 +1262,41 @@ static char s_notified_pid = 0;
|
|
1119
1262
|
|
1120
1263
|
static struct lsapi_packet_header s_ack = {'L', 'S',
|
1121
1264
|
LSAPI_REQ_RECEIVED, LSAPI_ENDIAN, {LSAPI_PACKET_HEADER_LEN} };
|
1265
|
+
static struct lsapi_packet_header s_conn_close_pkt = {'L', 'S',
|
1266
|
+
LSAPI_CONN_CLOSE, LSAPI_ENDIAN, {LSAPI_PACKET_HEADER_LEN} };
|
1267
|
+
|
1122
1268
|
|
1123
|
-
|
1124
|
-
static inline int write_req_received_notification( int fd )
|
1269
|
+
static inline int send_notification_pkt( int fd, struct lsapi_packet_header *pkt )
|
1125
1270
|
{
|
1126
|
-
if ( write( fd,
|
1127
|
-
< LSAPI_PACKET_HEADER_LEN )
|
1271
|
+
if ( write( fd, pkt, LSAPI_PACKET_HEADER_LEN ) < LSAPI_PACKET_HEADER_LEN )
|
1128
1272
|
return -1;
|
1129
1273
|
return 0;
|
1130
1274
|
}
|
1131
1275
|
|
1132
|
-
|
1276
|
+
|
1277
|
+
static inline int send_req_received_notification( int fd )
|
1133
1278
|
{
|
1134
|
-
|
1135
|
-
{
|
1136
|
-
s_notify_scheduled = 0;
|
1137
|
-
if ( g_req.m_fd != -1 )
|
1138
|
-
write_req_received_notification( g_req.m_fd );
|
1139
|
-
}
|
1279
|
+
return send_notification_pkt(fd, &s_ack);
|
1140
1280
|
}
|
1141
1281
|
|
1282
|
+
|
1283
|
+
static inline int send_conn_close_notification( int fd )
|
1284
|
+
{
|
1285
|
+
return send_notification_pkt(fd, &s_conn_close_pkt);
|
1286
|
+
}
|
1287
|
+
|
1288
|
+
|
1289
|
+
//static void lsapi_sigalarm( int sig )
|
1290
|
+
//{
|
1291
|
+
// if ( s_notify_scheduled )
|
1292
|
+
// {
|
1293
|
+
// s_notify_scheduled = 0;
|
1294
|
+
// if ( g_req.m_fd != -1 )
|
1295
|
+
// write_req_received_notification( g_req.m_fd );
|
1296
|
+
// }
|
1297
|
+
//}
|
1298
|
+
|
1299
|
+
|
1142
1300
|
static inline int lsapi_schedule_notify(void)
|
1143
1301
|
{
|
1144
1302
|
if ( !s_notify_scheduled )
|
@@ -1149,11 +1307,12 @@ static inline int lsapi_schedule_notify(void)
|
|
1149
1307
|
return 0;
|
1150
1308
|
}
|
1151
1309
|
|
1310
|
+
|
1152
1311
|
static inline int notify_req_received( int fd )
|
1153
1312
|
{
|
1154
1313
|
if ( s_schedule_notify )
|
1155
1314
|
return lsapi_schedule_notify();
|
1156
|
-
return
|
1315
|
+
return send_req_received_notification( fd );
|
1157
1316
|
|
1158
1317
|
}
|
1159
1318
|
|
@@ -1171,6 +1330,7 @@ static inline int lsapi_notify_pid( int fd )
|
|
1171
1330
|
return 0;
|
1172
1331
|
}
|
1173
1332
|
|
1333
|
+
|
1174
1334
|
static char s_conn_key_packet[16];
|
1175
1335
|
static inline int init_conn_key( int fd )
|
1176
1336
|
{
|
@@ -1193,6 +1353,7 @@ static inline int init_conn_key( int fd )
|
|
1193
1353
|
|
1194
1354
|
}
|
1195
1355
|
|
1356
|
+
|
1196
1357
|
static int readReq( LSAPI_Request * pReq )
|
1197
1358
|
{
|
1198
1359
|
int len;
|
@@ -1217,12 +1378,12 @@ static int readReq( LSAPI_Request * pReq )
|
|
1217
1378
|
packetLen = verifyHeader( &pReq->m_pHeader->m_pktHeader, LSAPI_BEGIN_REQUEST );
|
1218
1379
|
if ( packetLen < 0 )
|
1219
1380
|
{
|
1220
|
-
|
1381
|
+
lsapi_log("packetLen < 0\n");
|
1221
1382
|
return -1;
|
1222
1383
|
}
|
1223
1384
|
if ( packetLen > LSAPI_MAX_HEADER_LEN )
|
1224
1385
|
{
|
1225
|
-
|
1386
|
+
lsapi_log("packetLen > %d\n", LSAPI_MAX_HEADER_LEN );
|
1226
1387
|
return -1;
|
1227
1388
|
}
|
1228
1389
|
|
@@ -1240,7 +1401,7 @@ static int readReq( LSAPI_Request * pReq )
|
|
1240
1401
|
}
|
1241
1402
|
if ( parseRequest( pReq, packetLen ) < 0 )
|
1242
1403
|
{
|
1243
|
-
|
1404
|
+
lsapi_log("ParseRequest error\n");
|
1244
1405
|
return -1;
|
1245
1406
|
}
|
1246
1407
|
|
@@ -1265,7 +1426,6 @@ static int readReq( LSAPI_Request * pReq )
|
|
1265
1426
|
}
|
1266
1427
|
|
1267
1428
|
|
1268
|
-
|
1269
1429
|
int LSAPI_Init(void)
|
1270
1430
|
{
|
1271
1431
|
if ( !g_inited )
|
@@ -1285,20 +1445,33 @@ int LSAPI_Init(void)
|
|
1285
1445
|
return -1;
|
1286
1446
|
g_inited = 1;
|
1287
1447
|
s_ppid = getppid();
|
1448
|
+
void *pthread_lib = dlopen("libpthread.so", RTLD_LAZY);
|
1449
|
+
if (pthread_lib)
|
1450
|
+
pthread_atfork_func = dlsym(pthread_lib, "pthread_atfork");
|
1451
|
+
|
1288
1452
|
}
|
1289
1453
|
return 0;
|
1290
1454
|
}
|
1291
1455
|
|
1456
|
+
|
1292
1457
|
void LSAPI_Stop(void)
|
1293
1458
|
{
|
1294
1459
|
g_running = 0;
|
1295
1460
|
}
|
1296
1461
|
|
1462
|
+
|
1297
1463
|
int LSAPI_IsRunning(void)
|
1298
1464
|
{
|
1299
1465
|
return g_running;
|
1300
1466
|
}
|
1301
1467
|
|
1468
|
+
|
1469
|
+
void LSAPI_Register_Pgrp_Timer_Callback(LSAPI_On_Timer_pf cb)
|
1470
|
+
{
|
1471
|
+
s_proc_group_timer_cb = cb;
|
1472
|
+
}
|
1473
|
+
|
1474
|
+
|
1302
1475
|
int LSAPI_InitRequest( LSAPI_Request * pReq, int fd )
|
1303
1476
|
{
|
1304
1477
|
int newfd;
|
@@ -1337,18 +1510,19 @@ int LSAPI_InitRequest( LSAPI_Request * pReq, int fd )
|
|
1337
1510
|
return 0;
|
1338
1511
|
}
|
1339
1512
|
|
1513
|
+
|
1340
1514
|
int LSAPI_Is_Listen( void )
|
1341
1515
|
{
|
1342
1516
|
return LSAPI_Is_Listen_r( &g_req );
|
1343
1517
|
}
|
1344
1518
|
|
1519
|
+
|
1345
1520
|
int LSAPI_Is_Listen_r( LSAPI_Request * pReq)
|
1346
1521
|
{
|
1347
1522
|
return pReq->m_fdListen != -1;
|
1348
1523
|
}
|
1349
1524
|
|
1350
1525
|
|
1351
|
-
|
1352
1526
|
int LSAPI_Accept_r( LSAPI_Request * pReq )
|
1353
1527
|
{
|
1354
1528
|
char achPeer[128];
|
@@ -1378,8 +1552,9 @@ int LSAPI_Accept_r( LSAPI_Request * pReq )
|
|
1378
1552
|
}
|
1379
1553
|
else
|
1380
1554
|
{
|
1381
|
-
if (
|
1382
|
-
|
1555
|
+
if (s_worker_status)
|
1556
|
+
__sync_lock_test_and_set(&s_worker_status->m_state,
|
1557
|
+
LSAPI_STATE_CONNECTED);
|
1383
1558
|
if (s_busy_workers)
|
1384
1559
|
__sync_fetch_and_add(s_busy_workers, 1);
|
1385
1560
|
lsapi_set_nblock( pReq->m_fd , 0 );
|
@@ -1407,8 +1582,13 @@ int LSAPI_Accept_r( LSAPI_Request * pReq )
|
|
1407
1582
|
return 0;
|
1408
1583
|
}
|
1409
1584
|
|
1410
|
-
|
1411
|
-
|
1585
|
+
|
1586
|
+
static struct lsapi_packet_header finish_close[2] =
|
1587
|
+
{
|
1588
|
+
{'L', 'S', LSAPI_RESP_END, LSAPI_ENDIAN, {LSAPI_PACKET_HEADER_LEN} },
|
1589
|
+
{'L', 'S', LSAPI_CONN_CLOSE, LSAPI_ENDIAN, {LSAPI_PACKET_HEADER_LEN} }
|
1590
|
+
};
|
1591
|
+
|
1412
1592
|
|
1413
1593
|
int LSAPI_Finish_r( LSAPI_Request * pReq )
|
1414
1594
|
{
|
@@ -1428,7 +1608,7 @@ int LSAPI_Finish_r( LSAPI_Request * pReq )
|
|
1428
1608
|
Flush_RespBuf_r( pReq );
|
1429
1609
|
}
|
1430
1610
|
|
1431
|
-
pReq->m_pIovecCur->iov_base = (void *)
|
1611
|
+
pReq->m_pIovecCur->iov_base = (void *)finish_close;
|
1432
1612
|
pReq->m_pIovecCur->iov_len = LSAPI_PACKET_HEADER_LEN;
|
1433
1613
|
pReq->m_totalLen += LSAPI_PACKET_HEADER_LEN;
|
1434
1614
|
++pReq->m_pIovecCur;
|
@@ -1440,6 +1620,41 @@ int LSAPI_Finish_r( LSAPI_Request * pReq )
|
|
1440
1620
|
}
|
1441
1621
|
|
1442
1622
|
|
1623
|
+
int LSAPI_End_Response_r(LSAPI_Request * pReq)
|
1624
|
+
{
|
1625
|
+
if (!pReq)
|
1626
|
+
return -1;
|
1627
|
+
if (pReq->m_reqState & LSAPI_ST_BACKGROUND)
|
1628
|
+
return 0;
|
1629
|
+
if (pReq->m_reqState)
|
1630
|
+
{
|
1631
|
+
if ( pReq->m_fd != -1 )
|
1632
|
+
{
|
1633
|
+
if ( pReq->m_reqState & LSAPI_ST_RESP_HEADER )
|
1634
|
+
{
|
1635
|
+
if ( pReq->m_pRespHeaderBufPos <= pReq->m_pRespHeaderBuf )
|
1636
|
+
return 0;
|
1637
|
+
|
1638
|
+
LSAPI_FinalizeRespHeaders_r( pReq );
|
1639
|
+
}
|
1640
|
+
if ( pReq->m_pRespBufPos != pReq->m_pRespBuf )
|
1641
|
+
{
|
1642
|
+
Flush_RespBuf_r( pReq );
|
1643
|
+
}
|
1644
|
+
|
1645
|
+
pReq->m_pIovecCur->iov_base = (void *)finish_close;
|
1646
|
+
pReq->m_pIovecCur->iov_len = LSAPI_PACKET_HEADER_LEN << 1;
|
1647
|
+
pReq->m_totalLen += LSAPI_PACKET_HEADER_LEN << 1;
|
1648
|
+
++pReq->m_pIovecCur;
|
1649
|
+
LSAPI_Flush_r( pReq );
|
1650
|
+
lsapi_close_connection(pReq);
|
1651
|
+
}
|
1652
|
+
pReq->m_reqState |= LSAPI_ST_BACKGROUND;
|
1653
|
+
}
|
1654
|
+
return 0;
|
1655
|
+
}
|
1656
|
+
|
1657
|
+
|
1443
1658
|
void LSAPI_Reset_r( LSAPI_Request * pReq )
|
1444
1659
|
{
|
1445
1660
|
pReq->m_pRespBufPos = pReq->m_pRespBuf;
|
@@ -1482,6 +1697,7 @@ char * LSAPI_GetHeader_r( LSAPI_Request * pReq, int headerIndex )
|
|
1482
1697
|
return pReq->m_pHttpHeader + off;
|
1483
1698
|
}
|
1484
1699
|
|
1700
|
+
|
1485
1701
|
static int readBodyToReqBuf( LSAPI_Request * pReq )
|
1486
1702
|
{
|
1487
1703
|
off_t bodyLeft;
|
@@ -1518,7 +1734,6 @@ int LSAPI_ReqBodyGetChar_r( LSAPI_Request * pReq )
|
|
1518
1734
|
}
|
1519
1735
|
|
1520
1736
|
|
1521
|
-
|
1522
1737
|
int LSAPI_ReqBodyGetLine_r( LSAPI_Request * pReq, char * pBuf, size_t bufLen, int *getLF )
|
1523
1738
|
{
|
1524
1739
|
ssize_t len;
|
@@ -1527,7 +1742,7 @@ int LSAPI_ReqBodyGetLine_r( LSAPI_Request * pReq, char * pBuf, size_t bufLen, in
|
|
1527
1742
|
char * pBufCur = pBuf;
|
1528
1743
|
char * pCur;
|
1529
1744
|
char * p;
|
1530
|
-
if (!pReq ||
|
1745
|
+
if (!pReq || pReq->m_fd == -1 || !pBuf || !getLF)
|
1531
1746
|
return -1;
|
1532
1747
|
*getLF = 0;
|
1533
1748
|
while( (left = pBufEnd - pBufCur ) > 0 )
|
@@ -1571,7 +1786,7 @@ ssize_t LSAPI_ReadReqBody_r( LSAPI_Request * pReq, char * pBuf, size_t bufLen )
|
|
1571
1786
|
ssize_t len;
|
1572
1787
|
off_t total;
|
1573
1788
|
/* char *pOldBuf = pBuf; */
|
1574
|
-
if (!pReq ||
|
1789
|
+
if (!pReq || pReq->m_fd == -1 || !pBuf || (ssize_t)bufLen < 0)
|
1575
1790
|
return -1;
|
1576
1791
|
|
1577
1792
|
total = pReq->m_reqBodyLen - pReq->m_reqBodyRead;
|
@@ -1625,7 +1840,11 @@ ssize_t LSAPI_Write_r( LSAPI_Request * pReq, const char * pBuf, size_t len )
|
|
1625
1840
|
ssize_t packetLen;
|
1626
1841
|
int skip = 0;
|
1627
1842
|
|
1628
|
-
if (
|
1843
|
+
if (!pReq || !pBuf)
|
1844
|
+
return -1;
|
1845
|
+
if (pReq->m_reqState & LSAPI_ST_BACKGROUND)
|
1846
|
+
return len;
|
1847
|
+
if (pReq->m_fd == -1)
|
1629
1848
|
return -1;
|
1630
1849
|
if ( pReq->m_reqState & LSAPI_ST_RESP_HEADER )
|
1631
1850
|
{
|
@@ -1700,6 +1919,7 @@ ssize_t LSAPI_Write_r( LSAPI_Request * pReq, const char * pBuf, size_t len )
|
|
1700
1919
|
return p - pBuf;
|
1701
1920
|
}
|
1702
1921
|
|
1922
|
+
|
1703
1923
|
#if defined(__FreeBSD__ ) || defined(__NetBSD__) || defined(__OpenBSD__)
|
1704
1924
|
ssize_t gsendfile( int fdOut, int fdIn, off_t* off, size_t size )
|
1705
1925
|
{
|
@@ -1715,6 +1935,7 @@ ssize_t gsendfile( int fdOut, int fdIn, off_t* off, size_t size )
|
|
1715
1935
|
}
|
1716
1936
|
#endif
|
1717
1937
|
|
1938
|
+
|
1718
1939
|
#if defined(macintosh) || defined(__APPLE__) || defined(__APPLE_CC__)
|
1719
1940
|
ssize_t gsendfile( int fdOut, int fdIn, off_t* off, size_t size )
|
1720
1941
|
{
|
@@ -1730,6 +1951,7 @@ ssize_t gsendfile( int fdOut, int fdIn, off_t* off, size_t size )
|
|
1730
1951
|
}
|
1731
1952
|
#endif
|
1732
1953
|
|
1954
|
+
|
1733
1955
|
#if defined(sun) || defined(__sun)
|
1734
1956
|
#include <sys/sendfile.h>
|
1735
1957
|
ssize_t gsendfile( int fdOut, int fdIn, off_t *off, size_t size )
|
@@ -1753,11 +1975,14 @@ ssize_t gsendfile( int fdOut, int fdIn, off_t *off, size_t size )
|
|
1753
1975
|
}
|
1754
1976
|
#endif
|
1755
1977
|
|
1978
|
+
|
1756
1979
|
#if defined(linux) || defined(__linux) || defined(__linux__) || \
|
1757
1980
|
defined(__gnu_linux__)
|
1758
1981
|
#include <sys/sendfile.h>
|
1759
1982
|
#define gsendfile sendfile
|
1760
1983
|
#endif
|
1984
|
+
|
1985
|
+
|
1761
1986
|
#if defined(HPUX)
|
1762
1987
|
ssize_t gsendfile( int fdOut, int fdIn, off_t * off, size_t size )
|
1763
1988
|
{
|
@@ -1765,6 +1990,7 @@ ssize_t gsendfile( int fdOut, int fdIn, off_t * off, size_t size )
|
|
1765
1990
|
}
|
1766
1991
|
#endif
|
1767
1992
|
|
1993
|
+
|
1768
1994
|
ssize_t LSAPI_sendfile_r( LSAPI_Request * pReq, int fdIn, off_t* off, size_t size )
|
1769
1995
|
{
|
1770
1996
|
struct lsapi_packet_header * pHeader = pReq->m_respPktHeader;
|
@@ -1813,8 +2039,6 @@ void Flush_RespBuf_r( LSAPI_Request * pReq )
|
|
1813
2039
|
}
|
1814
2040
|
|
1815
2041
|
|
1816
|
-
|
1817
|
-
|
1818
2042
|
int LSAPI_Flush_r( LSAPI_Request * pReq )
|
1819
2043
|
{
|
1820
2044
|
int ret = 0;
|
@@ -1871,7 +2095,7 @@ ssize_t LSAPI_Write_Stderr_r( LSAPI_Request * pReq, const char * pBuf, size_t le
|
|
1871
2095
|
|
1872
2096
|
if ( !pReq )
|
1873
2097
|
return -1;
|
1874
|
-
if (
|
2098
|
+
if (s_stderr_log_path || pReq->m_fd == -1 || pReq->m_fd == pReq->m_fdListen)
|
1875
2099
|
return write( 2, pBuf, len );
|
1876
2100
|
if ( pReq->m_pRespBufPos != pReq->m_pRespBuf )
|
1877
2101
|
{
|
@@ -1910,6 +2134,7 @@ ssize_t LSAPI_Write_Stderr_r( LSAPI_Request * pReq, const char * pBuf, size_t le
|
|
1910
2134
|
return p - pBuf;
|
1911
2135
|
}
|
1912
2136
|
|
2137
|
+
|
1913
2138
|
static char * GetHeaderVar( LSAPI_Request * pReq, const char * name )
|
1914
2139
|
{
|
1915
2140
|
int i;
|
@@ -1989,6 +2214,7 @@ char * LSAPI_GetEnv_r( LSAPI_Request * pReq, const char * name )
|
|
1989
2214
|
return NULL;
|
1990
2215
|
}
|
1991
2216
|
|
2217
|
+
|
1992
2218
|
struct _headerInfo
|
1993
2219
|
{
|
1994
2220
|
const char * _name;
|
@@ -1997,12 +2223,14 @@ struct _headerInfo
|
|
1997
2223
|
int _valueLen;
|
1998
2224
|
};
|
1999
2225
|
|
2226
|
+
|
2000
2227
|
int compareValueLocation(const void * v1, const void *v2 )
|
2001
2228
|
{
|
2002
2229
|
return ((const struct _headerInfo *)v1)->_value -
|
2003
2230
|
((const struct _headerInfo *)v2)->_value;
|
2004
2231
|
}
|
2005
2232
|
|
2233
|
+
|
2006
2234
|
int LSAPI_ForeachOrgHeader_r( LSAPI_Request * pReq,
|
2007
2235
|
LSAPI_CB_EnvHandler fn, void * arg )
|
2008
2236
|
{
|
@@ -2076,7 +2304,6 @@ int LSAPI_ForeachOrgHeader_r( LSAPI_Request * pReq,
|
|
2076
2304
|
return ret;
|
2077
2305
|
}
|
2078
2306
|
return count;
|
2079
|
-
|
2080
2307
|
}
|
2081
2308
|
|
2082
2309
|
|
@@ -2145,9 +2372,9 @@ int LSAPI_ForeachHeader_r( LSAPI_Request * pReq,
|
|
2145
2372
|
}
|
2146
2373
|
}
|
2147
2374
|
return count + pReq->m_pHeader->m_cntUnknownHeaders;
|
2148
|
-
|
2149
2375
|
}
|
2150
2376
|
|
2377
|
+
|
2151
2378
|
static int EnvForeach( struct LSAPI_key_value_pair * pEnv,
|
2152
2379
|
int n, LSAPI_CB_EnvHandler fn, void * arg )
|
2153
2380
|
{
|
@@ -2167,7 +2394,6 @@ static int EnvForeach( struct LSAPI_key_value_pair * pEnv,
|
|
2167
2394
|
}
|
2168
2395
|
|
2169
2396
|
|
2170
|
-
|
2171
2397
|
int LSAPI_ForeachEnv_r( LSAPI_Request * pReq,
|
2172
2398
|
LSAPI_CB_EnvHandler fn, void * arg )
|
2173
2399
|
{
|
@@ -2182,7 +2408,6 @@ int LSAPI_ForeachEnv_r( LSAPI_Request * pReq,
|
|
2182
2408
|
}
|
2183
2409
|
|
2184
2410
|
|
2185
|
-
|
2186
2411
|
int LSAPI_ForeachSpecialEnv_r( LSAPI_Request * pReq,
|
2187
2412
|
LSAPI_CB_EnvHandler fn, void * arg )
|
2188
2413
|
{
|
@@ -2199,7 +2424,6 @@ int LSAPI_ForeachSpecialEnv_r( LSAPI_Request * pReq,
|
|
2199
2424
|
}
|
2200
2425
|
|
2201
2426
|
|
2202
|
-
|
2203
2427
|
int LSAPI_FinalizeRespHeaders_r( LSAPI_Request * pReq )
|
2204
2428
|
{
|
2205
2429
|
if ( !pReq || !pReq->m_pIovec )
|
@@ -2283,7 +2507,6 @@ int LSAPI_AppendRespHeader2_r( LSAPI_Request * pReq, const char * pHeaderName,
|
|
2283
2507
|
}
|
2284
2508
|
|
2285
2509
|
|
2286
|
-
|
2287
2510
|
int LSAPI_AppendRespHeader_r( LSAPI_Request * pReq, const char * pBuf, int len )
|
2288
2511
|
{
|
2289
2512
|
if ( !pReq || !pBuf || len <= 0 || len > LSAPI_RESP_HTTP_HEADER_MAX )
|
@@ -2364,9 +2587,9 @@ int LSAPI_CreateListenSock2( const struct sockaddr * pServerAddr, int backlog )
|
|
2364
2587
|
close(fd);
|
2365
2588
|
errno = ret;
|
2366
2589
|
return -1;
|
2367
|
-
|
2368
2590
|
}
|
2369
2591
|
|
2592
|
+
|
2370
2593
|
int LSAPI_ParseSockAddr( const char * pBind, struct sockaddr * pAddr )
|
2371
2594
|
{
|
2372
2595
|
char achAddr[256];
|
@@ -2464,6 +2687,7 @@ int LSAPI_ParseSockAddr( const char * pBind, struct sockaddr * pAddr )
|
|
2464
2687
|
|
2465
2688
|
}
|
2466
2689
|
|
2690
|
+
|
2467
2691
|
int LSAPI_CreateListenSock( const char * pBind, int backlog )
|
2468
2692
|
{
|
2469
2693
|
char serverAddr[128];
|
@@ -2477,8 +2701,8 @@ int LSAPI_CreateListenSock( const char * pBind, int backlog )
|
|
2477
2701
|
return fd;
|
2478
2702
|
}
|
2479
2703
|
|
2480
|
-
static fn_select_t g_fnSelect = select;
|
2481
2704
|
|
2705
|
+
static fn_select_t g_fnSelect = select;
|
2482
2706
|
typedef struct _lsapi_prefork_server
|
2483
2707
|
{
|
2484
2708
|
int m_fd;
|
@@ -2496,12 +2720,11 @@ typedef struct _lsapi_prefork_server
|
|
2496
2720
|
lsapi_child_status * m_pChildrenStatusEnd;
|
2497
2721
|
|
2498
2722
|
}lsapi_prefork_server;
|
2499
|
-
|
2500
2723
|
static lsapi_prefork_server * g_prefork_server = NULL;
|
2501
2724
|
|
2725
|
+
|
2502
2726
|
int LSAPI_Init_Prefork_Server( int max_children, fn_select_t fp, int avoidFork )
|
2503
2727
|
{
|
2504
|
-
int pid;
|
2505
2728
|
if ( g_prefork_server )
|
2506
2729
|
return 0;
|
2507
2730
|
if ( max_children <= 1 )
|
@@ -2509,7 +2732,8 @@ int LSAPI_Init_Prefork_Server( int max_children, fn_select_t fp, int avoidFork )
|
|
2509
2732
|
if ( max_children >= 10000)
|
2510
2733
|
max_children = 10000;
|
2511
2734
|
|
2512
|
-
|
2735
|
+
if (s_max_busy_workers == 0)
|
2736
|
+
s_max_busy_workers = max_children / 2 + 1;
|
2513
2737
|
|
2514
2738
|
g_prefork_server = (lsapi_prefork_server *)malloc( sizeof( lsapi_prefork_server ) );
|
2515
2739
|
if ( !g_prefork_server )
|
@@ -2520,8 +2744,11 @@ int LSAPI_Init_Prefork_Server( int max_children, fn_select_t fp, int avoidFork )
|
|
2520
2744
|
g_fnSelect = fp;
|
2521
2745
|
|
2522
2746
|
s_ppid = getppid();
|
2523
|
-
|
2524
|
-
setpgid(
|
2747
|
+
s_pid = getpid();
|
2748
|
+
setpgid( s_pid, s_pid );
|
2749
|
+
#if defined(linux) || defined(__linux) || defined(__linux__) || defined(__gnu_linux__)
|
2750
|
+
s_total_pages = sysconf(_SC_PHYS_PAGES);
|
2751
|
+
#endif
|
2525
2752
|
g_prefork_server->m_iAvoidFork = avoidFork;
|
2526
2753
|
g_prefork_server->m_iMaxChildren = max_children;
|
2527
2754
|
|
@@ -2531,9 +2758,13 @@ int LSAPI_Init_Prefork_Server( int max_children, fn_select_t fp, int avoidFork )
|
|
2531
2758
|
g_prefork_server->m_iMaxIdleChildren = 1;
|
2532
2759
|
g_prefork_server->m_iChildrenMaxIdleTime = 300;
|
2533
2760
|
g_prefork_server->m_iMaxReqProcessTime = 3600;
|
2761
|
+
|
2762
|
+
setsid();
|
2763
|
+
|
2534
2764
|
return 0;
|
2535
2765
|
}
|
2536
2766
|
|
2767
|
+
|
2537
2768
|
void LSAPI_Set_Server_fd( int fd )
|
2538
2769
|
{
|
2539
2770
|
if( g_prefork_server )
|
@@ -2567,12 +2798,8 @@ static int lsapi_accept( int fdListen )
|
|
2567
2798
|
}
|
2568
2799
|
|
2569
2800
|
|
2570
|
-
|
2571
|
-
|
2572
|
-
static int s_req_processed = 0;
|
2573
|
-
static int s_max_reqs = 10000;
|
2801
|
+
static unsigned int s_max_reqs = UINT_MAX;
|
2574
2802
|
static int s_max_idle_secs = 300;
|
2575
|
-
|
2576
2803
|
static int s_stop;
|
2577
2804
|
|
2578
2805
|
static void lsapi_cleanup(int signal)
|
@@ -2580,6 +2807,7 @@ static void lsapi_cleanup(int signal)
|
|
2580
2807
|
s_stop = signal;
|
2581
2808
|
}
|
2582
2809
|
|
2810
|
+
|
2583
2811
|
static lsapi_child_status * find_child_status( int pid )
|
2584
2812
|
{
|
2585
2813
|
lsapi_child_status * pStatus = g_prefork_server->m_pChildrenStatus;
|
@@ -2588,6 +2816,11 @@ static lsapi_child_status * find_child_status( int pid )
|
|
2588
2816
|
{
|
2589
2817
|
if ( pStatus->m_pid == pid )
|
2590
2818
|
{
|
2819
|
+
if (pid == 0)
|
2820
|
+
{
|
2821
|
+
memset(pStatus, 0, sizeof( *pStatus ) );
|
2822
|
+
pStatus->m_pid = -1;
|
2823
|
+
}
|
2591
2824
|
if ( pStatus + 1 > g_prefork_server->m_pChildrenStatusCur )
|
2592
2825
|
g_prefork_server->m_pChildrenStatusCur = pStatus + 1;
|
2593
2826
|
return pStatus;
|
@@ -2598,11 +2831,33 @@ static lsapi_child_status * find_child_status( int pid )
|
|
2598
2831
|
}
|
2599
2832
|
|
2600
2833
|
|
2834
|
+
void LSAPI_reset_server_state( void )
|
2835
|
+
{
|
2836
|
+
/*
|
2837
|
+
Reset child status
|
2838
|
+
*/
|
2839
|
+
g_prefork_server->m_iCurChildren = 0;
|
2840
|
+
lsapi_child_status * pStatus = g_prefork_server->m_pChildrenStatus;
|
2841
|
+
lsapi_child_status * pEnd = g_prefork_server->m_pChildrenStatusEnd;
|
2842
|
+
while( pStatus < pEnd )
|
2843
|
+
{
|
2844
|
+
pStatus->m_pid = 0;
|
2845
|
+
++pStatus;
|
2846
|
+
}
|
2847
|
+
if (s_busy_workers)
|
2848
|
+
__sync_lock_release(s_busy_workers);
|
2849
|
+
if (s_accepting_workers)
|
2850
|
+
__sync_lock_release(s_accepting_workers);
|
2851
|
+
|
2852
|
+
}
|
2853
|
+
|
2601
2854
|
|
2602
2855
|
static void lsapi_sigchild( int signal )
|
2603
2856
|
{
|
2604
2857
|
int status, pid;
|
2605
2858
|
lsapi_child_status * child_status;
|
2859
|
+
if (g_prefork_server == NULL)
|
2860
|
+
return;
|
2606
2861
|
while( 1 )
|
2607
2862
|
{
|
2608
2863
|
pid = waitpid( -1, &status, WNOHANG|WUNTRACED );
|
@@ -2614,21 +2869,36 @@ static void lsapi_sigchild( int signal )
|
|
2614
2869
|
{
|
2615
2870
|
int sig_num = WTERMSIG( status );
|
2616
2871
|
int dump = WCOREDUMP( status );
|
2617
|
-
|
2872
|
+
lsapi_log("Child process with pid: %d was killed by signal: "
|
2873
|
+
"%d, core dump: %d\n", pid, sig_num, dump );
|
2618
2874
|
}
|
2619
2875
|
if ( pid == s_pid_dump_debug_info )
|
2620
2876
|
{
|
2621
2877
|
pid = 0;
|
2622
2878
|
continue;
|
2623
2879
|
}
|
2880
|
+
if ( pid == s_ignore_pid )
|
2881
|
+
{
|
2882
|
+
pid = 0;
|
2883
|
+
s_ignore_pid = -1;
|
2884
|
+
continue;
|
2885
|
+
}
|
2624
2886
|
child_status = find_child_status( pid );
|
2625
2887
|
if ( child_status )
|
2626
2888
|
{
|
2627
|
-
if (child_status->
|
2889
|
+
if (__sync_bool_compare_and_swap(&child_status->m_state,
|
2890
|
+
LSAPI_STATE_CONNECTED,
|
2891
|
+
LSAPI_STATE_IDLE))
|
2628
2892
|
{
|
2629
2893
|
if (s_busy_workers)
|
2630
2894
|
__sync_fetch_and_sub(s_busy_workers, 1);
|
2631
|
-
|
2895
|
+
}
|
2896
|
+
else if (__sync_bool_compare_and_swap(&child_status->m_state,
|
2897
|
+
LSAPI_STATE_ACCEPTING,
|
2898
|
+
LSAPI_STATE_IDLE))
|
2899
|
+
{
|
2900
|
+
if (s_accepting_workers)
|
2901
|
+
__sync_fetch_and_sub(s_accepting_workers, 1);
|
2632
2902
|
}
|
2633
2903
|
child_status->m_pid = 0;
|
2634
2904
|
--g_prefork_server->m_iCurChildren;
|
@@ -2640,13 +2910,19 @@ static void lsapi_sigchild( int signal )
|
|
2640
2910
|
|
2641
2911
|
}
|
2642
2912
|
|
2913
|
+
|
2643
2914
|
static int lsapi_init_children_status(void)
|
2644
2915
|
{
|
2645
|
-
int size = 4096;
|
2646
|
-
|
2647
2916
|
char * pBuf;
|
2648
|
-
size =
|
2649
|
-
|
2917
|
+
int size = 4096;
|
2918
|
+
int max_children;
|
2919
|
+
if (g_prefork_server->m_pChildrenStatus)
|
2920
|
+
return 0;
|
2921
|
+
max_children = g_prefork_server->m_iMaxChildren
|
2922
|
+
+ g_prefork_server->m_iExtraChildren;
|
2923
|
+
|
2924
|
+
size = max_children * sizeof( lsapi_child_status ) * 2 + 3 * sizeof(int);
|
2925
|
+
size = (size + 4095) / 4096 * 4096;
|
2650
2926
|
pBuf =( char*) mmap( NULL, size, PROT_READ | PROT_WRITE,
|
2651
2927
|
MAP_ANON | MAP_SHARED, -1, 0 );
|
2652
2928
|
if ( pBuf == MAP_FAILED )
|
@@ -2657,10 +2933,17 @@ static int lsapi_init_children_status(void)
|
|
2657
2933
|
memset( pBuf, 0, size );
|
2658
2934
|
g_prefork_server->m_pChildrenStatus = (lsapi_child_status *)pBuf;
|
2659
2935
|
g_prefork_server->m_pChildrenStatusCur = (lsapi_child_status *)pBuf;
|
2660
|
-
g_prefork_server->m_pChildrenStatusEnd = (lsapi_child_status *)pBuf +
|
2936
|
+
g_prefork_server->m_pChildrenStatusEnd = (lsapi_child_status *)pBuf + max_children;
|
2937
|
+
s_busy_workers = (int *)g_prefork_server->m_pChildrenStatusEnd;
|
2938
|
+
s_accepting_workers = s_busy_workers + 1;
|
2939
|
+
s_global_counter = s_accepting_workers + 1;
|
2940
|
+
s_avail_pages = (size_t *)(s_global_counter + 1);
|
2941
|
+
|
2942
|
+
setsid();
|
2661
2943
|
return 0;
|
2662
2944
|
}
|
2663
2945
|
|
2946
|
+
|
2664
2947
|
static void dump_debug_info( lsapi_child_status * pStatus, long tmCur )
|
2665
2948
|
{
|
2666
2949
|
char achCmd[1024];
|
@@ -2669,17 +2952,26 @@ static void dump_debug_info( lsapi_child_status * pStatus, long tmCur )
|
|
2669
2952
|
if ( kill( s_pid_dump_debug_info, 0 ) == 0 )
|
2670
2953
|
return;
|
2671
2954
|
}
|
2672
|
-
s_pid_dump_debug_info = fork();
|
2673
2955
|
|
2674
|
-
|
2675
|
-
|
2676
|
-
|
2677
|
-
|
2678
|
-
|
2679
|
-
|
2680
|
-
|
2956
|
+
lsapi_log("Possible runaway process, PPID: %d, PID: %d, "
|
2957
|
+
"reqCount: %d, process time: %ld, checkpoint time: %ld, start "
|
2958
|
+
"time: %ld\n", getpid(), pStatus->m_pid,
|
2959
|
+
pStatus->m_iReqCounter, tmCur - pStatus->m_tmReqBegin,
|
2960
|
+
tmCur - pStatus->m_tmLastCheckPoint, tmCur - pStatus->m_tmStart );
|
2961
|
+
|
2962
|
+
s_pid_dump_debug_info = fork();
|
2963
|
+
if (s_pid_dump_debug_info == 0)
|
2964
|
+
{
|
2965
|
+
snprintf( achCmd, 1024, "gdb --batch -ex \"attach %d\" -ex \"set height 0\" "
|
2966
|
+
"-ex \"bt\" >&2;PATH=$PATH:/usr/sbin lsof -p %d >&2",
|
2967
|
+
pStatus->m_pid, pStatus->m_pid );
|
2968
|
+
if ( system( achCmd ) == -1 )
|
2969
|
+
perror( "system()" );
|
2970
|
+
exit( 0 );
|
2971
|
+
}
|
2681
2972
|
}
|
2682
2973
|
|
2974
|
+
|
2683
2975
|
static void lsapi_check_child_status( long tmCur )
|
2684
2976
|
{
|
2685
2977
|
int idle = 0;
|
@@ -2697,15 +2989,17 @@ static void lsapi_check_child_status( long tmCur )
|
|
2697
2989
|
if ( !pStatus->m_inProcess )
|
2698
2990
|
{
|
2699
2991
|
|
2700
|
-
if (
|
2701
|
-
|
2992
|
+
if (g_prefork_server->m_iCurChildren - dying
|
2993
|
+
> g_prefork_server->m_iMaxChildren
|
2994
|
+
|| idle > g_prefork_server->m_iMaxIdleChildren)
|
2702
2995
|
{
|
2703
2996
|
++pStatus->m_iKillSent;
|
2704
2997
|
//tobekilled = SIGUSR1;
|
2705
2998
|
}
|
2706
2999
|
else
|
2707
3000
|
{
|
2708
|
-
if (
|
3001
|
+
if (s_max_idle_secs> 0
|
3002
|
+
&& tmCur - pStatus->m_tmWaitBegin > s_max_idle_secs + 5)
|
2709
3003
|
{
|
2710
3004
|
++pStatus->m_iKillSent;
|
2711
3005
|
//tobekilled = SIGUSR1;
|
@@ -2716,26 +3010,29 @@ static void lsapi_check_child_status( long tmCur )
|
|
2716
3010
|
}
|
2717
3011
|
else
|
2718
3012
|
{
|
2719
|
-
if (
|
2720
|
-
g_prefork_server->m_iMaxReqProcessTime
|
3013
|
+
if (tmCur - pStatus->m_tmReqBegin >
|
3014
|
+
g_prefork_server->m_iMaxReqProcessTime)
|
2721
3015
|
{
|
2722
|
-
if ((
|
3016
|
+
if ((pStatus->m_iKillSent % 5) == 0 && s_dump_debug_info)
|
2723
3017
|
dump_debug_info( pStatus, tmCur );
|
2724
3018
|
if ( pStatus->m_iKillSent > 5 )
|
2725
3019
|
{
|
2726
3020
|
tobekilled = SIGKILL;
|
2727
|
-
|
3021
|
+
lsapi_log("Force killing runaway process PID: %d"
|
3022
|
+
" with SIGKILL\n", pStatus->m_pid );
|
2728
3023
|
}
|
2729
3024
|
else
|
2730
3025
|
{
|
2731
3026
|
tobekilled = SIGTERM;
|
2732
|
-
|
3027
|
+
lsapi_log("Killing runaway process PID: %d with "
|
3028
|
+
"SIGTERM\n", pStatus->m_pid );
|
2733
3029
|
}
|
2734
3030
|
}
|
2735
3031
|
}
|
2736
3032
|
if ( tobekilled )
|
2737
3033
|
{
|
2738
|
-
if (( kill( pStatus->m_pid, tobekilled ) == -1 )&&
|
3034
|
+
if (( kill( pStatus->m_pid, tobekilled ) == -1 ) &&
|
3035
|
+
( errno == ESRCH ))
|
2739
3036
|
{
|
2740
3037
|
pStatus->m_pid = 0;
|
2741
3038
|
--count;
|
@@ -2751,34 +3048,50 @@ static void lsapi_check_child_status( long tmCur )
|
|
2751
3048
|
}
|
2752
3049
|
if ( abs( g_prefork_server->m_iCurChildren - count ) > 1 )
|
2753
3050
|
{
|
2754
|
-
|
2755
|
-
|
2756
|
-
|
3051
|
+
lsapi_log("Children tracking is wrong: Cur Children: %d,"
|
3052
|
+
" count: %d, idle: %d, dying: %d\n",
|
3053
|
+
g_prefork_server->m_iCurChildren, count, idle, dying );
|
2757
3054
|
}
|
2758
3055
|
}
|
2759
3056
|
|
2760
|
-
static int lsapi_all_children_must_die(void)
|
2761
|
-
{
|
2762
|
-
int maxWait;
|
2763
|
-
int sec =0;
|
2764
|
-
g_prefork_server->m_iMaxReqProcessTime = 10;
|
2765
|
-
g_prefork_server->m_iMaxIdleChildren = -1;
|
2766
|
-
maxWait = 15;
|
2767
3057
|
|
2768
|
-
|
2769
|
-
|
2770
|
-
|
2771
|
-
|
2772
|
-
|
2773
|
-
|
2774
|
-
|
2775
|
-
|
2776
|
-
|
2777
|
-
|
3058
|
+
//static int lsapi_all_children_must_die(void)
|
3059
|
+
//{
|
3060
|
+
// int maxWait;
|
3061
|
+
// int sec =0;
|
3062
|
+
// g_prefork_server->m_iMaxReqProcessTime = 10;
|
3063
|
+
// g_prefork_server->m_iMaxIdleChildren = -1;
|
3064
|
+
// maxWait = 15;
|
3065
|
+
//
|
3066
|
+
// while( g_prefork_server->m_iCurChildren && (sec < maxWait) )
|
3067
|
+
// {
|
3068
|
+
// lsapi_check_child_status(time(NULL));
|
3069
|
+
// sleep( 1 );
|
3070
|
+
// sec++;
|
3071
|
+
// }
|
3072
|
+
// if ( g_prefork_server->m_iCurChildren != 0 )
|
3073
|
+
// kill( -getpgrp(), SIGKILL );
|
3074
|
+
// return 0;
|
3075
|
+
//}
|
3076
|
+
|
3077
|
+
|
3078
|
+
void set_skip_write()
|
3079
|
+
{ s_skip_write = 1; }
|
3080
|
+
|
2778
3081
|
|
3082
|
+
int is_enough_free_mem()
|
3083
|
+
{
|
3084
|
+
#if defined(linux) || defined(__linux) || defined(__linux__) || defined(__gnu_linux__)
|
3085
|
+
//minimum 1GB or 10% available free memory
|
3086
|
+
return (*s_avail_pages > s_min_avail_pages
|
3087
|
+
|| (*s_avail_pages * 10) / s_total_pages > 0);
|
3088
|
+
#endif
|
3089
|
+
return 1;
|
3090
|
+
}
|
2779
3091
|
|
2780
3092
|
|
2781
|
-
static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer,
|
3093
|
+
static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer,
|
3094
|
+
LSAPI_Request * pReq )
|
2782
3095
|
{
|
2783
3096
|
struct sigaction act, old_term, old_quit, old_int,
|
2784
3097
|
old_usr1, old_child;
|
@@ -2796,10 +3109,9 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2796
3109
|
|
2797
3110
|
lsapi_init_children_status();
|
2798
3111
|
|
2799
|
-
setsid();
|
2800
|
-
|
2801
3112
|
act.sa_flags = 0;
|
2802
3113
|
act.sa_handler = lsapi_sigchild;
|
3114
|
+
sigemptyset(&(act.sa_mask));
|
2803
3115
|
if( sigaction( SIGCHLD, &act, &old_child ) )
|
2804
3116
|
{
|
2805
3117
|
perror( "Can't set signal handler for SIGCHILD" );
|
@@ -2809,6 +3121,7 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2809
3121
|
/* Set up handler to kill children upon exit */
|
2810
3122
|
act.sa_flags = 0;
|
2811
3123
|
act.sa_handler = lsapi_cleanup;
|
3124
|
+
sigemptyset(&(act.sa_mask));
|
2812
3125
|
if( sigaction( SIGTERM, &act, &old_term ) ||
|
2813
3126
|
sigaction( SIGINT, &act, &old_int ) ||
|
2814
3127
|
sigaction( SIGUSR1, &act, &old_usr1 ) ||
|
@@ -2817,14 +3130,18 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2817
3130
|
perror( "Can't set signals" );
|
2818
3131
|
return -1;
|
2819
3132
|
}
|
2820
|
-
|
3133
|
+
|
2821
3134
|
while( !s_stop )
|
2822
3135
|
{
|
3136
|
+
if (s_proc_group_timer_cb != NULL) {
|
3137
|
+
s_proc_group_timer_cb(&s_ignore_pid);
|
3138
|
+
}
|
3139
|
+
|
2823
3140
|
curTime = time( NULL );
|
2824
3141
|
if (curTime != lastTime )
|
2825
3142
|
{
|
2826
3143
|
lastTime = curTime;
|
2827
|
-
if (
|
3144
|
+
if (lsapi_parent_dead())
|
2828
3145
|
break;
|
2829
3146
|
lsapi_check_child_status(curTime );
|
2830
3147
|
if (pServer->m_iServerMaxIdle)
|
@@ -2840,29 +3157,33 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2840
3157
|
}
|
2841
3158
|
}
|
2842
3159
|
|
2843
|
-
|
2844
|
-
|
2845
|
-
|
2846
|
-
|
2847
|
-
usleep( 100000 );
|
2848
|
-
continue;
|
2849
|
-
}
|
3160
|
+
#if defined(linux) || defined(__linux) || defined(__linux__) || defined(__gnu_linux__)
|
3161
|
+
*s_avail_pages = sysconf(_SC_AVPHYS_PAGES);
|
3162
|
+
// lsapi_log("Memory total: %zd, free: %zd, free %%%zd\n",
|
3163
|
+
// s_total_pages, *s_avail_pages, *s_avail_pages * 100 / s_total_pages);
|
2850
3164
|
|
3165
|
+
#endif
|
2851
3166
|
FD_ZERO( &readfds );
|
2852
3167
|
FD_SET( pServer->m_fd, &readfds );
|
2853
|
-
timeout.tv_sec = 1;
|
2854
|
-
|
3168
|
+
timeout.tv_sec = 1;
|
3169
|
+
timeout.tv_usec = 0;
|
3170
|
+
ret = (*g_fnSelect)(pServer->m_fd+1, &readfds, NULL, NULL, &timeout);
|
3171
|
+
if (ret == 1 )
|
2855
3172
|
{
|
2856
|
-
|
2857
|
-
if (
|
3173
|
+
int accepting = 0;
|
3174
|
+
if (s_accepting_workers)
|
3175
|
+
accepting = __sync_add_and_fetch(s_accepting_workers, 0);
|
3176
|
+
|
3177
|
+
if (pServer->m_iCurChildren > 0
|
3178
|
+
&& accepting > 0)
|
2858
3179
|
{
|
2859
|
-
|
2860
|
-
|
2861
|
-
|
2862
|
-
|
2863
|
-
|
2864
|
-
|
2865
|
-
}
|
3180
|
+
lsapi_log("children: %d, accepting: %d\n",
|
3181
|
+
pServer->m_iCurChildren, accepting);
|
3182
|
+
usleep( 400);
|
3183
|
+
while(accepting-- > 0)
|
3184
|
+
sched_yield();
|
3185
|
+
continue;
|
3186
|
+
}
|
2866
3187
|
}
|
2867
3188
|
else if ( ret == -1 )
|
2868
3189
|
{
|
@@ -2876,12 +3197,23 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2876
3197
|
continue;
|
2877
3198
|
}
|
2878
3199
|
|
3200
|
+
if (pServer->m_iCurChildren >=
|
3201
|
+
pServer->m_iMaxChildren + pServer->m_iExtraChildren)
|
3202
|
+
{
|
3203
|
+
lsapi_log("Reached max children process limit: %d, extra: %d,"
|
3204
|
+
" current: %d, busy: %d, please increase LSAPI_CHILDREN.\n",
|
3205
|
+
pServer->m_iMaxChildren, pServer->m_iExtraChildren,
|
3206
|
+
pServer->m_iCurChildren,
|
3207
|
+
s_busy_workers ? *s_busy_workers : -1 );
|
3208
|
+
usleep( 100000 );
|
3209
|
+
continue;
|
3210
|
+
}
|
3211
|
+
|
2879
3212
|
pReq->m_fd = lsapi_accept( pServer->m_fd );
|
2880
3213
|
if ( pReq->m_fd != -1 )
|
2881
3214
|
{
|
3215
|
+
wait_secs = 0;
|
2882
3216
|
child_status = find_child_status( 0 );
|
2883
|
-
if ( child_status )
|
2884
|
-
memset( child_status, 0, sizeof( *child_status ) );
|
2885
3217
|
|
2886
3218
|
sigemptyset( &mask );
|
2887
3219
|
sigaddset( &mask, SIGCHLD );
|
@@ -2895,19 +3227,30 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2895
3227
|
|
2896
3228
|
if ( !pid )
|
2897
3229
|
{
|
3230
|
+
setsid();
|
2898
3231
|
if (sigprocmask(SIG_SETMASK, &orig_mask, NULL) < 0)
|
2899
3232
|
perror( "sigprocmask( SIG_SETMASK ) to restore SIGMASK in child" );
|
2900
3233
|
g_prefork_server = NULL;
|
2901
3234
|
s_ppid = getppid();
|
3235
|
+
s_pid = getpid();
|
2902
3236
|
s_req_processed = 0;
|
2903
|
-
|
3237
|
+
s_proc_group_timer_cb = NULL;
|
3238
|
+
s_worker_status = child_status;
|
3239
|
+
|
3240
|
+
if (pthread_atfork_func)
|
3241
|
+
(*pthread_atfork_func)(NULL, NULL, set_skip_write);
|
2904
3242
|
|
2905
|
-
|
3243
|
+
__sync_lock_test_and_set(&s_worker_status->m_state,
|
3244
|
+
LSAPI_STATE_CONNECTED);
|
2906
3245
|
if (s_busy_workers)
|
2907
|
-
|
2908
|
-
|
3246
|
+
__sync_add_and_fetch(s_busy_workers, 1);
|
2909
3247
|
lsapi_set_nblock( pReq->m_fd, 0 );
|
2910
|
-
|
3248
|
+
//keep it open if busy_count is used.
|
3249
|
+
if (s_busy_workers
|
3250
|
+
&& *s_busy_workers > (pServer->m_iMaxChildren >> 1))
|
3251
|
+
s_keepListener = 1;
|
3252
|
+
if ((s_uid == 0 || !s_keepListener || !is_enough_free_mem())
|
3253
|
+
&& pReq->m_fdListen != -1 )
|
2911
3254
|
{
|
2912
3255
|
close( pReq->m_fdListen );
|
2913
3256
|
pReq->m_fdListen = -1;
|
@@ -2961,11 +3304,220 @@ static int lsapi_prefork_server_accept( lsapi_prefork_server * pServer, LSAPI_Re
|
|
2961
3304
|
|
2962
3305
|
}
|
2963
3306
|
|
2964
|
-
|
3307
|
+
|
3308
|
+
static struct sigaction old_term, old_quit, old_int,
|
3309
|
+
old_usr1, old_child;
|
3310
|
+
|
3311
|
+
|
3312
|
+
int LSAPI_Postfork_Child(LSAPI_Request * pReq)
|
3313
|
+
{
|
3314
|
+
int max_children = g_prefork_server->m_iMaxChildren;
|
3315
|
+
s_pid = getpid();
|
3316
|
+
__sync_lock_test_and_set(&pReq->child_status->m_pid, s_pid);
|
3317
|
+
s_worker_status = pReq->child_status;
|
3318
|
+
|
3319
|
+
setsid();
|
3320
|
+
g_prefork_server = NULL;
|
3321
|
+
s_ppid = getppid();
|
3322
|
+
s_req_processed = 0;
|
3323
|
+
s_proc_group_timer_cb = NULL;
|
3324
|
+
|
3325
|
+
if (pthread_atfork_func)
|
3326
|
+
(*pthread_atfork_func)(NULL, NULL, set_skip_write);
|
3327
|
+
|
3328
|
+
__sync_lock_test_and_set(&s_worker_status->m_state,
|
3329
|
+
LSAPI_STATE_CONNECTED);
|
3330
|
+
if (s_busy_workers)
|
3331
|
+
__sync_add_and_fetch(s_busy_workers, 1);
|
3332
|
+
lsapi_set_nblock( pReq->m_fd, 0 );
|
3333
|
+
//keep it open if busy_count is used.
|
3334
|
+
if (s_busy_workers
|
3335
|
+
&& *s_busy_workers > (max_children >> 1))
|
3336
|
+
s_keepListener = 1;
|
3337
|
+
if ((s_uid == 0 || !s_keepListener || !is_enough_free_mem())
|
3338
|
+
&& pReq->m_fdListen != -1 )
|
3339
|
+
{
|
3340
|
+
close(pReq->m_fdListen);
|
3341
|
+
pReq->m_fdListen = -1;
|
3342
|
+
}
|
3343
|
+
|
3344
|
+
//init_conn_key( pReq->m_fd );
|
3345
|
+
lsapi_notify_pid(pReq->m_fd);
|
3346
|
+
s_notified_pid = 1;
|
3347
|
+
//if ( s_accept_notify )
|
3348
|
+
// return notify_req_received( pReq->m_fd );
|
3349
|
+
return 0;
|
3350
|
+
}
|
3351
|
+
|
3352
|
+
|
3353
|
+
int LSAPI_Postfork_Parent(LSAPI_Request * pReq)
|
3354
|
+
{
|
3355
|
+
++g_prefork_server->m_iCurChildren;
|
3356
|
+
if (pReq->child_status)
|
3357
|
+
{
|
3358
|
+
time_t curTime = time( NULL );
|
3359
|
+
pReq->child_status->m_tmWaitBegin = curTime;
|
3360
|
+
pReq->child_status->m_tmStart = curTime;
|
3361
|
+
}
|
3362
|
+
close(pReq->m_fd);
|
3363
|
+
pReq->m_fd = -1;
|
3364
|
+
return 0;
|
3365
|
+
}
|
3366
|
+
|
3367
|
+
|
3368
|
+
int LSAPI_Accept_Before_Fork(LSAPI_Request * pReq)
|
3369
|
+
{
|
3370
|
+
time_t lastTime = 0;
|
3371
|
+
time_t curTime = 0;
|
3372
|
+
fd_set readfds;
|
3373
|
+
struct timeval timeout;
|
3374
|
+
int wait_secs = 0;
|
3375
|
+
int ret = 0;
|
3376
|
+
|
3377
|
+
lsapi_prefork_server * pServer = g_prefork_server;
|
3378
|
+
|
3379
|
+
struct sigaction act;
|
3380
|
+
|
3381
|
+
lsapi_init_children_status();
|
3382
|
+
|
3383
|
+
act.sa_flags = 0;
|
3384
|
+
act.sa_handler = lsapi_sigchild;
|
3385
|
+
sigemptyset(&(act.sa_mask));
|
3386
|
+
if (sigaction(SIGCHLD, &act, &old_child))
|
3387
|
+
{
|
3388
|
+
perror( "Can't set signal handler for SIGCHILD" );
|
3389
|
+
return -1;
|
3390
|
+
}
|
3391
|
+
|
3392
|
+
/* Set up handler to kill children upon exit */
|
3393
|
+
act.sa_flags = 0;
|
3394
|
+
act.sa_handler = lsapi_cleanup;
|
3395
|
+
sigemptyset(&(act.sa_mask));
|
3396
|
+
if (sigaction(SIGTERM, &act, &old_term) ||
|
3397
|
+
sigaction(SIGINT, &act, &old_int ) ||
|
3398
|
+
sigaction(SIGUSR1, &act, &old_usr1) ||
|
3399
|
+
sigaction(SIGQUIT, &act, &old_quit))
|
3400
|
+
{
|
3401
|
+
perror( "Can't set signals" );
|
3402
|
+
return -1;
|
3403
|
+
}
|
3404
|
+
s_stop = 0;
|
3405
|
+
pReq->m_reqState = 0;
|
3406
|
+
|
3407
|
+
while(!s_stop)
|
3408
|
+
{
|
3409
|
+
if (s_proc_group_timer_cb != NULL) {
|
3410
|
+
s_proc_group_timer_cb(&s_ignore_pid);
|
3411
|
+
}
|
3412
|
+
|
3413
|
+
curTime = time(NULL);
|
3414
|
+
if (curTime != lastTime)
|
3415
|
+
{
|
3416
|
+
lastTime = curTime;
|
3417
|
+
if (lsapi_parent_dead())
|
3418
|
+
break;
|
3419
|
+
lsapi_check_child_status(curTime);
|
3420
|
+
if (pServer->m_iServerMaxIdle)
|
3421
|
+
{
|
3422
|
+
if (pServer->m_iCurChildren <= 0)
|
3423
|
+
{
|
3424
|
+
++wait_secs;
|
3425
|
+
if ( wait_secs > pServer->m_iServerMaxIdle )
|
3426
|
+
return -1;
|
3427
|
+
}
|
3428
|
+
else
|
3429
|
+
wait_secs = 0;
|
3430
|
+
}
|
3431
|
+
}
|
3432
|
+
|
3433
|
+
#if defined(linux) || defined(__linux) || defined(__linux__) || defined(__gnu_linux__)
|
3434
|
+
*s_avail_pages = sysconf(_SC_AVPHYS_PAGES);
|
3435
|
+
// lsapi_log("Memory total: %zd, free: %zd, free %%%zd\n",
|
3436
|
+
// s_total_pages, *s_avail_pages, *s_avail_pages * 100 / s_total_pages);
|
3437
|
+
|
3438
|
+
#endif
|
3439
|
+
FD_ZERO(&readfds);
|
3440
|
+
FD_SET(pServer->m_fd, &readfds);
|
3441
|
+
timeout.tv_sec = 1;
|
3442
|
+
timeout.tv_usec = 0;
|
3443
|
+
ret = (*g_fnSelect)(pServer->m_fd+1, &readfds, NULL, NULL, &timeout);
|
3444
|
+
if (ret == 1 )
|
3445
|
+
{
|
3446
|
+
int accepting = 0;
|
3447
|
+
if (s_accepting_workers)
|
3448
|
+
accepting = __sync_add_and_fetch(s_accepting_workers, 0);
|
3449
|
+
|
3450
|
+
if (pServer->m_iCurChildren > 0
|
3451
|
+
&& accepting > 0)
|
3452
|
+
{
|
3453
|
+
lsapi_log("children: %d, accepting: %d\n",
|
3454
|
+
pServer->m_iCurChildren, accepting);
|
3455
|
+
usleep( 400);
|
3456
|
+
while(accepting-- > 0)
|
3457
|
+
sched_yield();
|
3458
|
+
continue;
|
3459
|
+
}
|
3460
|
+
}
|
3461
|
+
else if (ret == -1)
|
3462
|
+
{
|
3463
|
+
if (errno == EINTR)
|
3464
|
+
continue;
|
3465
|
+
/* perror( "select()" ); */
|
3466
|
+
break;
|
3467
|
+
}
|
3468
|
+
else
|
3469
|
+
{
|
3470
|
+
continue;
|
3471
|
+
}
|
3472
|
+
|
3473
|
+
if (pServer->m_iCurChildren >=
|
3474
|
+
pServer->m_iMaxChildren + pServer->m_iExtraChildren)
|
3475
|
+
{
|
3476
|
+
lsapi_log("Reached max children process limit: %d, extra: %d,"
|
3477
|
+
" current: %d, busy: %d, please increase LSAPI_CHILDREN.\n",
|
3478
|
+
pServer->m_iMaxChildren, pServer->m_iExtraChildren,
|
3479
|
+
pServer->m_iCurChildren,
|
3480
|
+
s_busy_workers ? *s_busy_workers : -1);
|
3481
|
+
usleep(100000);
|
3482
|
+
continue;
|
3483
|
+
}
|
3484
|
+
|
3485
|
+
pReq->m_fd = lsapi_accept(pServer->m_fd);
|
3486
|
+
if (pReq->m_fd != -1)
|
3487
|
+
{
|
3488
|
+
wait_secs = 0;
|
3489
|
+
pReq->child_status = find_child_status(0);
|
3490
|
+
|
3491
|
+
ret = 0;
|
3492
|
+
break;
|
3493
|
+
}
|
3494
|
+
else
|
3495
|
+
{
|
3496
|
+
if ((errno == EINTR) || (errno == EAGAIN))
|
3497
|
+
continue;
|
3498
|
+
perror( "accept() failed" );
|
3499
|
+
ret = -1;
|
3500
|
+
break;
|
3501
|
+
}
|
3502
|
+
}
|
3503
|
+
|
3504
|
+
sigaction(SIGCHLD, &old_child, 0);
|
3505
|
+
sigaction(SIGTERM, &old_term, 0);
|
3506
|
+
sigaction(SIGQUIT, &old_quit, 0);
|
3507
|
+
sigaction(SIGINT, &old_int, 0);
|
3508
|
+
sigaction(SIGUSR1, &old_usr1, 0);
|
3509
|
+
|
3510
|
+
return ret;
|
3511
|
+
}
|
3512
|
+
|
3513
|
+
|
3514
|
+
void lsapi_perror( const char * pMessage, int err_no )
|
2965
3515
|
{
|
2966
|
-
|
3516
|
+
lsapi_log("%s, errno: %d (%s)\n", pMessage, err_no,
|
3517
|
+
strerror( err_no ) );
|
2967
3518
|
}
|
2968
3519
|
|
3520
|
+
|
2969
3521
|
int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
2970
3522
|
{
|
2971
3523
|
int fd;
|
@@ -2974,11 +3526,10 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
2974
3526
|
fd_set readfds;
|
2975
3527
|
struct timeval timeout;
|
2976
3528
|
|
2977
|
-
|
3529
|
+
if (s_skip_write)
|
3530
|
+
return -1;
|
2978
3531
|
|
2979
|
-
|
2980
|
-
&& *s_busy_workers >= s_max_busy_children)
|
2981
|
-
lsapi_close_connection(pReq);
|
3532
|
+
LSAPI_Finish_r( pReq );
|
2982
3533
|
|
2983
3534
|
if ( g_prefork_server )
|
2984
3535
|
{
|
@@ -2986,12 +3537,22 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
2986
3537
|
if ( lsapi_prefork_server_accept( g_prefork_server, pReq ) == -1 )
|
2987
3538
|
return -1;
|
2988
3539
|
}
|
2989
|
-
if (
|
3540
|
+
else if (s_req_processed > 0 && s_max_busy_workers > 0 && s_busy_workers)
|
3541
|
+
{
|
3542
|
+
ret = __sync_fetch_and_add(s_busy_workers, 0);
|
3543
|
+
if (ret >= s_max_busy_workers)
|
3544
|
+
{
|
3545
|
+
send_conn_close_notification(pReq->m_fd);
|
3546
|
+
lsapi_close_connection(pReq);
|
3547
|
+
}
|
3548
|
+
}
|
3549
|
+
|
3550
|
+
if ( (unsigned int)s_req_processed > s_max_reqs )
|
2990
3551
|
return -1;
|
2991
3552
|
|
2992
|
-
if (
|
3553
|
+
if ( s_worker_status )
|
2993
3554
|
{
|
2994
|
-
|
3555
|
+
s_worker_status->m_tmWaitBegin = time( NULL );
|
2995
3556
|
}
|
2996
3557
|
|
2997
3558
|
|
@@ -3012,23 +3573,44 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
3012
3573
|
{
|
3013
3574
|
if ( !g_running )
|
3014
3575
|
return -1;
|
3015
|
-
if (
|
3576
|
+
if (s_req_processed && s_worker_status
|
3577
|
+
&& s_worker_status->m_iKillSent)
|
3016
3578
|
return -1;
|
3017
3579
|
FD_ZERO( &readfds );
|
3018
3580
|
FD_SET( fd, &readfds );
|
3019
3581
|
timeout.tv_sec = 1;
|
3020
3582
|
timeout.tv_usec = 0;
|
3583
|
+
if (fd == pReq->m_fdListen)
|
3584
|
+
{
|
3585
|
+
if (s_worker_status)
|
3586
|
+
__sync_lock_test_and_set(&s_worker_status->m_state,
|
3587
|
+
LSAPI_STATE_ACCEPTING);
|
3588
|
+
if (s_accepting_workers)
|
3589
|
+
__sync_fetch_and_add(s_accepting_workers, 1);
|
3590
|
+
}
|
3021
3591
|
ret = (*g_fnSelect)(fd+1, &readfds, NULL, NULL, &timeout);
|
3592
|
+
if (fd == pReq->m_fdListen)
|
3593
|
+
{
|
3594
|
+
if (s_accepting_workers)
|
3595
|
+
__sync_fetch_and_sub(s_accepting_workers, 1);
|
3596
|
+
if (s_worker_status)
|
3597
|
+
__sync_lock_test_and_set(&s_worker_status->m_state,
|
3598
|
+
LSAPI_STATE_IDLE);
|
3599
|
+
}
|
3600
|
+
|
3022
3601
|
if ( ret == 0 )
|
3023
3602
|
{
|
3024
|
-
if (
|
3603
|
+
if ( s_worker_status )
|
3025
3604
|
{
|
3026
|
-
|
3605
|
+
s_worker_status->m_inProcess = 0;
|
3606
|
+
if (fd == pReq->m_fdListen
|
3607
|
+
&& (s_keepListener != 2 || !is_enough_free_mem()))
|
3608
|
+
return -1;
|
3027
3609
|
}
|
3028
3610
|
++wait_secs;
|
3029
3611
|
if (( s_max_idle_secs > 0 )&&(wait_secs >= s_max_idle_secs ))
|
3030
3612
|
return -1;
|
3031
|
-
if (
|
3613
|
+
if ( lsapi_parent_dead() )
|
3032
3614
|
return -1;
|
3033
3615
|
}
|
3034
3616
|
else if ( ret == -1 )
|
@@ -3040,15 +3622,17 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
3040
3622
|
}
|
3041
3623
|
else if ( ret >= 1 )
|
3042
3624
|
{
|
3043
|
-
if (s_req_processed &&
|
3625
|
+
if (s_req_processed && s_worker_status
|
3626
|
+
&& s_worker_status->m_iKillSent)
|
3044
3627
|
return -1;
|
3045
3628
|
if ( fd == pReq->m_fdListen )
|
3046
3629
|
{
|
3047
3630
|
pReq->m_fd = lsapi_accept( pReq->m_fdListen );
|
3048
3631
|
if ( pReq->m_fd != -1 )
|
3049
3632
|
{
|
3050
|
-
if (
|
3051
|
-
|
3633
|
+
if (s_worker_status)
|
3634
|
+
__sync_lock_test_and_set(&s_worker_status->m_state,
|
3635
|
+
LSAPI_STATE_CONNECTED);
|
3052
3636
|
if (s_busy_workers)
|
3053
3637
|
__sync_fetch_and_add(s_busy_workers, 1);
|
3054
3638
|
|
@@ -3056,7 +3640,7 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
3056
3640
|
|
3057
3641
|
lsapi_set_nblock( fd, 0 );
|
3058
3642
|
//init_conn_key( pReq->m_fd );
|
3059
|
-
if (
|
3643
|
+
if (!s_keepListener)
|
3060
3644
|
{
|
3061
3645
|
close( pReq->m_fdListen );
|
3062
3646
|
pReq->m_fdListen = -1;
|
@@ -3069,7 +3653,7 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
3069
3653
|
{
|
3070
3654
|
if (( errno == EINTR )||( errno == EAGAIN))
|
3071
3655
|
continue;
|
3072
|
-
|
3656
|
+
lsapi_perror( "lsapi_accept() error", errno );
|
3073
3657
|
return -1;
|
3074
3658
|
}
|
3075
3659
|
}
|
@@ -3080,12 +3664,13 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
3080
3664
|
|
3081
3665
|
if ( !readReq( pReq ) )
|
3082
3666
|
{
|
3083
|
-
if (
|
3667
|
+
if ( s_worker_status )
|
3084
3668
|
{
|
3085
|
-
|
3086
|
-
|
3087
|
-
++
|
3088
|
-
|
3669
|
+
s_worker_status->m_iKillSent = 0;
|
3670
|
+
s_worker_status->m_inProcess = 1;
|
3671
|
+
++s_worker_status->m_iReqCounter;
|
3672
|
+
s_worker_status->m_tmReqBegin =
|
3673
|
+
s_worker_status->m_tmLastCheckPoint = time(NULL);
|
3089
3674
|
}
|
3090
3675
|
++s_req_processed;
|
3091
3676
|
return 0;
|
@@ -3097,24 +3682,28 @@ int LSAPI_Prefork_Accept_r( LSAPI_Request * pReq )
|
|
3097
3682
|
|
3098
3683
|
}
|
3099
3684
|
|
3685
|
+
|
3100
3686
|
void LSAPI_Set_Max_Reqs( int reqs )
|
3101
|
-
{ s_max_reqs = reqs;
|
3687
|
+
{ s_max_reqs = reqs - 1; }
|
3102
3688
|
|
3103
3689
|
void LSAPI_Set_Max_Idle( int secs )
|
3104
3690
|
{ s_max_idle_secs = secs; }
|
3105
3691
|
|
3692
|
+
|
3106
3693
|
void LSAPI_Set_Max_Children( int maxChildren )
|
3107
3694
|
{
|
3108
3695
|
if ( g_prefork_server )
|
3109
3696
|
g_prefork_server->m_iMaxChildren = maxChildren;
|
3110
3697
|
}
|
3111
3698
|
|
3699
|
+
|
3112
3700
|
void LSAPI_Set_Extra_Children( int extraChildren )
|
3113
3701
|
{
|
3114
3702
|
if (( g_prefork_server )&&( extraChildren >= 0 ))
|
3115
3703
|
g_prefork_server->m_iExtraChildren = extraChildren;
|
3116
3704
|
}
|
3117
3705
|
|
3706
|
+
|
3118
3707
|
void LSAPI_Set_Max_Process_Time( int secs )
|
3119
3708
|
{
|
3120
3709
|
if (( g_prefork_server )&&( secs > 0 ))
|
@@ -3128,17 +3717,20 @@ void LSAPI_Set_Max_Idle_Children( int maxIdleChld )
|
|
3128
3717
|
g_prefork_server->m_iMaxIdleChildren = maxIdleChld;
|
3129
3718
|
}
|
3130
3719
|
|
3720
|
+
|
3131
3721
|
void LSAPI_Set_Server_Max_Idle_Secs( int serverMaxIdle )
|
3132
3722
|
{
|
3133
3723
|
if ( g_prefork_server )
|
3134
3724
|
g_prefork_server->m_iServerMaxIdle = serverMaxIdle;
|
3135
3725
|
}
|
3136
3726
|
|
3727
|
+
|
3137
3728
|
void LSAPI_Set_Slow_Req_Msecs( int msecs )
|
3138
3729
|
{
|
3139
3730
|
s_slow_req_msecs = msecs;
|
3140
3731
|
}
|
3141
3732
|
|
3733
|
+
|
3142
3734
|
int LSAPI_Get_Slow_Req_Msecs(void)
|
3143
3735
|
{
|
3144
3736
|
return s_slow_req_msecs;
|
@@ -3150,6 +3742,13 @@ void LSAPI_No_Check_ppid(void)
|
|
3150
3742
|
s_ppid = 0;
|
3151
3743
|
}
|
3152
3744
|
|
3745
|
+
|
3746
|
+
int LSAPI_Get_ppid()
|
3747
|
+
{
|
3748
|
+
return(s_ppid);
|
3749
|
+
}
|
3750
|
+
|
3751
|
+
|
3153
3752
|
#if defined(macintosh) || defined(__APPLE__) || defined(__APPLE_CC__)
|
3154
3753
|
#include <crt_externs.h>
|
3155
3754
|
#else
|
@@ -3178,6 +3777,7 @@ static void unset_lsapi_envs(void)
|
|
3178
3777
|
}
|
3179
3778
|
}
|
3180
3779
|
|
3780
|
+
|
3181
3781
|
static int lsapi_initSuEXEC(void)
|
3182
3782
|
{
|
3183
3783
|
int i;
|
@@ -3237,7 +3837,7 @@ static int lsapi_check_path(const char *p, char *final, int max_len)
|
|
3237
3837
|
{
|
3238
3838
|
char resolved_path[PATH_MAX+1];
|
3239
3839
|
int len = 0;
|
3240
|
-
char *end
|
3840
|
+
char *end;
|
3241
3841
|
if (*p != '/')
|
3242
3842
|
{
|
3243
3843
|
if (getcwd(final, max_len) == NULL)
|
@@ -3270,7 +3870,7 @@ static int lsapi_reopen_stderr2(const char *full_path)
|
|
3270
3870
|
int newfd = open(full_path, O_WRONLY | O_CREAT | O_APPEND, 0644);
|
3271
3871
|
if (newfd == -1)
|
3272
3872
|
{
|
3273
|
-
LSAPI_perror_r(NULL, "
|
3873
|
+
LSAPI_perror_r(NULL, "Failed to open custom stderr log", full_path);
|
3274
3874
|
return -1;
|
3275
3875
|
}
|
3276
3876
|
if (newfd != 2)
|
@@ -3279,12 +3879,12 @@ static int lsapi_reopen_stderr2(const char *full_path)
|
|
3279
3879
|
close(newfd);
|
3280
3880
|
dup2(2, 1);
|
3281
3881
|
}
|
3282
|
-
if (
|
3882
|
+
if (s_stderr_log_path && full_path != s_stderr_log_path)
|
3283
3883
|
{
|
3284
|
-
free(
|
3285
|
-
|
3884
|
+
free(s_stderr_log_path);
|
3885
|
+
s_stderr_log_path = NULL;
|
3286
3886
|
}
|
3287
|
-
|
3887
|
+
s_stderr_log_path = strdup(full_path);
|
3288
3888
|
return 0;
|
3289
3889
|
}
|
3290
3890
|
|
@@ -3296,7 +3896,7 @@ static int lsapi_reopen_stderr(const char *p)
|
|
3296
3896
|
return -1;
|
3297
3897
|
if (lsapi_check_path(p, full_path, PATH_MAX) == -1)
|
3298
3898
|
{
|
3299
|
-
LSAPI_perror_r(NULL, "
|
3899
|
+
LSAPI_perror_r(NULL, "Invalid custom stderr log path", p);
|
3300
3900
|
return -1;
|
3301
3901
|
}
|
3302
3902
|
return lsapi_reopen_stderr2(full_path);
|
@@ -3306,6 +3906,7 @@ static int lsapi_reopen_stderr(const char *p)
|
|
3306
3906
|
int LSAPI_Init_Env_Parameters( fn_select_t fp )
|
3307
3907
|
{
|
3308
3908
|
const char *p;
|
3909
|
+
char ch;
|
3309
3910
|
int n;
|
3310
3911
|
int avoidFork = 0;
|
3311
3912
|
|
@@ -3314,7 +3915,9 @@ int LSAPI_Init_Env_Parameters( fn_select_t fp )
|
|
3314
3915
|
{
|
3315
3916
|
lsapi_reopen_stderr(p);
|
3316
3917
|
}
|
3317
|
-
|
3918
|
+
if (!s_stderr_log_path)
|
3919
|
+
s_stderr_is_pipe = isPipe(STDERR_FILENO);
|
3920
|
+
|
3318
3921
|
p = getenv( "PHP_LSAPI_MAX_REQUESTS" );
|
3319
3922
|
if ( !p )
|
3320
3923
|
p = getenv( "LSAPI_MAX_REQS" );
|
@@ -3325,10 +3928,28 @@ int LSAPI_Init_Env_Parameters( fn_select_t fp )
|
|
3325
3928
|
LSAPI_Set_Max_Reqs( n );
|
3326
3929
|
}
|
3327
3930
|
|
3931
|
+
p = getenv( "LSAPI_KEEP_LISTEN" );
|
3932
|
+
if ( p )
|
3933
|
+
{
|
3934
|
+
n = atoi( p );
|
3935
|
+
s_keepListener = n;
|
3936
|
+
}
|
3937
|
+
|
3328
3938
|
p = getenv( "LSAPI_AVOID_FORK" );
|
3329
3939
|
if ( p )
|
3330
3940
|
{
|
3331
3941
|
avoidFork = atoi( p );
|
3942
|
+
if (avoidFork)
|
3943
|
+
{
|
3944
|
+
s_keepListener = 2;
|
3945
|
+
ch = *(p + strlen(p) - 1);
|
3946
|
+
if ( ch == 'G' || ch == 'g' )
|
3947
|
+
avoidFork *= 1024 * 1024 * 1024;
|
3948
|
+
else if ( ch == 'M' || ch == 'm' )
|
3949
|
+
avoidFork *= 1024 * 1024;
|
3950
|
+
if (avoidFork >= 1024 * 10240)
|
3951
|
+
s_min_avail_pages = avoidFork / 4096;
|
3952
|
+
}
|
3332
3953
|
}
|
3333
3954
|
|
3334
3955
|
p = getenv( "LSAPI_ACCEPT_NOTIFY" );
|
@@ -3363,14 +3984,6 @@ int LSAPI_Init_Env_Parameters( fn_select_t fp )
|
|
3363
3984
|
LSAPI_Set_Max_Idle( n );
|
3364
3985
|
}
|
3365
3986
|
|
3366
|
-
p = getenv( "LSAPI_KEEP_LISTEN" );
|
3367
|
-
if ( p )
|
3368
|
-
{
|
3369
|
-
n = atoi( p );
|
3370
|
-
s_keepListener = n;
|
3371
|
-
}
|
3372
|
-
|
3373
|
-
|
3374
3987
|
if ( LSAPI_Is_Listen() )
|
3375
3988
|
{
|
3376
3989
|
n = 0;
|
@@ -3381,7 +3994,7 @@ int LSAPI_Init_Env_Parameters( fn_select_t fp )
|
|
3381
3994
|
n = atoi( p );
|
3382
3995
|
if ( n > 1 )
|
3383
3996
|
{
|
3384
|
-
LSAPI_Init_Prefork_Server( n, fp, avoidFork );
|
3997
|
+
LSAPI_Init_Prefork_Server( n, fp, avoidFork != 0 );
|
3385
3998
|
LSAPI_Set_Server_fd( g_req.m_fdListen );
|
3386
3999
|
}
|
3387
4000
|
|
@@ -3407,6 +4020,16 @@ int LSAPI_Init_Env_Parameters( fn_select_t fp )
|
|
3407
4020
|
{
|
3408
4021
|
LSAPI_No_Check_ppid();
|
3409
4022
|
}
|
4023
|
+
|
4024
|
+
p = getenv("LSAPI_MAX_BUSY_WORKER");
|
4025
|
+
if (p)
|
4026
|
+
{
|
4027
|
+
n = atoi(p);
|
4028
|
+
s_max_busy_workers = n;
|
4029
|
+
if (n >= 0)
|
4030
|
+
LSAPI_No_Check_ppid();
|
4031
|
+
}
|
4032
|
+
|
3410
4033
|
|
3411
4034
|
p = getenv( "LSAPI_DUMP_DEBUG_INFO" );
|
3412
4035
|
if ( p )
|
@@ -3460,6 +4083,7 @@ static void byteReverse(unsigned char *buf, unsigned longs)
|
|
3460
4083
|
} while (--longs);
|
3461
4084
|
}
|
3462
4085
|
|
4086
|
+
|
3463
4087
|
/*
|
3464
4088
|
* Start MD5 accumulation. Set bit count to 0 and buffer to mysterious
|
3465
4089
|
* initialization constants.
|
@@ -3523,6 +4147,7 @@ void lsapi_MD5Update(struct lsapi_MD5Context *ctx, unsigned char const *buf, uns
|
|
3523
4147
|
memmove(ctx->in, buf, len);
|
3524
4148
|
}
|
3525
4149
|
|
4150
|
+
|
3526
4151
|
/*
|
3527
4152
|
* Final wrapup - pad to 64-byte boundary with the bit pattern
|
3528
4153
|
* 1 0* (64-bit count of bits processed, MSB-first)
|
@@ -3568,6 +4193,7 @@ void lsapi_MD5Final(unsigned char digest[16], struct lsapi_MD5Context *ctx)
|
|
3568
4193
|
memset(ctx, 0, sizeof(*ctx)); /* In case it's sensitive */
|
3569
4194
|
}
|
3570
4195
|
|
4196
|
+
|
3571
4197
|
/* The four core functions - F1 is optimized somewhat */
|
3572
4198
|
|
3573
4199
|
/* #define F1(x, y, z) (x & y | ~x & z) */
|
@@ -3668,3 +4294,18 @@ static void lsapi_MD5Transform(uint32 buf[4], uint32 const in[16])
|
|
3668
4294
|
buf[3] += d;
|
3669
4295
|
}
|
3670
4296
|
|
4297
|
+
|
4298
|
+
int LSAPI_Set_Restored_Parent_Pid(int pid)
|
4299
|
+
{
|
4300
|
+
int old_ppid = s_ppid;
|
4301
|
+
s_restored_ppid = pid;
|
4302
|
+
return old_ppid;
|
4303
|
+
}
|
4304
|
+
|
4305
|
+
|
4306
|
+
int LSAPI_Inc_Req_Processed(int cnt)
|
4307
|
+
{
|
4308
|
+
return __sync_add_and_fetch(s_global_counter, cnt);
|
4309
|
+
}
|
4310
|
+
|
4311
|
+
|