diff options
| author | Garrett D'Amore <garrett@damore.org> | 2016-12-12 03:42:26 -0800 |
|---|---|---|
| committer | Garrett D'Amore <garrett@damore.org> | 2016-12-12 03:42:26 -0800 |
| commit | 1adefe3879b211a47a784f477d56a9416ae72254 (patch) | |
| tree | cf017599969fb109d62981cbef56eeeef4d2b108 /src/core | |
| parent | 091043a0df9568b18e9bb49b07762b95e3508108 (diff) | |
| download | nng-1adefe3879b211a47a784f477d56a9416ae72254.tar.gz nng-1adefe3879b211a47a784f477d56a9416ae72254.tar.bz2 nng-1adefe3879b211a47a784f477d56a9416ae72254.zip | |
New inproc transport.
Lots of supporting changes.
Diffstat (limited to 'src/core')
| -rw-r--r-- | src/core/defs.h | 33 | ||||
| -rw-r--r-- | src/core/list.c | 36 | ||||
| -rw-r--r-- | src/core/list.h | 28 | ||||
| -rw-r--r-- | src/core/message.c | 4 | ||||
| -rw-r--r-- | src/core/msgqueue.c (renamed from src/core/msqueue.c) | 2 | ||||
| -rw-r--r-- | src/core/msgqueue.h | 73 | ||||
| -rw-r--r-- | src/core/nng_impl.h | 88 | ||||
| -rw-r--r-- | src/core/panic.c | 2 | ||||
| -rw-r--r-- | src/core/panic.h | 37 | ||||
| -rw-r--r-- | src/core/platform.h | 142 | ||||
| -rw-r--r-- | src/core/snprintf.c | 2 | ||||
| -rw-r--r-- | src/core/snprintf.h | 35 | ||||
| -rw-r--r-- | src/core/socket.c | 4 | ||||
| -rw-r--r-- | src/core/transport.h | 117 |
14 files changed, 488 insertions, 115 deletions
diff --git a/src/core/defs.h b/src/core/defs.h new file mode 100644 index 00000000..f747f901 --- /dev/null +++ b/src/core/defs.h @@ -0,0 +1,33 @@ +/* + * Copyright 2016 Garrett D'Amore <garrett@damore.org> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom + * the Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef CORE_DEFS_H +#define CORE_DEFS_H + +/* + * C compilers may get unhappy when named arguments are not used. While + * there are things like __attribute__((unused)) which are arguably + * superior, support for such are not universal. + */ +#define NNI_ARG_UNUSED(x) ((void)x); + +#endif /* NNG_IMPL_H */ diff --git a/src/core/list.c b/src/core/list.c index f59c75e0..d81c6379 100644 --- a/src/core/list.c +++ b/src/core/list.c @@ -31,12 +31,12 @@ */ #define NODE(list, item) \ - (nni_list_node_t)(void *)(((char *)item) + list->ll_offset) + (nni_list_node_t *)(void *)(((char *)item) + list->ll_offset) #define ITEM(list, node) \ (void *)(((char *)node) - list->ll_offset) void -nni_list_init_offset(nni_list_t list, size_t offset) +nni_list_init_offset(nni_list_t *list, size_t offset) { list->ll_offset = offset; list->ll_head.ln_next = &list->ll_head; @@ -44,9 +44,9 @@ nni_list_init_offset(nni_list_t list, size_t offset) } void * -nni_list_first(nni_list_t list) +nni_list_first(nni_list_t *list) { - nni_list_node_t node = list->ll_head.ln_next; + nni_list_node_t *node = list->ll_head.ln_next; if (node == &list->ll_head) { return (NULL); } @@ -54,9 +54,9 @@ nni_list_first(nni_list_t list) } void * -nni_list_last(nni_list_t list) +nni_list_last(nni_list_t *list) { - nni_list_node_t node = list->ll_head.ln_prev; + nni_list_node_t *node = list->ll_head.ln_prev; if (node == &list->ll_head) { return (NULL); } @@ -64,9 +64,9 @@ nni_list_last(nni_list_t list) } void -nni_list_append(nni_list_t list, void *item) +nni_list_append(nni_list_t *list, void *item) { - nni_list_node_t node = NODE(list, item); + nni_list_node_t *node = NODE(list, item); node->ln_prev = list->ll_head.ln_prev; node->ln_next = &list->ll_head; @@ -74,9 +74,9 @@ nni_list_append(nni_list_t list, void *item) node->ln_prev->ln_next = node; } void -nni_list_prepend(nni_list_t list, void *item) +nni_list_prepend(nni_list_t *list, void *item) { - nni_list_node_t node = NODE(list, item); + nni_list_node_t *node = NODE(list, item); node->ln_next = list->ll_head.ln_next; node->ln_prev = &list->ll_head; @@ -85,9 +85,9 @@ nni_list_prepend(nni_list_t list, void *item) } void * -nni_list_next(nni_list_t list, void *item) +nni_list_next(nni_list_t *list, void *item) { - nni_list_node_t node = NODE(list, item); + nni_list_node_t *node = NODE(list, item); if ((node = node->ln_next) == &list->ll_head) { return (NULL); @@ -96,9 +96,9 @@ nni_list_next(nni_list_t list, void *item) } void * -nni_list_prev(nni_list_t list, void *item) +nni_list_prev(nni_list_t *list, void *item) { - nni_list_node_t node = NODE(list, item); + nni_list_node_t *node = NODE(list, item); if ((node = node->ln_prev) == &list->ll_head) { return (NULL); @@ -107,16 +107,16 @@ nni_list_prev(nni_list_t list, void *item) } void -nni_list_remove(nni_list_t list, void *item) +nni_list_remove(nni_list_t *list, void *item) { - nni_list_node_t node = NODE(list, item); + nni_list_node_t *node = NODE(list, item); node->ln_prev->ln_next = node->ln_next; node->ln_next->ln_prev = node->ln_prev; } void -nni_list_node_init(nni_list_t list, void *item) +nni_list_node_init(nni_list_t *list, void *item) { - nni_list_node_t node = NODE(list, item); + nni_list_node_t *node = NODE(list, item); node->ln_prev = node->ln_next = NULL; } diff --git a/src/core/list.h b/src/core/list.h index c55870cb..f12087a2 100644 --- a/src/core/list.h +++ b/src/core/list.h @@ -32,23 +32,25 @@ typedef struct nni_list_node { struct nni_list_node *ln_next; struct nni_list_node *ln_prev; -} *nni_list_node_t; +} nni_list_node_t; typedef struct nni_list { struct nni_list_node ll_head; size_t ll_offset; -} *nni_list_t; +} nni_list_t; -extern void nni_list_init_offset(nni_list_t list, size_t offset); +extern void nni_list_init_offset(nni_list_t *list, size_t offset); #define NNI_LIST_INIT(list, type, field) \ - nni_list_init_offset(list, type, (size_t)&((type *)0)->field) -extern void *nni_list_first(nni_list_t list); -extern void *nni_list_last(nni_list_t list); -extern void nni_list_append(nni_list_t list, void *item); -extern void nni_list_prepend(nni_list_t list, void *item); -extern void *nni_list_next(nni_list_t list, void *item); -extern void *nni_list_prev(nni_list_t list, void *item); -extern void nni_list_remove(nni_list_t list, void *item); -extern void nni_list_node_init(nni_list_t, void *); + nni_list_init_offset(list, offsetof (type, field)) +extern void *nni_list_first(nni_list_t *); +extern void *nni_list_last(nni_list_t *); +extern void nni_list_append(nni_list_t *, void *); +extern void nni_list_prepend(nni_list_t *, void *); +extern void *nni_list_next(nni_list_t *, void *); +extern void *nni_list_prev(nni_list_t *, void *); +extern void nni_list_remove(nni_list_t *, void *); +extern void nni_list_node_init(nni_list_t *, void *); +#define NNI_LIST_FOREACH(l, it) \ + for (it = nni_list_first(l); it != NULL; it = nni_list_next(l, it)) -#endif /* CORE_MSQUEUE_H */ +#endif /* CORE_LIST_H */ diff --git a/src/core/message.c b/src/core/message.c index 82f58dc5..581f7683 100644 --- a/src/core/message.c +++ b/src/core/message.c @@ -23,9 +23,7 @@ #include <stdlib.h> #include <string.h> -#include "../nng.h" - -#include "nng_impl.h" +#include "core/nng_impl.h" /* * Message API. diff --git a/src/core/msqueue.c b/src/core/msgqueue.c index 7becabfb..9f168878 100644 --- a/src/core/msqueue.c +++ b/src/core/msgqueue.c @@ -20,8 +20,6 @@ * IN THE SOFTWARE. */ -#include "../nng.h" - #include "nng_impl.h" /* diff --git a/src/core/msgqueue.h b/src/core/msgqueue.h new file mode 100644 index 00000000..9d856edd --- /dev/null +++ b/src/core/msgqueue.h @@ -0,0 +1,73 @@ +/* + * Copyright 2016 Garrett D'Amore <garrett@damore.org> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom + * the Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef CORE_MSGQUEUE_H +#define CORE_MSGQUEUE_H + +#include "nng.h" + +/* + * Message queues. Message queues work in some ways like Go channels; + * they are a thread-safe way to pass messages between subsystems. + */ +typedef struct nni_msgqueue *nni_msgqueue_t; + +/* + * nni_msgqueue_create creates a message queue with the given capacity, + * which must be a positive number. It returns NNG_EINVAL if the capacity + * is invalid, or NNG_ENOMEM if resources cannot be allocated. + */ +extern int nni_msgqueue_create(nni_msgqueue_t *, int); + +/* + * nni_msgqueue_destroy destroys a message queue. It will also free any + * messages that may be in the queue. + */ +extern void nni_msgqueue_destroy(nni_msgqueue_t); + +/* + * nni_msgqueue_put attempts to put a message to the queue. It will wait + * for the timeout (us), if the value is positive. If the value is negative + * then it will wait forever. If the value is zero, it will just check, and + * return immediately whether a message can be put or not. Valid returns are + * NNG_ECLOSED if the queue is closed or NNG_ETIMEDOUT if the message cannot + * be placed after a time, or NNG_EAGAIN if the operation cannot succeed + * immediately and a zero timeout is specified. Note that timeout granularity + * may be limited -- for example Windows systems have a millisecond resolution + * timeout capability. + */ +extern int nni_msgqueue_put(nni_msgqueue_t, nng_msg_t, int); + +/* + * nni_msgqueue_get gets the message from the queue, using a timeout just + * like nni_msgqueue_put. + */ +extern int nni_msgqueue_get(nni_msgqueue_t, nng_msg_t *, int); + +/* + * nni_msgqueue_close closes the queue. After this all operates on the + * message queue will return NNG_ECLOSED. Messages inside the queue + * are freed. Unlike closing a go channel, this operation is idempotent. + */ +extern void nni_msgqueue_close(nni_msgqueue_t); + +#endif /* CORE_MSQUEUE_H */ diff --git a/src/core/nng_impl.h b/src/core/nng_impl.h index 683e0df1..d728c652 100644 --- a/src/core/nng_impl.h +++ b/src/core/nng_impl.h @@ -20,90 +20,30 @@ * IN THE SOFTWARE. */ -#ifndef NNG_IMPL_H -#define NNG_IMPL_H +#ifndef CORE_NNG_IMPL_H +#define CORE_NNG_IMPL_H #include "nng.h" -#include "platform/platform.h" /* * Internal implementation things for NNG, common definitions, etc. + * All internal modules wind up including this file to avoid having + * to figure out which header(s) to include. * * Hopefully it should be clear by the name that this file and its contents * are *NOT* for use outside of this library. * * Symbols that are private to the library begin with the nni_ prefix, whereas - * those starting with nng_ are intended for external consumption. + * those starting with nng_ are intended for external consumption. The latter + * symbols should be found in the toplevel nng.h header. */ -/* - * C compilers may get unhappy when named arguments are not used. While - * there are things like __attribute__((unused)) which are arguably - * superior, support for such are not universal. - */ -#define NNI_ARG_UNUSED(x) ((void)x); - -/* - * We have our own snprintf, because some platforms lack this, while - * others need special handling. Ours just calls the vsnprintf version - * from the platform. - */ -extern void nni_snprintf(char *, size_t, const char *, ...); - -/* - * nni_panic is used to terminate the process with prejudice, and - * should only be called in the face of a critical programming error, - * or other situation where it would be unsafe to attempt to continue. - * As this crashes the program, it should never be used when factors outside - * the program can cause it, such as receiving protocol errors, or running - * out of memory. Its better in those cases to return an error to the - * program and let the caller handle the error situation. - */ -extern void nni_panic(const char *, ...); - -/* - * Message queues. Message queues work in some ways like Go channels; - * they are a thread-safe way to pass messages between subsystems. - */ -typedef struct nni_msgqueue *nni_msgqueue_t; - -/* - * nni_msgqueue_create creates a message queue with the given capacity, - * which must be a positive number. It returns NNG_EINVAL if the capacity - * is invalid, or NNG_ENOMEM if resources cannot be allocated. - */ -extern int nni_msgqueue_create(nni_msgqueue_t *, int); - -/* - * nni_msgqueue_destroy destroys a message queue. It will also free any - * messages that may be in the queue. - */ -extern void nni_msgqueue_destroy(nni_msgqueue_t); - -/* - * nni_msgqueue_put attempts to put a message to the queue. It will wait - * for the timeout (us), if the value is positive. If the value is negative - * then it will wait forever. If the value is zero, it will just check, and - * return immediately whether a message can be put or not. Valid returns are - * NNG_ECLOSED if the queue is closed or NNG_ETIMEDOUT if the message cannot - * be placed after a time, or NNG_EAGAIN if the operation cannot succeed - * immediately and a zero timeout is specified. Note that timeout granularity - * may be limited -- for example Windows systems have a millisecond resolution - * timeout capability. - */ -extern int nni_msgqueue_put(nni_msgqueue_t, nng_msg_t, int); - -/* - * nni_msgqueue_get gets the message from the queue, using a timeout just - * like nni_msgqueue_put. - */ -extern int nni_msgqueue_get(nni_msgqueue_t, nng_msg_t *, int); - -/* - * nni_msgqueue_close closes the queue. After this all operates on the - * message queue will return NNG_ECLOSED. Messages inside the queue - * are freed. Unlike closing a go channel, this operation is idempotent. - */ -extern void nni_msgqueue_close(nni_msgqueue_t); +#include "core/defs.h" +#include "core/list.h" +#include "core/msgqueue.h" +#include "core/panic.h" +#include "core/snprintf.h" +#include "core/platform.h" +#include "core/transport.h" -#endif /* NNG_IMPL_H */ +#endif /* CORE_NNG_IMPL_H */ diff --git a/src/core/panic.c b/src/core/panic.c index 60c790ac..52dcb8c8 100644 --- a/src/core/panic.c +++ b/src/core/panic.c @@ -28,7 +28,7 @@ #include <execinfo.h> #endif -#include "nng_impl.h" +#include "core/nng_impl.h" /* * Panic handling. diff --git a/src/core/panic.h b/src/core/panic.h new file mode 100644 index 00000000..6deef964 --- /dev/null +++ b/src/core/panic.h @@ -0,0 +1,37 @@ +/* + * Copyright 2016 Garrett D'Amore <garrett@damore.org> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom + * the Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef CORE_PANIC_H +#define CORE_PANIC_H + +/* + * nni_panic is used to terminate the process with prejudice, and + * should only be called in the face of a critical programming error, + * or other situation where it would be unsafe to attempt to continue. + * As this crashes the program, it should never be used when factors outside + * the program can cause it, such as receiving protocol errors, or running + * out of memory. Its better in those cases to return an error to the + * program and let the caller handle the error situation. + */ +extern void nni_panic(const char *, ...); + +#endif /* CORE_PANIC_H */ diff --git a/src/core/platform.h b/src/core/platform.h new file mode 100644 index 00000000..ea8f1378 --- /dev/null +++ b/src/core/platform.h @@ -0,0 +1,142 @@ +/* + * Copyright 2016 Garrett D'Amore <garrett@damore.org> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom + * the Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef CORE_PLATFORM_H +#define CORE_PLATFORM_H + +/* + * We require some standard C header files. The only one of these that might + * be problematic is <stdint.h>, which is required for C99. Older versions + * of the Windows compilers might not have this. However, latest versions of + * MS Studio have a functional <stdint.h>. If this impacts you, just upgrade + * your tool chain. + */ +#include <stdarg.h> +#include <stddef.h> +#include <stdint.h> + +/* + * These are the APIs that a platform must implement to support nng. + */ + +/* + * nni_abort crashes the system; it should do whatever is appropriate + * for abnormal programs on the platform, such as calling abort(). + */ +void nni_abort(void); + +/* + * nni_vnsprintf is exactly like its POSIX counterpart. + * Some platforms (Windows!) need a special version of this. + */ +void nni_vsnprintf(char *, size_t, const char *, va_list); + +/* + * nni_debug_output is used to emit debug messages. Typically this is used + * during core debugging, or to emit panic messages. Message content will + * not contain newlines, but the output will add them. + */ +void nni_debug_out(const char *); + +/* + * nni_set_debug_output is used to redirect debug output; for example an + * application could replace the default output routine with one that sends + * it's output to syslog. If NULL is specified, then a default handler + * used instead. The handler should add any newlines to the output as + * required. The default handler writes to standard error. + */ +void nni_set_debug_out(void (*)(const char *)); + +/* + * nni_alloc allocates memory. In most cases this can just be malloc(). + * However, you may provide a different allocator, for example it is + * possible to use a slab allocator or somesuch. It is permissible for this + * to return NULL if memory cannot be allocated. + */ +void *nni_alloc(size_t); + +/* + * nni_free frees memory allocated with nni_alloc. It takes a size because + * some allocators do not track size, or can operate more efficiently if + * the size is provided with the free call. Examples of this are slab + * allocators like this found in Solaris/illumos (see libumem or kmem). + * This routine does nothing if supplied with a NULL pointer and zero size. + * Most implementations can just call free() here. + */ +void nni_free(void *, size_t); + +typedef struct nni_mutex *nni_mutex_t; +typedef struct nni_cond *nni_cond_t; + +/* + * Mutex handling. + */ +int nni_mutex_create(nni_mutex_t *); +void nni_mutex_destroy(nni_mutex_t); +void nni_mutex_enter(nni_mutex_t); +void nni_mutex_exit(nni_mutex_t); +int nni_mutex_tryenter(nni_mutex_t); +int nni_cond_create(nni_cond_t *, nni_mutex_t); +void nni_cond_destroy(nni_cond_t); + +/* + * nni_cond_broadcast wakes all waiters on the condition. This should be + * called with the lock held. + */ +void nni_cond_broadcast(nni_cond_t); + +/* + * nni_cond_signal wakes a signal waiter. + */ +void nni_cond_signal(nni_cond_t); + +/* + * nni_condwait waits for a wake up on the condition variable. The + * associated lock is atomically released and reacquired upon wake up. + * Callers can be spuriously woken. The associated lock must be held. + */ +void nni_cond_wait(nni_cond_t); + +/* + * nni_cond_timedwait waits for a wakeup on the condition variable, just + * as with nni_condwait, but it will also wake after the given number of + * microseconds has passed. (This is a relative timed wait.) Early + * wakeups are permitted, and the caller must take care to double check any + * conditions. The return value is 0 on success, or an error code, which + * can be NNG_ETIMEDOUT. Note that it is permissible to wait for longer + * than the timeout based on the resolution of your system clock. + */ +int nni_cond_timedwait(nni_cond_t, uint64_t); + +/* + * nn_clock returns a number of microseconds since some arbitrary time + * in the past. The values returned by nni_clock may be used with + * nni_cond_timedwait. + */ +uint64_t nni_clock(void); + +/* + * nni_usleep sleeps for the specified number of microseconds (at least). + */ +void nni_usleep(uint64_t); + +#endif /* CORE_PLATFORM_H */ diff --git a/src/core/snprintf.c b/src/core/snprintf.c index 3ca73e00..574d537a 100644 --- a/src/core/snprintf.c +++ b/src/core/snprintf.c @@ -24,7 +24,7 @@ #include <stdint.h> #include <stdlib.h> -#include "nng_impl.h" +#include "core/nng_impl.h" void nni_snprintf(char *dst, size_t sz, const char *fmt, ...) diff --git a/src/core/snprintf.h b/src/core/snprintf.h new file mode 100644 index 00000000..b98b6ee7 --- /dev/null +++ b/src/core/snprintf.h @@ -0,0 +1,35 @@ +/* + * Copyright 2016 Garrett D'Amore <garrett@damore.org> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom + * the Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef CORE_SNPRINTF_H +#define CORE_SNPRINTF_H + +#include <stddef.h> + +/* + * We have our own snprintf, because some platforms lack this, while + * others need special handling. Ours just calls the vsnprintf version + * from the platform. + */ +extern void nni_snprintf(char *, size_t, const char *, ...); + +#endif /* CORE_SNPRINTF_H */ diff --git a/src/core/socket.c b/src/core/socket.c index e9963b74..6bb1d5d5 100644 --- a/src/core/socket.c +++ b/src/core/socket.c @@ -20,9 +20,7 @@ * IN THE SOFTWARE. */ -#include "../nng.h" - -#include "nng_impl.h" +#include "core/nng_impl.h" /* * Socket implementation. diff --git a/src/core/transport.h b/src/core/transport.h new file mode 100644 index 00000000..567cc0c5 --- /dev/null +++ b/src/core/transport.h @@ -0,0 +1,117 @@ +/* + * Copyright 2016 Garrett D'Amore <garrett@damore.org> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom + * the Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef CORE_TRANSPORT_H +#define CORE_TRANSPORT_H + +/* + * Transport implementation details. Transports must implement the + * interfaces in this file. + */ + +struct nni_transport_ops { + /* + * tran_scheme is the transport scheme, such as "tcp" or "inproc". + */ + const char *tran_scheme; + + /* + * tran_ep_ops links our endpoint operations. + */ + const struct nni_endpt_ops *tran_ep_ops; + + /* + * tran_pipe_ops links our pipe operations. + */ + const struct nni_pipe_ops *tran_pipe_ops; +}; + +struct nni_endpt_ops { + /* + * ep_create creates a vanilla endpoint. The value created is + * used for the first argument for all other endpoint functions. + */ + int (*ep_create)(void **, const char *, uint16_t); + + /* + * ep_destroy frees the resources associated with the endpoint. + * The endpoint will already have been closed. + */ + void (*ep_destroy)(void *); + + /* + * ep_dial starts dialing, and creates a new pipe, + * which is returned in the final argument. It can return errors + * NNG_EACCESS, NNG_ECONNREFUSED, NNG_EBADADDR, NNG_ECONNFAILED, + * NNG_ETIMEDOUT, and NNG_EPROTO. + */ + int (*ep_dial)(void *, void **); + + /* + * ep_listen just does the bind() and listen() work, + * reserving the address but not creating any connections. + * It should return NNG_EADDRINUSE if the address is already + * taken. It can also return NNG_EBADADDR for an unsuitable + * address, or NNG_EACCESS for permission problems. + */ + int (*ep_listen)(void *); + + /* + * ep_accept accepts an inbound connection, and creates + * a transport pipe, which is returned in the final argument. + */ + int (*ep_accept)(void *, void **); + + /* + * ep_close stops the endpoint from operating altogether. It does + * not affect pipes that have already been created. + */ + void (*ep_close)(void *); + + /* ep_setopt sets an endpoint (transport-specific) option */ + int (*ep_setopt)(void *, int, const void *, size_t); + + /* ep_getopt gets an endpoint (transport-specific) option */ + int (*ep_getopt)(void *, int, void *, size_t *); +}; + +struct nni_pipe_ops { + /* p_destroy destroys the pipe */ + void (*p_destroy)(void *); + + /* p_send sends the message */ + int (*p_send)(void *, nng_msg_t); + + /* p_recv recvs the message */ + int (*p_recv)(void *, nng_msg_t *); + + /* p_close closes the pipe */ + void (*p_close)(void *); + + /* p_proto returns the peer protocol */ + uint16_t (*p_proto)(void *); + + /* p_getopt gets an pipe (transport-specific) property */ + int (*p_getopt)(void *, int, void *, size_t *); +}; + +#endif /* CORE_TRANSPORT_H */ |
