├── deps
├── jemalloc
│ ├── config.stamp.in
│ ├── test
│ │ ├── bitmap.exp
│ │ ├── mremap.exp
│ │ ├── rallocm.exp
│ │ ├── ALLOCM_ARENA.exp
│ │ ├── allocated.exp
│ │ ├── thread_arena.exp
│ │ ├── thread_tcache_enabled.exp
│ │ ├── allocm.exp
│ │ ├── aligned_alloc.exp
│ │ ├── posix_memalign.exp
│ │ ├── jemalloc_test.h.in
│ │ ├── mremap.c
│ │ ├── ALLOCM_ARENA.c
│ │ ├── thread_arena.c
│ │ ├── thread_tcache_enabled.c
│ │ ├── allocated.c
│ │ ├── posix_memalign.c
│ │ ├── aligned_alloc.c
│ │ ├── rallocm.c
│ │ ├── bitmap.c
│ │ └── allocm.c
│ ├── VERSION
│ ├── src
│ │ ├── mb.c
│ │ ├── hash.c
│ │ ├── atomic.c
│ │ ├── extent.c
│ │ ├── rtree.c
│ │ ├── tsd.c
│ │ ├── bitmap.c
│ │ ├── base.c
│ │ ├── mutex.c
│ │ ├── chunk_dss.c
│ │ └── chunk_mmap.c
│ ├── doc
│ │ ├── jemalloc.html
│ │ ├── html.xsl.in
│ │ ├── manpages.xsl.in
│ │ └── stylesheet.xsl
│ ├── bin
│ │ ├── jemalloc.sh
│ │ └── jemalloc.sh.in
│ ├── autogen.sh
│ ├── include
│ │ ├── msvc_compat
│ │ │ ├── stdbool.h
│ │ │ └── strings.h
│ │ └── jemalloc
│ │ │ ├── internal
│ │ │ ├── chunk_mmap.h
│ │ │ ├── quarantine.h
│ │ │ ├── base.h
│ │ │ ├── chunk_dss.h
│ │ │ ├── extent.h
│ │ │ ├── huge.h
│ │ │ ├── hash.h
│ │ │ ├── prng.h
│ │ │ ├── chunk.h
│ │ │ ├── qr.h
│ │ │ ├── ql.h
│ │ │ ├── ckh.h
│ │ │ ├── mutex.h
│ │ │ ├── mb.h
│ │ │ ├── size_classes.sh
│ │ │ ├── ctl.h
│ │ │ ├── util.h
│ │ │ ├── stats.h
│ │ │ └── rtree.h
│ │ │ └── jemalloc.h.in
│ ├── .gitignore
│ ├── README
│ └── COPYING
└── Makefile
├── .gitignore
├── src
├── logo.h
├── version.h
├── fmacros.h
├── config.h
├── Makefile
├── Makefile.dep
├── network.h
├── storage.h
├── message.c
├── object.h
├── route_t.h
├── channel_t.h
├── handlers.h
├── message.h
├── object.c
├── xmalloc.h
├── utils.h
├── queue.h
├── keylist.h
├── list.h
├── queue_t.h
├── user.c
├── event.h
├── user.h
├── event_select.c
├── keylist.c
├── lzf.h
├── config.c
├── event_epoll.c
├── queue.c
└── list.c
├── Makefile
├── eaglemq.conf
├── README.md
└── COPYING
/deps/jemalloc/config.stamp.in:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | eaglemq.log
2 | eaglemq.dat
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/bitmap.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/mremap.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/rallocm.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/ALLOCM_ARENA.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/allocated.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/thread_arena.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/thread_tcache_enabled.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Test end
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/VERSION:
--------------------------------------------------------------------------------
1 | 3.2.0-0-g87499f6748ebe4817571e817e9f680ccb5bf54a9
2 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/mb.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MB_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/hash.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_HASH_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/atomic.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_ATOMIC_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
--------------------------------------------------------------------------------
/deps/jemalloc/doc/jemalloc.html:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/yakushstanislav/EagleMQ/HEAD/deps/jemalloc/doc/jemalloc.html
--------------------------------------------------------------------------------
/src/logo.h:
--------------------------------------------------------------------------------
1 | char *ascii_logo =
2 | "EagleMQ\n"
3 | "Version ..... %s\n"
4 | "Host ........ %s\n"
5 | "Port ........ %d\n"
6 | "Event API ... %s\n";
7 |
--------------------------------------------------------------------------------
/src/version.h:
--------------------------------------------------------------------------------
1 | #define EAGLE_VERSION_MAJOR 1
2 | #define EAGLE_VERSION_MINOR 3
3 | #define EAGLE_VERSION_PATCH 0
4 |
5 | #define EAGLE_VERSION "1.3.0"
6 |
--------------------------------------------------------------------------------
/deps/jemalloc/bin/jemalloc.sh:
--------------------------------------------------------------------------------
1 | #!/bin/sh
2 |
3 | prefix=/usr/local
4 | exec_prefix=/usr/local
5 | libdir=${exec_prefix}/lib
6 |
7 | LD_PRELOAD=${libdir}/libjemalloc.so.1
8 | export LD_PRELOAD
9 | exec "$@"
10 |
--------------------------------------------------------------------------------
/deps/jemalloc/bin/jemalloc.sh.in:
--------------------------------------------------------------------------------
1 | #!/bin/sh
2 |
3 | prefix=@prefix@
4 | exec_prefix=@exec_prefix@
5 | libdir=@libdir@
6 |
7 | @LD_PRELOAD_VAR@=${libdir}/libjemalloc.@SOREV@
8 | export @LD_PRELOAD_VAR@
9 | exec "$@"
10 |
--------------------------------------------------------------------------------
/deps/jemalloc/doc/html.xsl.in:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/deps/jemalloc/doc/manpages.xsl.in:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/src/fmacros.h:
--------------------------------------------------------------------------------
1 | #ifndef __EAGLE_MACROS_H__
2 | #define __EAGLE_MACROS_H__
3 |
4 | #define _BSD_SOURCE
5 |
6 | #if defined(__linux__)
7 | #define _GNU_SOURCE
8 | #endif
9 |
10 | #if defined(__linux__) || defined(__OpenBSD__)
11 | #define _XOPEN_SOURCE 700
12 | #else
13 | #define _XOPEN_SOURCE
14 | #endif
15 |
16 | #endif
17 |
--------------------------------------------------------------------------------
/deps/jemalloc/doc/stylesheet.xsl:
--------------------------------------------------------------------------------
1 |
2 | ansi
3 |
4 |
5 | ""
6 |
7 |
8 |
--------------------------------------------------------------------------------
/deps/jemalloc/autogen.sh:
--------------------------------------------------------------------------------
1 | #!/bin/sh
2 |
3 | for i in autoconf; do
4 | echo "$i"
5 | $i
6 | if [ $? -ne 0 ]; then
7 | echo "Error $? in $i"
8 | exit 1
9 | fi
10 | done
11 |
12 | echo "./configure --enable-autogen $@"
13 | ./configure --enable-autogen $@
14 | if [ $? -ne 0 ]; then
15 | echo "Error $? in ./configure"
16 | exit 1
17 | fi
18 |
--------------------------------------------------------------------------------
/deps/Makefile:
--------------------------------------------------------------------------------
1 | default:
2 | @echo "Explicit target required"
3 |
4 | jemalloc:
5 | cd jemalloc && ./configure --with-jemalloc-prefix=je_ --enable-cc-silence CFLAGS="$(JEMALLOC_CFLAGS)" LDFLAGS="$(JEMALLOC_LDFLAGS)"
6 | cd jemalloc && $(MAKE) lib/libjemalloc.a
7 |
8 | distclean:
9 | -(cd jemalloc && [ -f Makefile ] && $(MAKE) distclean) > /dev/null || true
10 |
11 | .PHONY: default jemalloc distclean
12 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/msvc_compat/stdbool.h:
--------------------------------------------------------------------------------
1 | #ifndef stdbool_h
2 | #define stdbool_h
3 |
4 | #include
5 |
6 | /* MSVC doesn't define _Bool or bool in C, but does have BOOL */
7 | /* Note this doesn't pass autoconf's test because (bool) 0.5 != true */
8 | typedef BOOL _Bool;
9 |
10 | #define bool _Bool
11 | #define true 1
12 | #define false 0
13 |
14 | #define __bool_true_false_are_defined 1
15 |
16 | #endif /* stdbool_h */
17 |
--------------------------------------------------------------------------------
/Makefile:
--------------------------------------------------------------------------------
1 | all:
2 | cd src && $(MAKE) $@
3 |
4 | run:
5 | cd src && $(MAKE) $@
6 |
7 | install:
8 | cd src && $(MAKE) $@
9 |
10 | uninstall:
11 | cd src && $(MAKE) $@
12 |
13 | clean:
14 | cd src && $(MAKE) $@
15 |
16 | distclean:
17 | cd src && $(MAKE) $@
18 |
19 | changelog:
20 | @echo "Changelog created!"
21 | @git log --no-merges --format="%cd %s (%an)" --date=short > Changelog
22 |
23 | .PHONY: all run install uninstall clean distclean changelog
24 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/msvc_compat/strings.h:
--------------------------------------------------------------------------------
1 | #ifndef strings_h
2 | #define strings_h
3 |
4 | /* MSVC doesn't define ffs/ffsl. This dummy strings.h header is provided
5 | * for both */
6 | #include
7 | #pragma intrinsic(_BitScanForward)
8 | static __forceinline int ffsl(long x)
9 | {
10 | unsigned long i;
11 |
12 | if (_BitScanForward(&i, x))
13 | return (i + 1);
14 | return (0);
15 | }
16 |
17 | static __forceinline int ffs(int x)
18 | {
19 |
20 | return (ffsl(x));
21 | }
22 |
23 | #endif
24 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/allocm.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Alignment: 8
3 | Alignment: 16
4 | Alignment: 32
5 | Alignment: 64
6 | Alignment: 128
7 | Alignment: 256
8 | Alignment: 512
9 | Alignment: 1024
10 | Alignment: 2048
11 | Alignment: 4096
12 | Alignment: 8192
13 | Alignment: 16384
14 | Alignment: 32768
15 | Alignment: 65536
16 | Alignment: 131072
17 | Alignment: 262144
18 | Alignment: 524288
19 | Alignment: 1048576
20 | Alignment: 2097152
21 | Alignment: 4194304
22 | Alignment: 8388608
23 | Alignment: 16777216
24 | Alignment: 33554432
25 | Test end
26 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/aligned_alloc.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Alignment: 8
3 | Alignment: 16
4 | Alignment: 32
5 | Alignment: 64
6 | Alignment: 128
7 | Alignment: 256
8 | Alignment: 512
9 | Alignment: 1024
10 | Alignment: 2048
11 | Alignment: 4096
12 | Alignment: 8192
13 | Alignment: 16384
14 | Alignment: 32768
15 | Alignment: 65536
16 | Alignment: 131072
17 | Alignment: 262144
18 | Alignment: 524288
19 | Alignment: 1048576
20 | Alignment: 2097152
21 | Alignment: 4194304
22 | Alignment: 8388608
23 | Alignment: 16777216
24 | Alignment: 33554432
25 | Test end
26 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/posix_memalign.exp:
--------------------------------------------------------------------------------
1 | Test begin
2 | Alignment: 8
3 | Alignment: 16
4 | Alignment: 32
5 | Alignment: 64
6 | Alignment: 128
7 | Alignment: 256
8 | Alignment: 512
9 | Alignment: 1024
10 | Alignment: 2048
11 | Alignment: 4096
12 | Alignment: 8192
13 | Alignment: 16384
14 | Alignment: 32768
15 | Alignment: 65536
16 | Alignment: 131072
17 | Alignment: 262144
18 | Alignment: 524288
19 | Alignment: 1048576
20 | Alignment: 2097152
21 | Alignment: 4194304
22 | Alignment: 8388608
23 | Alignment: 16777216
24 | Alignment: 33554432
25 | Test end
26 |
--------------------------------------------------------------------------------
/deps/jemalloc/.gitignore:
--------------------------------------------------------------------------------
1 | /autom4te.cache/
2 | /config.stamp
3 | /config.log
4 | /config.status
5 | /configure
6 | /doc/html.xsl
7 | /doc/manpages.xsl
8 | /doc/jemalloc.xml
9 | /doc/jemalloc.html
10 | /doc/jemalloc.3
11 | /lib/
12 | /Makefile
13 | /include/jemalloc/internal/jemalloc_internal\.h
14 | /include/jemalloc/internal/size_classes\.h
15 | /include/jemalloc/jemalloc\.h
16 | /include/jemalloc/jemalloc_defs\.h
17 | /test/jemalloc_test\.h
18 | /src/*.[od]
19 | /test/*.[od]
20 | /test/*.out
21 | /test/[a-zA-Z_]*
22 | !test/*.c
23 | !test/*.exp
24 | /VERSION
25 | /bin/jemalloc.sh
26 |
--------------------------------------------------------------------------------
/eaglemq.conf:
--------------------------------------------------------------------------------
1 | # EagleMQ default configuration file
2 |
3 | # Server address
4 | addr 127.0.0.1
5 |
6 | # Server port
7 | port 7851
8 |
9 | # Unix socket path
10 | unix-socket /tmp/eaglemq
11 |
12 | # Admin name
13 | admin-name eagle
14 |
15 | # Admin password
16 | admin-password eagle
17 |
18 | # Daemonization
19 | daemonize off
20 |
21 | # Path to the PID file
22 | pid-file /tmp/eaglemq.pid
23 |
24 | # Path to the log file
25 | log-file /tmp/eaglemq.log
26 |
27 | # Path to the storage file
28 | storage-file eaglemq.dat
29 |
30 | # Maximum connections on the server
31 | max-clients 16384
32 |
33 | # Max memory usage
34 | max-memory 0B
35 |
36 | # Save timeout
37 | save-timeout 10000
38 |
39 | # Timeout to kill not active clients
40 | client-timeout 0
41 |
--------------------------------------------------------------------------------
/deps/jemalloc/README:
--------------------------------------------------------------------------------
1 | jemalloc is a general-purpose scalable concurrent malloc(3) implementation.
2 | This distribution is a "portable" implementation that currently targets
3 | FreeBSD, Linux, Apple OS X, and MinGW. jemalloc is included as the default
4 | allocator in the FreeBSD and NetBSD operating systems, and it is used by the
5 | Mozilla Firefox web browser on Microsoft Windows-related platforms. Depending
6 | on your needs, one of the other divergent versions may suit your needs better
7 | than this distribution.
8 |
9 | The COPYING file contains copyright and licensing information.
10 |
11 | The INSTALL file contains information on how to configure, build, and install
12 | jemalloc.
13 |
14 | The ChangeLog file contains a brief summary of changes for each release.
15 |
16 | URL: http://www.canonware.com/jemalloc/
17 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/chunk_mmap.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | #endif /* JEMALLOC_H_TYPES */
5 | /******************************************************************************/
6 | #ifdef JEMALLOC_H_STRUCTS
7 |
8 | #endif /* JEMALLOC_H_STRUCTS */
9 | /******************************************************************************/
10 | #ifdef JEMALLOC_H_EXTERNS
11 |
12 | bool pages_purge(void *addr, size_t length);
13 |
14 | void *chunk_alloc_mmap(size_t size, size_t alignment, bool *zero);
15 | bool chunk_dealloc_mmap(void *chunk, size_t size);
16 |
17 | #endif /* JEMALLOC_H_EXTERNS */
18 | /******************************************************************************/
19 | #ifdef JEMALLOC_H_INLINES
20 |
21 | #endif /* JEMALLOC_H_INLINES */
22 | /******************************************************************************/
23 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/quarantine.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | /* Default per thread quarantine size if valgrind is enabled. */
5 | #define JEMALLOC_VALGRIND_QUARANTINE_DEFAULT (ZU(1) << 24)
6 |
7 | #endif /* JEMALLOC_H_TYPES */
8 | /******************************************************************************/
9 | #ifdef JEMALLOC_H_STRUCTS
10 |
11 | #endif /* JEMALLOC_H_STRUCTS */
12 | /******************************************************************************/
13 | #ifdef JEMALLOC_H_EXTERNS
14 |
15 | void quarantine(void *ptr);
16 | bool quarantine_boot(void);
17 |
18 | #endif /* JEMALLOC_H_EXTERNS */
19 | /******************************************************************************/
20 | #ifdef JEMALLOC_H_INLINES
21 |
22 | #endif /* JEMALLOC_H_INLINES */
23 | /******************************************************************************/
24 |
25 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/base.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | #endif /* JEMALLOC_H_TYPES */
5 | /******************************************************************************/
6 | #ifdef JEMALLOC_H_STRUCTS
7 |
8 | #endif /* JEMALLOC_H_STRUCTS */
9 | /******************************************************************************/
10 | #ifdef JEMALLOC_H_EXTERNS
11 |
12 | void *base_alloc(size_t size);
13 | void *base_calloc(size_t number, size_t size);
14 | extent_node_t *base_node_alloc(void);
15 | void base_node_dealloc(extent_node_t *node);
16 | bool base_boot(void);
17 | void base_prefork(void);
18 | void base_postfork_parent(void);
19 | void base_postfork_child(void);
20 |
21 | #endif /* JEMALLOC_H_EXTERNS */
22 | /******************************************************************************/
23 | #ifdef JEMALLOC_H_INLINES
24 |
25 | #endif /* JEMALLOC_H_INLINES */
26 | /******************************************************************************/
27 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/extent.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_EXTENT_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | /******************************************************************************/
5 |
6 | static inline int
7 | extent_szad_comp(extent_node_t *a, extent_node_t *b)
8 | {
9 | int ret;
10 | size_t a_size = a->size;
11 | size_t b_size = b->size;
12 |
13 | ret = (a_size > b_size) - (a_size < b_size);
14 | if (ret == 0) {
15 | uintptr_t a_addr = (uintptr_t)a->addr;
16 | uintptr_t b_addr = (uintptr_t)b->addr;
17 |
18 | ret = (a_addr > b_addr) - (a_addr < b_addr);
19 | }
20 |
21 | return (ret);
22 | }
23 |
24 | /* Generate red-black tree functions. */
25 | rb_gen(, extent_tree_szad_, extent_tree_t, extent_node_t, link_szad,
26 | extent_szad_comp)
27 |
28 | static inline int
29 | extent_ad_comp(extent_node_t *a, extent_node_t *b)
30 | {
31 | uintptr_t a_addr = (uintptr_t)a->addr;
32 | uintptr_t b_addr = (uintptr_t)b->addr;
33 |
34 | return ((a_addr > b_addr) - (a_addr < b_addr));
35 | }
36 |
37 | /* Generate red-black tree functions. */
38 | rb_gen(, extent_tree_ad_, extent_tree_t, extent_node_t, link_ad,
39 | extent_ad_comp)
40 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | EagleMQ
2 | -------
3 | EagleMQ is an open source, high-performance and lightweight queue manager.
4 |
5 | Documentation
6 | -------------
7 | The latest documentation can be found here: http://github.com/yakushstanislav/EagleMQ/tree/unstable/docs
8 |
9 | Building
10 | --------
11 | Currently EagleMQ can be compiled and used only on Linux.
12 |
13 | The command to build EagleMQ:
14 |
15 | % make
16 |
17 | Installing EagleMQ
18 | ------------------
19 | To install EagleMQ use:
20 |
21 | % make install
22 |
23 | EagleMQ will be installed in /usr/local/bin.
24 |
25 | Running EagleMQ
26 | ---------------
27 | To run EagleMQ with the default configuration type:
28 |
29 | % ./src/eaglemq
30 |
31 | You can also specify options on the command line. Example:
32 |
33 | % ./src/eaglemq eaglemq.conf --daemonize on --unix-socket /tmp/eaglemq --log-file /tmp/eaglemq.log
34 |
35 | Memory allocator
36 | ----------------
37 | EagleMQ supports 3 memory allocator: libc malloc, tcmalloc, jemalloc.
38 |
39 | The default memory allocator libc malloc.
40 |
41 | To compile against libc malloc, use:
42 |
43 | % make MALLOC=libc
44 |
45 | To compile against tcmalloc, use:
46 |
47 | % make MALLOC=tcmalloc
48 |
49 | To compile against jemalloc, use:
50 |
51 | % make MALLOC=jemalloc
52 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/jemalloc_test.h.in:
--------------------------------------------------------------------------------
1 | /*
2 | * This header should be included by tests, rather than directly including
3 | * jemalloc/jemalloc.h, because --with-install-suffix may cause the header to
4 | * have a different name.
5 | */
6 | #include "jemalloc/jemalloc@install_suffix@.h"
7 | #include "jemalloc/internal/jemalloc_internal.h"
8 |
9 | /* Abstraction layer for threading in tests */
10 | #ifdef _WIN32
11 | #include
12 |
13 | typedef HANDLE je_thread_t;
14 |
15 | void
16 | je_thread_create(je_thread_t *thread, void *(*proc)(void *), void *arg)
17 | {
18 | LPTHREAD_START_ROUTINE routine = (LPTHREAD_START_ROUTINE)proc;
19 | *thread = CreateThread(NULL, 0, routine, arg, 0, NULL);
20 | if (*thread == NULL) {
21 | malloc_printf("Error in CreateThread()\n");
22 | exit(1);
23 | }
24 | }
25 |
26 | void
27 | je_thread_join(je_thread_t thread, void **ret)
28 | {
29 | WaitForSingleObject(thread, INFINITE);
30 | }
31 |
32 | #else
33 | #include
34 |
35 | typedef pthread_t je_thread_t;
36 |
37 | void
38 | je_thread_create(je_thread_t *thread, void *(*proc)(void *), void *arg)
39 | {
40 |
41 | if (pthread_create(thread, NULL, proc, arg) != 0) {
42 | malloc_printf("Error in pthread_create()\n");
43 | exit(1);
44 | }
45 | }
46 |
47 | void
48 | je_thread_join(je_thread_t thread, void **ret)
49 | {
50 |
51 | pthread_join(thread, ret);
52 | }
53 | #endif
54 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/chunk_dss.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | typedef enum {
5 | dss_prec_disabled = 0,
6 | dss_prec_primary = 1,
7 | dss_prec_secondary = 2,
8 |
9 | dss_prec_limit = 3
10 | } dss_prec_t ;
11 | #define DSS_PREC_DEFAULT dss_prec_secondary
12 | #define DSS_DEFAULT "secondary"
13 |
14 | #endif /* JEMALLOC_H_TYPES */
15 | /******************************************************************************/
16 | #ifdef JEMALLOC_H_STRUCTS
17 |
18 | extern const char *dss_prec_names[];
19 |
20 | #endif /* JEMALLOC_H_STRUCTS */
21 | /******************************************************************************/
22 | #ifdef JEMALLOC_H_EXTERNS
23 |
24 | dss_prec_t chunk_dss_prec_get(void);
25 | bool chunk_dss_prec_set(dss_prec_t dss_prec);
26 | void *chunk_alloc_dss(size_t size, size_t alignment, bool *zero);
27 | bool chunk_in_dss(void *chunk);
28 | bool chunk_dss_boot(void);
29 | void chunk_dss_prefork(void);
30 | void chunk_dss_postfork_parent(void);
31 | void chunk_dss_postfork_child(void);
32 |
33 | #endif /* JEMALLOC_H_EXTERNS */
34 | /******************************************************************************/
35 | #ifdef JEMALLOC_H_INLINES
36 |
37 | #endif /* JEMALLOC_H_INLINES */
38 | /******************************************************************************/
39 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/mremap.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | int
5 | main(void)
6 | {
7 | int ret, err;
8 | size_t sz, lg_chunk, chunksize, i;
9 | char *p, *q;
10 |
11 | malloc_printf("Test begin\n");
12 |
13 | sz = sizeof(lg_chunk);
14 | if ((err = mallctl("opt.lg_chunk", &lg_chunk, &sz, NULL, 0))) {
15 | assert(err != ENOENT);
16 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
17 | strerror(err));
18 | ret = 1;
19 | goto label_return;
20 | }
21 | chunksize = ((size_t)1U) << lg_chunk;
22 |
23 | p = (char *)malloc(chunksize);
24 | if (p == NULL) {
25 | malloc_printf("malloc(%zu) --> %p\n", chunksize, p);
26 | ret = 1;
27 | goto label_return;
28 | }
29 | memset(p, 'a', chunksize);
30 |
31 | q = (char *)realloc(p, chunksize * 2);
32 | if (q == NULL) {
33 | malloc_printf("realloc(%p, %zu) --> %p\n", p, chunksize * 2,
34 | q);
35 | ret = 1;
36 | goto label_return;
37 | }
38 | for (i = 0; i < chunksize; i++) {
39 | assert(q[i] == 'a');
40 | }
41 |
42 | p = q;
43 |
44 | q = (char *)realloc(p, chunksize);
45 | if (q == NULL) {
46 | malloc_printf("realloc(%p, %zu) --> %p\n", p, chunksize, q);
47 | ret = 1;
48 | goto label_return;
49 | }
50 | for (i = 0; i < chunksize; i++) {
51 | assert(q[i] == 'a');
52 | }
53 |
54 | free(q);
55 |
56 | ret = 0;
57 | label_return:
58 | malloc_printf("Test end\n");
59 | return (ret);
60 | }
61 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/extent.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | typedef struct extent_node_s extent_node_t;
5 |
6 | #endif /* JEMALLOC_H_TYPES */
7 | /******************************************************************************/
8 | #ifdef JEMALLOC_H_STRUCTS
9 |
10 | /* Tree of extents. */
11 | struct extent_node_s {
12 | /* Linkage for the size/address-ordered tree. */
13 | rb_node(extent_node_t) link_szad;
14 |
15 | /* Linkage for the address-ordered tree. */
16 | rb_node(extent_node_t) link_ad;
17 |
18 | /* Profile counters, used for huge objects. */
19 | prof_ctx_t *prof_ctx;
20 |
21 | /* Pointer to the extent that this tree node is responsible for. */
22 | void *addr;
23 |
24 | /* Total region size. */
25 | size_t size;
26 |
27 | /* True if zero-filled; used by chunk recycling code. */
28 | bool zeroed;
29 | };
30 | typedef rb_tree(extent_node_t) extent_tree_t;
31 |
32 | #endif /* JEMALLOC_H_STRUCTS */
33 | /******************************************************************************/
34 | #ifdef JEMALLOC_H_EXTERNS
35 |
36 | rb_proto(, extent_tree_szad_, extent_tree_t, extent_node_t)
37 |
38 | rb_proto(, extent_tree_ad_, extent_tree_t, extent_node_t)
39 |
40 | #endif /* JEMALLOC_H_EXTERNS */
41 | /******************************************************************************/
42 | #ifdef JEMALLOC_H_INLINES
43 |
44 | #endif /* JEMALLOC_H_INLINES */
45 | /******************************************************************************/
46 |
47 |
--------------------------------------------------------------------------------
/COPYING:
--------------------------------------------------------------------------------
1 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
2 | All rights reserved.
3 |
4 | Redistribution and use in source and binary forms, with or without
5 | modification, are permitted provided that the following conditions are met:
6 | * Redistributions of source code must retain the above copyright
7 | notice, this list of conditions and the following disclaimer.
8 | * Redistributions in binary form must reproduce the above copyright
9 | notice, this list of conditions and the following disclaimer in the
10 | documentation and/or other materials provided with the distribution.
11 | * Neither the name of the EagleMQ nor the
12 | names of its contributors may be used to endorse or promote products
13 | derived from this software without specific prior written permission.
14 |
15 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
16 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
18 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
19 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
22 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
24 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/huge.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | #endif /* JEMALLOC_H_TYPES */
5 | /******************************************************************************/
6 | #ifdef JEMALLOC_H_STRUCTS
7 |
8 | #endif /* JEMALLOC_H_STRUCTS */
9 | /******************************************************************************/
10 | #ifdef JEMALLOC_H_EXTERNS
11 |
12 | /* Huge allocation statistics. */
13 | extern uint64_t huge_nmalloc;
14 | extern uint64_t huge_ndalloc;
15 | extern size_t huge_allocated;
16 |
17 | /* Protects chunk-related data structures. */
18 | extern malloc_mutex_t huge_mtx;
19 |
20 | void *huge_malloc(size_t size, bool zero);
21 | void *huge_palloc(size_t size, size_t alignment, bool zero);
22 | void *huge_ralloc_no_move(void *ptr, size_t oldsize, size_t size,
23 | size_t extra);
24 | void *huge_ralloc(void *ptr, size_t oldsize, size_t size, size_t extra,
25 | size_t alignment, bool zero, bool try_tcache_dalloc);
26 | void huge_dalloc(void *ptr, bool unmap);
27 | size_t huge_salloc(const void *ptr);
28 | prof_ctx_t *huge_prof_ctx_get(const void *ptr);
29 | void huge_prof_ctx_set(const void *ptr, prof_ctx_t *ctx);
30 | bool huge_boot(void);
31 | void huge_prefork(void);
32 | void huge_postfork_parent(void);
33 | void huge_postfork_child(void);
34 |
35 | #endif /* JEMALLOC_H_EXTERNS */
36 | /******************************************************************************/
37 | #ifdef JEMALLOC_H_INLINES
38 |
39 | #endif /* JEMALLOC_H_INLINES */
40 | /******************************************************************************/
41 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/ALLOCM_ARENA.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | #define NTHREADS 10
5 |
6 | void *
7 | je_thread_start(void *arg)
8 | {
9 | unsigned thread_ind = (unsigned)(uintptr_t)arg;
10 | unsigned arena_ind;
11 | int r;
12 | void *p;
13 | size_t rsz, sz;
14 |
15 | sz = sizeof(arena_ind);
16 | if (mallctl("arenas.extend", &arena_ind, &sz, NULL, 0)
17 | != 0) {
18 | malloc_printf("Error in arenas.extend\n");
19 | abort();
20 | }
21 |
22 | if (thread_ind % 4 != 3) {
23 | size_t mib[3];
24 | size_t miblen = sizeof(mib) / sizeof(size_t);
25 | const char *dss_precs[] = {"disabled", "primary", "secondary"};
26 | const char *dss = dss_precs[thread_ind % 4];
27 | if (mallctlnametomib("arena.0.dss", mib, &miblen) != 0) {
28 | malloc_printf("Error in mallctlnametomib()\n");
29 | abort();
30 | }
31 | mib[1] = arena_ind;
32 | if (mallctlbymib(mib, miblen, NULL, NULL, (void *)&dss,
33 | sizeof(const char *))) {
34 | malloc_printf("Error in mallctlbymib()\n");
35 | abort();
36 | }
37 | }
38 |
39 | r = allocm(&p, &rsz, 1, ALLOCM_ARENA(arena_ind));
40 | if (r != ALLOCM_SUCCESS) {
41 | malloc_printf("Unexpected allocm() error\n");
42 | abort();
43 | }
44 |
45 | return (NULL);
46 | }
47 |
48 | int
49 | main(void)
50 | {
51 | je_thread_t threads[NTHREADS];
52 | unsigned i;
53 |
54 | malloc_printf("Test begin\n");
55 |
56 | for (i = 0; i < NTHREADS; i++) {
57 | je_thread_create(&threads[i], je_thread_start,
58 | (void *)(uintptr_t)i);
59 | }
60 |
61 | for (i = 0; i < NTHREADS; i++)
62 | je_thread_join(threads[i], NULL);
63 |
64 | malloc_printf("Test end\n");
65 | return (0);
66 | }
67 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/rtree.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_RTREE_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | rtree_t *
5 | rtree_new(unsigned bits)
6 | {
7 | rtree_t *ret;
8 | unsigned bits_per_level, height, i;
9 |
10 | bits_per_level = ffs(pow2_ceil((RTREE_NODESIZE / sizeof(void *)))) - 1;
11 | height = bits / bits_per_level;
12 | if (height * bits_per_level != bits)
13 | height++;
14 | assert(height * bits_per_level >= bits);
15 |
16 | ret = (rtree_t*)base_alloc(offsetof(rtree_t, level2bits) +
17 | (sizeof(unsigned) * height));
18 | if (ret == NULL)
19 | return (NULL);
20 | memset(ret, 0, offsetof(rtree_t, level2bits) + (sizeof(unsigned) *
21 | height));
22 |
23 | if (malloc_mutex_init(&ret->mutex)) {
24 | /* Leak the rtree. */
25 | return (NULL);
26 | }
27 | ret->height = height;
28 | if (bits_per_level * height > bits)
29 | ret->level2bits[0] = bits % bits_per_level;
30 | else
31 | ret->level2bits[0] = bits_per_level;
32 | for (i = 1; i < height; i++)
33 | ret->level2bits[i] = bits_per_level;
34 |
35 | ret->root = (void**)base_alloc(sizeof(void *) << ret->level2bits[0]);
36 | if (ret->root == NULL) {
37 | /*
38 | * We leak the rtree here, since there's no generic base
39 | * deallocation.
40 | */
41 | return (NULL);
42 | }
43 | memset(ret->root, 0, sizeof(void *) << ret->level2bits[0]);
44 |
45 | return (ret);
46 | }
47 |
48 | void
49 | rtree_prefork(rtree_t *rtree)
50 | {
51 |
52 | malloc_mutex_prefork(&rtree->mutex);
53 | }
54 |
55 | void
56 | rtree_postfork_parent(rtree_t *rtree)
57 | {
58 |
59 | malloc_mutex_postfork_parent(&rtree->mutex);
60 | }
61 |
62 | void
63 | rtree_postfork_child(rtree_t *rtree)
64 | {
65 |
66 | malloc_mutex_postfork_child(&rtree->mutex);
67 | }
68 |
--------------------------------------------------------------------------------
/deps/jemalloc/COPYING:
--------------------------------------------------------------------------------
1 | Unless otherwise specified, files in the jemalloc source distribution are
2 | subject to the following license:
3 | --------------------------------------------------------------------------------
4 | Copyright (C) 2002-2012 Jason Evans .
5 | All rights reserved.
6 | Copyright (C) 2007-2012 Mozilla Foundation. All rights reserved.
7 | Copyright (C) 2009-2012 Facebook, Inc. All rights reserved.
8 |
9 | Redistribution and use in source and binary forms, with or without
10 | modification, are permitted provided that the following conditions are met:
11 | 1. Redistributions of source code must retain the above copyright notice(s),
12 | this list of conditions and the following disclaimer.
13 | 2. Redistributions in binary form must reproduce the above copyright notice(s),
14 | this list of conditions and the following disclaimer in the documentation
15 | and/or other materials provided with the distribution.
16 |
17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER(S) ``AS IS'' AND ANY EXPRESS
18 | OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
19 | MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
20 | EVENT SHALL THE COPYRIGHT HOLDER(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
21 | INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 | LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
23 | PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
24 | LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
25 | OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
26 | ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 | --------------------------------------------------------------------------------
28 |
--------------------------------------------------------------------------------
/src/config.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __CONFIG_H__
29 | #define __CONFIG_H__
30 |
31 | int config_parse_key_value(char *key, char *value);
32 | int config_load(const char *filename);
33 |
34 | #endif
35 |
--------------------------------------------------------------------------------
/src/Makefile:
--------------------------------------------------------------------------------
1 | EAGLEMQ_BIN=eaglemq
2 | EAGLEMQ_LDFLAGS=-pthread
3 | EAGLEMQ_OBJ=eagle.o event.o network.o xmalloc.o utils.o object.o handlers.o keylist.o list.o queue.o user.o message.o queue_t.o route_t.o channel_t.o storage.o config.o lzf_c.o lzf_d.o
4 |
5 | CC=gcc
6 | OPTIMIZATION?=-O2
7 |
8 | CFLAGS=-std=c99 -pedantic -Wall $(OPTIMIZATION) -g
9 |
10 | INSTALL_DIR=/usr/local/bin
11 | INSTALL_CMD=cp -pf
12 |
13 | ifeq ($(USE_SELECT),yes)
14 | CFLAGS+=-D_EVENT_SELECT_
15 | endif
16 |
17 | MALLOC=libc
18 |
19 | ifeq ($(USE_JEMALLOC),yes)
20 | MALLOC=jemalloc
21 | endif
22 |
23 | ifeq ($(USE_TCMALLOC),yes)
24 | MALLOC=tcmalloc
25 | endif
26 |
27 | ifeq ($(USE_TCMALLOC_MINIMAL),yes)
28 | MALLOC=tcmalloc_minimal
29 | endif
30 |
31 | ifeq ($(MALLOC),libc)
32 | CFLAGS+=-D_USE_MALLOC_
33 | endif
34 |
35 | ifeq ($(MALLOC),jemalloc)
36 | CFLAGS+=-D_USE_JEMALLOC_ -I../deps/jemalloc/include
37 | EAGLEMQ_LDFLAGS+=../deps/jemalloc/lib/libjemalloc.a -ldl
38 | DEPS+=jemalloc
39 | endif
40 |
41 | ifeq ($(MALLOC),tcmalloc)
42 | CFLAGS+=-D_USE_TCMALLOC_
43 | EAGLEMQ_LDFLAGS+=-ltcmalloc
44 | endif
45 |
46 | ifeq ($(MALLOC),tcmalloc_minimal)
47 | CFLAGS+=-D_USE_TCMALLOC_
48 | EAGLEMQ_LDFLAGS+=-ltcmalloc_minimal
49 | endif
50 |
51 | all: $(DEPS) $(EAGLEMQ_BIN)
52 |
53 | jemalloc:
54 | cd ../deps && $(MAKE) JEMALLOC_CFLAGS="-std=gnu99 -Wall -pipe -g3 -O3 -funroll-loops" jemalloc
55 |
56 | $(EAGLEMQ_BIN): $(EAGLEMQ_OBJ)
57 | $(CC) -o $@ $^ $(EAGLEMQ_LDFLAGS)
58 |
59 | %.o: %.c
60 | $(CC) -c $< $(CFLAGS)
61 |
62 | dep:
63 | $(CC) -MM *.c > Makefile.dep
64 |
65 | run:
66 | ./$(EAGLEMQ_BIN)
67 |
68 | install: all
69 | mkdir -p $(INSTALL_DIR)
70 | $(INSTALL_CMD) $(EAGLEMQ_BIN) $(INSTALL_DIR)
71 |
72 | uninstall:
73 | rm -rf $(INSTALL_DIR)/$(EAGLEMQ_BIN)
74 |
75 | clean:
76 | rm -rf *.o $(EAGLEMQ_BIN)
77 |
78 | distclean: clean
79 | cd ../deps && $(MAKE) distclean
80 |
81 | .PHONY: all dep run install uninstall clean
82 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/thread_arena.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | #define NTHREADS 10
5 |
6 | void *
7 | je_thread_start(void *arg)
8 | {
9 | unsigned main_arena_ind = *(unsigned *)arg;
10 | void *p;
11 | unsigned arena_ind;
12 | size_t size;
13 | int err;
14 |
15 | p = malloc(1);
16 | if (p == NULL) {
17 | malloc_printf("%s(): Error in malloc()\n", __func__);
18 | return (void *)1;
19 | }
20 |
21 | size = sizeof(arena_ind);
22 | if ((err = mallctl("thread.arena", &arena_ind, &size, &main_arena_ind,
23 | sizeof(main_arena_ind)))) {
24 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
25 | strerror(err));
26 | return (void *)1;
27 | }
28 |
29 | size = sizeof(arena_ind);
30 | if ((err = mallctl("thread.arena", &arena_ind, &size, NULL,
31 | 0))) {
32 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
33 | strerror(err));
34 | return (void *)1;
35 | }
36 | assert(arena_ind == main_arena_ind);
37 |
38 | return (NULL);
39 | }
40 |
41 | int
42 | main(void)
43 | {
44 | int ret = 0;
45 | void *p;
46 | unsigned arena_ind;
47 | size_t size;
48 | int err;
49 | je_thread_t threads[NTHREADS];
50 | unsigned i;
51 |
52 | malloc_printf("Test begin\n");
53 |
54 | p = malloc(1);
55 | if (p == NULL) {
56 | malloc_printf("%s(): Error in malloc()\n", __func__);
57 | ret = 1;
58 | goto label_return;
59 | }
60 |
61 | size = sizeof(arena_ind);
62 | if ((err = mallctl("thread.arena", &arena_ind, &size, NULL, 0))) {
63 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
64 | strerror(err));
65 | ret = 1;
66 | goto label_return;
67 | }
68 |
69 | for (i = 0; i < NTHREADS; i++) {
70 | je_thread_create(&threads[i], je_thread_start,
71 | (void *)&arena_ind);
72 | }
73 |
74 | for (i = 0; i < NTHREADS; i++)
75 | je_thread_join(threads[i], (void *)&ret);
76 |
77 | label_return:
78 | malloc_printf("Test end\n");
79 | return (ret);
80 | }
81 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/thread_tcache_enabled.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | void *
5 | je_thread_start(void *arg)
6 | {
7 | int err;
8 | size_t sz;
9 | bool e0, e1;
10 |
11 | sz = sizeof(bool);
12 | if ((err = mallctl("thread.tcache.enabled", &e0, &sz, NULL, 0))) {
13 | if (err == ENOENT) {
14 | #ifdef JEMALLOC_TCACHE
15 | assert(false);
16 | #endif
17 | }
18 | goto label_return;
19 | }
20 |
21 | if (e0) {
22 | e1 = false;
23 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz)
24 | == 0);
25 | assert(e0);
26 | }
27 |
28 | e1 = true;
29 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
30 | assert(e0 == false);
31 |
32 | e1 = true;
33 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
34 | assert(e0);
35 |
36 | e1 = false;
37 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
38 | assert(e0);
39 |
40 | e1 = false;
41 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
42 | assert(e0 == false);
43 |
44 | free(malloc(1));
45 | e1 = true;
46 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
47 | assert(e0 == false);
48 |
49 | free(malloc(1));
50 | e1 = true;
51 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
52 | assert(e0);
53 |
54 | free(malloc(1));
55 | e1 = false;
56 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
57 | assert(e0);
58 |
59 | free(malloc(1));
60 | e1 = false;
61 | assert(mallctl("thread.tcache.enabled", &e0, &sz, &e1, sz) == 0);
62 | assert(e0 == false);
63 |
64 | free(malloc(1));
65 | label_return:
66 | return (NULL);
67 | }
68 |
69 | int
70 | main(void)
71 | {
72 | int ret = 0;
73 | je_thread_t thread;
74 |
75 | malloc_printf("Test begin\n");
76 |
77 | je_thread_start(NULL);
78 |
79 | je_thread_create(&thread, je_thread_start, NULL);
80 | je_thread_join(thread, (void *)&ret);
81 |
82 | je_thread_start(NULL);
83 |
84 | je_thread_create(&thread, je_thread_start, NULL);
85 | je_thread_join(thread, (void *)&ret);
86 |
87 | je_thread_start(NULL);
88 |
89 | malloc_printf("Test end\n");
90 | return (ret);
91 | }
92 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/hash.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | #endif /* JEMALLOC_H_TYPES */
5 | /******************************************************************************/
6 | #ifdef JEMALLOC_H_STRUCTS
7 |
8 | #endif /* JEMALLOC_H_STRUCTS */
9 | /******************************************************************************/
10 | #ifdef JEMALLOC_H_EXTERNS
11 |
12 | #endif /* JEMALLOC_H_EXTERNS */
13 | /******************************************************************************/
14 | #ifdef JEMALLOC_H_INLINES
15 |
16 | #ifndef JEMALLOC_ENABLE_INLINE
17 | uint64_t hash(const void *key, size_t len, uint64_t seed);
18 | #endif
19 |
20 | #if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_HASH_C_))
21 | /*
22 | * The following hash function is based on MurmurHash64A(), placed into the
23 | * public domain by Austin Appleby. See http://murmurhash.googlepages.com/ for
24 | * details.
25 | */
26 | JEMALLOC_INLINE uint64_t
27 | hash(const void *key, size_t len, uint64_t seed)
28 | {
29 | const uint64_t m = UINT64_C(0xc6a4a7935bd1e995);
30 | const int r = 47;
31 | uint64_t h = seed ^ (len * m);
32 | const uint64_t *data = (const uint64_t *)key;
33 | const uint64_t *end = data + (len/8);
34 | const unsigned char *data2;
35 |
36 | assert(((uintptr_t)key & 0x7) == 0);
37 |
38 | while(data != end) {
39 | uint64_t k = *data++;
40 |
41 | k *= m;
42 | k ^= k >> r;
43 | k *= m;
44 |
45 | h ^= k;
46 | h *= m;
47 | }
48 |
49 | data2 = (const unsigned char *)data;
50 | switch(len & 7) {
51 | case 7: h ^= ((uint64_t)(data2[6])) << 48;
52 | case 6: h ^= ((uint64_t)(data2[5])) << 40;
53 | case 5: h ^= ((uint64_t)(data2[4])) << 32;
54 | case 4: h ^= ((uint64_t)(data2[3])) << 24;
55 | case 3: h ^= ((uint64_t)(data2[2])) << 16;
56 | case 2: h ^= ((uint64_t)(data2[1])) << 8;
57 | case 1: h ^= ((uint64_t)(data2[0]));
58 | h *= m;
59 | }
60 |
61 | h ^= h >> r;
62 | h *= m;
63 | h ^= h >> r;
64 |
65 | return (h);
66 | }
67 | #endif
68 |
69 | #endif /* JEMALLOC_H_INLINES */
70 | /******************************************************************************/
71 |
--------------------------------------------------------------------------------
/src/Makefile.dep:
--------------------------------------------------------------------------------
1 | channel_t.o: channel_t.c eagle.h event.h network.h list.h keylist.h \
2 | queue.h user.h channel_t.h object.h handlers.h queue_t.h message.h \
3 | protocol.h xmalloc.h utils.h
4 | config.o: config.c eagle.h event.h network.h list.h keylist.h queue.h \
5 | user.h config.h xmalloc.h utils.h
6 | eagle.o: eagle.c fmacros.h eagle.h event.h network.h list.h keylist.h \
7 | queue.h user.h logo.h version.h xmalloc.h handlers.h object.h queue_t.h \
8 | message.h channel_t.h utils.h route_t.h storage.h config.h
9 | event.o: event.c xmalloc.h event.h event_epoll.c
10 | event_epoll.o: event_epoll.c
11 | event_select.o: event_select.c
12 | handlers.o: handlers.c eagle.h event.h network.h list.h keylist.h queue.h \
13 | user.h handlers.h object.h queue_t.h message.h channel_t.h version.h \
14 | protocol.h route_t.h storage.h xmalloc.h utils.h
15 | keylist.o: keylist.c eagle.h event.h network.h list.h keylist.h queue.h \
16 | user.h xmalloc.h
17 | list.o: list.c eagle.h event.h network.h list.h keylist.h queue.h user.h \
18 | xmalloc.h
19 | lzf_c.o: lzf_c.c lzfP.h
20 | lzf_d.o: lzf_d.c lzfP.h
21 | message.o: message.c eagle.h event.h network.h list.h keylist.h queue.h \
22 | user.h message.h object.h xmalloc.h
23 | network.o: network.c fmacros.h network.h utils.h
24 | object.o: object.c eagle.h event.h network.h list.h keylist.h queue.h \
25 | user.h object.h xmalloc.h
26 | queue.o: queue.c queue.h xmalloc.h
27 | queue_t.o: queue_t.c eagle.h event.h network.h list.h keylist.h queue.h \
28 | user.h queue_t.h object.h message.h route_t.h protocol.h handlers.h \
29 | channel_t.h xmalloc.h utils.h
30 | route_t.o: route_t.c eagle.h event.h network.h list.h keylist.h queue.h \
31 | user.h route_t.h object.h message.h queue_t.h protocol.h xmalloc.h \
32 | utils.h
33 | storage.o: storage.c fmacros.h eagle.h event.h network.h list.h keylist.h \
34 | queue.h user.h storage.h version.h protocol.h queue_t.h object.h \
35 | message.h route_t.h channel_t.h lzf.h xmalloc.h utils.h
36 | user.o: user.c eagle.h event.h network.h list.h keylist.h queue.h user.h \
37 | xmalloc.h utils.h
38 | utils.o: utils.c fmacros.h eagle.h event.h network.h list.h keylist.h \
39 | queue.h user.h utils.h
40 | xmalloc.o: xmalloc.c xmalloc.h utils.h
41 |
--------------------------------------------------------------------------------
/src/network.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2006-2012, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __NET_LIB_H__
29 | #define __NET_LIB_H__
30 |
31 | #include
32 | #include
33 |
34 | #define EG_NET_OK 0
35 | #define EG_NET_ERR -1
36 |
37 | #define NET_ERR_LEN 256
38 |
39 | int net_set_nonblock(char *err, int fd);
40 | int net_tcp_nodelay(char *err, int fd);
41 | int net_tcp_server(char *err, const char *addr, int port);
42 | int net_unix_server(char *err, const char *path, mode_t perm);
43 | int net_tcp_accept(char *err, int sock, char *ip, int *port);
44 | int net_unix_accept(char *err, int sock);
45 |
46 | #endif
47 |
--------------------------------------------------------------------------------
/src/storage.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __STORAGE_H__
29 | #define __STORAGE_H__
30 |
31 | #define EG_STORAGE_VERSION 1
32 |
33 | #define EG_STORAGE_TYPE_USER 0x1
34 | #define EG_STORAGE_TYPE_QUEUE 0x2
35 | #define EG_STORAGE_TYPE_MESSAGE 0x3
36 | #define EG_STORAGE_TYPE_ROUTE 0x4
37 | #define EG_STORAGE_TYPE_ROUTE_KEY 0x5
38 | #define EG_STORAGE_TYPE_CHANNEL 0x6
39 |
40 | #define EG_STORAGE_EOF 0xFF
41 |
42 | int storage_load(const char *filename);
43 | int storage_save(const char *filename);
44 | int storage_save_background(const char *filename);
45 | void remove_temp_file(pid_t pid);
46 |
47 | #endif
48 |
--------------------------------------------------------------------------------
/src/message.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 |
30 | #include "eagle.h"
31 | #include "message.h"
32 | #include "list.h"
33 | #include "xmalloc.h"
34 |
35 | Message *create_message(Object *data, uint64_t tag, uint32_t expiration)
36 | {
37 | Message *msg = (Message*)xcalloc(sizeof(*msg));
38 |
39 | msg->value = data;
40 | msg->tag = tag;
41 | msg->confirm = 0;
42 | msg->expiration = expiration;
43 |
44 | return msg;
45 | }
46 |
47 | void release_message(Message *msg)
48 | {
49 | decrement_references_count(msg->value);
50 | xfree(msg);
51 | }
52 |
53 | void free_message_list_handler(void *ptr)
54 | {
55 | release_message(ptr);
56 | }
57 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/prng.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | /*
5 | * Simple linear congruential pseudo-random number generator:
6 | *
7 | * prng(y) = (a*x + c) % m
8 | *
9 | * where the following constants ensure maximal period:
10 | *
11 | * a == Odd number (relatively prime to 2^n), and (a-1) is a multiple of 4.
12 | * c == Odd number (relatively prime to 2^n).
13 | * m == 2^32
14 | *
15 | * See Knuth's TAOCP 3rd Ed., Vol. 2, pg. 17 for details on these constraints.
16 | *
17 | * This choice of m has the disadvantage that the quality of the bits is
18 | * proportional to bit position. For example. the lowest bit has a cycle of 2,
19 | * the next has a cycle of 4, etc. For this reason, we prefer to use the upper
20 | * bits.
21 | *
22 | * Macro parameters:
23 | * uint32_t r : Result.
24 | * unsigned lg_range : (0..32], number of least significant bits to return.
25 | * uint32_t state : Seed value.
26 | * const uint32_t a, c : See above discussion.
27 | */
28 | #define prng32(r, lg_range, state, a, c) do { \
29 | assert(lg_range > 0); \
30 | assert(lg_range <= 32); \
31 | \
32 | r = (state * (a)) + (c); \
33 | state = r; \
34 | r >>= (32 - lg_range); \
35 | } while (false)
36 |
37 | /* Same as prng32(), but 64 bits of pseudo-randomness, using uint64_t. */
38 | #define prng64(r, lg_range, state, a, c) do { \
39 | assert(lg_range > 0); \
40 | assert(lg_range <= 64); \
41 | \
42 | r = (state * (a)) + (c); \
43 | state = r; \
44 | r >>= (64 - lg_range); \
45 | } while (false)
46 |
47 | #endif /* JEMALLOC_H_TYPES */
48 | /******************************************************************************/
49 | #ifdef JEMALLOC_H_STRUCTS
50 |
51 | #endif /* JEMALLOC_H_STRUCTS */
52 | /******************************************************************************/
53 | #ifdef JEMALLOC_H_EXTERNS
54 |
55 | #endif /* JEMALLOC_H_EXTERNS */
56 | /******************************************************************************/
57 | #ifdef JEMALLOC_H_INLINES
58 |
59 | #endif /* JEMALLOC_H_INLINES */
60 | /******************************************************************************/
61 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/chunk.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | /*
5 | * Size and alignment of memory chunks that are allocated by the OS's virtual
6 | * memory system.
7 | */
8 | #define LG_CHUNK_DEFAULT 22
9 |
10 | /* Return the chunk address for allocation address a. */
11 | #define CHUNK_ADDR2BASE(a) \
12 | ((void *)((uintptr_t)(a) & ~chunksize_mask))
13 |
14 | /* Return the chunk offset of address a. */
15 | #define CHUNK_ADDR2OFFSET(a) \
16 | ((size_t)((uintptr_t)(a) & chunksize_mask))
17 |
18 | /* Return the smallest chunk multiple that is >= s. */
19 | #define CHUNK_CEILING(s) \
20 | (((s) + chunksize_mask) & ~chunksize_mask)
21 |
22 | #endif /* JEMALLOC_H_TYPES */
23 | /******************************************************************************/
24 | #ifdef JEMALLOC_H_STRUCTS
25 |
26 | #endif /* JEMALLOC_H_STRUCTS */
27 | /******************************************************************************/
28 | #ifdef JEMALLOC_H_EXTERNS
29 |
30 | extern size_t opt_lg_chunk;
31 | extern const char *opt_dss;
32 |
33 | /* Protects stats_chunks; currently not used for any other purpose. */
34 | extern malloc_mutex_t chunks_mtx;
35 | /* Chunk statistics. */
36 | extern chunk_stats_t stats_chunks;
37 |
38 | extern rtree_t *chunks_rtree;
39 |
40 | extern size_t chunksize;
41 | extern size_t chunksize_mask; /* (chunksize - 1). */
42 | extern size_t chunk_npages;
43 | extern size_t map_bias; /* Number of arena chunk header pages. */
44 | extern size_t arena_maxclass; /* Max size class for arenas. */
45 |
46 | void *chunk_alloc(size_t size, size_t alignment, bool base, bool *zero,
47 | dss_prec_t dss_prec);
48 | void chunk_unmap(void *chunk, size_t size);
49 | void chunk_dealloc(void *chunk, size_t size, bool unmap);
50 | bool chunk_boot(void);
51 | void chunk_prefork(void);
52 | void chunk_postfork_parent(void);
53 | void chunk_postfork_child(void);
54 |
55 | #endif /* JEMALLOC_H_EXTERNS */
56 | /******************************************************************************/
57 | #ifdef JEMALLOC_H_INLINES
58 |
59 | #endif /* JEMALLOC_H_INLINES */
60 | /******************************************************************************/
61 |
62 | #include "jemalloc/internal/chunk_dss.h"
63 | #include "jemalloc/internal/chunk_mmap.h"
64 |
--------------------------------------------------------------------------------
/src/object.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __OBJECT_H__
29 | #define __OBJECT_H__
30 |
31 | #include
32 |
33 | #include "eagle.h"
34 |
35 | #define EG_OBJECT_SIZE(x) ((x)->size)
36 | #define EG_OBJECT_DATA(x) ((x)->data)
37 | #define EG_OBJECT_RESET_REFCOUNT(x) ((x)->refcount = 0)
38 |
39 | typedef struct Object {
40 | void *data;
41 | size_t size;
42 | unsigned int refcount;
43 | } Object;
44 |
45 | Object *create_object(void *ptr, size_t size);
46 | Object *create_dup_object(void *ptr, size_t size);
47 | void release_object(Object *object);
48 | void increment_references_count(Object *object);
49 | void decrement_references_count(Object *object);
50 | void free_object_list_handler(void *ptr);
51 |
52 | #endif
53 |
--------------------------------------------------------------------------------
/src/route_t.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __ROUTE_H__
29 | #define __ROUTE_H__
30 |
31 | #include
32 |
33 | #include "eagle.h"
34 | #include "object.h"
35 | #include "message.h"
36 |
37 | Route_t *create_route_t(const char *name, uint32_t flags);
38 | void delete_route_t(Route_t *route);
39 | int push_message_route_t(Route_t *route, const char *key, Object *msg, uint32_t expiration);
40 | void bind_route_t(Route_t *route, Queue_t *queue_t, const char *key);
41 | int unbind_route_t(Route_t *route, Queue_t *queue_t, const char *key);
42 | Route_t *find_route_t(List *list, const char *name);
43 | void rename_route_t(Route_t *route, const char *name);
44 | uint32_t get_queue_number_route_t(Route_t *route);
45 | void free_route_list_handler(void *ptr);
46 |
47 | #endif
48 |
--------------------------------------------------------------------------------
/src/channel_t.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __CHANNEL_H__
29 | #define __CHANNEL_H__
30 |
31 | #include "eagle.h"
32 | #include "object.h"
33 |
34 | Channel_t *create_channel_t(const char *name, uint32_t flags);
35 | void delete_channel_t(Channel_t *channel);
36 | void publish_message_channel_t(Channel_t *channel, const char *topic, Object *msg);
37 | Channel_t *find_channel_t(List *list, const char *name);
38 | void rename_channel_t(Channel_t *channel, const char *name);
39 | void subscribe_channel_t(Channel_t *channel, EagleClient *client, const char *topic);
40 | void psubscribe_channel_t(Channel_t *channel, EagleClient *client, const char *pattern);
41 | int unsubscribe_channel_t(Channel_t *channel, EagleClient *client, const char *topic);
42 | int punsubscribe_channel_t(Channel_t *channel, EagleClient *client, const char *pattern);
43 | void free_channel_list_handler(void *ptr);
44 |
45 | #endif
46 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/tsd.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_TSD_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | /******************************************************************************/
5 | /* Data. */
6 |
7 | static unsigned ncleanups;
8 | static malloc_tsd_cleanup_t cleanups[MALLOC_TSD_CLEANUPS_MAX];
9 |
10 | /******************************************************************************/
11 |
12 | void *
13 | malloc_tsd_malloc(size_t size)
14 | {
15 |
16 | /* Avoid choose_arena() in order to dodge bootstrapping issues. */
17 | return (arena_malloc(arenas[0], size, false, false));
18 | }
19 |
20 | void
21 | malloc_tsd_dalloc(void *wrapper)
22 | {
23 |
24 | idalloc(wrapper);
25 | }
26 |
27 | void
28 | malloc_tsd_no_cleanup(void *arg)
29 | {
30 |
31 | not_reached();
32 | }
33 |
34 | #if defined(JEMALLOC_MALLOC_THREAD_CLEANUP) || defined(_WIN32)
35 | #ifndef _WIN32
36 | JEMALLOC_EXPORT
37 | #endif
38 | void
39 | _malloc_thread_cleanup(void)
40 | {
41 | bool pending[MALLOC_TSD_CLEANUPS_MAX], again;
42 | unsigned i;
43 |
44 | for (i = 0; i < ncleanups; i++)
45 | pending[i] = true;
46 |
47 | do {
48 | again = false;
49 | for (i = 0; i < ncleanups; i++) {
50 | if (pending[i]) {
51 | pending[i] = cleanups[i]();
52 | if (pending[i])
53 | again = true;
54 | }
55 | }
56 | } while (again);
57 | }
58 | #endif
59 |
60 | void
61 | malloc_tsd_cleanup_register(bool (*f)(void))
62 | {
63 |
64 | assert(ncleanups < MALLOC_TSD_CLEANUPS_MAX);
65 | cleanups[ncleanups] = f;
66 | ncleanups++;
67 | }
68 |
69 | void
70 | malloc_tsd_boot(void)
71 | {
72 |
73 | ncleanups = 0;
74 | }
75 |
76 | #ifdef _WIN32
77 | static BOOL WINAPI
78 | _tls_callback(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
79 | {
80 |
81 | switch (fdwReason) {
82 | #ifdef JEMALLOC_LAZY_LOCK
83 | case DLL_THREAD_ATTACH:
84 | isthreaded = true;
85 | break;
86 | #endif
87 | case DLL_THREAD_DETACH:
88 | _malloc_thread_cleanup();
89 | break;
90 | default:
91 | break;
92 | }
93 | return (true);
94 | }
95 |
96 | #ifdef _MSC_VER
97 | # ifdef _M_IX86
98 | # pragma comment(linker, "/INCLUDE:__tls_used")
99 | # else
100 | # pragma comment(linker, "/INCLUDE:_tls_used")
101 | # endif
102 | # pragma section(".CRT$XLY",long,read)
103 | #endif
104 | JEMALLOC_SECTION(".CRT$XLY") JEMALLOC_ATTR(used)
105 | static const BOOL (WINAPI *tls_callback)(HINSTANCE hinstDLL,
106 | DWORD fdwReason, LPVOID lpvReserved) = _tls_callback;
107 | #endif
108 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/qr.h:
--------------------------------------------------------------------------------
1 | /* Ring definitions. */
2 | #define qr(a_type) \
3 | struct { \
4 | a_type *qre_next; \
5 | a_type *qre_prev; \
6 | }
7 |
8 | /* Ring functions. */
9 | #define qr_new(a_qr, a_field) do { \
10 | (a_qr)->a_field.qre_next = (a_qr); \
11 | (a_qr)->a_field.qre_prev = (a_qr); \
12 | } while (0)
13 |
14 | #define qr_next(a_qr, a_field) ((a_qr)->a_field.qre_next)
15 |
16 | #define qr_prev(a_qr, a_field) ((a_qr)->a_field.qre_prev)
17 |
18 | #define qr_before_insert(a_qrelm, a_qr, a_field) do { \
19 | (a_qr)->a_field.qre_prev = (a_qrelm)->a_field.qre_prev; \
20 | (a_qr)->a_field.qre_next = (a_qrelm); \
21 | (a_qr)->a_field.qre_prev->a_field.qre_next = (a_qr); \
22 | (a_qrelm)->a_field.qre_prev = (a_qr); \
23 | } while (0)
24 |
25 | #define qr_after_insert(a_qrelm, a_qr, a_field) \
26 | do \
27 | { \
28 | (a_qr)->a_field.qre_next = (a_qrelm)->a_field.qre_next; \
29 | (a_qr)->a_field.qre_prev = (a_qrelm); \
30 | (a_qr)->a_field.qre_next->a_field.qre_prev = (a_qr); \
31 | (a_qrelm)->a_field.qre_next = (a_qr); \
32 | } while (0)
33 |
34 | #define qr_meld(a_qr_a, a_qr_b, a_field) do { \
35 | void *t; \
36 | (a_qr_a)->a_field.qre_prev->a_field.qre_next = (a_qr_b); \
37 | (a_qr_b)->a_field.qre_prev->a_field.qre_next = (a_qr_a); \
38 | t = (a_qr_a)->a_field.qre_prev; \
39 | (a_qr_a)->a_field.qre_prev = (a_qr_b)->a_field.qre_prev; \
40 | (a_qr_b)->a_field.qre_prev = t; \
41 | } while (0)
42 |
43 | /* qr_meld() and qr_split() are functionally equivalent, so there's no need to
44 | * have two copies of the code. */
45 | #define qr_split(a_qr_a, a_qr_b, a_field) \
46 | qr_meld((a_qr_a), (a_qr_b), a_field)
47 |
48 | #define qr_remove(a_qr, a_field) do { \
49 | (a_qr)->a_field.qre_prev->a_field.qre_next \
50 | = (a_qr)->a_field.qre_next; \
51 | (a_qr)->a_field.qre_next->a_field.qre_prev \
52 | = (a_qr)->a_field.qre_prev; \
53 | (a_qr)->a_field.qre_next = (a_qr); \
54 | (a_qr)->a_field.qre_prev = (a_qr); \
55 | } while (0)
56 |
57 | #define qr_foreach(var, a_qr, a_field) \
58 | for ((var) = (a_qr); \
59 | (var) != NULL; \
60 | (var) = (((var)->a_field.qre_next != (a_qr)) \
61 | ? (var)->a_field.qre_next : NULL))
62 |
63 | #define qr_reverse_foreach(var, a_qr, a_field) \
64 | for ((var) = ((a_qr) != NULL) ? qr_prev(a_qr, a_field) : NULL; \
65 | (var) != NULL; \
66 | (var) = (((var) != (a_qr)) \
67 | ? (var)->a_field.qre_prev : NULL))
68 |
--------------------------------------------------------------------------------
/src/handlers.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __HANDLERS_H__
29 | #define __HANDLERS_H__
30 |
31 | #include "eagle.h"
32 | #include "event.h"
33 | #include "object.h"
34 | #include "queue_t.h"
35 | #include "channel_t.h"
36 |
37 | void queue_client_event_notify(EagleClient *client, Queue_t *queue_t);
38 | void queue_client_event_message(EagleClient *client, Queue_t *queue_t, Message *msg);
39 | void channel_client_event_message(EagleClient *client, Channel_t *channel, const char *topic, Object *msg);
40 | void channel_client_event_pattern_message(EagleClient *client, Channel_t *channel,
41 | const char *topic, const char *pattern, Object *msg);
42 | void process_request(EagleClient *client);
43 | void read_request(EventLoop *loop, int fd, void *data, int mask);
44 | void client_timeout(void);
45 | EagleClient *create_client(int fd);
46 | void free_client(EagleClient *client);
47 | void accept_tcp_handler(EventLoop *loop, int fd, void *data, int mask);
48 | void accept_unix_handler(EventLoop *loop, int fd, void *data, int mask);
49 |
50 | #endif
51 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/ql.h:
--------------------------------------------------------------------------------
1 | /*
2 | * List definitions.
3 | */
4 | #define ql_head(a_type) \
5 | struct { \
6 | a_type *qlh_first; \
7 | }
8 |
9 | #define ql_head_initializer(a_head) {NULL}
10 |
11 | #define ql_elm(a_type) qr(a_type)
12 |
13 | /* List functions. */
14 | #define ql_new(a_head) do { \
15 | (a_head)->qlh_first = NULL; \
16 | } while (0)
17 |
18 | #define ql_elm_new(a_elm, a_field) qr_new((a_elm), a_field)
19 |
20 | #define ql_first(a_head) ((a_head)->qlh_first)
21 |
22 | #define ql_last(a_head, a_field) \
23 | ((ql_first(a_head) != NULL) \
24 | ? qr_prev(ql_first(a_head), a_field) : NULL)
25 |
26 | #define ql_next(a_head, a_elm, a_field) \
27 | ((ql_last(a_head, a_field) != (a_elm)) \
28 | ? qr_next((a_elm), a_field) : NULL)
29 |
30 | #define ql_prev(a_head, a_elm, a_field) \
31 | ((ql_first(a_head) != (a_elm)) ? qr_prev((a_elm), a_field) \
32 | : NULL)
33 |
34 | #define ql_before_insert(a_head, a_qlelm, a_elm, a_field) do { \
35 | qr_before_insert((a_qlelm), (a_elm), a_field); \
36 | if (ql_first(a_head) == (a_qlelm)) { \
37 | ql_first(a_head) = (a_elm); \
38 | } \
39 | } while (0)
40 |
41 | #define ql_after_insert(a_qlelm, a_elm, a_field) \
42 | qr_after_insert((a_qlelm), (a_elm), a_field)
43 |
44 | #define ql_head_insert(a_head, a_elm, a_field) do { \
45 | if (ql_first(a_head) != NULL) { \
46 | qr_before_insert(ql_first(a_head), (a_elm), a_field); \
47 | } \
48 | ql_first(a_head) = (a_elm); \
49 | } while (0)
50 |
51 | #define ql_tail_insert(a_head, a_elm, a_field) do { \
52 | if (ql_first(a_head) != NULL) { \
53 | qr_before_insert(ql_first(a_head), (a_elm), a_field); \
54 | } \
55 | ql_first(a_head) = qr_next((a_elm), a_field); \
56 | } while (0)
57 |
58 | #define ql_remove(a_head, a_elm, a_field) do { \
59 | if (ql_first(a_head) == (a_elm)) { \
60 | ql_first(a_head) = qr_next(ql_first(a_head), a_field); \
61 | } \
62 | if (ql_first(a_head) != (a_elm)) { \
63 | qr_remove((a_elm), a_field); \
64 | } else { \
65 | ql_first(a_head) = NULL; \
66 | } \
67 | } while (0)
68 |
69 | #define ql_head_remove(a_head, a_type, a_field) do { \
70 | a_type *t = ql_first(a_head); \
71 | ql_remove((a_head), t, a_field); \
72 | } while (0)
73 |
74 | #define ql_tail_remove(a_head, a_type, a_field) do { \
75 | a_type *t = ql_last(a_head, a_field); \
76 | ql_remove((a_head), t, a_field); \
77 | } while (0)
78 |
79 | #define ql_foreach(a_var, a_head, a_field) \
80 | qr_foreach((a_var), ql_first(a_head), a_field)
81 |
82 | #define ql_reverse_foreach(a_var, a_head, a_field) \
83 | qr_reverse_foreach((a_var), ql_first(a_head), a_field)
84 |
--------------------------------------------------------------------------------
/src/message.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __MESSAGE_H__
29 | #define __MESSAGE_H__
30 |
31 | #include
32 |
33 | #include "eagle.h"
34 | #include "object.h"
35 |
36 | #define EG_MESSAGE_OBJECT(m) ((m)->value)
37 | #define EG_MESSAGE_VALUE(m) ((m)->value->data)
38 | #define EG_MESSAGE_SIZE(m) ((m)->value->size)
39 |
40 | #define EG_MESSAGE_GET_DATA(m, i) ((m)->data[i])
41 | #define EG_MESSAGE_SET_DATA(m, i, v) ((m)->data[i] = (v))
42 |
43 | #define EG_MESSAGE_GET_TAG(m) ((m)->tag)
44 | #define EG_MESSAGE_SET_TAG(m, v) ((m)->tag = (v))
45 |
46 | #define EG_MESSAGE_GET_CONFIRM_TIME(m) ((m)->confirm)
47 | #define EG_MESSAGE_SET_CONFIRM_TIME(m, v) ((m)->confirm = (v))
48 |
49 | #define EG_MESSAGE_GET_EXPIRATION_TIME(m) ((m)->expiration)
50 | #define EG_MESSAGE_SET_EXPIRATION_TIME(m, v) ((m)->expiration = (v))
51 |
52 | typedef struct Message {
53 | Object *value;
54 | uint64_t tag;
55 | uint32_t confirm;
56 | uint32_t expiration;
57 | void *data[2];
58 | } Message;
59 |
60 | Message *create_message(Object *data, uint64_t tag, uint32_t expiration);
61 | void release_message(Message *msg);
62 | void free_message_list_handler(void *ptr);
63 |
64 | #endif
65 |
--------------------------------------------------------------------------------
/src/object.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 |
30 | #include "eagle.h"
31 | #include "object.h"
32 | #include "xmalloc.h"
33 | #include "list.h"
34 |
35 | Object *create_object(void *ptr, size_t size)
36 | {
37 | Object *object = (Object*)xmalloc(sizeof(*object));
38 |
39 | object->data = ptr;
40 | object->size = size;
41 | object->refcount = 1;
42 |
43 | return object;
44 | }
45 |
46 | Object *create_dup_object(void *ptr, size_t size)
47 | {
48 | Object *object = (Object*)xmalloc(sizeof(*object));
49 |
50 | object->data = xmalloc(size);
51 | object->size = size;
52 | object->refcount = 1;
53 |
54 | memcpy(object->data, ptr, size);
55 |
56 | return object;
57 | }
58 |
59 | void release_object(Object *object)
60 | {
61 | xfree(object->data);
62 | xfree(object);
63 | }
64 |
65 | void increment_references_count(Object *object)
66 | {
67 | object->refcount++;
68 | }
69 |
70 | void decrement_references_count(Object *object)
71 | {
72 | if (object->refcount <= 1) {
73 | release_object(object);
74 | } else {
75 | object->refcount--;
76 | }
77 | }
78 |
79 | void free_object_list_handler(void *ptr)
80 | {
81 | decrement_references_count(ptr);
82 | }
83 |
--------------------------------------------------------------------------------
/src/xmalloc.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2009-2010, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __XMALLOC_H__
29 | #define __XMALLOC_H__
30 |
31 | #include
32 |
33 | #if defined(_USE_TCMALLOC_)
34 | #include
35 | #if (TC_VERSION_MAJOR == 1 && TC_VERSION_MINOR >= 6) || (TC_VERSION_MAJOR > 1)
36 | #define HAVE_MALLOC_SIZE 1
37 | #define xmalloc_size(p) tc_malloc_size(p)
38 | #else
39 | #error "Newer version of tcmalloc required"
40 | #endif
41 | #endif
42 |
43 | #if defined(_USE_JEMALLOC_)
44 | #include
45 | #if (JEMALLOC_VERSION_MAJOR == 2 && JEMALLOC_VERSION_MINOR >= 1) || (JEMALLOC_VERSION_MAJOR > 2)
46 | #define HAVE_MALLOC_SIZE 1
47 | #define xmalloc_size(p) je_malloc_usable_size(p)
48 | #else
49 | #error "Newer version of jemalloc required"
50 | #endif
51 | #endif
52 |
53 | void *xmalloc(size_t size);
54 | void *xcalloc(size_t size);
55 | void *xrealloc(void *ptr, size_t size);
56 | char *xstrdup(const char *str);
57 | void xfree(void *ptr);
58 | size_t xmalloc_used_memory(void);
59 | void xmalloc_state_lock_on(void);
60 | size_t xmalloc_memory_rss(void);
61 | float xmalloc_fragmentation_ratio(void);
62 |
63 | #ifndef HAVE_MALLOC_SIZE
64 | size_t xmalloc_size(void *ptr);
65 | #endif
66 |
67 | #endif
68 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/bitmap.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_BITMAP_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | /******************************************************************************/
5 | /* Function prototypes for non-inline static functions. */
6 |
7 | static size_t bits2groups(size_t nbits);
8 |
9 | /******************************************************************************/
10 |
11 | static size_t
12 | bits2groups(size_t nbits)
13 | {
14 |
15 | return ((nbits >> LG_BITMAP_GROUP_NBITS) +
16 | !!(nbits & BITMAP_GROUP_NBITS_MASK));
17 | }
18 |
19 | void
20 | bitmap_info_init(bitmap_info_t *binfo, size_t nbits)
21 | {
22 | unsigned i;
23 | size_t group_count;
24 |
25 | assert(nbits > 0);
26 | assert(nbits <= (ZU(1) << LG_BITMAP_MAXBITS));
27 |
28 | /*
29 | * Compute the number of groups necessary to store nbits bits, and
30 | * progressively work upward through the levels until reaching a level
31 | * that requires only one group.
32 | */
33 | binfo->levels[0].group_offset = 0;
34 | group_count = bits2groups(nbits);
35 | for (i = 1; group_count > 1; i++) {
36 | assert(i < BITMAP_MAX_LEVELS);
37 | binfo->levels[i].group_offset = binfo->levels[i-1].group_offset
38 | + group_count;
39 | group_count = bits2groups(group_count);
40 | }
41 | binfo->levels[i].group_offset = binfo->levels[i-1].group_offset
42 | + group_count;
43 | binfo->nlevels = i;
44 | binfo->nbits = nbits;
45 | }
46 |
47 | size_t
48 | bitmap_info_ngroups(const bitmap_info_t *binfo)
49 | {
50 |
51 | return (binfo->levels[binfo->nlevels].group_offset << LG_SIZEOF_BITMAP);
52 | }
53 |
54 | size_t
55 | bitmap_size(size_t nbits)
56 | {
57 | bitmap_info_t binfo;
58 |
59 | bitmap_info_init(&binfo, nbits);
60 | return (bitmap_info_ngroups(&binfo));
61 | }
62 |
63 | void
64 | bitmap_init(bitmap_t *bitmap, const bitmap_info_t *binfo)
65 | {
66 | size_t extra;
67 | unsigned i;
68 |
69 | /*
70 | * Bits are actually inverted with regard to the external bitmap
71 | * interface, so the bitmap starts out with all 1 bits, except for
72 | * trailing unused bits (if any). Note that each group uses bit 0 to
73 | * correspond to the first logical bit in the group, so extra bits
74 | * are the most significant bits of the last group.
75 | */
76 | memset(bitmap, 0xffU, binfo->levels[binfo->nlevels].group_offset <<
77 | LG_SIZEOF_BITMAP);
78 | extra = (BITMAP_GROUP_NBITS - (binfo->nbits & BITMAP_GROUP_NBITS_MASK))
79 | & BITMAP_GROUP_NBITS_MASK;
80 | if (extra != 0)
81 | bitmap[binfo->levels[1].group_offset - 1] >>= extra;
82 | for (i = 1; i < binfo->nlevels; i++) {
83 | size_t group_count = binfo->levels[i].group_offset -
84 | binfo->levels[i-1].group_offset;
85 | extra = (BITMAP_GROUP_NBITS - (group_count &
86 | BITMAP_GROUP_NBITS_MASK)) & BITMAP_GROUP_NBITS_MASK;
87 | if (extra != 0)
88 | bitmap[binfo->levels[i+1].group_offset - 1] >>= extra;
89 | }
90 | }
91 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/allocated.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | void *
5 | je_thread_start(void *arg)
6 | {
7 | int err;
8 | void *p;
9 | uint64_t a0, a1, d0, d1;
10 | uint64_t *ap0, *ap1, *dp0, *dp1;
11 | size_t sz, usize;
12 |
13 | sz = sizeof(a0);
14 | if ((err = mallctl("thread.allocated", &a0, &sz, NULL, 0))) {
15 | if (err == ENOENT) {
16 | #ifdef JEMALLOC_STATS
17 | assert(false);
18 | #endif
19 | goto label_return;
20 | }
21 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
22 | strerror(err));
23 | exit(1);
24 | }
25 | sz = sizeof(ap0);
26 | if ((err = mallctl("thread.allocatedp", &ap0, &sz, NULL, 0))) {
27 | if (err == ENOENT) {
28 | #ifdef JEMALLOC_STATS
29 | assert(false);
30 | #endif
31 | goto label_return;
32 | }
33 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
34 | strerror(err));
35 | exit(1);
36 | }
37 | assert(*ap0 == a0);
38 |
39 | sz = sizeof(d0);
40 | if ((err = mallctl("thread.deallocated", &d0, &sz, NULL, 0))) {
41 | if (err == ENOENT) {
42 | #ifdef JEMALLOC_STATS
43 | assert(false);
44 | #endif
45 | goto label_return;
46 | }
47 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
48 | strerror(err));
49 | exit(1);
50 | }
51 | sz = sizeof(dp0);
52 | if ((err = mallctl("thread.deallocatedp", &dp0, &sz, NULL, 0))) {
53 | if (err == ENOENT) {
54 | #ifdef JEMALLOC_STATS
55 | assert(false);
56 | #endif
57 | goto label_return;
58 | }
59 | malloc_printf("%s(): Error in mallctl(): %s\n", __func__,
60 | strerror(err));
61 | exit(1);
62 | }
63 | assert(*dp0 == d0);
64 |
65 | p = malloc(1);
66 | if (p == NULL) {
67 | malloc_printf("%s(): Error in malloc()\n", __func__);
68 | exit(1);
69 | }
70 |
71 | sz = sizeof(a1);
72 | mallctl("thread.allocated", &a1, &sz, NULL, 0);
73 | sz = sizeof(ap1);
74 | mallctl("thread.allocatedp", &ap1, &sz, NULL, 0);
75 | assert(*ap1 == a1);
76 | assert(ap0 == ap1);
77 |
78 | usize = malloc_usable_size(p);
79 | assert(a0 + usize <= a1);
80 |
81 | free(p);
82 |
83 | sz = sizeof(d1);
84 | mallctl("thread.deallocated", &d1, &sz, NULL, 0);
85 | sz = sizeof(dp1);
86 | mallctl("thread.deallocatedp", &dp1, &sz, NULL, 0);
87 | assert(*dp1 == d1);
88 | assert(dp0 == dp1);
89 |
90 | assert(d0 + usize <= d1);
91 |
92 | label_return:
93 | return (NULL);
94 | }
95 |
96 | int
97 | main(void)
98 | {
99 | int ret = 0;
100 | je_thread_t thread;
101 |
102 | malloc_printf("Test begin\n");
103 |
104 | je_thread_start(NULL);
105 |
106 | je_thread_create(&thread, je_thread_start, NULL);
107 | je_thread_join(thread, (void *)&ret);
108 |
109 | je_thread_start(NULL);
110 |
111 | je_thread_create(&thread, je_thread_start, NULL);
112 | je_thread_join(thread, (void *)&ret);
113 |
114 | je_thread_start(NULL);
115 |
116 | malloc_printf("Test end\n");
117 | return (ret);
118 | }
119 |
--------------------------------------------------------------------------------
/src/utils.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __UTILS_H__
29 | #define __UTILS_H__
30 |
31 | #include
32 | #include
33 |
34 | #define MESSAGE_BUFFER_SIZE 256
35 |
36 | #define TO_LOWER(c) (unsigned char)(c | 0x20)
37 | #define IS_ALPHA(c) (TO_LOWER(c) >= 'a' && TO_LOWER(c) <= 'z')
38 | #define IS_NUM(c) ((c) >= '0' && (c) <= '9')
39 | #define IS_ALPHANUM(c) (IS_ALPHA(c) || IS_NUM(c))
40 | #define IS_EXTRA1(c) ((c) == '_' || (c) == '-' || (c) == '.')
41 | #define IS_EXTRA2(c) ((c) == '*' || (c) == '?' || (c) == '[' || (c) == ']' || (c) == '\\')
42 | #define IS_EXTRA3(c) (IS_EXTRA1(c) || IS_EXTRA2(c))
43 |
44 | #define strlenz(s) (strlen(s) + 1)
45 |
46 | typedef enum { INFO_LEVEL, WARNING_LEVEL, FATAL_LEVEL, LOG_ONLY_LEVEL } message_level;
47 |
48 | void enable_log(const char *logfile);
49 | void disable_log();
50 | void warning(const char *fmt,...);
51 | void info(const char *fmt,...);
52 | void fatal(const char *fmt,...);
53 | void wlog(const char *fmt,...);
54 |
55 | int pattern_match_length(const char *string, int slength, const char *pattern, int plength, int nocase);
56 | int pattern_match(const char *string, const char *pattern, int nocase);
57 |
58 | uint64_t make_message_tag(uint32_t msg_counter, uint32_t time);
59 |
60 | long long memtoll(const char *value, int *err);
61 |
62 | int check_input_buffer1(char *buffer, size_t size);
63 | int check_input_buffer2(char *buffer, size_t size);
64 | int check_input_buffer3(char *buffer, size_t size);
65 |
66 | #endif
67 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/ckh.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | typedef struct ckh_s ckh_t;
5 | typedef struct ckhc_s ckhc_t;
6 |
7 | /* Typedefs to allow easy function pointer passing. */
8 | typedef void ckh_hash_t (const void *, unsigned, size_t *, size_t *);
9 | typedef bool ckh_keycomp_t (const void *, const void *);
10 |
11 | /* Maintain counters used to get an idea of performance. */
12 | /* #define CKH_COUNT */
13 | /* Print counter values in ckh_delete() (requires CKH_COUNT). */
14 | /* #define CKH_VERBOSE */
15 |
16 | /*
17 | * There are 2^LG_CKH_BUCKET_CELLS cells in each hash table bucket. Try to fit
18 | * one bucket per L1 cache line.
19 | */
20 | #define LG_CKH_BUCKET_CELLS (LG_CACHELINE - LG_SIZEOF_PTR - 1)
21 |
22 | #endif /* JEMALLOC_H_TYPES */
23 | /******************************************************************************/
24 | #ifdef JEMALLOC_H_STRUCTS
25 |
26 | /* Hash table cell. */
27 | struct ckhc_s {
28 | const void *key;
29 | const void *data;
30 | };
31 |
32 | struct ckh_s {
33 | #ifdef CKH_COUNT
34 | /* Counters used to get an idea of performance. */
35 | uint64_t ngrows;
36 | uint64_t nshrinks;
37 | uint64_t nshrinkfails;
38 | uint64_t ninserts;
39 | uint64_t nrelocs;
40 | #endif
41 |
42 | /* Used for pseudo-random number generation. */
43 | #define CKH_A 1103515241
44 | #define CKH_C 12347
45 | uint32_t prng_state;
46 |
47 | /* Total number of items. */
48 | size_t count;
49 |
50 | /*
51 | * Minimum and current number of hash table buckets. There are
52 | * 2^LG_CKH_BUCKET_CELLS cells per bucket.
53 | */
54 | unsigned lg_minbuckets;
55 | unsigned lg_curbuckets;
56 |
57 | /* Hash and comparison functions. */
58 | ckh_hash_t *hash;
59 | ckh_keycomp_t *keycomp;
60 |
61 | /* Hash table with 2^lg_curbuckets buckets. */
62 | ckhc_t *tab;
63 | };
64 |
65 | #endif /* JEMALLOC_H_STRUCTS */
66 | /******************************************************************************/
67 | #ifdef JEMALLOC_H_EXTERNS
68 |
69 | bool ckh_new(ckh_t *ckh, size_t minitems, ckh_hash_t *hash,
70 | ckh_keycomp_t *keycomp);
71 | void ckh_delete(ckh_t *ckh);
72 | size_t ckh_count(ckh_t *ckh);
73 | bool ckh_iter(ckh_t *ckh, size_t *tabind, void **key, void **data);
74 | bool ckh_insert(ckh_t *ckh, const void *key, const void *data);
75 | bool ckh_remove(ckh_t *ckh, const void *searchkey, void **key,
76 | void **data);
77 | bool ckh_search(ckh_t *ckh, const void *seachkey, void **key, void **data);
78 | void ckh_string_hash(const void *key, unsigned minbits, size_t *hash1,
79 | size_t *hash2);
80 | bool ckh_string_keycomp(const void *k1, const void *k2);
81 | void ckh_pointer_hash(const void *key, unsigned minbits, size_t *hash1,
82 | size_t *hash2);
83 | bool ckh_pointer_keycomp(const void *k1, const void *k2);
84 |
85 | #endif /* JEMALLOC_H_EXTERNS */
86 | /******************************************************************************/
87 | #ifdef JEMALLOC_H_INLINES
88 |
89 | #endif /* JEMALLOC_H_INLINES */
90 | /******************************************************************************/
91 |
--------------------------------------------------------------------------------
/src/queue.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __QUEUE_LIB_H__
29 | #define __QUEUE_LIB_H__
30 |
31 | #define EG_START_HEAD 0
32 | #define EG_START_TAIL 1
33 |
34 | #define EG_QUEUE_LENGTH(q) ((q)->len)
35 | #define EG_QUEUE_FIRST(q) ((q)->head)
36 | #define EG_QUEUE_LAST(q) ((q)->tail)
37 | #define EG_QUEUE_PREV_NODE(n) ((n)->prev)
38 | #define EG_QUEUE_NEXT_NODE(n) ((n)->next)
39 | #define EG_QUEUE_NODE_VALUE(n) ((n)->value)
40 |
41 | #define EG_QUEUE_SET_FREE_METHOD(q, m) ((q)->free = (m))
42 | #define EG_QUEUE_GET_FREE_METHOD(q) ((q)->free)
43 |
44 | typedef struct QueueNode {
45 | struct QueueNode *prev;
46 | struct QueueNode *next;
47 | void *value;
48 | } QueueNode;
49 |
50 | typedef struct QueueIterator {
51 | QueueNode *next;
52 | int direction;
53 | } QueueIterator;
54 |
55 | typedef struct Queue {
56 | QueueNode *head;
57 | QueueNode *tail;
58 | void (*free)(void *ptr);
59 | unsigned int len;
60 | } Queue;
61 |
62 | Queue *queue_create(void);
63 | void queue_release(Queue *queue);
64 | Queue *queue_push_value_head(Queue *queue, void *value);
65 | Queue *queue_push_value_tail(Queue *queue, void *value);
66 | void *queue_get_value(Queue *queue);
67 | void *queue_pop_value(Queue *queue);
68 | Queue *queue_purge(Queue *queue);
69 | void queue_delete_node(Queue *queue, QueueNode *node);
70 | QueueIterator *queue_get_iterator(Queue *queue, int direction);
71 | void queue_release_iterator(QueueIterator *iter);
72 | QueueNode *queue_next_node(QueueIterator *iter);
73 | void queue_rewind(Queue *queue, QueueIterator *iter);
74 |
75 | #endif
76 |
--------------------------------------------------------------------------------
/src/keylist.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __KEYLIST_LIB_H__
29 | #define __KEYLIST_LIB_H__
30 |
31 | #define EG_KEYLIST_LENGTH(l) ((l)->len)
32 | #define EG_KEYLIST_FIRST(l) ((l)->head)
33 | #define EG_KEYLIST_LAST(l) ((l)->tail)
34 | #define EG_KEYLIST_PREV_NODE(n) ((n)->prev)
35 | #define EG_KEYLIST_NEXT_NODE(n) ((n)->next)
36 | #define EG_KEYLIST_NODE_KEY(n) ((n)->key)
37 | #define EG_KEYLIST_NODE_VALUE(n) ((n)->value)
38 |
39 | #define EG_KEYLIST_SET_FREE_METHOD(l, m) ((l)->free = (m))
40 | #define EG_KEYLIST_SET_MATCH_METHOD(l, m) ((l)->match = (m))
41 |
42 | #define EG_KEYLIST_GET_FREE_METHOD(l) ((l)->free)
43 | #define EG_KEYLIST_GET_MATCH_METHOD(l) ((l)->match)
44 |
45 | typedef struct KeylistNode {
46 | struct KeylistNode *prev;
47 | struct KeylistNode *next;
48 | void *key;
49 | void *value;
50 | } KeylistNode;
51 |
52 | typedef struct KeylistIterator {
53 | KeylistNode *next;
54 | } KeylistIterator;
55 |
56 | typedef struct Keylist {
57 | KeylistNode *head;
58 | KeylistNode *tail;
59 | void (*free)(void *key, void *value);
60 | int (*match)(void *key1, void *key2);
61 | unsigned int len;
62 | } Keylist;
63 |
64 | Keylist *keylist_create(void);
65 | void keylist_release(Keylist *keylist);
66 | KeylistNode *keylist_get_value(Keylist *keylist, void *key);
67 | Keylist *keylist_set_value(Keylist *keylist, void *key, void *value);
68 | void keylist_delete_node(Keylist *keylist, KeylistNode *node);
69 | KeylistNode *keylist_next_node(KeylistIterator *iter);
70 | void keylist_rewind(Keylist *keylist, KeylistIterator *iter);
71 |
72 | #endif
73 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/posix_memalign.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | #define CHUNK 0x400000
5 | /* #define MAXALIGN ((size_t)UINT64_C(0x80000000000)) */
6 | #define MAXALIGN ((size_t)0x2000000LU)
7 | #define NITER 4
8 |
9 | int
10 | main(void)
11 | {
12 | size_t alignment, size, total;
13 | unsigned i;
14 | int err;
15 | void *p, *ps[NITER];
16 |
17 | malloc_printf("Test begin\n");
18 |
19 | /* Test error conditions. */
20 | for (alignment = 0; alignment < sizeof(void *); alignment++) {
21 | err = posix_memalign(&p, alignment, 1);
22 | if (err != EINVAL) {
23 | malloc_printf(
24 | "Expected error for invalid alignment %zu\n",
25 | alignment);
26 | }
27 | }
28 |
29 | for (alignment = sizeof(size_t); alignment < MAXALIGN;
30 | alignment <<= 1) {
31 | err = posix_memalign(&p, alignment + 1, 1);
32 | if (err == 0) {
33 | malloc_printf(
34 | "Expected error for invalid alignment %zu\n",
35 | alignment + 1);
36 | }
37 | }
38 |
39 | #if LG_SIZEOF_PTR == 3
40 | alignment = UINT64_C(0x8000000000000000);
41 | size = UINT64_C(0x8000000000000000);
42 | #else
43 | alignment = 0x80000000LU;
44 | size = 0x80000000LU;
45 | #endif
46 | err = posix_memalign(&p, alignment, size);
47 | if (err == 0) {
48 | malloc_printf(
49 | "Expected error for posix_memalign(&p, %zu, %zu)\n",
50 | alignment, size);
51 | }
52 |
53 | #if LG_SIZEOF_PTR == 3
54 | alignment = UINT64_C(0x4000000000000000);
55 | size = UINT64_C(0x8400000000000001);
56 | #else
57 | alignment = 0x40000000LU;
58 | size = 0x84000001LU;
59 | #endif
60 | err = posix_memalign(&p, alignment, size);
61 | if (err == 0) {
62 | malloc_printf(
63 | "Expected error for posix_memalign(&p, %zu, %zu)\n",
64 | alignment, size);
65 | }
66 |
67 | alignment = 0x10LU;
68 | #if LG_SIZEOF_PTR == 3
69 | size = UINT64_C(0xfffffffffffffff0);
70 | #else
71 | size = 0xfffffff0LU;
72 | #endif
73 | err = posix_memalign(&p, alignment, size);
74 | if (err == 0) {
75 | malloc_printf(
76 | "Expected error for posix_memalign(&p, %zu, %zu)\n",
77 | alignment, size);
78 | }
79 |
80 | for (i = 0; i < NITER; i++)
81 | ps[i] = NULL;
82 |
83 | for (alignment = 8;
84 | alignment <= MAXALIGN;
85 | alignment <<= 1) {
86 | total = 0;
87 | malloc_printf("Alignment: %zu\n", alignment);
88 | for (size = 1;
89 | size < 3 * alignment && size < (1U << 31);
90 | size += (alignment >> (LG_SIZEOF_PTR-1)) - 1) {
91 | for (i = 0; i < NITER; i++) {
92 | err = posix_memalign(&ps[i],
93 | alignment, size);
94 | if (err) {
95 | malloc_printf(
96 | "Error for size %zu (%#zx): %s\n",
97 | size, size, strerror(err));
98 | exit(1);
99 | }
100 | total += malloc_usable_size(ps[i]);
101 | if (total >= (MAXALIGN << 1))
102 | break;
103 | }
104 | for (i = 0; i < NITER; i++) {
105 | if (ps[i] != NULL) {
106 | free(ps[i]);
107 | ps[i] = NULL;
108 | }
109 | }
110 | }
111 | }
112 |
113 | malloc_printf("Test end\n");
114 | return (0);
115 | }
116 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/mutex.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | typedef struct malloc_mutex_s malloc_mutex_t;
5 |
6 | #ifdef _WIN32
7 | # define MALLOC_MUTEX_INITIALIZER
8 | #elif (defined(JEMALLOC_OSSPIN))
9 | # define MALLOC_MUTEX_INITIALIZER {0}
10 | #elif (defined(JEMALLOC_MUTEX_INIT_CB))
11 | # define MALLOC_MUTEX_INITIALIZER {PTHREAD_MUTEX_INITIALIZER, NULL}
12 | #else
13 | # if (defined(PTHREAD_MUTEX_ADAPTIVE_NP) && \
14 | defined(PTHREAD_ADAPTIVE_MUTEX_INITIALIZER_NP))
15 | # define MALLOC_MUTEX_TYPE PTHREAD_MUTEX_ADAPTIVE_NP
16 | # define MALLOC_MUTEX_INITIALIZER {PTHREAD_ADAPTIVE_MUTEX_INITIALIZER_NP}
17 | # else
18 | # define MALLOC_MUTEX_TYPE PTHREAD_MUTEX_DEFAULT
19 | # define MALLOC_MUTEX_INITIALIZER {PTHREAD_MUTEX_INITIALIZER}
20 | # endif
21 | #endif
22 |
23 | #endif /* JEMALLOC_H_TYPES */
24 | /******************************************************************************/
25 | #ifdef JEMALLOC_H_STRUCTS
26 |
27 | struct malloc_mutex_s {
28 | #ifdef _WIN32
29 | CRITICAL_SECTION lock;
30 | #elif (defined(JEMALLOC_OSSPIN))
31 | OSSpinLock lock;
32 | #elif (defined(JEMALLOC_MUTEX_INIT_CB))
33 | pthread_mutex_t lock;
34 | malloc_mutex_t *postponed_next;
35 | #else
36 | pthread_mutex_t lock;
37 | #endif
38 | };
39 |
40 | #endif /* JEMALLOC_H_STRUCTS */
41 | /******************************************************************************/
42 | #ifdef JEMALLOC_H_EXTERNS
43 |
44 | #ifdef JEMALLOC_LAZY_LOCK
45 | extern bool isthreaded;
46 | #else
47 | # undef isthreaded /* Undo private_namespace.h definition. */
48 | # define isthreaded true
49 | #endif
50 |
51 | bool malloc_mutex_init(malloc_mutex_t *mutex);
52 | void malloc_mutex_prefork(malloc_mutex_t *mutex);
53 | void malloc_mutex_postfork_parent(malloc_mutex_t *mutex);
54 | void malloc_mutex_postfork_child(malloc_mutex_t *mutex);
55 | bool mutex_boot(void);
56 |
57 | #endif /* JEMALLOC_H_EXTERNS */
58 | /******************************************************************************/
59 | #ifdef JEMALLOC_H_INLINES
60 |
61 | #ifndef JEMALLOC_ENABLE_INLINE
62 | void malloc_mutex_lock(malloc_mutex_t *mutex);
63 | void malloc_mutex_unlock(malloc_mutex_t *mutex);
64 | #endif
65 |
66 | #if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_MUTEX_C_))
67 | JEMALLOC_INLINE void
68 | malloc_mutex_lock(malloc_mutex_t *mutex)
69 | {
70 |
71 | if (isthreaded) {
72 | #ifdef _WIN32
73 | EnterCriticalSection(&mutex->lock);
74 | #elif (defined(JEMALLOC_OSSPIN))
75 | OSSpinLockLock(&mutex->lock);
76 | #else
77 | pthread_mutex_lock(&mutex->lock);
78 | #endif
79 | }
80 | }
81 |
82 | JEMALLOC_INLINE void
83 | malloc_mutex_unlock(malloc_mutex_t *mutex)
84 | {
85 |
86 | if (isthreaded) {
87 | #ifdef _WIN32
88 | LeaveCriticalSection(&mutex->lock);
89 | #elif (defined(JEMALLOC_OSSPIN))
90 | OSSpinLockUnlock(&mutex->lock);
91 | #else
92 | pthread_mutex_unlock(&mutex->lock);
93 | #endif
94 | }
95 | }
96 | #endif
97 |
98 | #endif /* JEMALLOC_H_INLINES */
99 | /******************************************************************************/
100 |
--------------------------------------------------------------------------------
/src/list.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2006-2010, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __LIST_LIB_H__
29 | #define __LIST_LIB_H__
30 |
31 | #define EG_START_HEAD 0
32 | #define EG_START_TAIL 1
33 |
34 | #define EG_LIST_LENGTH(l) ((l)->len)
35 | #define EG_LIST_FIRST(l) ((l)->head)
36 | #define EG_LIST_LAST(l) ((l)->tail)
37 | #define EG_LIST_PREV_NODE(n) ((n)->prev)
38 | #define EG_LIST_NEXT_NODE(n) ((n)->next)
39 | #define EG_LIST_NODE_VALUE(n) ((n)->value)
40 |
41 | #define EG_LIST_SET_FREE_METHOD(l, m) ((l)->free = (m))
42 | #define EG_LIST_SET_MATCH_METHOD(l, m) ((l)->match = (m))
43 |
44 | #define EG_LIST_GET_FREE_METHOD(l) ((l)->free)
45 | #define EG_LIST_GET_MATCH_METHOD(l) ((l)->match)
46 |
47 | typedef struct ListNode {
48 | struct ListNode *prev;
49 | struct ListNode *next;
50 | void *value;
51 | } ListNode;
52 |
53 | typedef struct ListIterator {
54 | ListNode *next;
55 | int direction;
56 | } ListIterator;
57 |
58 | typedef struct List {
59 | ListNode *head;
60 | ListNode *tail;
61 | void (*free)(void *ptr);
62 | int (*match)(void *ptr, void *value);
63 | unsigned int len;
64 | } List;
65 |
66 | List *list_create(void);
67 | void list_release(List *list);
68 | List *list_add_value_head(List *list, void *value);
69 | List *list_add_value_tail(List *list, void *value);
70 | int list_delete_value(List *list, void *value);
71 | void list_delete_node(List *list, ListNode *node);
72 | ListIterator *list_get_iterator(List *list, int direction);
73 | void list_release_iterator(ListIterator *iter);
74 | ListNode *list_next_node(ListIterator *iter);
75 | ListNode *list_search_node(List *list, void *value);
76 | void list_rotate(List *list);
77 | void list_rewind(List *list, ListIterator *iter);
78 |
79 | #endif
80 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/mb.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | #endif /* JEMALLOC_H_TYPES */
5 | /******************************************************************************/
6 | #ifdef JEMALLOC_H_STRUCTS
7 |
8 | #endif /* JEMALLOC_H_STRUCTS */
9 | /******************************************************************************/
10 | #ifdef JEMALLOC_H_EXTERNS
11 |
12 | #endif /* JEMALLOC_H_EXTERNS */
13 | /******************************************************************************/
14 | #ifdef JEMALLOC_H_INLINES
15 |
16 | #ifndef JEMALLOC_ENABLE_INLINE
17 | void mb_write(void);
18 | #endif
19 |
20 | #if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_MB_C_))
21 | #ifdef __i386__
22 | /*
23 | * According to the Intel Architecture Software Developer's Manual, current
24 | * processors execute instructions in order from the perspective of other
25 | * processors in a multiprocessor system, but 1) Intel reserves the right to
26 | * change that, and 2) the compiler's optimizer could re-order instructions if
27 | * there weren't some form of barrier. Therefore, even if running on an
28 | * architecture that does not need memory barriers (everything through at least
29 | * i686), an "optimizer barrier" is necessary.
30 | */
31 | JEMALLOC_INLINE void
32 | mb_write(void)
33 | {
34 |
35 | # if 0
36 | /* This is a true memory barrier. */
37 | asm volatile ("pusha;"
38 | "xor %%eax,%%eax;"
39 | "cpuid;"
40 | "popa;"
41 | : /* Outputs. */
42 | : /* Inputs. */
43 | : "memory" /* Clobbers. */
44 | );
45 | #else
46 | /*
47 | * This is hopefully enough to keep the compiler from reordering
48 | * instructions around this one.
49 | */
50 | asm volatile ("nop;"
51 | : /* Outputs. */
52 | : /* Inputs. */
53 | : "memory" /* Clobbers. */
54 | );
55 | #endif
56 | }
57 | #elif (defined(__amd64__) || defined(__x86_64__))
58 | JEMALLOC_INLINE void
59 | mb_write(void)
60 | {
61 |
62 | asm volatile ("sfence"
63 | : /* Outputs. */
64 | : /* Inputs. */
65 | : "memory" /* Clobbers. */
66 | );
67 | }
68 | #elif defined(__powerpc__)
69 | JEMALLOC_INLINE void
70 | mb_write(void)
71 | {
72 |
73 | asm volatile ("eieio"
74 | : /* Outputs. */
75 | : /* Inputs. */
76 | : "memory" /* Clobbers. */
77 | );
78 | }
79 | #elif defined(__sparc64__)
80 | JEMALLOC_INLINE void
81 | mb_write(void)
82 | {
83 |
84 | asm volatile ("membar #StoreStore"
85 | : /* Outputs. */
86 | : /* Inputs. */
87 | : "memory" /* Clobbers. */
88 | );
89 | }
90 | #elif defined(__tile__)
91 | JEMALLOC_INLINE void
92 | mb_write(void)
93 | {
94 |
95 | __sync_synchronize();
96 | }
97 | #else
98 | /*
99 | * This is much slower than a simple memory barrier, but the semantics of mutex
100 | * unlock make this work.
101 | */
102 | JEMALLOC_INLINE void
103 | mb_write(void)
104 | {
105 | malloc_mutex_t mtx;
106 |
107 | malloc_mutex_init(&mtx);
108 | malloc_mutex_lock(&mtx);
109 | malloc_mutex_unlock(&mtx);
110 | }
111 | #endif
112 | #endif
113 |
114 | #endif /* JEMALLOC_H_INLINES */
115 | /******************************************************************************/
116 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/aligned_alloc.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | #define CHUNK 0x400000
5 | /* #define MAXALIGN ((size_t)UINT64_C(0x80000000000)) */
6 | #define MAXALIGN ((size_t)0x2000000LU)
7 | #define NITER 4
8 |
9 | int
10 | main(void)
11 | {
12 | size_t alignment, size, total;
13 | unsigned i;
14 | void *p, *ps[NITER];
15 |
16 | malloc_printf("Test begin\n");
17 |
18 | /* Test error conditions. */
19 | alignment = 0;
20 | set_errno(0);
21 | p = aligned_alloc(alignment, 1);
22 | if (p != NULL || get_errno() != EINVAL) {
23 | malloc_printf(
24 | "Expected error for invalid alignment %zu\n", alignment);
25 | }
26 |
27 | for (alignment = sizeof(size_t); alignment < MAXALIGN;
28 | alignment <<= 1) {
29 | set_errno(0);
30 | p = aligned_alloc(alignment + 1, 1);
31 | if (p != NULL || get_errno() != EINVAL) {
32 | malloc_printf(
33 | "Expected error for invalid alignment %zu\n",
34 | alignment + 1);
35 | }
36 | }
37 |
38 | #if LG_SIZEOF_PTR == 3
39 | alignment = UINT64_C(0x8000000000000000);
40 | size = UINT64_C(0x8000000000000000);
41 | #else
42 | alignment = 0x80000000LU;
43 | size = 0x80000000LU;
44 | #endif
45 | set_errno(0);
46 | p = aligned_alloc(alignment, size);
47 | if (p != NULL || get_errno() != ENOMEM) {
48 | malloc_printf(
49 | "Expected error for aligned_alloc(%zu, %zu)\n",
50 | alignment, size);
51 | }
52 |
53 | #if LG_SIZEOF_PTR == 3
54 | alignment = UINT64_C(0x4000000000000000);
55 | size = UINT64_C(0x8400000000000001);
56 | #else
57 | alignment = 0x40000000LU;
58 | size = 0x84000001LU;
59 | #endif
60 | set_errno(0);
61 | p = aligned_alloc(alignment, size);
62 | if (p != NULL || get_errno() != ENOMEM) {
63 | malloc_printf(
64 | "Expected error for aligned_alloc(%zu, %zu)\n",
65 | alignment, size);
66 | }
67 |
68 | alignment = 0x10LU;
69 | #if LG_SIZEOF_PTR == 3
70 | size = UINT64_C(0xfffffffffffffff0);
71 | #else
72 | size = 0xfffffff0LU;
73 | #endif
74 | set_errno(0);
75 | p = aligned_alloc(alignment, size);
76 | if (p != NULL || get_errno() != ENOMEM) {
77 | malloc_printf(
78 | "Expected error for aligned_alloc(&p, %zu, %zu)\n",
79 | alignment, size);
80 | }
81 |
82 | for (i = 0; i < NITER; i++)
83 | ps[i] = NULL;
84 |
85 | for (alignment = 8;
86 | alignment <= MAXALIGN;
87 | alignment <<= 1) {
88 | total = 0;
89 | malloc_printf("Alignment: %zu\n", alignment);
90 | for (size = 1;
91 | size < 3 * alignment && size < (1U << 31);
92 | size += (alignment >> (LG_SIZEOF_PTR-1)) - 1) {
93 | for (i = 0; i < NITER; i++) {
94 | ps[i] = aligned_alloc(alignment, size);
95 | if (ps[i] == NULL) {
96 | char buf[BUFERROR_BUF];
97 |
98 | buferror(buf, sizeof(buf));
99 | malloc_printf(
100 | "Error for size %zu (%#zx): %s\n",
101 | size, size, buf);
102 | exit(1);
103 | }
104 | total += malloc_usable_size(ps[i]);
105 | if (total >= (MAXALIGN << 1))
106 | break;
107 | }
108 | for (i = 0; i < NITER; i++) {
109 | if (ps[i] != NULL) {
110 | free(ps[i]);
111 | ps[i] = NULL;
112 | }
113 | }
114 | }
115 | }
116 |
117 | malloc_printf("Test end\n");
118 | return (0);
119 | }
120 |
--------------------------------------------------------------------------------
/src/queue_t.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __QUEUE_H__
29 | #define __QUEUE_H__
30 |
31 | #include
32 |
33 | #include "eagle.h"
34 | #include "list.h"
35 | #include "keylist.h"
36 | #include "object.h"
37 | #include "message.h"
38 |
39 | Queue_t *create_queue_t(const char *name, uint32_t max_msg, uint32_t max_msg_size, uint32_t flags);
40 | void delete_queue_t(Queue_t *queue_t);
41 | int push_message_queue_t(Queue_t *queue_t, Object *data, uint32_t expiration);
42 | Message *get_message_queue_t(Queue_t *queue_t);
43 | void pop_message_queue_t(Queue_t *queue_t, uint32_t timeout);
44 | int confirm_message_queue_t(Queue_t *queue_t, uint64_t tag);
45 | Queue_t *find_queue_t(List *list, const char *name);
46 | void rename_queue_t(Queue_t *queue_t, const char *name);
47 | uint32_t get_declared_clients_queue_t(Queue_t *queue_t);
48 | uint32_t get_subscribed_clients_queue_t(Queue_t *queue_t);
49 | uint32_t get_size_queue_t(Queue_t *queue_t);
50 | void purge_queue_t(Queue_t *queue_t);
51 | void declare_client_queue_t(Queue_t *queue_t, EagleClient *client);
52 | void undeclare_client_queue_t(Queue_t *queue_t, EagleClient *client);
53 | void subscribe_client_queue_t(Queue_t *queue_t, EagleClient *client, uint32_t flags);
54 | void unsubscribe_client_queue_t(Queue_t *queue_t, EagleClient *client);
55 | void link_queue_route_t(Queue_t *queue_t, Route_t *route, const char *key);
56 | void unlink_queue_route_t(Queue_t *queue_t, Route_t *route, const char *key);
57 | void process_queue_t(Queue_t *queue_t);
58 | void process_expired_messages_queue_t(Queue_t *queue_t, uint32_t time);
59 | void process_unconfirmed_messages_queue_t(Queue_t *queue_t, uint32_t time);
60 | void free_queue_list_handler(void *ptr);
61 |
62 | #endif
63 |
--------------------------------------------------------------------------------
/src/user.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 | #include
30 | #include
31 | #include
32 |
33 | #include "eagle.h"
34 | #include "user.h"
35 | #include "xmalloc.h"
36 | #include "list.h"
37 | #include "utils.h"
38 |
39 | EagleUser *create_user(const char *name, const char *password, uint64_t perm)
40 | {
41 | EagleUser *user = (EagleUser*)xmalloc(sizeof(*user));
42 |
43 | memcpy(user->name, name, strlenz(name));
44 | memcpy(user->password, password, strlenz(password));
45 |
46 | user->perm = perm;
47 |
48 | return user;
49 | }
50 |
51 | void delete_user(EagleUser *user)
52 | {
53 | xfree(user);
54 | }
55 |
56 | EagleUser *find_user(List *list, const char *name, const char *password)
57 | {
58 | EagleUser *user;
59 | ListNode *node;
60 | ListIterator iterator;
61 |
62 | list_rewind(list, &iterator);
63 | while ((node = list_next_node(&iterator)) != NULL)
64 | {
65 | user = EG_LIST_NODE_VALUE(node);
66 |
67 | if (password != NULL) {
68 | if (!strcmp(user->name, name) && !strcmp(user->password, password)) {
69 | return user;
70 | }
71 | } else {
72 | if (!strcmp(user->name, name)) {
73 | return user;
74 | }
75 | }
76 | }
77 |
78 | return NULL;
79 | }
80 |
81 | void rename_user(EagleUser *user, const char *name)
82 | {
83 | memcpy(user->name, name, strlenz(name));
84 | }
85 |
86 | void set_user_perm(EagleUser *user, uint64_t perm)
87 | {
88 | user->perm = perm;
89 | }
90 |
91 | uint64_t get_user_perm(EagleUser *user)
92 | {
93 | return user->perm;
94 | }
95 |
96 | void free_user_list_handler(void *ptr)
97 | {
98 | delete_user(ptr);
99 | }
100 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/rallocm.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | int
5 | main(void)
6 | {
7 | size_t pagesize;
8 | void *p, *q;
9 | size_t sz, tsz;
10 | int r;
11 |
12 | malloc_printf("Test begin\n");
13 |
14 | /* Get page size. */
15 | {
16 | #ifdef _WIN32
17 | SYSTEM_INFO si;
18 | GetSystemInfo(&si);
19 | pagesize = (size_t)si.dwPageSize;
20 | #else
21 | long result = sysconf(_SC_PAGESIZE);
22 | assert(result != -1);
23 | pagesize = (size_t)result;
24 | #endif
25 | }
26 |
27 | r = allocm(&p, &sz, 42, 0);
28 | if (r != ALLOCM_SUCCESS) {
29 | malloc_printf("Unexpected allocm() error\n");
30 | abort();
31 | }
32 |
33 | q = p;
34 | r = rallocm(&q, &tsz, sz, 0, ALLOCM_NO_MOVE);
35 | if (r != ALLOCM_SUCCESS)
36 | malloc_printf("Unexpected rallocm() error\n");
37 | if (q != p)
38 | malloc_printf("Unexpected object move\n");
39 | if (tsz != sz) {
40 | malloc_printf("Unexpected size change: %zu --> %zu\n",
41 | sz, tsz);
42 | }
43 |
44 | q = p;
45 | r = rallocm(&q, &tsz, sz, 5, ALLOCM_NO_MOVE);
46 | if (r != ALLOCM_SUCCESS)
47 | malloc_printf("Unexpected rallocm() error\n");
48 | if (q != p)
49 | malloc_printf("Unexpected object move\n");
50 | if (tsz != sz) {
51 | malloc_printf("Unexpected size change: %zu --> %zu\n",
52 | sz, tsz);
53 | }
54 |
55 | q = p;
56 | r = rallocm(&q, &tsz, sz + 5, 0, ALLOCM_NO_MOVE);
57 | if (r != ALLOCM_ERR_NOT_MOVED)
58 | malloc_printf("Unexpected rallocm() result\n");
59 | if (q != p)
60 | malloc_printf("Unexpected object move\n");
61 | if (tsz != sz) {
62 | malloc_printf("Unexpected size change: %zu --> %zu\n",
63 | sz, tsz);
64 | }
65 |
66 | q = p;
67 | r = rallocm(&q, &tsz, sz + 5, 0, 0);
68 | if (r != ALLOCM_SUCCESS)
69 | malloc_printf("Unexpected rallocm() error\n");
70 | if (q == p)
71 | malloc_printf("Expected object move\n");
72 | if (tsz == sz) {
73 | malloc_printf("Expected size change: %zu --> %zu\n",
74 | sz, tsz);
75 | }
76 | p = q;
77 | sz = tsz;
78 |
79 | r = rallocm(&q, &tsz, pagesize*2, 0, 0);
80 | if (r != ALLOCM_SUCCESS)
81 | malloc_printf("Unexpected rallocm() error\n");
82 | if (q == p)
83 | malloc_printf("Expected object move\n");
84 | if (tsz == sz) {
85 | malloc_printf("Expected size change: %zu --> %zu\n",
86 | sz, tsz);
87 | }
88 | p = q;
89 | sz = tsz;
90 |
91 | r = rallocm(&q, &tsz, pagesize*4, 0, 0);
92 | if (r != ALLOCM_SUCCESS)
93 | malloc_printf("Unexpected rallocm() error\n");
94 | if (tsz == sz) {
95 | malloc_printf("Expected size change: %zu --> %zu\n",
96 | sz, tsz);
97 | }
98 | p = q;
99 | sz = tsz;
100 |
101 | r = rallocm(&q, &tsz, pagesize*2, 0, ALLOCM_NO_MOVE);
102 | if (r != ALLOCM_SUCCESS)
103 | malloc_printf("Unexpected rallocm() error\n");
104 | if (q != p)
105 | malloc_printf("Unexpected object move\n");
106 | if (tsz == sz) {
107 | malloc_printf("Expected size change: %zu --> %zu\n",
108 | sz, tsz);
109 | }
110 | sz = tsz;
111 |
112 | r = rallocm(&q, &tsz, pagesize*4, 0, ALLOCM_NO_MOVE);
113 | if (r != ALLOCM_SUCCESS)
114 | malloc_printf("Unexpected rallocm() error\n");
115 | if (q != p)
116 | malloc_printf("Unexpected object move\n");
117 | if (tsz == sz) {
118 | malloc_printf("Expected size change: %zu --> %zu\n",
119 | sz, tsz);
120 | }
121 | sz = tsz;
122 |
123 | dallocm(p, 0);
124 |
125 | malloc_printf("Test end\n");
126 | return (0);
127 | }
128 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/base.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_BASE_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | /******************************************************************************/
5 | /* Data. */
6 |
7 | static malloc_mutex_t base_mtx;
8 |
9 | /*
10 | * Current pages that are being used for internal memory allocations. These
11 | * pages are carved up in cacheline-size quanta, so that there is no chance of
12 | * false cache line sharing.
13 | */
14 | static void *base_pages;
15 | static void *base_next_addr;
16 | static void *base_past_addr; /* Addr immediately past base_pages. */
17 | static extent_node_t *base_nodes;
18 |
19 | /******************************************************************************/
20 | /* Function prototypes for non-inline static functions. */
21 |
22 | static bool base_pages_alloc(size_t minsize);
23 |
24 | /******************************************************************************/
25 |
26 | static bool
27 | base_pages_alloc(size_t minsize)
28 | {
29 | size_t csize;
30 | bool zero;
31 |
32 | assert(minsize != 0);
33 | csize = CHUNK_CEILING(minsize);
34 | zero = false;
35 | base_pages = chunk_alloc(csize, chunksize, true, &zero,
36 | chunk_dss_prec_get());
37 | if (base_pages == NULL)
38 | return (true);
39 | base_next_addr = base_pages;
40 | base_past_addr = (void *)((uintptr_t)base_pages + csize);
41 |
42 | return (false);
43 | }
44 |
45 | void *
46 | base_alloc(size_t size)
47 | {
48 | void *ret;
49 | size_t csize;
50 |
51 | /* Round size up to nearest multiple of the cacheline size. */
52 | csize = CACHELINE_CEILING(size);
53 |
54 | malloc_mutex_lock(&base_mtx);
55 | /* Make sure there's enough space for the allocation. */
56 | if ((uintptr_t)base_next_addr + csize > (uintptr_t)base_past_addr) {
57 | if (base_pages_alloc(csize)) {
58 | malloc_mutex_unlock(&base_mtx);
59 | return (NULL);
60 | }
61 | }
62 | /* Allocate. */
63 | ret = base_next_addr;
64 | base_next_addr = (void *)((uintptr_t)base_next_addr + csize);
65 | malloc_mutex_unlock(&base_mtx);
66 |
67 | return (ret);
68 | }
69 |
70 | void *
71 | base_calloc(size_t number, size_t size)
72 | {
73 | void *ret = base_alloc(number * size);
74 |
75 | if (ret != NULL)
76 | memset(ret, 0, number * size);
77 |
78 | return (ret);
79 | }
80 |
81 | extent_node_t *
82 | base_node_alloc(void)
83 | {
84 | extent_node_t *ret;
85 |
86 | malloc_mutex_lock(&base_mtx);
87 | if (base_nodes != NULL) {
88 | ret = base_nodes;
89 | base_nodes = *(extent_node_t **)ret;
90 | malloc_mutex_unlock(&base_mtx);
91 | } else {
92 | malloc_mutex_unlock(&base_mtx);
93 | ret = (extent_node_t *)base_alloc(sizeof(extent_node_t));
94 | }
95 |
96 | return (ret);
97 | }
98 |
99 | void
100 | base_node_dealloc(extent_node_t *node)
101 | {
102 |
103 | malloc_mutex_lock(&base_mtx);
104 | *(extent_node_t **)node = base_nodes;
105 | base_nodes = node;
106 | malloc_mutex_unlock(&base_mtx);
107 | }
108 |
109 | bool
110 | base_boot(void)
111 | {
112 |
113 | base_nodes = NULL;
114 | if (malloc_mutex_init(&base_mtx))
115 | return (true);
116 |
117 | return (false);
118 | }
119 |
120 | void
121 | base_prefork(void)
122 | {
123 |
124 | malloc_mutex_prefork(&base_mtx);
125 | }
126 |
127 | void
128 | base_postfork_parent(void)
129 | {
130 |
131 | malloc_mutex_postfork_parent(&base_mtx);
132 | }
133 |
134 | void
135 | base_postfork_child(void)
136 | {
137 |
138 | malloc_mutex_postfork_child(&base_mtx);
139 | }
140 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/bitmap.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | #if (LG_BITMAP_MAXBITS > 12)
5 | # define MAXBITS 4500
6 | #else
7 | # define MAXBITS (1U << LG_BITMAP_MAXBITS)
8 | #endif
9 |
10 | static void
11 | test_bitmap_size(void)
12 | {
13 | size_t i, prev_size;
14 |
15 | prev_size = 0;
16 | for (i = 1; i <= MAXBITS; i++) {
17 | size_t size = bitmap_size(i);
18 | assert(size >= prev_size);
19 | prev_size = size;
20 | }
21 | }
22 |
23 | static void
24 | test_bitmap_init(void)
25 | {
26 | size_t i;
27 |
28 | for (i = 1; i <= MAXBITS; i++) {
29 | bitmap_info_t binfo;
30 | bitmap_info_init(&binfo, i);
31 | {
32 | size_t j;
33 | bitmap_t *bitmap = malloc(sizeof(bitmap_t) *
34 | bitmap_info_ngroups(&binfo));
35 | bitmap_init(bitmap, &binfo);
36 |
37 | for (j = 0; j < i; j++)
38 | assert(bitmap_get(bitmap, &binfo, j) == false);
39 | free(bitmap);
40 |
41 | }
42 | }
43 | }
44 |
45 | static void
46 | test_bitmap_set(void)
47 | {
48 | size_t i;
49 |
50 | for (i = 1; i <= MAXBITS; i++) {
51 | bitmap_info_t binfo;
52 | bitmap_info_init(&binfo, i);
53 | {
54 | size_t j;
55 | bitmap_t *bitmap = malloc(sizeof(bitmap_t) *
56 | bitmap_info_ngroups(&binfo));
57 | bitmap_init(bitmap, &binfo);
58 |
59 | for (j = 0; j < i; j++)
60 | bitmap_set(bitmap, &binfo, j);
61 | assert(bitmap_full(bitmap, &binfo));
62 | free(bitmap);
63 | }
64 | }
65 | }
66 |
67 | static void
68 | test_bitmap_unset(void)
69 | {
70 | size_t i;
71 |
72 | for (i = 1; i <= MAXBITS; i++) {
73 | bitmap_info_t binfo;
74 | bitmap_info_init(&binfo, i);
75 | {
76 | size_t j;
77 | bitmap_t *bitmap = malloc(sizeof(bitmap_t) *
78 | bitmap_info_ngroups(&binfo));
79 | bitmap_init(bitmap, &binfo);
80 |
81 | for (j = 0; j < i; j++)
82 | bitmap_set(bitmap, &binfo, j);
83 | assert(bitmap_full(bitmap, &binfo));
84 | for (j = 0; j < i; j++)
85 | bitmap_unset(bitmap, &binfo, j);
86 | for (j = 0; j < i; j++)
87 | bitmap_set(bitmap, &binfo, j);
88 | assert(bitmap_full(bitmap, &binfo));
89 | free(bitmap);
90 | }
91 | }
92 | }
93 |
94 | static void
95 | test_bitmap_sfu(void)
96 | {
97 | size_t i;
98 |
99 | for (i = 1; i <= MAXBITS; i++) {
100 | bitmap_info_t binfo;
101 | bitmap_info_init(&binfo, i);
102 | {
103 | ssize_t j;
104 | bitmap_t *bitmap = malloc(sizeof(bitmap_t) *
105 | bitmap_info_ngroups(&binfo));
106 | bitmap_init(bitmap, &binfo);
107 |
108 | /* Iteratively set bits starting at the beginning. */
109 | for (j = 0; j < i; j++)
110 | assert(bitmap_sfu(bitmap, &binfo) == j);
111 | assert(bitmap_full(bitmap, &binfo));
112 |
113 | /*
114 | * Iteratively unset bits starting at the end, and
115 | * verify that bitmap_sfu() reaches the unset bits.
116 | */
117 | for (j = i - 1; j >= 0; j--) {
118 | bitmap_unset(bitmap, &binfo, j);
119 | assert(bitmap_sfu(bitmap, &binfo) == j);
120 | bitmap_unset(bitmap, &binfo, j);
121 | }
122 | assert(bitmap_get(bitmap, &binfo, 0) == false);
123 |
124 | /*
125 | * Iteratively set bits starting at the beginning, and
126 | * verify that bitmap_sfu() looks past them.
127 | */
128 | for (j = 1; j < i; j++) {
129 | bitmap_set(bitmap, &binfo, j - 1);
130 | assert(bitmap_sfu(bitmap, &binfo) == j);
131 | bitmap_unset(bitmap, &binfo, j);
132 | }
133 | assert(bitmap_sfu(bitmap, &binfo) == i - 1);
134 | assert(bitmap_full(bitmap, &binfo));
135 | free(bitmap);
136 | }
137 | }
138 | }
139 |
140 | int
141 | main(void)
142 | {
143 | malloc_printf("Test begin\n");
144 |
145 | test_bitmap_size();
146 | test_bitmap_init();
147 | test_bitmap_set();
148 | test_bitmap_unset();
149 | test_bitmap_sfu();
150 |
151 | malloc_printf("Test end\n");
152 | return (0);
153 | }
154 |
--------------------------------------------------------------------------------
/src/event.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2006-2012, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __EVENT_H__
29 | #define __EVENT_H__
30 |
31 | #define EG_EVENT_OK 0
32 | #define EG_EVENT_ERR -1
33 |
34 | #define EG_EVENT_NONE 0
35 | #define EG_EVENT_READABLE 1
36 | #define EG_EVENT_WRITABLE 2
37 |
38 | #define EG_EVENT_FILE 1
39 | #define EG_EVENT_TIME 2
40 | #define EG_EVENTS_ALL (EG_EVENT_FILE|EG_EVENT_TIME)
41 | #define EG_DONT_WAIT 4
42 |
43 | struct EventLoop;
44 |
45 | typedef void file_handler(struct EventLoop *loop, int fd, void *data, int mask);
46 | typedef int time_handler(struct EventLoop *loop, long long id, void *data);
47 | typedef void finalizer_handler(struct EventLoop *loop, void *data);
48 | typedef void before_sleep_handler(struct EventLoop *loop);
49 |
50 | typedef struct FileEvent {
51 | int mask;
52 | file_handler *read_handler;
53 | file_handler *write_handler;
54 | void *data;
55 | } FileEvent;
56 |
57 | typedef struct TimeEvent {
58 | long long id;
59 | long sec;
60 | long ms;
61 | time_handler *time_handler;
62 | finalizer_handler *finalizer_handler;
63 | void *data;
64 | struct TimeEvent *next;
65 | } TimeEvent;
66 |
67 | typedef struct FiredEvent {
68 | int fd;
69 | int mask;
70 | } FiredEvent;
71 |
72 | typedef struct EventLoop {
73 | int maxfd;
74 | int size;
75 | long long time_event_id;
76 | FileEvent *events;
77 | FiredEvent *fired;
78 | TimeEvent *time_event;
79 | int stop;
80 | void *api_data;
81 | before_sleep_handler *before_sleep_handler;
82 | } EventLoop;
83 |
84 | EventLoop *create_event_loop(int size);
85 | void delete_event_loop(EventLoop *loop);
86 | void stop_event_loop(EventLoop *loop);
87 | int create_file_event(EventLoop *loop, int fd, int mask, file_handler *handler, void *data);
88 | void delete_file_event(EventLoop *loop, int fd, int mask);
89 | int get_file_events(EventLoop *loop, int fd);
90 | long long create_time_event(EventLoop *loop, long long milliseconds, time_handler *time_handler,
91 | finalizer_handler *finalizer_handler, void *data);
92 | int delete_time_event(EventLoop *loop, long long id);
93 | int process_events(EventLoop *loop, int flags);
94 | void start_main_loop(EventLoop *loop);
95 | void set_before_sleep_handler(EventLoop *loop, before_sleep_handler *before_sleep_handler);
96 | char *get_event_api_name(void);
97 |
98 | #endif
99 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/size_classes.sh:
--------------------------------------------------------------------------------
1 | #!/bin/sh
2 |
3 | # The following limits are chosen such that they cover all supported platforms.
4 |
5 | # Range of quanta.
6 | lg_qmin=3
7 | lg_qmax=4
8 |
9 | # The range of tiny size classes is [2^lg_tmin..2^(lg_q-1)].
10 | lg_tmin=3
11 |
12 | # Range of page sizes.
13 | lg_pmin=12
14 | lg_pmax=16
15 |
16 | pow2() {
17 | e=$1
18 | pow2_result=1
19 | while [ ${e} -gt 0 ] ; do
20 | pow2_result=$((${pow2_result} + ${pow2_result}))
21 | e=$((${e} - 1))
22 | done
23 | }
24 |
25 | cat < 255)
102 | # error "Too many small size classes"
103 | #endif
104 |
105 | #endif /* JEMALLOC_H_TYPES */
106 | /******************************************************************************/
107 | #ifdef JEMALLOC_H_STRUCTS
108 |
109 |
110 | #endif /* JEMALLOC_H_STRUCTS */
111 | /******************************************************************************/
112 | #ifdef JEMALLOC_H_EXTERNS
113 |
114 |
115 | #endif /* JEMALLOC_H_EXTERNS */
116 | /******************************************************************************/
117 | #ifdef JEMALLOC_H_INLINES
118 |
119 |
120 | #endif /* JEMALLOC_H_INLINES */
121 | /******************************************************************************/
122 | EOF
123 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/ctl.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | typedef struct ctl_node_s ctl_node_t;
5 | typedef struct ctl_named_node_s ctl_named_node_t;
6 | typedef struct ctl_indexed_node_s ctl_indexed_node_t;
7 | typedef struct ctl_arena_stats_s ctl_arena_stats_t;
8 | typedef struct ctl_stats_s ctl_stats_t;
9 |
10 | #endif /* JEMALLOC_H_TYPES */
11 | /******************************************************************************/
12 | #ifdef JEMALLOC_H_STRUCTS
13 |
14 | struct ctl_node_s {
15 | bool named;
16 | };
17 |
18 | struct ctl_named_node_s {
19 | struct ctl_node_s node;
20 | const char *name;
21 | /* If (nchildren == 0), this is a terminal node. */
22 | unsigned nchildren;
23 | const ctl_node_t *children;
24 | int (*ctl)(const size_t *, size_t, void *, size_t *,
25 | void *, size_t);
26 | };
27 |
28 | struct ctl_indexed_node_s {
29 | struct ctl_node_s node;
30 | const ctl_named_node_t *(*index)(const size_t *, size_t, size_t);
31 | };
32 |
33 | struct ctl_arena_stats_s {
34 | bool initialized;
35 | unsigned nthreads;
36 | const char *dss;
37 | size_t pactive;
38 | size_t pdirty;
39 | arena_stats_t astats;
40 |
41 | /* Aggregate stats for small size classes, based on bin stats. */
42 | size_t allocated_small;
43 | uint64_t nmalloc_small;
44 | uint64_t ndalloc_small;
45 | uint64_t nrequests_small;
46 |
47 | malloc_bin_stats_t bstats[NBINS];
48 | malloc_large_stats_t *lstats; /* nlclasses elements. */
49 | };
50 |
51 | struct ctl_stats_s {
52 | size_t allocated;
53 | size_t active;
54 | size_t mapped;
55 | struct {
56 | size_t current; /* stats_chunks.curchunks */
57 | uint64_t total; /* stats_chunks.nchunks */
58 | size_t high; /* stats_chunks.highchunks */
59 | } chunks;
60 | struct {
61 | size_t allocated; /* huge_allocated */
62 | uint64_t nmalloc; /* huge_nmalloc */
63 | uint64_t ndalloc; /* huge_ndalloc */
64 | } huge;
65 | unsigned narenas;
66 | ctl_arena_stats_t *arenas; /* (narenas + 1) elements. */
67 | };
68 |
69 | #endif /* JEMALLOC_H_STRUCTS */
70 | /******************************************************************************/
71 | #ifdef JEMALLOC_H_EXTERNS
72 |
73 | int ctl_byname(const char *name, void *oldp, size_t *oldlenp, void *newp,
74 | size_t newlen);
75 | int ctl_nametomib(const char *name, size_t *mibp, size_t *miblenp);
76 |
77 | int ctl_bymib(const size_t *mib, size_t miblen, void *oldp, size_t *oldlenp,
78 | void *newp, size_t newlen);
79 | bool ctl_boot(void);
80 | void ctl_prefork(void);
81 | void ctl_postfork_parent(void);
82 | void ctl_postfork_child(void);
83 |
84 | #define xmallctl(name, oldp, oldlenp, newp, newlen) do { \
85 | if (je_mallctl(name, oldp, oldlenp, newp, newlen) \
86 | != 0) { \
87 | malloc_printf( \
88 | ": Failure in xmallctl(\"%s\", ...)\n", \
89 | name); \
90 | abort(); \
91 | } \
92 | } while (0)
93 |
94 | #define xmallctlnametomib(name, mibp, miblenp) do { \
95 | if (je_mallctlnametomib(name, mibp, miblenp) != 0) { \
96 | malloc_printf(": Failure in " \
97 | "xmallctlnametomib(\"%s\", ...)\n", name); \
98 | abort(); \
99 | } \
100 | } while (0)
101 |
102 | #define xmallctlbymib(mib, miblen, oldp, oldlenp, newp, newlen) do { \
103 | if (je_mallctlbymib(mib, miblen, oldp, oldlenp, newp, \
104 | newlen) != 0) { \
105 | malloc_write( \
106 | ": Failure in xmallctlbymib()\n"); \
107 | abort(); \
108 | } \
109 | } while (0)
110 |
111 | #endif /* JEMALLOC_H_EXTERNS */
112 | /******************************************************************************/
113 | #ifdef JEMALLOC_H_INLINES
114 |
115 | #endif /* JEMALLOC_H_INLINES */
116 | /******************************************************************************/
117 |
118 |
--------------------------------------------------------------------------------
/src/user.h:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #ifndef __USER_H__
29 | #define __USER_H__
30 |
31 | #include
32 |
33 | #include "list.h"
34 |
35 | #define EG_USER_ALL_PERM 0x3F
36 | #define EG_USER_SUPER_PERM 0x7F
37 |
38 | #define EG_USER_QUEUE_PERM 0
39 | #define EG_USER_ROUTE_PERM 1
40 | #define EG_USER_CHANNEL_PERM 2
41 | #define EG_USER_RESV3_PERM 3
42 | #define EG_USER_RESV4_PERM 4
43 | #define EG_USER_ADMIN_PERM 5
44 | #define EG_USER_NOT_CHANGE_PERM 6
45 |
46 | #define EG_USER_QUEUE_CREATE_PERM 20
47 | #define EG_USER_QUEUE_DECLARE_PERM 21
48 | #define EG_USER_QUEUE_EXIST_PERM 22
49 | #define EG_USER_QUEUE_LIST_PERM 23
50 | #define EG_USER_QUEUE_RENAME_PERM 24
51 | #define EG_USER_QUEUE_SIZE_PERM 25
52 | #define EG_USER_QUEUE_PUSH_PERM 26
53 | #define EG_USER_QUEUE_GET_PERM 27
54 | #define EG_USER_QUEUE_POP_PERM 28
55 | #define EG_USER_QUEUE_CONFIRM_PERM 29
56 | #define EG_USER_QUEUE_SUBSCRIBE_PERM 30
57 | #define EG_USER_QUEUE_UNSUBSCRIBE_PERM 31
58 | #define EG_USER_QUEUE_PURGE_PERM 32
59 | #define EG_USER_QUEUE_DELETE_PERM 33
60 |
61 | #define EG_USER_ROUTE_CREATE_PERM 34
62 | #define EG_USER_ROUTE_EXIST_PERM 35
63 | #define EG_USER_ROUTE_LIST_PERM 36
64 | #define EG_USER_ROUTE_KEYS_PERM 37
65 | #define EG_USER_ROUTE_RENAME_PERM 38
66 | #define EG_USER_ROUTE_BIND_PERM 39
67 | #define EG_USER_ROUTE_UNBIND_PERM 40
68 | #define EG_USER_ROUTE_PUSH_PERM 41
69 | #define EG_USER_ROUTE_DELETE_PERM 42
70 |
71 | #define EG_USER_CHANNEL_CREATE_PERM 43
72 | #define EG_USER_CHANNEL_EXIST_PERM 44
73 | #define EG_USER_CHANNEL_LIST_PERM 45
74 | #define EG_USER_CHANNEL_RENAME_PERM 46
75 | #define EG_USER_CHANNEL_PUBLISH_PERM 47
76 | #define EG_USER_CHANNEL_SUBSCRIBE_PERM 48
77 | #define EG_USER_CHANNEL_PSUBSCRIBE_PERM 49
78 | #define EG_USER_CHANNEL_UNSUBSCRIBE_PERM 50
79 | #define EG_USER_CHANNEL_PUNSUBSCRIBE_PERM 51
80 | #define EG_USER_CHANNEL_DELETE_PERM 52
81 |
82 | typedef struct EagleUser {
83 | char name[32];
84 | char password[32];
85 | uint64_t perm;
86 | } EagleUser;
87 |
88 | EagleUser *create_user(const char *name, const char *password, uint64_t perm);
89 | void delete_user(EagleUser *user);
90 | EagleUser *find_user(List *list, const char *name, const char *password);
91 | void rename_user(EagleUser *user, const char *name);
92 | void set_user_perm(EagleUser *user, uint64_t perm);
93 | uint64_t get_user_perm(EagleUser *user);
94 | void free_user_list_handler(void *ptr);
95 |
96 | #endif
97 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/mutex.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MUTEX_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | #if defined(JEMALLOC_LAZY_LOCK) && !defined(_WIN32)
5 | #include
6 | #endif
7 |
8 | #ifndef _CRT_SPINCOUNT
9 | #define _CRT_SPINCOUNT 4000
10 | #endif
11 |
12 | /******************************************************************************/
13 | /* Data. */
14 |
15 | #ifdef JEMALLOC_LAZY_LOCK
16 | bool isthreaded = false;
17 | #endif
18 | #ifdef JEMALLOC_MUTEX_INIT_CB
19 | static bool postpone_init = true;
20 | static malloc_mutex_t *postponed_mutexes = NULL;
21 | #endif
22 |
23 | #if defined(JEMALLOC_LAZY_LOCK) && !defined(_WIN32)
24 | static void pthread_create_once(void);
25 | #endif
26 |
27 | /******************************************************************************/
28 | /*
29 | * We intercept pthread_create() calls in order to toggle isthreaded if the
30 | * process goes multi-threaded.
31 | */
32 |
33 | #if defined(JEMALLOC_LAZY_LOCK) && !defined(_WIN32)
34 | static int (*pthread_create_fptr)(pthread_t *__restrict, const pthread_attr_t *,
35 | void *(*)(void *), void *__restrict);
36 |
37 | static void
38 | pthread_create_once(void)
39 | {
40 |
41 | pthread_create_fptr = dlsym(RTLD_NEXT, "pthread_create");
42 | if (pthread_create_fptr == NULL) {
43 | malloc_write(": Error in dlsym(RTLD_NEXT, "
44 | "\"pthread_create\")\n");
45 | abort();
46 | }
47 |
48 | isthreaded = true;
49 | }
50 |
51 | JEMALLOC_EXPORT int
52 | pthread_create(pthread_t *__restrict thread,
53 | const pthread_attr_t *__restrict attr, void *(*start_routine)(void *),
54 | void *__restrict arg)
55 | {
56 | static pthread_once_t once_control = PTHREAD_ONCE_INIT;
57 |
58 | pthread_once(&once_control, pthread_create_once);
59 |
60 | return (pthread_create_fptr(thread, attr, start_routine, arg));
61 | }
62 | #endif
63 |
64 | /******************************************************************************/
65 |
66 | #ifdef JEMALLOC_MUTEX_INIT_CB
67 | JEMALLOC_EXPORT int _pthread_mutex_init_calloc_cb(pthread_mutex_t *mutex,
68 | void *(calloc_cb)(size_t, size_t));
69 | #endif
70 |
71 | bool
72 | malloc_mutex_init(malloc_mutex_t *mutex)
73 | {
74 |
75 | #ifdef _WIN32
76 | if (!InitializeCriticalSectionAndSpinCount(&mutex->lock,
77 | _CRT_SPINCOUNT))
78 | return (true);
79 | #elif (defined(JEMALLOC_OSSPIN))
80 | mutex->lock = 0;
81 | #elif (defined(JEMALLOC_MUTEX_INIT_CB))
82 | if (postpone_init) {
83 | mutex->postponed_next = postponed_mutexes;
84 | postponed_mutexes = mutex;
85 | } else {
86 | if (_pthread_mutex_init_calloc_cb(&mutex->lock, base_calloc) !=
87 | 0)
88 | return (true);
89 | }
90 | #else
91 | pthread_mutexattr_t attr;
92 |
93 | if (pthread_mutexattr_init(&attr) != 0)
94 | return (true);
95 | pthread_mutexattr_settype(&attr, MALLOC_MUTEX_TYPE);
96 | if (pthread_mutex_init(&mutex->lock, &attr) != 0) {
97 | pthread_mutexattr_destroy(&attr);
98 | return (true);
99 | }
100 | pthread_mutexattr_destroy(&attr);
101 | #endif
102 | return (false);
103 | }
104 |
105 | void
106 | malloc_mutex_prefork(malloc_mutex_t *mutex)
107 | {
108 |
109 | malloc_mutex_lock(mutex);
110 | }
111 |
112 | void
113 | malloc_mutex_postfork_parent(malloc_mutex_t *mutex)
114 | {
115 |
116 | malloc_mutex_unlock(mutex);
117 | }
118 |
119 | void
120 | malloc_mutex_postfork_child(malloc_mutex_t *mutex)
121 | {
122 |
123 | #ifdef JEMALLOC_MUTEX_INIT_CB
124 | malloc_mutex_unlock(mutex);
125 | #else
126 | if (malloc_mutex_init(mutex)) {
127 | malloc_printf(": Error re-initializing mutex in "
128 | "child\n");
129 | if (opt_abort)
130 | abort();
131 | }
132 | #endif
133 | }
134 |
135 | bool
136 | mutex_boot(void)
137 | {
138 |
139 | #ifdef JEMALLOC_MUTEX_INIT_CB
140 | postpone_init = false;
141 | while (postponed_mutexes != NULL) {
142 | if (_pthread_mutex_init_calloc_cb(&postponed_mutexes->lock,
143 | base_calloc) != 0)
144 | return (true);
145 | postponed_mutexes = postponed_mutexes->postponed_next;
146 | }
147 | #endif
148 | return (false);
149 | }
150 |
--------------------------------------------------------------------------------
/src/event_select.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2009-2012, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 | #include
30 | #include
31 | #include
32 | #include
33 | #include
34 |
35 | typedef struct ApiData {
36 | fd_set rfds, wfds;
37 | fd_set _rfds, _wfds;
38 | } ApiData;
39 |
40 | static int event_api_init(EventLoop *loop)
41 | {
42 | ApiData *data;
43 |
44 | data = (ApiData*)xmalloc(sizeof(*data));
45 |
46 | FD_ZERO(&data->rfds);
47 | FD_ZERO(&data->wfds);
48 |
49 | loop->api_data = data;
50 |
51 | return 0;
52 | }
53 |
54 | static void event_api_free(EventLoop *loop)
55 | {
56 | xfree(loop->api_data);
57 | }
58 |
59 | static int event_api_add(EventLoop *loop, int fd, int mask)
60 | {
61 | ApiData *data;
62 |
63 | data = loop->api_data;
64 |
65 | if (mask & EG_EVENT_READABLE) {
66 | FD_SET(fd, &data->rfds);
67 | }
68 |
69 | if (mask & EG_EVENT_WRITABLE) {
70 | FD_SET(fd, &data->wfds);
71 | }
72 |
73 | return 0;
74 | }
75 |
76 | static void event_api_delete(EventLoop *loop, int fd, int mask)
77 | {
78 | ApiData *data;
79 |
80 | data = loop->api_data;
81 |
82 | if (mask & EG_EVENT_READABLE) {
83 | FD_CLR(fd, &data->rfds);
84 | }
85 |
86 | if (mask & EG_EVENT_WRITABLE) {
87 | FD_CLR(fd, &data->wfds);
88 | }
89 | }
90 |
91 | static int event_api_poll(EventLoop *loop, struct timeval *tvp)
92 | {
93 | ApiData *data;
94 | FileEvent *file_event;
95 | int retval, i, mask, events = 0;
96 |
97 | data = loop->api_data;
98 |
99 | memcpy(&data->_rfds, &data->rfds, sizeof(fd_set));
100 | memcpy(&data->_wfds, &data->wfds, sizeof(fd_set));
101 |
102 | retval = select(loop->maxfd + 1, &data->_rfds, &data->_wfds, NULL, tvp);
103 |
104 | if (retval > 0)
105 | {
106 | for (i = 0; i <= loop->maxfd; i++)
107 | {
108 | mask = 0;
109 | file_event = &loop->events[i];
110 |
111 | if (file_event->mask == EG_EVENT_NONE) {
112 | continue;
113 | }
114 |
115 | if (file_event->mask & EG_EVENT_READABLE && FD_ISSET(i, &data->_rfds)) {
116 | mask |= EG_EVENT_READABLE;
117 | }
118 |
119 | if (file_event->mask & EG_EVENT_WRITABLE && FD_ISSET(i, &data->_wfds)) {
120 | mask |= EG_EVENT_WRITABLE;
121 | }
122 |
123 | loop->fired[events].fd = i;
124 | loop->fired[events].mask = mask;
125 | events++;
126 | }
127 | }
128 |
129 | return events;
130 | }
131 |
132 | static char *event_api_name(void)
133 | {
134 | return "select";
135 | }
136 |
--------------------------------------------------------------------------------
/src/keylist.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 |
30 | #include "eagle.h"
31 | #include "keylist.h"
32 | #include "xmalloc.h"
33 |
34 | Keylist *keylist_create(void)
35 | {
36 | Keylist *keylist;
37 |
38 | keylist = (Keylist*)xmalloc(sizeof(*keylist));
39 |
40 | keylist->head = keylist->tail = NULL;
41 | keylist->len = 0;
42 | keylist->free = NULL;
43 | keylist->match = NULL;
44 |
45 | return keylist;
46 | }
47 |
48 | void keylist_release(Keylist *keylist)
49 | {
50 | unsigned int len;
51 | KeylistNode *current, *next;
52 |
53 | current = keylist->head;
54 | len = keylist->len;
55 |
56 | while (len--) {
57 | next = current->next;
58 |
59 | if (keylist->free) {
60 | keylist->free(current->key, current->value);
61 | }
62 |
63 | xfree(current);
64 | current = next;
65 | }
66 |
67 | xfree(keylist);
68 | }
69 |
70 | KeylistNode *keylist_get_value(Keylist *keylist, void *key)
71 | {
72 | KeylistIterator iter;
73 | KeylistNode *node;
74 |
75 | keylist_rewind(keylist, &iter);
76 | while ((node = keylist_next_node(&iter)) != NULL)
77 | {
78 | if (keylist->match) {
79 | if (keylist->match(node->key, key)) {
80 | return node;
81 | }
82 | } else {
83 | if (node->key == key) {
84 | return node;
85 | }
86 | }
87 | }
88 |
89 | return NULL;
90 | }
91 |
92 | Keylist *keylist_set_value(Keylist *keylist, void *key, void *value)
93 | {
94 | KeylistNode *node = keylist_get_value(keylist, key);
95 |
96 | if (node != NULL) {
97 | node->value = value;
98 | return keylist;
99 | }
100 |
101 | node = (KeylistNode*)xmalloc(sizeof(*node));
102 |
103 | node->key = key;
104 | node->value = value;
105 |
106 | if (keylist->len == 0) {
107 | keylist->head = keylist->tail = node;
108 | node->prev = node->next = NULL;
109 | } else {
110 | node->prev = keylist->tail;
111 | node->next = NULL;
112 | keylist->tail->next = node;
113 | keylist->tail = node;
114 | }
115 |
116 | keylist->len++;
117 |
118 | return keylist;
119 | }
120 |
121 | void keylist_delete_node(Keylist *keylist, KeylistNode *node)
122 | {
123 | if (node->prev) {
124 | node->prev->next = node->next;
125 | } else {
126 | keylist->head = node->next;
127 | }
128 |
129 | if (node->next) {
130 | node->next->prev = node->prev;
131 | } else {
132 | keylist->tail = node->prev;
133 | }
134 |
135 | if (keylist->free) {
136 | keylist->free(node->key, node->value);
137 | }
138 |
139 | xfree(node);
140 | keylist->len--;
141 | }
142 |
143 | KeylistNode *keylist_next_node(KeylistIterator *iter)
144 | {
145 | KeylistNode *current = iter->next;
146 |
147 | if (current != NULL) {
148 | iter->next = current->next;
149 | }
150 |
151 | return current;
152 | }
153 |
154 | void keylist_rewind(Keylist *keylist, KeylistIterator *iter)
155 | {
156 | iter->next = keylist->head;
157 | }
158 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/util.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | /* Size of stack-allocated buffer passed to buferror(). */
5 | #define BUFERROR_BUF 64
6 |
7 | /*
8 | * Size of stack-allocated buffer used by malloc_{,v,vc}printf(). This must be
9 | * large enough for all possible uses within jemalloc.
10 | */
11 | #define MALLOC_PRINTF_BUFSIZE 4096
12 |
13 | /*
14 | * Wrap a cpp argument that contains commas such that it isn't broken up into
15 | * multiple arguments.
16 | */
17 | #define JEMALLOC_CONCAT(...) __VA_ARGS__
18 |
19 | /*
20 | * Silence compiler warnings due to uninitialized values. This is used
21 | * wherever the compiler fails to recognize that the variable is never used
22 | * uninitialized.
23 | */
24 | #ifdef JEMALLOC_CC_SILENCE
25 | # define JEMALLOC_CC_SILENCE_INIT(v) = v
26 | #else
27 | # define JEMALLOC_CC_SILENCE_INIT(v)
28 | #endif
29 |
30 | /*
31 | * Define a custom assert() in order to reduce the chances of deadlock during
32 | * assertion failure.
33 | */
34 | #ifndef assert
35 | #define assert(e) do { \
36 | if (config_debug && !(e)) { \
37 | malloc_printf( \
38 | ": %s:%d: Failed assertion: \"%s\"\n", \
39 | __FILE__, __LINE__, #e); \
40 | abort(); \
41 | } \
42 | } while (0)
43 | #endif
44 |
45 | /* Use to assert a particular configuration, e.g., cassert(config_debug). */
46 | #define cassert(c) do { \
47 | if ((c) == false) \
48 | assert(false); \
49 | } while (0)
50 |
51 | #ifndef not_reached
52 | #define not_reached() do { \
53 | if (config_debug) { \
54 | malloc_printf( \
55 | ": %s:%d: Unreachable code reached\n", \
56 | __FILE__, __LINE__); \
57 | abort(); \
58 | } \
59 | } while (0)
60 | #endif
61 |
62 | #ifndef not_implemented
63 | #define not_implemented() do { \
64 | if (config_debug) { \
65 | malloc_printf(": %s:%d: Not implemented\n", \
66 | __FILE__, __LINE__); \
67 | abort(); \
68 | } \
69 | } while (0)
70 | #endif
71 |
72 | #define assert_not_implemented(e) do { \
73 | if (config_debug && !(e)) \
74 | not_implemented(); \
75 | } while (0)
76 |
77 | #endif /* JEMALLOC_H_TYPES */
78 | /******************************************************************************/
79 | #ifdef JEMALLOC_H_STRUCTS
80 |
81 | #endif /* JEMALLOC_H_STRUCTS */
82 | /******************************************************************************/
83 | #ifdef JEMALLOC_H_EXTERNS
84 |
85 | int buferror(char *buf, size_t buflen);
86 | uintmax_t malloc_strtoumax(const char *nptr, char **endptr, int base);
87 | void malloc_write(const char *s);
88 |
89 | /*
90 | * malloc_vsnprintf() supports a subset of snprintf(3) that avoids floating
91 | * point math.
92 | */
93 | int malloc_vsnprintf(char *str, size_t size, const char *format,
94 | va_list ap);
95 | int malloc_snprintf(char *str, size_t size, const char *format, ...)
96 | JEMALLOC_ATTR(format(printf, 3, 4));
97 | void malloc_vcprintf(void (*write_cb)(void *, const char *), void *cbopaque,
98 | const char *format, va_list ap);
99 | void malloc_cprintf(void (*write)(void *, const char *), void *cbopaque,
100 | const char *format, ...) JEMALLOC_ATTR(format(printf, 3, 4));
101 | void malloc_printf(const char *format, ...)
102 | JEMALLOC_ATTR(format(printf, 1, 2));
103 |
104 | #endif /* JEMALLOC_H_EXTERNS */
105 | /******************************************************************************/
106 | #ifdef JEMALLOC_H_INLINES
107 |
108 | #ifndef JEMALLOC_ENABLE_INLINE
109 | size_t pow2_ceil(size_t x);
110 | void malloc_write(const char *s);
111 | void set_errno(int errnum);
112 | int get_errno(void);
113 | #endif
114 |
115 | #if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_UTIL_C_))
116 | /* Compute the smallest power of 2 that is >= x. */
117 | JEMALLOC_INLINE size_t
118 | pow2_ceil(size_t x)
119 | {
120 |
121 | x--;
122 | x |= x >> 1;
123 | x |= x >> 2;
124 | x |= x >> 4;
125 | x |= x >> 8;
126 | x |= x >> 16;
127 | #if (LG_SIZEOF_PTR == 3)
128 | x |= x >> 32;
129 | #endif
130 | x++;
131 | return (x);
132 | }
133 |
134 | /* Sets error code */
135 | JEMALLOC_INLINE void
136 | set_errno(int errnum)
137 | {
138 |
139 | #ifdef _WIN32
140 | SetLastError(errnum);
141 | #else
142 | errno = errnum;
143 | #endif
144 | }
145 |
146 | /* Get last error code */
147 | JEMALLOC_INLINE int
148 | get_errno(void)
149 | {
150 |
151 | #ifdef _WIN32
152 | return (GetLastError());
153 | #else
154 | return (errno);
155 | #endif
156 | }
157 | #endif
158 |
159 | #endif /* JEMALLOC_H_INLINES */
160 | /******************************************************************************/
161 |
--------------------------------------------------------------------------------
/src/lzf.h:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright (c) 2000-2008 Marc Alexander Lehmann
3 | *
4 | * Redistribution and use in source and binary forms, with or without modifica-
5 | * tion, are permitted provided that the following conditions are met:
6 | *
7 | * 1. Redistributions of source code must retain the above copyright notice,
8 | * this list of conditions and the following disclaimer.
9 | *
10 | * 2. Redistributions in binary form must reproduce the above copyright
11 | * notice, this list of conditions and the following disclaimer in the
12 | * documentation and/or other materials provided with the distribution.
13 | *
14 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
15 | * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MER-
16 | * CHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
17 | * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPE-
18 | * CIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19 | * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
20 | * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
21 | * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTH-
22 | * ERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
23 | * OF THE POSSIBILITY OF SUCH DAMAGE.
24 | *
25 | * Alternatively, the contents of this file may be used under the terms of
26 | * the GNU General Public License ("GPL") version 2 or any later version,
27 | * in which case the provisions of the GPL are applicable instead of
28 | * the above. If you wish to allow the use of your version of this file
29 | * only under the terms of the GPL and not to allow others to use your
30 | * version of this file under the BSD license, indicate your decision
31 | * by deleting the provisions above and replace them with the notice
32 | * and other provisions required by the GPL. If you do not delete the
33 | * provisions above, a recipient may use your version of this file under
34 | * either the BSD or the GPL.
35 | */
36 |
37 | #ifndef LZF_H
38 | #define LZF_H
39 |
40 | /***********************************************************************
41 | **
42 | ** lzf -- an extremely fast/free compression/decompression-method
43 | ** http://liblzf.plan9.de/
44 | **
45 | ** This algorithm is believed to be patent-free.
46 | **
47 | ***********************************************************************/
48 |
49 | #define LZF_VERSION 0x0105 /* 1.5, API version */
50 |
51 | /*
52 | * Compress in_len bytes stored at the memory block starting at
53 | * in_data and write the result to out_data, up to a maximum length
54 | * of out_len bytes.
55 | *
56 | * If the output buffer is not large enough or any error occurs return 0,
57 | * otherwise return the number of bytes used, which might be considerably
58 | * more than in_len (but less than 104% of the original size), so it
59 | * makes sense to always use out_len == in_len - 1), to ensure _some_
60 | * compression, and store the data uncompressed otherwise (with a flag, of
61 | * course.
62 | *
63 | * lzf_compress might use different algorithms on different systems and
64 | * even different runs, thus might result in different compressed strings
65 | * depending on the phase of the moon or similar factors. However, all
66 | * these strings are architecture-independent and will result in the
67 | * original data when decompressed using lzf_decompress.
68 | *
69 | * The buffers must not be overlapping.
70 | *
71 | * If the option LZF_STATE_ARG is enabled, an extra argument must be
72 | * supplied which is not reflected in this header file. Refer to lzfP.h
73 | * and lzf_c.c.
74 | *
75 | */
76 | unsigned int
77 | lzf_compress (const void *const in_data, unsigned int in_len,
78 | void *out_data, unsigned int out_len);
79 |
80 | /*
81 | * Decompress data compressed with some version of the lzf_compress
82 | * function and stored at location in_data and length in_len. The result
83 | * will be stored at out_data up to a maximum of out_len characters.
84 | *
85 | * If the output buffer is not large enough to hold the decompressed
86 | * data, a 0 is returned and errno is set to E2BIG. Otherwise the number
87 | * of decompressed bytes (i.e. the original length of the data) is
88 | * returned.
89 | *
90 | * If an error in the compressed data is detected, a zero is returned and
91 | * errno is set to EINVAL.
92 | *
93 | * This function is very fast, about as fast as a copying loop.
94 | */
95 | unsigned int
96 | lzf_decompress (const void *const in_data, unsigned int in_len,
97 | void *out_data, unsigned int out_len);
98 |
99 | #endif
100 |
101 |
--------------------------------------------------------------------------------
/src/config.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 | #include
30 | #include
31 |
32 | #include "eagle.h"
33 | #include "config.h"
34 | #include "xmalloc.h"
35 | #include "utils.h"
36 |
37 | static void set_value_string(char **dest, char *value)
38 | {
39 | if (*dest)
40 | xfree(*dest);
41 |
42 | *dest = xstrdup(value);
43 | }
44 |
45 | static int parse_on_off(char *value)
46 | {
47 | int result = 0;
48 |
49 | if (!strcmp(value, "on"))
50 | result = 1;
51 |
52 | return result;
53 | }
54 |
55 | int config_parse_key_value(char *key, char *value)
56 | {
57 | int err;
58 | long long max_memory;
59 |
60 | if (!strcmp(key, "addr")) {
61 | set_value_string(&server->addr, value);
62 | } else if (!strcmp(key, "port")) {
63 | server->port = atoi(value);
64 | } else if (!strcmp(key, "unix-socket")) {
65 | set_value_string(&server->unix_socket, value);
66 | } else if (!strcmp(key, "admin-name")) {
67 | set_value_string(&server->name, value);
68 | } else if (!strcmp(key, "admin-password")) {
69 | set_value_string(&server->password, value);
70 | } else if (!strcmp(key, "daemonize")) {
71 | server->daemonize = parse_on_off(value);
72 | } else if (!strcmp(key, "pid-file")) {
73 | set_value_string(&server->pidfile, value);
74 | } else if (!strcmp(key, "log-file")) {
75 | set_value_string(&server->logfile, value);
76 | } else if (!strcmp(key, "storage-file")) {
77 | set_value_string(&server->storage, value);
78 | } else if (!strcmp(key, "max-clients")) {
79 | server->max_clients = atoi(value);
80 | } else if (!strcmp(key, "max-memory")) {
81 | max_memory = memtoll(value, &err);
82 | if (err) return EG_STATUS_ERR;
83 | server->max_memory = max_memory;
84 | } else if (!strcmp(key, "save-timeout")) {
85 | server->storage_timeout = atoi(value);
86 | } else if (!strcmp(key, "client-timeout")) {
87 | server->client_timeout = atoi(value);
88 | } else {
89 | info("Error parse key: %s", key);
90 | return EG_STATUS_ERR;
91 | }
92 |
93 | return EG_STATUS_OK;
94 | }
95 |
96 | static int parse_config_line(char *line)
97 | {
98 | char *ptr;
99 | char *key = NULL;
100 | char *value = NULL;
101 |
102 | if (line[0] == '#' || line[0] == '\0' || line[0] == '\n')
103 | return EG_STATUS_OK;
104 |
105 | ptr = strtok(line, "\t\n ");
106 | while (ptr != NULL)
107 | {
108 | if (!key) {
109 | key = ptr;
110 | } else if (!value) {
111 | value = ptr;
112 | } else {
113 | return EG_STATUS_ERR;
114 | }
115 |
116 | ptr = strtok(NULL, "\t\n ");
117 | }
118 |
119 | if (key && value)
120 | {
121 | if (config_parse_key_value(key, value) != EG_STATUS_OK)
122 | return EG_STATUS_ERR;
123 | } else {
124 | return EG_STATUS_ERR;
125 | }
126 |
127 | return EG_STATUS_OK;
128 | }
129 |
130 | int config_load(const char *filename)
131 | {
132 | char line[512];
133 | FILE *fp;
134 |
135 | fp = fopen(filename, "r");
136 | if (!fp)
137 | return EG_STATUS_ERR;
138 |
139 | while (fgets(line, sizeof(line), fp) != NULL)
140 | {
141 | if (parse_config_line(line) != EG_STATUS_OK)
142 | {
143 | fclose(fp);
144 | return EG_STATUS_ERR;
145 | }
146 | }
147 |
148 | fclose(fp);
149 |
150 | return EG_STATUS_OK;
151 | }
152 |
--------------------------------------------------------------------------------
/src/event_epoll.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2009-2012, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 |
30 | typedef struct ApiData {
31 | int epfd;
32 | struct epoll_event *events;
33 | } ApiData;
34 |
35 | static int event_api_init(EventLoop *loop)
36 | {
37 | ApiData *data = (ApiData*)xmalloc(sizeof(*data));
38 |
39 | data->events = (struct epoll_event*)xmalloc(sizeof(struct epoll_event) * loop->size);
40 |
41 | data->epfd = epoll_create(1024);
42 | if (data->epfd == -1) {
43 | xfree(data->events);
44 | xfree(data);
45 | return -1;
46 | }
47 |
48 | loop->api_data = data;
49 |
50 | return 0;
51 | }
52 |
53 | static void event_api_free(EventLoop *loop)
54 | {
55 | ApiData *data = (ApiData*)loop->api_data;
56 |
57 | close(data->epfd);
58 | xfree(data->events);
59 | xfree(data);
60 | }
61 |
62 | static int event_api_add(EventLoop *loop, int fd, int mask)
63 | {
64 | ApiData *data = (ApiData*)loop->api_data;
65 | struct epoll_event epoll_ev;
66 | int op = loop->events[fd].mask == EG_EVENT_NONE ? EPOLL_CTL_ADD : EPOLL_CTL_MOD;
67 |
68 | epoll_ev.events = 0;
69 | mask |= loop->events[fd].mask;
70 |
71 | if (mask & EG_EVENT_READABLE) {
72 | epoll_ev.events |= EPOLLIN;
73 | }
74 |
75 | if (mask & EG_EVENT_WRITABLE) {
76 | epoll_ev.events |= EPOLLOUT;
77 | }
78 |
79 | epoll_ev.data.u64 = 0;
80 | epoll_ev.data.fd = fd;
81 |
82 | if (epoll_ctl(data->epfd, op, fd, &epoll_ev) == -1) {
83 | return -1;
84 | }
85 |
86 | return 0;
87 | }
88 |
89 | static void event_api_delete(EventLoop *loop, int fd, int mask)
90 | {
91 | ApiData *data = (ApiData*)loop->api_data;
92 | struct epoll_event epoll_ev;
93 | int nmask = loop->events[fd].mask & (~mask);
94 |
95 | epoll_ev.events = 0;
96 |
97 | if (nmask & EG_EVENT_READABLE) {
98 | epoll_ev.events |= EPOLLIN;
99 | }
100 |
101 | if (nmask & EG_EVENT_WRITABLE) {
102 | epoll_ev.events |= EPOLLOUT;
103 | }
104 |
105 | epoll_ev.data.u64 = 0;
106 | epoll_ev.data.fd = fd;
107 |
108 | if (nmask != EG_EVENT_NONE) {
109 | epoll_ctl(data->epfd, EPOLL_CTL_MOD, fd, &epoll_ev);
110 | } else {
111 | epoll_ctl(data->epfd, EPOLL_CTL_DEL, fd, &epoll_ev);
112 | }
113 | }
114 |
115 | static int event_api_poll(EventLoop *loop, struct timeval *tvp)
116 | {
117 | ApiData *data = (ApiData*)loop->api_data;
118 | struct epoll_event *epoll_ev;
119 | int retval, i, mask, events = 0;
120 |
121 | retval = epoll_wait(data->epfd, data->events, loop->size,
122 | tvp ? (tvp->tv_sec * 1000 + tvp->tv_usec / 1000) : -1);
123 |
124 | if (retval > 0)
125 | {
126 | events = retval;
127 | for (i = 0; i < events; i++)
128 | {
129 | mask = 0;
130 | epoll_ev = data->events + i;
131 |
132 | if (epoll_ev->events & EPOLLIN) {
133 | mask |= EG_EVENT_READABLE;
134 | }
135 |
136 | if (epoll_ev->events & EPOLLOUT) {
137 | mask |= EG_EVENT_WRITABLE;
138 | }
139 |
140 | if (epoll_ev->events & EPOLLERR) {
141 | mask |= EG_EVENT_WRITABLE;
142 | }
143 |
144 | if (epoll_ev->events & EPOLLHUP) {
145 | mask |= EG_EVENT_WRITABLE;
146 | }
147 |
148 | loop->fired[i].fd = epoll_ev->data.fd;
149 | loop->fired[i].mask = mask;
150 | }
151 | }
152 |
153 | return events;
154 | }
155 |
156 | static char *event_api_name(void)
157 | {
158 | return "epoll";
159 | }
160 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/chunk_dss.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_CHUNK_DSS_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 | /******************************************************************************/
4 | /* Data. */
5 |
6 | const char *dss_prec_names[] = {
7 | "disabled",
8 | "primary",
9 | "secondary",
10 | "N/A"
11 | };
12 |
13 | /* Current dss precedence default, used when creating new arenas. */
14 | static dss_prec_t dss_prec_default = DSS_PREC_DEFAULT;
15 |
16 | /*
17 | * Protects sbrk() calls. This avoids malloc races among threads, though it
18 | * does not protect against races with threads that call sbrk() directly.
19 | */
20 | static malloc_mutex_t dss_mtx;
21 |
22 | /* Base address of the DSS. */
23 | static void *dss_base;
24 | /* Current end of the DSS, or ((void *)-1) if the DSS is exhausted. */
25 | static void *dss_prev;
26 | /* Current upper limit on DSS addresses. */
27 | static void *dss_max;
28 |
29 | /******************************************************************************/
30 |
31 | #ifndef JEMALLOC_HAVE_SBRK
32 | static void *
33 | sbrk(intptr_t increment)
34 | {
35 |
36 | not_implemented();
37 |
38 | return (NULL);
39 | }
40 | #endif
41 |
42 | dss_prec_t
43 | chunk_dss_prec_get(void)
44 | {
45 | dss_prec_t ret;
46 |
47 | if (config_dss == false)
48 | return (dss_prec_disabled);
49 | malloc_mutex_lock(&dss_mtx);
50 | ret = dss_prec_default;
51 | malloc_mutex_unlock(&dss_mtx);
52 | return (ret);
53 | }
54 |
55 | bool
56 | chunk_dss_prec_set(dss_prec_t dss_prec)
57 | {
58 |
59 | if (config_dss == false)
60 | return (true);
61 | malloc_mutex_lock(&dss_mtx);
62 | dss_prec_default = dss_prec;
63 | malloc_mutex_unlock(&dss_mtx);
64 | return (false);
65 | }
66 |
67 | void *
68 | chunk_alloc_dss(size_t size, size_t alignment, bool *zero)
69 | {
70 | void *ret;
71 |
72 | cassert(config_dss);
73 | assert(size > 0 && (size & chunksize_mask) == 0);
74 | assert(alignment > 0 && (alignment & chunksize_mask) == 0);
75 |
76 | /*
77 | * sbrk() uses a signed increment argument, so take care not to
78 | * interpret a huge allocation request as a negative increment.
79 | */
80 | if ((intptr_t)size < 0)
81 | return (NULL);
82 |
83 | malloc_mutex_lock(&dss_mtx);
84 | if (dss_prev != (void *)-1) {
85 | size_t gap_size, cpad_size;
86 | void *cpad, *dss_next;
87 | intptr_t incr;
88 |
89 | /*
90 | * The loop is necessary to recover from races with other
91 | * threads that are using the DSS for something other than
92 | * malloc.
93 | */
94 | do {
95 | /* Get the current end of the DSS. */
96 | dss_max = sbrk(0);
97 | /*
98 | * Calculate how much padding is necessary to
99 | * chunk-align the end of the DSS.
100 | */
101 | gap_size = (chunksize - CHUNK_ADDR2OFFSET(dss_max)) &
102 | chunksize_mask;
103 | /*
104 | * Compute how much chunk-aligned pad space (if any) is
105 | * necessary to satisfy alignment. This space can be
106 | * recycled for later use.
107 | */
108 | cpad = (void *)((uintptr_t)dss_max + gap_size);
109 | ret = (void *)ALIGNMENT_CEILING((uintptr_t)dss_max,
110 | alignment);
111 | cpad_size = (uintptr_t)ret - (uintptr_t)cpad;
112 | dss_next = (void *)((uintptr_t)ret + size);
113 | if ((uintptr_t)ret < (uintptr_t)dss_max ||
114 | (uintptr_t)dss_next < (uintptr_t)dss_max) {
115 | /* Wrap-around. */
116 | malloc_mutex_unlock(&dss_mtx);
117 | return (NULL);
118 | }
119 | incr = gap_size + cpad_size + size;
120 | dss_prev = sbrk(incr);
121 | if (dss_prev == dss_max) {
122 | /* Success. */
123 | dss_max = dss_next;
124 | malloc_mutex_unlock(&dss_mtx);
125 | if (cpad_size != 0)
126 | chunk_unmap(cpad, cpad_size);
127 | if (*zero) {
128 | VALGRIND_MAKE_MEM_UNDEFINED(ret, size);
129 | memset(ret, 0, size);
130 | }
131 | return (ret);
132 | }
133 | } while (dss_prev != (void *)-1);
134 | }
135 | malloc_mutex_unlock(&dss_mtx);
136 |
137 | return (NULL);
138 | }
139 |
140 | bool
141 | chunk_in_dss(void *chunk)
142 | {
143 | bool ret;
144 |
145 | cassert(config_dss);
146 |
147 | malloc_mutex_lock(&dss_mtx);
148 | if ((uintptr_t)chunk >= (uintptr_t)dss_base
149 | && (uintptr_t)chunk < (uintptr_t)dss_max)
150 | ret = true;
151 | else
152 | ret = false;
153 | malloc_mutex_unlock(&dss_mtx);
154 |
155 | return (ret);
156 | }
157 |
158 | bool
159 | chunk_dss_boot(void)
160 | {
161 |
162 | cassert(config_dss);
163 |
164 | if (malloc_mutex_init(&dss_mtx))
165 | return (true);
166 | dss_base = sbrk(0);
167 | dss_prev = dss_base;
168 | dss_max = dss_base;
169 |
170 | return (false);
171 | }
172 |
173 | void
174 | chunk_dss_prefork(void)
175 | {
176 |
177 | if (config_dss)
178 | malloc_mutex_prefork(&dss_mtx);
179 | }
180 |
181 | void
182 | chunk_dss_postfork_parent(void)
183 | {
184 |
185 | if (config_dss)
186 | malloc_mutex_postfork_parent(&dss_mtx);
187 | }
188 |
189 | void
190 | chunk_dss_postfork_child(void)
191 | {
192 |
193 | if (config_dss)
194 | malloc_mutex_postfork_child(&dss_mtx);
195 | }
196 |
197 | /******************************************************************************/
198 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/stats.h:
--------------------------------------------------------------------------------
1 | /******************************************************************************/
2 | #ifdef JEMALLOC_H_TYPES
3 |
4 | typedef struct tcache_bin_stats_s tcache_bin_stats_t;
5 | typedef struct malloc_bin_stats_s malloc_bin_stats_t;
6 | typedef struct malloc_large_stats_s malloc_large_stats_t;
7 | typedef struct arena_stats_s arena_stats_t;
8 | typedef struct chunk_stats_s chunk_stats_t;
9 |
10 | #endif /* JEMALLOC_H_TYPES */
11 | /******************************************************************************/
12 | #ifdef JEMALLOC_H_STRUCTS
13 |
14 | struct tcache_bin_stats_s {
15 | /*
16 | * Number of allocation requests that corresponded to the size of this
17 | * bin.
18 | */
19 | uint64_t nrequests;
20 | };
21 |
22 | struct malloc_bin_stats_s {
23 | /*
24 | * Current number of bytes allocated, including objects currently
25 | * cached by tcache.
26 | */
27 | size_t allocated;
28 |
29 | /*
30 | * Total number of allocation/deallocation requests served directly by
31 | * the bin. Note that tcache may allocate an object, then recycle it
32 | * many times, resulting many increments to nrequests, but only one
33 | * each to nmalloc and ndalloc.
34 | */
35 | uint64_t nmalloc;
36 | uint64_t ndalloc;
37 |
38 | /*
39 | * Number of allocation requests that correspond to the size of this
40 | * bin. This includes requests served by tcache, though tcache only
41 | * periodically merges into this counter.
42 | */
43 | uint64_t nrequests;
44 |
45 | /* Number of tcache fills from this bin. */
46 | uint64_t nfills;
47 |
48 | /* Number of tcache flushes to this bin. */
49 | uint64_t nflushes;
50 |
51 | /* Total number of runs created for this bin's size class. */
52 | uint64_t nruns;
53 |
54 | /*
55 | * Total number of runs reused by extracting them from the runs tree for
56 | * this bin's size class.
57 | */
58 | uint64_t reruns;
59 |
60 | /* Current number of runs in this bin. */
61 | size_t curruns;
62 | };
63 |
64 | struct malloc_large_stats_s {
65 | /*
66 | * Total number of allocation/deallocation requests served directly by
67 | * the arena. Note that tcache may allocate an object, then recycle it
68 | * many times, resulting many increments to nrequests, but only one
69 | * each to nmalloc and ndalloc.
70 | */
71 | uint64_t nmalloc;
72 | uint64_t ndalloc;
73 |
74 | /*
75 | * Number of allocation requests that correspond to this size class.
76 | * This includes requests served by tcache, though tcache only
77 | * periodically merges into this counter.
78 | */
79 | uint64_t nrequests;
80 |
81 | /* Current number of runs of this size class. */
82 | size_t curruns;
83 | };
84 |
85 | struct arena_stats_s {
86 | /* Number of bytes currently mapped. */
87 | size_t mapped;
88 |
89 | /*
90 | * Total number of purge sweeps, total number of madvise calls made,
91 | * and total pages purged in order to keep dirty unused memory under
92 | * control.
93 | */
94 | uint64_t npurge;
95 | uint64_t nmadvise;
96 | uint64_t purged;
97 |
98 | /* Per-size-category statistics. */
99 | size_t allocated_large;
100 | uint64_t nmalloc_large;
101 | uint64_t ndalloc_large;
102 | uint64_t nrequests_large;
103 |
104 | /*
105 | * One element for each possible size class, including sizes that
106 | * overlap with bin size classes. This is necessary because ipalloc()
107 | * sometimes has to use such large objects in order to assure proper
108 | * alignment.
109 | */
110 | malloc_large_stats_t *lstats;
111 | };
112 |
113 | struct chunk_stats_s {
114 | /* Number of chunks that were allocated. */
115 | uint64_t nchunks;
116 |
117 | /* High-water mark for number of chunks allocated. */
118 | size_t highchunks;
119 |
120 | /*
121 | * Current number of chunks allocated. This value isn't maintained for
122 | * any other purpose, so keep track of it in order to be able to set
123 | * highchunks.
124 | */
125 | size_t curchunks;
126 | };
127 |
128 | #endif /* JEMALLOC_H_STRUCTS */
129 | /******************************************************************************/
130 | #ifdef JEMALLOC_H_EXTERNS
131 |
132 | extern bool opt_stats_print;
133 |
134 | extern size_t stats_cactive;
135 |
136 | void stats_print(void (*write)(void *, const char *), void *cbopaque,
137 | const char *opts);
138 |
139 | #endif /* JEMALLOC_H_EXTERNS */
140 | /******************************************************************************/
141 | #ifdef JEMALLOC_H_INLINES
142 |
143 | #ifndef JEMALLOC_ENABLE_INLINE
144 | size_t stats_cactive_get(void);
145 | void stats_cactive_add(size_t size);
146 | void stats_cactive_sub(size_t size);
147 | #endif
148 |
149 | #if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_STATS_C_))
150 | JEMALLOC_INLINE size_t
151 | stats_cactive_get(void)
152 | {
153 |
154 | return (atomic_read_z(&stats_cactive));
155 | }
156 |
157 | JEMALLOC_INLINE void
158 | stats_cactive_add(size_t size)
159 | {
160 |
161 | atomic_add_z(&stats_cactive, size);
162 | }
163 |
164 | JEMALLOC_INLINE void
165 | stats_cactive_sub(size_t size)
166 | {
167 |
168 | atomic_sub_z(&stats_cactive, size);
169 | }
170 | #endif
171 |
172 | #endif /* JEMALLOC_H_INLINES */
173 | /******************************************************************************/
174 |
--------------------------------------------------------------------------------
/deps/jemalloc/test/allocm.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_MANGLE
2 | #include "jemalloc_test.h"
3 |
4 | #define CHUNK 0x400000
5 | /* #define MAXALIGN ((size_t)UINT64_C(0x80000000000)) */
6 | #define MAXALIGN ((size_t)0x2000000LU)
7 | #define NITER 4
8 |
9 | int
10 | main(void)
11 | {
12 | int r;
13 | void *p;
14 | size_t nsz, rsz, sz, alignment, total;
15 | unsigned i;
16 | void *ps[NITER];
17 |
18 | malloc_printf("Test begin\n");
19 |
20 | sz = 42;
21 | nsz = 0;
22 | r = nallocm(&nsz, sz, 0);
23 | if (r != ALLOCM_SUCCESS) {
24 | malloc_printf("Unexpected nallocm() error\n");
25 | abort();
26 | }
27 | rsz = 0;
28 | r = allocm(&p, &rsz, sz, 0);
29 | if (r != ALLOCM_SUCCESS) {
30 | malloc_printf("Unexpected allocm() error\n");
31 | abort();
32 | }
33 | if (rsz < sz)
34 | malloc_printf("Real size smaller than expected\n");
35 | if (nsz != rsz)
36 | malloc_printf("nallocm()/allocm() rsize mismatch\n");
37 | if (dallocm(p, 0) != ALLOCM_SUCCESS)
38 | malloc_printf("Unexpected dallocm() error\n");
39 |
40 | r = allocm(&p, NULL, sz, 0);
41 | if (r != ALLOCM_SUCCESS) {
42 | malloc_printf("Unexpected allocm() error\n");
43 | abort();
44 | }
45 | if (dallocm(p, 0) != ALLOCM_SUCCESS)
46 | malloc_printf("Unexpected dallocm() error\n");
47 |
48 | nsz = 0;
49 | r = nallocm(&nsz, sz, ALLOCM_ZERO);
50 | if (r != ALLOCM_SUCCESS) {
51 | malloc_printf("Unexpected nallocm() error\n");
52 | abort();
53 | }
54 | rsz = 0;
55 | r = allocm(&p, &rsz, sz, ALLOCM_ZERO);
56 | if (r != ALLOCM_SUCCESS) {
57 | malloc_printf("Unexpected allocm() error\n");
58 | abort();
59 | }
60 | if (nsz != rsz)
61 | malloc_printf("nallocm()/allocm() rsize mismatch\n");
62 | if (dallocm(p, 0) != ALLOCM_SUCCESS)
63 | malloc_printf("Unexpected dallocm() error\n");
64 |
65 | #if LG_SIZEOF_PTR == 3
66 | alignment = UINT64_C(0x8000000000000000);
67 | sz = UINT64_C(0x8000000000000000);
68 | #else
69 | alignment = 0x80000000LU;
70 | sz = 0x80000000LU;
71 | #endif
72 | nsz = 0;
73 | r = nallocm(&nsz, sz, ALLOCM_ALIGN(alignment));
74 | if (r == ALLOCM_SUCCESS) {
75 | malloc_printf(
76 | "Expected error for nallocm(&nsz, %zu, %#x)\n",
77 | sz, ALLOCM_ALIGN(alignment));
78 | }
79 | rsz = 0;
80 | r = allocm(&p, &rsz, sz, ALLOCM_ALIGN(alignment));
81 | if (r == ALLOCM_SUCCESS) {
82 | malloc_printf(
83 | "Expected error for allocm(&p, %zu, %#x)\n",
84 | sz, ALLOCM_ALIGN(alignment));
85 | }
86 | if (nsz != rsz)
87 | malloc_printf("nallocm()/allocm() rsize mismatch\n");
88 |
89 | #if LG_SIZEOF_PTR == 3
90 | alignment = UINT64_C(0x4000000000000000);
91 | sz = UINT64_C(0x8400000000000001);
92 | #else
93 | alignment = 0x40000000LU;
94 | sz = 0x84000001LU;
95 | #endif
96 | nsz = 0;
97 | r = nallocm(&nsz, sz, ALLOCM_ALIGN(alignment));
98 | if (r != ALLOCM_SUCCESS)
99 | malloc_printf("Unexpected nallocm() error\n");
100 | rsz = 0;
101 | r = allocm(&p, &rsz, sz, ALLOCM_ALIGN(alignment));
102 | if (r == ALLOCM_SUCCESS) {
103 | malloc_printf(
104 | "Expected error for allocm(&p, %zu, %#x)\n",
105 | sz, ALLOCM_ALIGN(alignment));
106 | }
107 |
108 | alignment = 0x10LU;
109 | #if LG_SIZEOF_PTR == 3
110 | sz = UINT64_C(0xfffffffffffffff0);
111 | #else
112 | sz = 0xfffffff0LU;
113 | #endif
114 | nsz = 0;
115 | r = nallocm(&nsz, sz, ALLOCM_ALIGN(alignment));
116 | if (r == ALLOCM_SUCCESS) {
117 | malloc_printf(
118 | "Expected error for nallocm(&nsz, %zu, %#x)\n",
119 | sz, ALLOCM_ALIGN(alignment));
120 | }
121 | rsz = 0;
122 | r = allocm(&p, &rsz, sz, ALLOCM_ALIGN(alignment));
123 | if (r == ALLOCM_SUCCESS) {
124 | malloc_printf(
125 | "Expected error for allocm(&p, %zu, %#x)\n",
126 | sz, ALLOCM_ALIGN(alignment));
127 | }
128 | if (nsz != rsz)
129 | malloc_printf("nallocm()/allocm() rsize mismatch\n");
130 |
131 | for (i = 0; i < NITER; i++)
132 | ps[i] = NULL;
133 |
134 | for (alignment = 8;
135 | alignment <= MAXALIGN;
136 | alignment <<= 1) {
137 | total = 0;
138 | malloc_printf("Alignment: %zu\n", alignment);
139 | for (sz = 1;
140 | sz < 3 * alignment && sz < (1U << 31);
141 | sz += (alignment >> (LG_SIZEOF_PTR-1)) - 1) {
142 | for (i = 0; i < NITER; i++) {
143 | nsz = 0;
144 | r = nallocm(&nsz, sz,
145 | ALLOCM_ALIGN(alignment) | ALLOCM_ZERO);
146 | if (r != ALLOCM_SUCCESS) {
147 | malloc_printf(
148 | "nallocm() error for size %zu"
149 | " (%#zx): %d\n",
150 | sz, sz, r);
151 | exit(1);
152 | }
153 | rsz = 0;
154 | r = allocm(&ps[i], &rsz, sz,
155 | ALLOCM_ALIGN(alignment) | ALLOCM_ZERO);
156 | if (r != ALLOCM_SUCCESS) {
157 | malloc_printf(
158 | "allocm() error for size %zu"
159 | " (%#zx): %d\n",
160 | sz, sz, r);
161 | exit(1);
162 | }
163 | if (rsz < sz) {
164 | malloc_printf(
165 | "Real size smaller than"
166 | " expected\n");
167 | }
168 | if (nsz != rsz) {
169 | malloc_printf(
170 | "nallocm()/allocm() rsize"
171 | " mismatch\n");
172 | }
173 | if ((uintptr_t)p & (alignment-1)) {
174 | malloc_printf(
175 | "%p inadequately aligned for"
176 | " alignment: %zu\n", p, alignment);
177 | }
178 | sallocm(ps[i], &rsz, 0);
179 | total += rsz;
180 | if (total >= (MAXALIGN << 1))
181 | break;
182 | }
183 | for (i = 0; i < NITER; i++) {
184 | if (ps[i] != NULL) {
185 | dallocm(ps[i], 0);
186 | ps[i] = NULL;
187 | }
188 | }
189 | }
190 | }
191 |
192 | malloc_printf("Test end\n");
193 | return (0);
194 | }
195 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/internal/rtree.h:
--------------------------------------------------------------------------------
1 | /*
2 | * This radix tree implementation is tailored to the singular purpose of
3 | * tracking which chunks are currently owned by jemalloc. This functionality
4 | * is mandatory for OS X, where jemalloc must be able to respond to object
5 | * ownership queries.
6 | *
7 | *******************************************************************************
8 | */
9 | #ifdef JEMALLOC_H_TYPES
10 |
11 | typedef struct rtree_s rtree_t;
12 |
13 | /*
14 | * Size of each radix tree node (must be a power of 2). This impacts tree
15 | * depth.
16 | */
17 | #if (LG_SIZEOF_PTR == 2)
18 | # define RTREE_NODESIZE (1U << 14)
19 | #else
20 | # define RTREE_NODESIZE CACHELINE
21 | #endif
22 |
23 | #endif /* JEMALLOC_H_TYPES */
24 | /******************************************************************************/
25 | #ifdef JEMALLOC_H_STRUCTS
26 |
27 | struct rtree_s {
28 | malloc_mutex_t mutex;
29 | void **root;
30 | unsigned height;
31 | unsigned level2bits[1]; /* Dynamically sized. */
32 | };
33 |
34 | #endif /* JEMALLOC_H_STRUCTS */
35 | /******************************************************************************/
36 | #ifdef JEMALLOC_H_EXTERNS
37 |
38 | rtree_t *rtree_new(unsigned bits);
39 | void rtree_prefork(rtree_t *rtree);
40 | void rtree_postfork_parent(rtree_t *rtree);
41 | void rtree_postfork_child(rtree_t *rtree);
42 |
43 | #endif /* JEMALLOC_H_EXTERNS */
44 | /******************************************************************************/
45 | #ifdef JEMALLOC_H_INLINES
46 |
47 | #ifndef JEMALLOC_ENABLE_INLINE
48 | #ifndef JEMALLOC_DEBUG
49 | void *rtree_get_locked(rtree_t *rtree, uintptr_t key);
50 | #endif
51 | void *rtree_get(rtree_t *rtree, uintptr_t key);
52 | bool rtree_set(rtree_t *rtree, uintptr_t key, void *val);
53 | #endif
54 |
55 | #if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_RTREE_C_))
56 | #define RTREE_GET_GENERATE(f) \
57 | /* The least significant bits of the key are ignored. */ \
58 | JEMALLOC_INLINE void * \
59 | f(rtree_t *rtree, uintptr_t key) \
60 | { \
61 | void *ret; \
62 | uintptr_t subkey; \
63 | unsigned i, lshift, height, bits; \
64 | void **node, **child; \
65 | \
66 | RTREE_LOCK(&rtree->mutex); \
67 | for (i = lshift = 0, height = rtree->height, node = rtree->root;\
68 | i < height - 1; \
69 | i++, lshift += bits, node = child) { \
70 | bits = rtree->level2bits[i]; \
71 | subkey = (key << lshift) >> ((ZU(1) << (LG_SIZEOF_PTR + \
72 | 3)) - bits); \
73 | child = (void**)node[subkey]; \
74 | if (child == NULL) { \
75 | RTREE_UNLOCK(&rtree->mutex); \
76 | return (NULL); \
77 | } \
78 | } \
79 | \
80 | /* \
81 | * node is a leaf, so it contains values rather than node \
82 | * pointers. \
83 | */ \
84 | bits = rtree->level2bits[i]; \
85 | subkey = (key << lshift) >> ((ZU(1) << (LG_SIZEOF_PTR+3)) - \
86 | bits); \
87 | ret = node[subkey]; \
88 | RTREE_UNLOCK(&rtree->mutex); \
89 | \
90 | RTREE_GET_VALIDATE \
91 | return (ret); \
92 | }
93 |
94 | #ifdef JEMALLOC_DEBUG
95 | # define RTREE_LOCK(l) malloc_mutex_lock(l)
96 | # define RTREE_UNLOCK(l) malloc_mutex_unlock(l)
97 | # define RTREE_GET_VALIDATE
98 | RTREE_GET_GENERATE(rtree_get_locked)
99 | # undef RTREE_LOCK
100 | # undef RTREE_UNLOCK
101 | # undef RTREE_GET_VALIDATE
102 | #endif
103 |
104 | #define RTREE_LOCK(l)
105 | #define RTREE_UNLOCK(l)
106 | #ifdef JEMALLOC_DEBUG
107 | /*
108 | * Suppose that it were possible for a jemalloc-allocated chunk to be
109 | * munmap()ped, followed by a different allocator in another thread re-using
110 | * overlapping virtual memory, all without invalidating the cached rtree
111 | * value. The result would be a false positive (the rtree would claim that
112 | * jemalloc owns memory that it had actually discarded). This scenario
113 | * seems impossible, but the following assertion is a prudent sanity check.
114 | */
115 | # define RTREE_GET_VALIDATE \
116 | assert(rtree_get_locked(rtree, key) == ret);
117 | #else
118 | # define RTREE_GET_VALIDATE
119 | #endif
120 | RTREE_GET_GENERATE(rtree_get)
121 | #undef RTREE_LOCK
122 | #undef RTREE_UNLOCK
123 | #undef RTREE_GET_VALIDATE
124 |
125 | JEMALLOC_INLINE bool
126 | rtree_set(rtree_t *rtree, uintptr_t key, void *val)
127 | {
128 | uintptr_t subkey;
129 | unsigned i, lshift, height, bits;
130 | void **node, **child;
131 |
132 | malloc_mutex_lock(&rtree->mutex);
133 | for (i = lshift = 0, height = rtree->height, node = rtree->root;
134 | i < height - 1;
135 | i++, lshift += bits, node = child) {
136 | bits = rtree->level2bits[i];
137 | subkey = (key << lshift) >> ((ZU(1) << (LG_SIZEOF_PTR+3)) -
138 | bits);
139 | child = (void**)node[subkey];
140 | if (child == NULL) {
141 | child = (void**)base_alloc(sizeof(void *) <<
142 | rtree->level2bits[i+1]);
143 | if (child == NULL) {
144 | malloc_mutex_unlock(&rtree->mutex);
145 | return (true);
146 | }
147 | memset(child, 0, sizeof(void *) <<
148 | rtree->level2bits[i+1]);
149 | node[subkey] = child;
150 | }
151 | }
152 |
153 | /* node is a leaf, so it contains values rather than node pointers. */
154 | bits = rtree->level2bits[i];
155 | subkey = (key << lshift) >> ((ZU(1) << (LG_SIZEOF_PTR+3)) - bits);
156 | node[subkey] = val;
157 | malloc_mutex_unlock(&rtree->mutex);
158 |
159 | return (false);
160 | }
161 | #endif
162 |
163 | #endif /* JEMALLOC_H_INLINES */
164 | /******************************************************************************/
165 |
--------------------------------------------------------------------------------
/src/queue.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2012, Stanislav Yakush(st.yakush@yandex.ru)
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of the EagleMQ nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 |
30 | #include "queue.h"
31 | #include "xmalloc.h"
32 |
33 | Queue *queue_create(void)
34 | {
35 | Queue *queue;
36 |
37 | queue = (Queue*)xmalloc(sizeof(*queue));
38 |
39 | queue->head = queue->tail = NULL;
40 | queue->len = 0;
41 | queue->free = NULL;
42 |
43 | return queue;
44 | }
45 |
46 | void queue_release(Queue *queue)
47 | {
48 | unsigned int len;
49 | QueueNode *current, *next;
50 |
51 | current = queue->head;
52 | len = queue->len;
53 |
54 | while (len--) {
55 | next = current->next;
56 |
57 | if (queue->free) {
58 | queue->free(current->value);
59 | }
60 |
61 | xfree(current);
62 | current = next;
63 | }
64 |
65 | xfree(queue);
66 | }
67 |
68 | Queue *queue_push_value_head(Queue *queue, void *value)
69 | {
70 | QueueNode *node;
71 |
72 | node = (QueueNode*)xmalloc(sizeof(*node));
73 |
74 | node->value = value;
75 |
76 | if (queue->len == 0) {
77 | queue->head = queue->tail = node;
78 | node->prev = node->next = NULL;
79 | } else {
80 | node->prev = NULL;
81 | node->next = queue->head;
82 | queue->head->prev = node;
83 | queue->head = node;
84 | }
85 |
86 | queue->len++;
87 |
88 | return queue;
89 | }
90 |
91 | Queue *queue_push_value_tail(Queue *queue, void *value)
92 | {
93 | QueueNode *node;
94 |
95 | node = (QueueNode*)xmalloc(sizeof(*node));
96 |
97 | node->value = value;
98 |
99 | if (queue->len == 0) {
100 | queue->head = queue->tail = node;
101 | node->prev = node->next = NULL;
102 | } else {
103 | node->prev = queue->tail;
104 | node->next = NULL;
105 | queue->tail->next = node;
106 | queue->tail = node;
107 | }
108 |
109 | queue->len++;
110 |
111 | return queue;
112 | }
113 |
114 | void *queue_get_value(Queue *queue)
115 | {
116 | void *value;
117 |
118 | if (!queue->len) {
119 | return NULL;
120 | }
121 |
122 | value = EG_QUEUE_NODE_VALUE(queue->tail);
123 |
124 | return value;
125 | }
126 |
127 | void *queue_pop_value(Queue *queue)
128 | {
129 | QueueNode *prev;
130 | void *value;
131 |
132 | if (!queue->len) {
133 | return NULL;
134 | }
135 |
136 | value = EG_QUEUE_NODE_VALUE(queue->tail);
137 | prev = queue->tail->prev;
138 |
139 | xfree(queue->tail);
140 |
141 | queue->tail = prev;
142 | queue->len--;
143 |
144 | return value;
145 | }
146 |
147 | Queue *queue_purge(Queue *queue)
148 | {
149 | unsigned int len;
150 | QueueNode *current, *next;
151 |
152 | current = queue->head;
153 | len = queue->len;
154 |
155 | while (len--) {
156 | next = current->next;
157 |
158 | if (queue->free) {
159 | queue->free(current->value);
160 | }
161 |
162 | xfree(current);
163 | current = next;
164 | }
165 |
166 | queue->len = 0;
167 |
168 | return queue;
169 | }
170 |
171 | void queue_delete_node(Queue *queue, QueueNode *node)
172 | {
173 | if (node->prev) {
174 | node->prev->next = node->next;
175 | } else {
176 | queue->head = node->next;
177 | }
178 |
179 | if (node->next) {
180 | node->next->prev = node->prev;
181 | } else {
182 | queue->tail = node->prev;
183 | }
184 |
185 | if (queue->free) {
186 | queue->free(node->value);
187 | }
188 |
189 | xfree(node);
190 | queue->len--;
191 | }
192 |
193 | QueueIterator *queue_get_iterator(Queue *queue, int direction)
194 | {
195 | QueueIterator *iter;
196 |
197 | iter = (QueueIterator*)xmalloc(sizeof(*iter));
198 |
199 | if (direction == EG_START_HEAD) {
200 | iter->next = queue->head;
201 | } else {
202 | iter->next = queue->tail;
203 | }
204 |
205 | iter->direction = direction;
206 |
207 | return iter;
208 | }
209 |
210 | void queue_release_iterator(QueueIterator *iter)
211 | {
212 | xfree(iter);
213 | }
214 |
215 | QueueNode *queue_next_node(QueueIterator *iter)
216 | {
217 | QueueNode *current = iter->next;
218 |
219 | if (current != NULL) {
220 | if (iter->direction == EG_START_HEAD) {
221 | iter->next = current->next;
222 | } else {
223 | iter->next = current->prev;
224 | }
225 | }
226 |
227 | return current;
228 | }
229 |
230 | void queue_rewind(Queue *queue, QueueIterator *iter)
231 | {
232 | iter->next = queue->head;
233 | iter->direction = EG_START_HEAD;
234 | }
235 |
--------------------------------------------------------------------------------
/deps/jemalloc/include/jemalloc/jemalloc.h.in:
--------------------------------------------------------------------------------
1 | #ifndef JEMALLOC_H_
2 | #define JEMALLOC_H_
3 | #ifdef __cplusplus
4 | extern "C" {
5 | #endif
6 |
7 | #include
8 | #include
9 |
10 | #define JEMALLOC_VERSION "@jemalloc_version@"
11 | #define JEMALLOC_VERSION_MAJOR @jemalloc_version_major@
12 | #define JEMALLOC_VERSION_MINOR @jemalloc_version_minor@
13 | #define JEMALLOC_VERSION_BUGFIX @jemalloc_version_bugfix@
14 | #define JEMALLOC_VERSION_NREV @jemalloc_version_nrev@
15 | #define JEMALLOC_VERSION_GID "@jemalloc_version_gid@"
16 |
17 | #include "jemalloc_defs@install_suffix@.h"
18 |
19 | #ifdef JEMALLOC_EXPERIMENTAL
20 | #define ALLOCM_LG_ALIGN(la) (la)
21 | #if LG_SIZEOF_PTR == 2
22 | #define ALLOCM_ALIGN(a) (ffs(a)-1)
23 | #else
24 | #define ALLOCM_ALIGN(a) ((a < (size_t)INT_MAX) ? ffs(a)-1 : ffs(a>>32)+31)
25 | #endif
26 | #define ALLOCM_ZERO ((int)0x40)
27 | #define ALLOCM_NO_MOVE ((int)0x80)
28 | /* Bias arena index bits so that 0 encodes "ALLOCM_ARENA() unspecified". */
29 | #define ALLOCM_ARENA(a) ((int)(((a)+1) << 8))
30 |
31 | #define ALLOCM_SUCCESS 0
32 | #define ALLOCM_ERR_OOM 1
33 | #define ALLOCM_ERR_NOT_MOVED 2
34 | #endif
35 |
36 | /*
37 | * The je_ prefix on the following public symbol declarations is an artifact of
38 | * namespace management, and should be omitted in application code unless
39 | * JEMALLOC_NO_DEMANGLE is defined (see below).
40 | */
41 | extern JEMALLOC_EXPORT const char *je_malloc_conf;
42 | extern JEMALLOC_EXPORT void (*je_malloc_message)(void *cbopaque,
43 | const char *s);
44 |
45 | JEMALLOC_EXPORT void *je_malloc(size_t size) JEMALLOC_ATTR(malloc);
46 | JEMALLOC_EXPORT void *je_calloc(size_t num, size_t size)
47 | JEMALLOC_ATTR(malloc);
48 | JEMALLOC_EXPORT int je_posix_memalign(void **memptr, size_t alignment,
49 | size_t size) JEMALLOC_ATTR(nonnull(1));
50 | JEMALLOC_EXPORT void *je_aligned_alloc(size_t alignment, size_t size)
51 | JEMALLOC_ATTR(malloc);
52 | JEMALLOC_EXPORT void *je_realloc(void *ptr, size_t size);
53 | JEMALLOC_EXPORT void je_free(void *ptr);
54 |
55 | #ifdef JEMALLOC_OVERRIDE_MEMALIGN
56 | JEMALLOC_EXPORT void * je_memalign(size_t alignment, size_t size)
57 | JEMALLOC_ATTR(malloc);
58 | #endif
59 |
60 | #ifdef JEMALLOC_OVERRIDE_VALLOC
61 | JEMALLOC_EXPORT void * je_valloc(size_t size) JEMALLOC_ATTR(malloc);
62 | #endif
63 |
64 | JEMALLOC_EXPORT size_t je_malloc_usable_size(
65 | JEMALLOC_USABLE_SIZE_CONST void *ptr);
66 | JEMALLOC_EXPORT void je_malloc_stats_print(void (*write_cb)(void *,
67 | const char *), void *je_cbopaque, const char *opts);
68 | JEMALLOC_EXPORT int je_mallctl(const char *name, void *oldp,
69 | size_t *oldlenp, void *newp, size_t newlen);
70 | JEMALLOC_EXPORT int je_mallctlnametomib(const char *name, size_t *mibp,
71 | size_t *miblenp);
72 | JEMALLOC_EXPORT int je_mallctlbymib(const size_t *mib, size_t miblen,
73 | void *oldp, size_t *oldlenp, void *newp, size_t newlen);
74 |
75 | #ifdef JEMALLOC_EXPERIMENTAL
76 | JEMALLOC_EXPORT int je_allocm(void **ptr, size_t *rsize, size_t size,
77 | int flags) JEMALLOC_ATTR(nonnull(1));
78 | JEMALLOC_EXPORT int je_rallocm(void **ptr, size_t *rsize, size_t size,
79 | size_t extra, int flags) JEMALLOC_ATTR(nonnull(1));
80 | JEMALLOC_EXPORT int je_sallocm(const void *ptr, size_t *rsize, int flags)
81 | JEMALLOC_ATTR(nonnull(1));
82 | JEMALLOC_EXPORT int je_dallocm(void *ptr, int flags)
83 | JEMALLOC_ATTR(nonnull(1));
84 | JEMALLOC_EXPORT int je_nallocm(size_t *rsize, size_t size, int flags);
85 | #endif
86 |
87 | /*
88 | * By default application code must explicitly refer to mangled symbol names,
89 | * so that it is possible to use jemalloc in conjunction with another allocator
90 | * in the same application. Define JEMALLOC_MANGLE in order to cause automatic
91 | * name mangling that matches the API prefixing that happened as a result of
92 | * --with-mangling and/or --with-jemalloc-prefix configuration settings.
93 | */
94 | #ifdef JEMALLOC_MANGLE
95 | #ifndef JEMALLOC_NO_DEMANGLE
96 | #define JEMALLOC_NO_DEMANGLE
97 | #endif
98 | #define malloc_conf je_malloc_conf
99 | #define malloc_message je_malloc_message
100 | #define malloc je_malloc
101 | #define calloc je_calloc
102 | #define posix_memalign je_posix_memalign
103 | #define aligned_alloc je_aligned_alloc
104 | #define realloc je_realloc
105 | #define free je_free
106 | #define malloc_usable_size je_malloc_usable_size
107 | #define malloc_stats_print je_malloc_stats_print
108 | #define mallctl je_mallctl
109 | #define mallctlnametomib je_mallctlnametomib
110 | #define mallctlbymib je_mallctlbymib
111 | #define memalign je_memalign
112 | #define valloc je_valloc
113 | #ifdef JEMALLOC_EXPERIMENTAL
114 | #define allocm je_allocm
115 | #define rallocm je_rallocm
116 | #define sallocm je_sallocm
117 | #define dallocm je_dallocm
118 | #define nallocm je_nallocm
119 | #endif
120 | #endif
121 |
122 | /*
123 | * The je_* macros can be used as stable alternative names for the public
124 | * jemalloc API if JEMALLOC_NO_DEMANGLE is defined. This is primarily meant
125 | * for use in jemalloc itself, but it can be used by application code to
126 | * provide isolation from the name mangling specified via --with-mangling
127 | * and/or --with-jemalloc-prefix.
128 | */
129 | #ifndef JEMALLOC_NO_DEMANGLE
130 | #undef je_malloc_conf
131 | #undef je_malloc_message
132 | #undef je_malloc
133 | #undef je_calloc
134 | #undef je_posix_memalign
135 | #undef je_aligned_alloc
136 | #undef je_realloc
137 | #undef je_free
138 | #undef je_malloc_usable_size
139 | #undef je_malloc_stats_print
140 | #undef je_mallctl
141 | #undef je_mallctlnametomib
142 | #undef je_mallctlbymib
143 | #undef je_memalign
144 | #undef je_valloc
145 | #ifdef JEMALLOC_EXPERIMENTAL
146 | #undef je_allocm
147 | #undef je_rallocm
148 | #undef je_sallocm
149 | #undef je_dallocm
150 | #undef je_nallocm
151 | #endif
152 | #endif
153 |
154 | #ifdef __cplusplus
155 | };
156 | #endif
157 | #endif /* JEMALLOC_H_ */
158 |
--------------------------------------------------------------------------------
/deps/jemalloc/src/chunk_mmap.c:
--------------------------------------------------------------------------------
1 | #define JEMALLOC_CHUNK_MMAP_C_
2 | #include "jemalloc/internal/jemalloc_internal.h"
3 |
4 | /******************************************************************************/
5 | /* Function prototypes for non-inline static functions. */
6 |
7 | static void *pages_map(void *addr, size_t size);
8 | static void pages_unmap(void *addr, size_t size);
9 | static void *chunk_alloc_mmap_slow(size_t size, size_t alignment,
10 | bool *zero);
11 |
12 | /******************************************************************************/
13 |
14 | static void *
15 | pages_map(void *addr, size_t size)
16 | {
17 | void *ret;
18 |
19 | assert(size != 0);
20 |
21 | #ifdef _WIN32
22 | /*
23 | * If VirtualAlloc can't allocate at the given address when one is
24 | * given, it fails and returns NULL.
25 | */
26 | ret = VirtualAlloc(addr, size, MEM_COMMIT | MEM_RESERVE,
27 | PAGE_READWRITE);
28 | #else
29 | /*
30 | * We don't use MAP_FIXED here, because it can cause the *replacement*
31 | * of existing mappings, and we only want to create new mappings.
32 | */
33 | ret = mmap(addr, size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANON,
34 | -1, 0);
35 | assert(ret != NULL);
36 |
37 | if (ret == MAP_FAILED)
38 | ret = NULL;
39 | else if (addr != NULL && ret != addr) {
40 | /*
41 | * We succeeded in mapping memory, but not in the right place.
42 | */
43 | if (munmap(ret, size) == -1) {
44 | char buf[BUFERROR_BUF];
45 |
46 | buferror(buf, sizeof(buf));
47 | malloc_printf(": Error in "
74 | #ifdef _WIN32
75 | "VirtualFree"
76 | #else
77 | "munmap"
78 | #endif
79 | "(): %s\n", buf);
80 | if (opt_abort)
81 | abort();
82 | }
83 | }
84 |
85 | static void *
86 | pages_trim(void *addr, size_t alloc_size, size_t leadsize, size_t size)
87 | {
88 | void *ret = (void *)((uintptr_t)addr + leadsize);
89 |
90 | assert(alloc_size >= leadsize + size);
91 | #ifdef _WIN32
92 | {
93 | void *new_addr;
94 |
95 | pages_unmap(addr, alloc_size);
96 | new_addr = pages_map(ret, size);
97 | if (new_addr == ret)
98 | return (ret);
99 | if (new_addr)
100 | pages_unmap(new_addr, size);
101 | return (NULL);
102 | }
103 | #else
104 | {
105 | size_t trailsize = alloc_size - leadsize - size;
106 |
107 | if (leadsize != 0)
108 | pages_unmap(addr, leadsize);
109 | if (trailsize != 0)
110 | pages_unmap((void *)((uintptr_t)ret + size), trailsize);
111 | return (ret);
112 | }
113 | #endif
114 | }
115 |
116 | bool
117 | pages_purge(void *addr, size_t length)
118 | {
119 | bool unzeroed;
120 |
121 | #ifdef _WIN32
122 | VirtualAlloc(addr, length, MEM_RESET, PAGE_READWRITE);
123 | unzeroed = true;
124 | #else
125 | # ifdef JEMALLOC_PURGE_MADVISE_DONTNEED
126 | # define JEMALLOC_MADV_PURGE MADV_DONTNEED
127 | # define JEMALLOC_MADV_ZEROS true
128 | # elif defined(JEMALLOC_PURGE_MADVISE_FREE)
129 | # define JEMALLOC_MADV_PURGE MADV_FREE
130 | # define JEMALLOC_MADV_ZEROS false
131 | # else
132 | # error "No method defined for purging unused dirty pages."
133 | # endif
134 | int err = madvise(addr, length, JEMALLOC_MADV_PURGE);
135 | unzeroed = (JEMALLOC_MADV_ZEROS == false || err != 0);
136 | # undef JEMALLOC_MADV_PURGE
137 | # undef JEMALLOC_MADV_ZEROS
138 | #endif
139 | return (unzeroed);
140 | }
141 |
142 | static void *
143 | chunk_alloc_mmap_slow(size_t size, size_t alignment, bool *zero)
144 | {
145 | void *ret, *pages;
146 | size_t alloc_size, leadsize;
147 |
148 | alloc_size = size + alignment - PAGE;
149 | /* Beware size_t wrap-around. */
150 | if (alloc_size < size)
151 | return (NULL);
152 | do {
153 | pages = pages_map(NULL, alloc_size);
154 | if (pages == NULL)
155 | return (NULL);
156 | leadsize = ALIGNMENT_CEILING((uintptr_t)pages, alignment) -
157 | (uintptr_t)pages;
158 | ret = pages_trim(pages, alloc_size, leadsize, size);
159 | } while (ret == NULL);
160 |
161 | assert(ret != NULL);
162 | *zero = true;
163 | return (ret);
164 | }
165 |
166 | void *
167 | chunk_alloc_mmap(size_t size, size_t alignment, bool *zero)
168 | {
169 | void *ret;
170 | size_t offset;
171 |
172 | /*
173 | * Ideally, there would be a way to specify alignment to mmap() (like
174 | * NetBSD has), but in the absence of such a feature, we have to work
175 | * hard to efficiently create aligned mappings. The reliable, but
176 | * slow method is to create a mapping that is over-sized, then trim the
177 | * excess. However, that always results in one or two calls to
178 | * pages_unmap().
179 | *
180 | * Optimistically try mapping precisely the right amount before falling
181 | * back to the slow method, with the expectation that the optimistic
182 | * approach works most of the time.
183 | */
184 |
185 | assert(alignment != 0);
186 | assert((alignment & chunksize_mask) == 0);
187 |
188 | ret = pages_map(NULL, size);
189 | if (ret == NULL)
190 | return (NULL);
191 | offset = ALIGNMENT_ADDR2OFFSET(ret, alignment);
192 | if (offset != 0) {
193 | pages_unmap(ret, size);
194 | return (chunk_alloc_mmap_slow(size, alignment, zero));
195 | }
196 |
197 | assert(ret != NULL);
198 | *zero = true;
199 | return (ret);
200 | }
201 |
202 | bool
203 | chunk_dealloc_mmap(void *chunk, size_t size)
204 | {
205 |
206 | if (config_munmap)
207 | pages_unmap(chunk, size);
208 |
209 | return (config_munmap == false);
210 | }
211 |
--------------------------------------------------------------------------------
/src/list.c:
--------------------------------------------------------------------------------
1 | /*
2 | Copyright (c) 2006-2010, Salvatore Sanfilippo
3 | All rights reserved.
4 |
5 | Redistribution and use in source and binary forms, with or without
6 | modification, are permitted provided that the following conditions are met:
7 | * Redistributions of source code must retain the above copyright
8 | notice, this list of conditions and the following disclaimer.
9 | * Redistributions in binary form must reproduce the above copyright
10 | notice, this list of conditions and the following disclaimer in the
11 | documentation and/or other materials provided with the distribution.
12 | * Neither the name of Redis nor the
13 | names of its contributors may be used to endorse or promote products
14 | derived from this software without specific prior written permission.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
20 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 | */
27 |
28 | #include
29 |
30 | #include "eagle.h"
31 | #include "list.h"
32 | #include "xmalloc.h"
33 |
34 | List *list_create(void)
35 | {
36 | List *list;
37 |
38 | list = (List*)xmalloc(sizeof(*list));
39 |
40 | list->head = list->tail = NULL;
41 | list->len = 0;
42 | list->free = NULL;
43 | list->match = NULL;
44 |
45 | return list;
46 | }
47 |
48 | void list_release(List *list)
49 | {
50 | unsigned int len;
51 | ListNode *current, *next;
52 |
53 | current = list->head;
54 | len = list->len;
55 |
56 | while (len--) {
57 | next = current->next;
58 |
59 | if (list->free) {
60 | list->free(current->value);
61 | }
62 |
63 | xfree(current);
64 | current = next;
65 | }
66 |
67 | xfree(list);
68 | }
69 |
70 | List *list_add_value_head(List *list, void *value)
71 | {
72 | ListNode *node;
73 |
74 | node = (ListNode*)xmalloc(sizeof(*node));
75 |
76 | node->value = value;
77 |
78 | if (list->len == 0) {
79 | list->head = list->tail = node;
80 | node->prev = node->next = NULL;
81 | } else {
82 | node->prev = NULL;
83 | node->next = list->head;
84 | list->head->prev = node;
85 | list->head = node;
86 | }
87 |
88 | list->len++;
89 |
90 | return list;
91 | }
92 |
93 | List *list_add_value_tail(List *list, void *value)
94 | {
95 | ListNode *node;
96 |
97 | node = (ListNode*)xmalloc(sizeof(*node));
98 |
99 | node->value = value;
100 |
101 | if (list->len == 0) {
102 | list->head = list->tail = node;
103 | node->prev = node->next = NULL;
104 | } else {
105 | node->prev = list->tail;
106 | node->next = NULL;
107 | list->tail->next = node;
108 | list->tail = node;
109 | }
110 |
111 | list->len++;
112 |
113 | return list;
114 | }
115 |
116 | int list_delete_value(List *list, void *value)
117 | {
118 | ListNode *node;
119 |
120 | node = list_search_node(list, value);
121 |
122 | if (!node) {
123 | return EG_STATUS_ERR;
124 | }
125 |
126 | list_delete_node(list, node);
127 |
128 | return EG_STATUS_OK;
129 | }
130 |
131 | void list_delete_node(List *list, ListNode *node)
132 | {
133 | if (node->prev) {
134 | node->prev->next = node->next;
135 | } else {
136 | list->head = node->next;
137 | }
138 |
139 | if (node->next) {
140 | node->next->prev = node->prev;
141 | } else {
142 | list->tail = node->prev;
143 | }
144 |
145 | if (list->free) {
146 | list->free(node->value);
147 | }
148 |
149 | xfree(node);
150 | list->len--;
151 | }
152 |
153 | ListIterator *list_get_iterator(List *list, int direction)
154 | {
155 | ListIterator *iter;
156 |
157 | iter = (ListIterator*)xmalloc(sizeof(*iter));
158 |
159 | if (direction == EG_START_HEAD) {
160 | iter->next = list->head;
161 | } else {
162 | iter->next = list->tail;
163 | }
164 |
165 | iter->direction = direction;
166 |
167 | return iter;
168 | }
169 |
170 | void list_release_iterator(ListIterator *iter)
171 | {
172 | xfree(iter);
173 | }
174 |
175 | ListNode *list_next_node(ListIterator *iter)
176 | {
177 | ListNode *current = iter->next;
178 |
179 | if (current != NULL) {
180 | if (iter->direction == EG_START_HEAD) {
181 | iter->next = current->next;
182 | } else {
183 | iter->next = current->prev;
184 | }
185 | }
186 |
187 | return current;
188 | }
189 |
190 | ListNode *list_search_node(List *list, void *value)
191 | {
192 | ListIterator *iter;
193 | ListNode *node;
194 |
195 | iter = list_get_iterator(list, EG_START_HEAD);
196 |
197 | while ((node = list_next_node(iter)) != NULL) {
198 | if (list->match) {
199 | if (list->match(node->value, value)) {
200 | list_release_iterator(iter);
201 | return node;
202 | }
203 | } else {
204 | if (node->value == value) {
205 | list_release_iterator(iter);
206 | return node;
207 | }
208 | }
209 | }
210 |
211 | list_release_iterator(iter);
212 |
213 | return NULL;
214 | }
215 |
216 | void list_rotate(List *list)
217 | {
218 | ListNode *tail = list->tail;
219 |
220 | if (EG_LIST_LENGTH(list) <= 1)
221 | return;
222 |
223 | list->tail = tail->prev;
224 | list->tail->next = NULL;
225 |
226 | list->head->prev = tail;
227 | tail->prev = NULL;
228 | tail->next = list->head;
229 | list->head = tail;
230 | }
231 |
232 | void list_rewind(List *list, ListIterator *iter)
233 | {
234 | iter->next = list->head;
235 | iter->direction = EG_START_HEAD;
236 | }
237 |
--------------------------------------------------------------------------------