root/eaccelerator/trunk/eaccelerator.h

Revision 350, 14.5 kB (checked in by bart, 1 month ago)

Failed to stage the commit properly

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1 /*
2    +----------------------------------------------------------------------+
3    | eAccelerator project                                                 |
4    +----------------------------------------------------------------------+
5    | Copyright (c) 2004 - 2007 eAccelerator                               |
6    | http://eaccelerator.net                                                  |
7    +----------------------------------------------------------------------+
8    | This program is free software; you can redistribute it and/or        |
9    | modify it under the terms of the GNU General Public License          |
10    | as published by the Free Software Foundation; either version 2       |
11    | of the License, or (at your option) any later version.               |
12    |                                                                      |
13    | This program is distributed in the hope that it will be useful,      |
14    | but WITHOUT ANY WARRANTY; without even the implied warranty of       |
15    | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        |
16    | GNU General Public License for more details.                         |
17    |                                                                      |
18    | You should have received a copy of the GNU General Public License    |
19    | along with this program; if not, write to the Free Software          |
20    | Foundation, Inc., 59 Temple Place - Suite 330, Boston,               |
21    | MA  02111-1307, USA.                                                 |
22    |                                                                      |
23    | A copy is availble at http://www.gnu.org/copyleft/gpl.txt            |
24    +----------------------------------------------------------------------+
25    $Id$
26 */
27
28 #ifndef INCLUDED_EACCELERATOR_H
29 #define INCLUDED_EACCELERATOR_H
30
31 #include "php.h"
32 #include "zend.h"
33 #include "zend_API.h"
34 #include "zend_extensions.h"
35
36 #if !defined(ZEND_WIN32) && defined(HAVE_CONFIG_H)
37 #  if ZEND_MODULE_API_NO >= 20001222
38 #    include "config.h"
39 #  else
40 #    include "php_config.h"
41 #  endif
42 #endif
43
44 #if PHP_MAJOR_VERSION == 4 || (PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION < 1)
45     #error "eAccelerator only supports PHP 5.1 and higher"
46 #endif
47
48 #if PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION >= 2
49 #   define ZEND_ENGINE_2_2
50 #endif
51
52 #if PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION >= 3
53 #   define ZEND_ENGINE_2_3
54 #endif
55
56 /* fixes compile errors on php5.1 */
57 #ifdef STR_EMPTY_ALLOC
58 #       define empty_string STR_EMPTY_ALLOC()
59 #endif
60
61 #if !defined(ZEND_WIN32) && defined(WITH_EACCELERATOR_USE_INODE)
62 /* UnDefine if your filesystem doesn't support inodes */
63 #  define EACCELERATOR_USE_INODE
64 #endif
65
66 #ifdef WITH_EACCELERATOR_CRASH_DETECTION
67 #  include <signal.h>
68 #endif
69
70 #define EACCELERATOR_MM_FILE "/tmp/eaccelerator"
71
72 #ifdef EACCELERATOR_WITHOUT_FILE_LOCKING
73 #  ifndef LOCK_SH
74 #    define LOCK_SH 1
75 #    define LOCK_EX 2
76 #    define LOCK_UN 8
77 #  endif
78 #  define EACCELERATOR_FLOCK(FILE,OP)
79 #else
80 #  ifndef ZEND_WIN32
81 #    ifdef HAVE_FLOCK
82 #          include <sys/file.h>
83 #      define EACCELERATOR_FLOCK(FILE,OP) flock((FILE),(OP))
84 #    else
85 #      ifndef LOCK_SH
86 #        define LOCK_SH 1
87 #        define LOCK_EX 2
88 #        define LOCK_UN 8
89 #      endif
90 #      define EACCELERATOR_FLOCK(FILE,OP)
91 #    endif
92 #  else
93 #    define LOCK_SH 0
94 #    define LOCK_EX 1
95 #    define LOCK_UN 2
96 #    define EACCELERATOR_FLOCK(FILE,OP) {OVERLAPPED offset = {0,0,0,0,NULL};\
97                                    if ((OP) == LOCK_EX) {\
98                                      LockFileEx((HANDLE)_get_osfhandle(FILE), \
99                                        LOCKFILE_EXCLUSIVE_LOCK, 0,\
100                                        1, 0, &offset);\
101                                    } else if ((OP) == LOCK_SH) {\
102                                      LockFileEx((HANDLE)_get_osfhandle(FILE), \
103                                        0, 0,\
104                                        1, 0, &offset);\
105                                    } else if ((OP) == LOCK_UN) {\
106                                      UnlockFileEx((HANDLE)_get_osfhandle(FILE), \
107                                        0,\
108                                        1, 0, &offset);\
109                                    }}
110 #  endif
111 #endif
112
113 #if !defined(_INTPTR_T_DEFINED) && ZEND_WIN32
114         typedef intptr_t;
115         #define _INTPTR_T_DEFINED
116 #endif
117
118 #if !defined(ssize_t) && ZEND_WIN32
119         /* define ssize_t for Win32. */
120         #define ssize_t int
121 #endif
122
123 #ifdef HAVE_EACCELERATOR
124
125 #include "mm.h"
126
127 #ifdef ZEND_WIN32
128 #  include <process.h>
129 #  ifndef S_ISREG
130 #    define S_ISREG(mode) (((mode)&S_IFMT) & S_IFREG)
131 #  endif
132 #  ifndef S_IRUSR
133 #    define S_IRUSR S_IREAD
134 #  endif
135 #  ifndef S_IWUSR
136 #    define S_IWUSR S_IWRITE
137 #  endif
138 #else
139 #  include <dirent.h>
140 #endif
141
142 #ifdef ZTS
143 #  define ZTS_LOCK()    tsrm_mutex_lock(ea_mutex)
144 #  define ZTS_UNLOCK()  tsrm_mutex_unlock(ea_mutex)
145 #else
146 #  define ZTS_LOCK()
147 #  define ZTS_UNLOCK()
148 #endif
149
150 #if defined(EACCELERATOR_PROTECT_SHM)
151 #  define EACCELERATOR_PROTECT()    do {mm_protect(eaccelerator_mm_instance->mm, MM_PROT_READ);} while(0)
152 #  define EACCELERATOR_UNPROTECT()  do {mm_protect(eaccelerator_mm_instance->mm, MM_PROT_READ|MM_PROT_WRITE);} while(0)
153 #else
154 #  define EACCELERATOR_PROTECT()
155 #  define EACCELERATOR_UNPROTECT()
156 #endif
157
158 #define EACCELERATOR_LOCK_RW()    do {ZTS_LOCK(); mm_lock(eaccelerator_mm_instance->mm, MM_LOCK_RW);} while(0)
159 #define EACCELERATOR_LOCK_RD()    do {ZTS_LOCK(); mm_lock(eaccelerator_mm_instance->mm, MM_LOCK_RD);} while(0)
160 #define EACCELERATOR_UNLOCK()     do {mm_unlock(eaccelerator_mm_instance->mm); ZTS_UNLOCK();} while(0)
161 #define EACCELERATOR_UNLOCK_RW()  EACCELERATOR_UNLOCK()
162 #define EACCELERATOR_UNLOCK_RD()  EACCELERATOR_UNLOCK()
163
164 #define EACCELERATOR_BLOCK_INTERRUPTIONS()   HANDLE_BLOCK_INTERRUPTIONS()
165 #define EACCELERATOR_UNBLOCK_INTERRUPTIONS() HANDLE_UNBLOCK_INTERRUPTIONS()
166
167 #define EACCELERATOR_HASH_LEVEL 2
168 #define EA_HASH_SIZE      512
169 #define EA_USER_HASH_SIZE 512
170
171 #define EA_HASH_MAX       (EA_HASH_SIZE-1)
172 #define EA_USER_HASH_MAX  (EA_USER_HASH_SIZE-1)
173
174 #define eaccelerator_malloc(size)        mm_malloc_lock(eaccelerator_mm_instance->mm, size)
175 #define eaccelerator_free(x)             mm_free_lock(eaccelerator_mm_instance->mm, x)
176 #define eaccelerator_malloc_nolock(size) mm_malloc_nolock(eaccelerator_mm_instance->mm, size)
177 #define eaccelerator_free_nolock(x)      mm_free_nolock(eaccelerator_mm_instance->mm, x)
178
179 #if (defined (__GNUC__) && __GNUC__ >= 2)
180 #define EACCELERATOR_PLATFORM_ALIGNMENT (__alignof__ (align_test))
181 #else
182 #define EACCELERATOR_PLATFORM_ALIGNMENT (sizeof(align_union))
183 #endif
184
185 #define EACCELERATOR_ALIGN(n) (n) = (void*)((((size_t)(n)-1) & ~(EACCELERATOR_PLATFORM_ALIGNMENT-1)) + EACCELERATOR_PLATFORM_ALIGNMENT)
186 #define EA_SIZE_ALIGN(n) (n) = ((((size_t)(n)-1) & ~(EACCELERATOR_PLATFORM_ALIGNMENT-1)) + EACCELERATOR_PLATFORM_ALIGNMENT)
187
188 #ifdef ZEND_ENGINE_2_3
189     #define RESET_PZVAL_REFCOUNT(z) Z_SET_REFCOUNT_P(z, 1)
190 #else
191     #define RESET_PZVAL_REFCOUNT(z) (z)->refcount = 1;
192 #endif
193
194 #define MAX_DUP_STR_LEN 256
195
196 /******************************************************************************/
197
198
199 #ifndef offsetof
200 #  define offsetof(str,fld) ((size_t)&(((str*)NULL)->fld))
201 #endif
202
203 typedef struct _eaccelerator_op_array {
204         zend_uchar type;
205 #ifdef ZEND_ENGINE_2_3
206     zend_uint this_var;
207 #else
208         zend_bool uses_this;
209 #endif
210         zend_bool return_reference;
211         zend_uint num_args;
212         zend_uint required_num_args;
213         zend_arg_info *arg_info;
214         zend_bool pass_rest_by_reference;
215         char *function_name;
216         char *scope_name;
217         int scope_name_len;
218         zend_uint fn_flags;
219         zend_op *opcodes;
220         zend_uint last;
221         zend_compiled_variable *vars;
222     int last_var;
223         zend_uint T;
224         zend_brk_cont_element *brk_cont_array;
225         zend_uint last_brk_cont;
226         zend_try_catch_element *try_catch_array;
227         int last_try_catch;
228         HashTable *static_variables;
229         char *filename;
230         zend_uint line_start;
231         zend_uint line_end;
232 #ifdef INCLUDE_DOC_COMMENTS
233     char *doc_comment;
234     zend_uint doc_comment_len;
235 #endif
236 } ea_op_array;
237
238 typedef struct _eaccelerator_class_entry {
239         char type;
240         char *name;
241         zend_uint name_length;
242         char *parent;
243         HashTable function_table;
244         HashTable default_properties;
245         HashTable properties_info;
246         HashTable default_static_members;
247         HashTable *static_members;
248         HashTable constants_table;
249         zend_uint ce_flags;
250         zend_uint num_interfaces;
251
252         char *filename;
253         zend_uint line_start;
254         zend_uint line_end;
255 #  ifdef INCLUDE_DOC_COMMENTS
256     char *doc_comment;
257     zend_uint doc_comment_len;
258 #  endif
259 } ea_class_entry;
260
261 /*
262  * To cache functions and classes.
263  */
264 typedef struct _ea_fc_entry {
265         void *fc;
266         struct _ea_fc_entry *next;
267         int htablen;
268         char htabkey[1];                        /* must be last element */
269 } ea_fc_entry;
270
271
272 /*
273  * A ea_cache_entry is a bucket for one PHP script file.
274  * User functions and classes defined in the file go into
275  * the list of ea_fc_entry.
276  */
277 typedef struct _ea_cache_entry {
278         struct _ea_cache_entry *next;
279 #ifdef EACCELERATOR_USE_INODE
280         dev_t st_dev;                           /* file's device                         */
281         ino_t st_ino;                           /* file's inode                          */
282 #else
283         unsigned int hv;                        /* hash value                            */
284 #endif
285         off_t filesize;                         /* file size */
286         time_t mtime;                           /* file last modification time           */
287         time_t ttl;                             /* expiration time (updated on each hit) */
288         time_t ts;                              /* timestamp of cache entry              */
289         unsigned int size;                      /* entry size (bytes)                    */
290         unsigned int nhits;                     /* hits count                            */
291         unsigned int nreloads;                  /* count of reloads                      */
292         int use_cnt;                    /* how many processes uses the entry     */
293         ea_op_array *op_array;  /* script's global scope code        */
294         ea_fc_entry *f_head;            /* list of nested functions          */
295         ea_fc_entry *c_head;            /* list of nested classes            */
296         zend_bool removed;                      /* the entry is scheduled to remove  */
297         char realfilename[1];           /* real file name (must be last el.) */
298 } ea_cache_entry;
299
300 /*
301  * bucket for user's cache
302  */
303 typedef struct _ea_user_cache_entry {
304         struct _ea_user_cache_entry *next;
305         unsigned int hv;                        /* hash value                  */
306         long ttl;                                       /* expiration time             */
307         long create;
308         int size;
309         zval value;                                     /* value                       */
310         char key[1];                            /* key value (must be last el) */
311 } ea_user_cache_entry;
312
313 /*
314  * Linked list of ea_cache_entry which are used by process/thread
315  */
316 typedef struct _ea_used_entry {
317         struct _ea_used_entry *next;
318         ea_cache_entry *entry;
319 } ea_used_entry;
320
321 /*
322  * Linked list of locks
323  */
324 typedef struct _ea_lock_entry {
325         struct _ea_lock_entry *next;
326         pid_t pid;
327 #ifdef ZTS
328         THREAD_T thread;
329 #endif
330         char key[1];
331 } ea_lock_entry;
332
333 typedef struct _ea_file_header {
334         char magic[8];                          /* "EACCELERATOR" */
335         int eaccelerator_version[2];
336         int zend_version[2];
337         int php_version[2];
338         int size;
339         time_t mtime;
340         time_t ts;
341         unsigned int crc32;
342 } ea_file_header;
343
344 int check_header(ea_file_header *hdr);
345 void init_header(ea_file_header *hdr);
346
347 typedef struct {
348         MM *mm;
349         pid_t owner;
350         size_t total;
351         unsigned int hash_cnt;
352         unsigned int user_hash_cnt;
353         zend_bool enabled;
354         zend_bool optimizer_enabled;
355         unsigned int rem_cnt;
356         time_t last_prune;
357         ea_cache_entry *removed;
358         ea_lock_entry *locks;
359
360         ea_cache_entry *hash[EA_HASH_SIZE];
361         ea_user_cache_entry *user_hash[EA_USER_HASH_SIZE];
362 } eaccelerator_mm;
363
364 /*
365  * Where to cache
366  */
367 typedef enum _ea_cache_place {
368         ea_shm_and_disk,        /* in shm and in disk */
369         ea_shm,                         /* in shm, but if it is not possible then on disk */
370         ea_shm_only,            /* in shm only  */
371         ea_disk_only,           /* on disk only */
372         ea_none                         /* don't cache  */
373 } ea_cache_place;
374
375 typedef union align_union {
376   double d;
377   void *v;
378   int (*func)(int);
379   long l;
380 } align_union;
381
382 #ifdef ZEND_ENGINE_2_2
383 typedef union _align_test {
384   void *ptr;
385   double dbl;
386   long lng;
387 } align_test;
388 #endif
389
390 /******************************************************************************/
391
392 #ifdef ZTS
393 #  ifdef __APPLE__
394 /* Workaround to prevent 'multiple definitions of symbol' during build on OSX */
395 static MUTEX_T ea_mutex;
396 #  else
397 MUTEX_T ea_mutex;
398 #  endif
399 #endif
400
401 /* needed to compile eA as a static php module */
402 extern zend_module_entry eaccelerator_module_entry;
403 #define phpext_eaccelerator_ptr &eaccelerator_module_entry
404
405
406 void format_size (char *s, unsigned int size, int legend);
407 void eaccelerator_prune (time_t t);
408
409 int eaccelerator_lock (const char *key, int key_len TSRMLS_DC);
410 int eaccelerator_unlock (const char *key, int key_len TSRMLS_DC);
411
412 void *eaccelerator_malloc2 (size_t size TSRMLS_DC);
413
414 unsigned int eaccelerator_crc32 (const char *p, size_t n);
415 int eaccelerator_md5 (char *s, const char *prefix, const char *key TSRMLS_DC);
416
417 #  ifdef WITH_EACCELERATOR_OPTIMIZER
418 void eaccelerator_optimize (zend_op_array * op_array);
419 #  endif
420
421 #ifdef ZTS
422 #  define EAG(v) TSRMG(eaccelerator_globals_id, zend_eaccelerator_globals*, v)
423 #else
424 #  define EAG(v) (eaccelerator_globals.v)
425 #endif
426
427 struct ea_pattern_t {
428   struct ea_pattern_t *next;
429   char *pattern;
430 };
431
432 /*
433  * Globals (different for each process/thread)
434  */
435 ZEND_BEGIN_MODULE_GLOBALS (eaccelerator)
436 void *used_entries;                     /* list of files which are used     */
437                                         /* by process/thread                */
438 zend_bool enabled;
439 zend_bool optimizer_enabled;
440 zend_bool compression_enabled;
441 zend_bool compiler;
442 zend_bool compress;
443 zend_bool compress_content;
444 zend_bool in_request;
445 zend_llist *content_headers;
446 long compress_level;
447 char *cache_dir;
448 char *eaccelerator_log_file;
449 char *name_space;
450 char *mem;
451 char *allowed_admin_path;
452 time_t req_start;                       /* time of request start (set in RINIT) */
453 HashTable strings;
454 HashTable restored;
455 zend_class_entry *class_entry;
456 zend_uint refcount_helper;
457 #if defined(WITH_EACCELERATOR_CONTENT_CACHING) || defined(WITH_EACCELERATOR_SESSIONS) || defined(WITH_EACCELERATOR_SHM)
458 char hostname[32];
459 #endif
460 struct ea_pattern_t *pattern_list;
461 #ifdef WITH_EACCELERATOR_CRASH_DETECTION
462 #ifdef SIGSEGV
463 void (*original_sigsegv_handler) (int);
464 #endif
465 #ifdef SIGFPE
466 void (*original_sigfpe_handler) (int);
467 #endif
468 #ifdef SIGBUS
469 void (*original_sigbus_handler) (int);
470 #endif
471 #ifdef SIGILL
472 void (*original_sigill_handler) (int);
473 #endif
474 #ifdef SIGABRT
475 void (*original_sigabrt_handler) (int);
476 #endif
477 #endif
478 #ifdef DEBUG
479 int xpad;
480 int profile_level;
481 long self_time[256];
482 #endif
483 #ifdef WITH_EACCELERATOR_SESSIONS
484 char *session;
485 #endif
486 ZEND_END_MODULE_GLOBALS (eaccelerator)
487
488 ZEND_EXTERN_MODULE_GLOBALS (eaccelerator)
489
490 #define EACCELERATOR_EXTENSION_NAME "eAccelerator"
491
492 #define EA_MAGIC "EACCELERATOR"
493
494 #define EACCELERATOR_VERSION_GUID   "PHPE8EDA1B6-806A-4851-B1C8-A6B4712F44FB"
495 #define EACCELERATOR_LOGO_GUID      "PHPE6F78DE9-13E4-4dee-8518-5FA2DACEA803"
496 #define EACCELERATOR_VERSION_STRING ("eAccelerator " EACCELERATOR_VERSION " (PHP " PHP_VERSION ")")
497
498 #endif          /* HAVE_EACCELERATOR */
499 #endif          /* #ifndef INCLUDED_EACCELERATOR_H */
Note: See TracBrowser for help on using the browser.