1 /** \file */
2 /*
3  * ***** BEGIN LICENSE BLOCK *****
4  * Version: MIT
5  *
6  * Portions created by Alan Antonuk are Copyright (c) 2012-2014
7  * Alan Antonuk. All Rights Reserved.
8  *
9  * Portions created by VMware are Copyright (c) 2007-2012 VMware, Inc.
10  * All Rights Reserved.
11  *
12  * Portions created by Tony Garnock-Jones are Copyright (c) 2009-2010
13  * VMware, Inc. and Tony Garnock-Jones. All Rights Reserved.
14  *
15  * Permission is hereby granted, free of charge, to any person
16  * obtaining a copy of this software and associated documentation
17  * files (the "Software"), to deal in the Software without
18  * restriction, including without limitation the rights to use, copy,
19  * modify, merge, publish, distribute, sublicense, and/or sell copies
20  * of the Software, and to permit persons to whom the Software is
21  * furnished to do so, subject to the following conditions:
22  *
23  * The above copyright notice and this permission notice shall be
24  * included in all copies or substantial portions of the Software.
25  *
26  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
27  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
28  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
29  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
30  * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
31  * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
32  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
33  * SOFTWARE.
34  * ***** END LICENSE BLOCK *****
35  */
36 
37 #ifndef AMQP_H
38 #define AMQP_H
39 
40 /** \cond HIDE_FROM_DOXYGEN */
41 
42 #ifdef __cplusplus
43 #define AMQP_BEGIN_DECLS extern "C" {
44 #define AMQP_END_DECLS }
45 #else
46 #define AMQP_BEGIN_DECLS
47 #define AMQP_END_DECLS
48 #endif
49 
50 /*
51  * \internal
52  * Important API decorators:
53  *  AMQP_PUBLIC_FUNCTION - a public API function
54  *  AMQP_PUBLIC_VARIABLE - a public API external variable
55  *  AMQP_CALL - calling convension (used on Win32)
56  */
57 
58 #if defined(_WIN32) && defined(_MSC_VER)
59 #if defined(AMQP_BUILD) && !defined(AMQP_STATIC)
60 #define AMQP_PUBLIC_FUNCTION __declspec(dllexport)
61 #define AMQP_PUBLIC_VARIABLE __declspec(dllexport) extern
62 #else
63 #define AMQP_PUBLIC_FUNCTION
64 #if !defined(AMQP_STATIC)
65 #define AMQP_PUBLIC_VARIABLE __declspec(dllimport) extern
66 #else
67 #define AMQP_PUBLIC_VARIABLE extern
68 #endif
69 #endif
70 #define AMQP_CALL __cdecl
71 
72 #elif defined(_WIN32) && defined(__BORLANDC__)
73 #if defined(AMQP_BUILD) && !defined(AMQP_STATIC)
74 #define AMQP_PUBLIC_FUNCTION __declspec(dllexport)
75 #define AMQP_PUBLIC_VARIABLE __declspec(dllexport) extern
76 #else
77 #define AMQP_PUBLIC_FUNCTION
78 #if !defined(AMQP_STATIC)
79 #define AMQP_PUBLIC_VARIABLE __declspec(dllimport) extern
80 #else
81 #define AMQP_PUBLIC_VARIABLE extern
82 #endif
83 #endif
84 #define AMQP_CALL __cdecl
85 
86 #elif defined(_WIN32) && defined(__MINGW32__)
87 #if defined(AMQP_BUILD) && !defined(AMQP_STATIC)
88 #define AMQP_PUBLIC_FUNCTION __declspec(dllexport)
89 #define AMQP_PUBLIC_VARIABLE __declspec(dllexport) extern
90 #else
91 #define AMQP_PUBLIC_FUNCTION
92 #if !defined(AMQP_STATIC)
93 #define AMQP_PUBLIC_VARIABLE __declspec(dllimport) extern
94 #else
95 #define AMQP_PUBLIC_VARIABLE extern
96 #endif
97 #endif
98 #define AMQP_CALL __cdecl
99 
100 #elif defined(_WIN32) && defined(__CYGWIN__)
101 #if defined(AMQP_BUILD) && !defined(AMQP_STATIC)
102 #define AMQP_PUBLIC_FUNCTION __declspec(dllexport)
103 #define AMQP_PUBLIC_VARIABLE __declspec(dllexport)
104 #else
105 #define AMQP_PUBLIC_FUNCTION
106 #if !defined(AMQP_STATIC)
107 #define AMQP_PUBLIC_VARIABLE __declspec(dllimport) extern
108 #else
109 #define AMQP_PUBLIC_VARIABLE extern
110 #endif
111 #endif
112 #define AMQP_CALL __cdecl
113 
114 #elif defined(__GNUC__) && __GNUC__ >= 4
115 #define AMQP_PUBLIC_FUNCTION __attribute__((visibility("default")))
116 #define AMQP_PUBLIC_VARIABLE __attribute__((visibility("default"))) extern
117 #define AMQP_CALL
118 #else
119 #define AMQP_PUBLIC_FUNCTION
120 #define AMQP_PUBLIC_VARIABLE extern
121 #define AMQP_CALL
122 #endif
123 
124 #if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1)
125 #define AMQP_DEPRECATED(function) function __attribute__((__deprecated__))
126 #elif defined(_MSC_VER)
127 #define AMQP_DEPRECATED(function) __declspec(deprecated) function
128 #else
129 #define AMQP_DEPRECATED(function)
130 #endif
131 
132 /* Define ssize_t on Win32/64 platforms
133    See: http://lists.cs.uiuc.edu/pipermail/llvmdev/2010-April/030649.html for
134    details
135    */
136 #if !defined(_W64)
137 #if !defined(__midl) && (defined(_X86_) || defined(_M_IX86)) && _MSC_VER >= 1300
138 #define _W64 __w64
139 #else
140 #define _W64
141 #endif
142 #endif
143 
144 #ifdef _MSC_VER
145 #ifdef _WIN64
146 typedef __int64 ssize_t;
147 #else
148 typedef _W64 int ssize_t;
149 #endif
150 #endif
151 
152 #if defined(_WIN32) && defined(__MINGW32__)
153 #include <sys/types.h>
154 #endif
155 
156 /** \endcond */
157 
158 #include <stddef.h>
159 #include <stdint.h>
160 
161 struct timeval;
162 
163 AMQP_BEGIN_DECLS
164 
165 /**
166  * \def AMQP_VERSION_MAJOR
167  *
168  * Major library version number compile-time constant
169  *
170  * The major version is incremented when backwards incompatible API changes
171  * are made.
172  *
173  * \sa AMQP_VERSION, AMQP_VERSION_STRING
174  *
175  * \since v0.4.0
176  */
177 
178 /**
179  * \def AMQP_VERSION_MINOR
180  *
181  * Minor library version number compile-time constant
182  *
183  * The minor version is incremented when new APIs are added. Existing APIs
184  * are left alone.
185  *
186  * \sa AMQP_VERSION, AMQP_VERSION_STRING
187  *
188  * \since v0.4.0
189  */
190 
191 /**
192  * \def AMQP_VERSION_PATCH
193  *
194  * Patch library version number compile-time constant
195  *
196  * The patch version is incremented when library code changes, but the API
197  * is not changed.
198  *
199  * \sa AMQP_VERSION, AMQP_VERSION_STRING
200  *
201  * \since v0.4.0
202  */
203 
204 /**
205  * \def AMQP_VERSION_IS_RELEASE
206  *
207  * Version constant set to 1 for tagged release, 0 otherwise
208  *
209  * NOTE: versions that are not tagged releases are not guaranteed to be API/ABI
210  * compatible with older releases, and may change commit-to-commit.
211  *
212  * \sa AMQP_VERSION, AMQP_VERSION_STRING
213  *
214  * \since v0.4.0
215  */
216 /*
217  * Developer note: when changing these, be sure to update SOVERSION constants
218  *  in CMakeLists.txt and configure.ac
219  */
220 
221 #define AMQP_VERSION_MAJOR 0
222 #define AMQP_VERSION_MINOR 11
223 #define AMQP_VERSION_PATCH 0
224 #define AMQP_VERSION_IS_RELEASE 1
225 
226 /**
227  * \def AMQP_VERSION_CODE
228  *
229  * Helper macro to geneate a packed version code suitable for
230  * comparison with AMQP_VERSION.
231  *
232  * \sa amqp_version_number() AMQP_VERSION_MAJOR, AMQP_VERSION_MINOR,
233  *     AMQP_VERSION_PATCH, AMQP_VERSION_IS_RELEASE, AMQP_VERSION
234  *
235  * \since v0.6.1
236  */
237 #define AMQP_VERSION_CODE(major, minor, patch, release) \
238   ((major << 24) | (minor << 16) | (patch << 8) | (release))
239 
240 /**
241  * \def AMQP_VERSION
242  *
243  * Packed version number
244  *
245  * AMQP_VERSION is a 4-byte unsigned integer with the most significant byte
246  * set to AMQP_VERSION_MAJOR, the second most significant byte set to
247  * AMQP_VERSION_MINOR, third most significant byte set to AMQP_VERSION_PATCH,
248  * and the lowest byte set to AMQP_VERSION_IS_RELEASE.
249  *
250  * For example version 2.3.4 which is released version would be encoded as
251  * 0x02030401
252  *
253  * \sa amqp_version_number() AMQP_VERSION_MAJOR, AMQP_VERSION_MINOR,
254  *     AMQP_VERSION_PATCH, AMQP_VERSION_IS_RELEASE, AMQP_VERSION_CODE
255  *
256  * \since v0.4.0
257  */
258 #define AMQP_VERSION                                        \
259   AMQP_VERSION_CODE(AMQP_VERSION_MAJOR, AMQP_VERSION_MINOR, \
260                     AMQP_VERSION_PATCH, AMQP_VERSION_IS_RELEASE)
261 
262 /** \cond HIDE_FROM_DOXYGEN */
263 #define AMQ_STRINGIFY(s) AMQ_STRINGIFY_HELPER(s)
264 #define AMQ_STRINGIFY_HELPER(s) #s
265 
266 #define AMQ_VERSION_STRING          \
267   AMQ_STRINGIFY(AMQP_VERSION_MAJOR) \
268   "." AMQ_STRINGIFY(AMQP_VERSION_MINOR) "." AMQ_STRINGIFY(AMQP_VERSION_PATCH)
269 /** \endcond */
270 
271 /**
272  * \def AMQP_VERSION_STRING
273  *
274  * Version string compile-time constant
275  *
276  * Non-released versions of the library will have "-pre" appended to the
277  * version string
278  *
279  * \sa amqp_version()
280  *
281  * \since v0.4.0
282  */
283 #if AMQP_VERSION_IS_RELEASE
284 #define AMQP_VERSION_STRING AMQ_VERSION_STRING
285 #else
286 #define AMQP_VERSION_STRING AMQ_VERSION_STRING "-pre"
287 #endif
288 
289 /**
290  * Returns the rabbitmq-c version as a packed integer.
291  *
292  * See \ref AMQP_VERSION
293  *
294  * \return packed 32-bit integer representing version of library at runtime
295  *
296  * \sa AMQP_VERSION, amqp_version()
297  *
298  * \since v0.4.0
299  */
300 AMQP_PUBLIC_FUNCTION
301 uint32_t AMQP_CALL amqp_version_number(void);
302 
303 /**
304  * Returns the rabbitmq-c version as a string.
305  *
306  * See \ref AMQP_VERSION_STRING
307  *
308  * \return a statically allocated string describing the version of rabbitmq-c.
309  *
310  * \sa amqp_version_number(), AMQP_VERSION_STRING, AMQP_VERSION
311  *
312  * \since v0.1
313  */
314 AMQP_PUBLIC_FUNCTION
315 char const *AMQP_CALL amqp_version(void);
316 
317 /**
318  * \def AMQP_DEFAULT_FRAME_SIZE
319  *
320  * Default frame size (128Kb)
321  *
322  * \sa amqp_login(), amqp_login_with_properties()
323  *
324  * \since v0.4.0
325  */
326 #define AMQP_DEFAULT_FRAME_SIZE 131072
327 
328 /**
329  * \def AMQP_DEFAULT_MAX_CHANNELS
330  *
331  * Default maximum number of channels (2047, RabbitMQ default limit of 2048,
332  * minus 1 for channel 0). RabbitMQ set a default limit of 2048 channels per
333  * connection in v3.7.5 to prevent broken clients from leaking too many
334  * channels.
335  *
336  * \sa amqp_login(), amqp_login_with_properties()
337  *
338  * \since v0.4.0
339  */
340 #define AMQP_DEFAULT_MAX_CHANNELS 2047
341 
342 /**
343  * \def AMQP_DEFAULT_HEARTBEAT
344  *
345  * Default heartbeat interval (0, heartbeat disabled)
346  *
347  * \sa amqp_login(), amqp_login_with_properties()
348  *
349  * \since v0.4.0
350  */
351 #define AMQP_DEFAULT_HEARTBEAT 0
352 
353 /**
354  * \def AMQP_DEFAULT_VHOST
355  *
356  * Default RabbitMQ vhost: "/"
357  *
358  * \sa amqp_login(), amqp_login_with_properties()
359  *
360  * \since v0.9.0
361  */
362 #define AMQP_DEFAULT_VHOST "/"
363 
364 /**
365  * boolean type 0 = false, true otherwise
366  *
367  * \since v0.1
368  */
369 typedef int amqp_boolean_t;
370 
371 /**
372  * Method number
373  *
374  * \since v0.1
375  */
376 typedef uint32_t amqp_method_number_t;
377 
378 /**
379  * Bitmask for flags
380  *
381  * \since v0.1
382  */
383 typedef uint32_t amqp_flags_t;
384 
385 /**
386  * Channel type
387  *
388  * \since v0.1
389  */
390 typedef uint16_t amqp_channel_t;
391 
392 /**
393  * Buffer descriptor
394  *
395  * \since v0.1
396  */
397 typedef struct amqp_bytes_t_ {
398   size_t len;  /**< length of the buffer in bytes */
399   void *bytes; /**< pointer to the beginning of the buffer */
400 } amqp_bytes_t;
401 
402 /**
403  * Decimal data type
404  *
405  * \since v0.1
406  */
407 typedef struct amqp_decimal_t_ {
408   uint8_t decimals; /**< the location of the decimal point */
409   uint32_t value;   /**< the value before the decimal point is applied */
410 } amqp_decimal_t;
411 
412 /**
413  * AMQP field table
414  *
415  * An AMQP field table is a set of key-value pairs.
416  * A key is a UTF-8 encoded string up to 128 bytes long, and are not null
417  * terminated.
418  * A value can be one of several different datatypes. \sa
419  * amqp_field_value_kind_t
420  *
421  * \sa amqp_table_entry_t
422  *
423  * \since v0.1
424  */
425 typedef struct amqp_table_t_ {
426   int num_entries;                     /**< length of entries array */
427   struct amqp_table_entry_t_ *entries; /**< an array of table entries */
428 } amqp_table_t;
429 
430 /**
431  * An AMQP Field Array
432  *
433  * A repeated set of field values, all must be of the same type
434  *
435  * \since v0.1
436  */
437 typedef struct amqp_array_t_ {
438   int num_entries;                     /**< Number of entries in the table */
439   struct amqp_field_value_t_ *entries; /**< linked list of field values */
440 } amqp_array_t;
441 
442 /*
443   0-9   0-9-1   Qpid/Rabbit  Type               Remarks
444 ---------------------------------------------------------------------------
445         t       t            Boolean
446         b       b            Signed 8-bit
447         B                    Unsigned 8-bit
448         U       s            Signed 16-bit      (A1)
449         u                    Unsigned 16-bit
450   I     I       I            Signed 32-bit
451         i                    Unsigned 32-bit
452         L       l            Signed 64-bit      (B)
453         l                    Unsigned 64-bit
454         f       f            32-bit float
455         d       d            64-bit float
456   D     D       D            Decimal
457         s                    Short string       (A2)
458   S     S       S            Long string
459         A                    Nested Array
460   T     T       T            Timestamp (u64)
461   F     F       F            Nested Table
462   V     V       V            Void
463                 x            Byte array
464 
465 Remarks:
466 
467  A1, A2: Notice how the types **CONFLICT** here. In Qpid and Rabbit,
468          's' means a signed 16-bit integer; in 0-9-1, it means a
469           short string.
470 
471  B: Notice how the signednesses **CONFLICT** here. In Qpid and Rabbit,
472     'l' means a signed 64-bit integer; in 0-9-1, it means an unsigned
473     64-bit integer.
474 
475 I'm going with the Qpid/Rabbit types, where there's a conflict, and
476 the 0-9-1 types otherwise. 0-8 is a subset of 0-9, which is a subset
477 of the other two, so this will work for both 0-8 and 0-9-1 branches of
478 the code.
479 */
480 
481 /**
482  * A field table value
483  *
484  * \since v0.1
485  */
486 typedef struct amqp_field_value_t_ {
487   uint8_t kind; /**< the type of the entry /sa amqp_field_value_kind_t */
488   union {
489     amqp_boolean_t boolean; /**< boolean type AMQP_FIELD_KIND_BOOLEAN */
490     int8_t i8;              /**< int8_t type AMQP_FIELD_KIND_I8 */
491     uint8_t u8;             /**< uint8_t type AMQP_FIELD_KIND_U8 */
492     int16_t i16;            /**< int16_t type AMQP_FIELD_KIND_I16 */
493     uint16_t u16;           /**< uint16_t type AMQP_FIELD_KIND_U16 */
494     int32_t i32;            /**< int32_t type AMQP_FIELD_KIND_I32 */
495     uint32_t u32;           /**< uint32_t type AMQP_FIELD_KIND_U32 */
496     int64_t i64;            /**< int64_t type AMQP_FIELD_KIND_I64 */
497     uint64_t u64;           /**< uint64_t type AMQP_FIELD_KIND_U64,
498                                AMQP_FIELD_KIND_TIMESTAMP */
499     float f32;              /**< float type AMQP_FIELD_KIND_F32 */
500     double f64;             /**< double type AMQP_FIELD_KIND_F64 */
501     amqp_decimal_t decimal; /**< amqp_decimal_t AMQP_FIELD_KIND_DECIMAL */
502     amqp_bytes_t bytes;     /**< amqp_bytes_t type AMQP_FIELD_KIND_UTF8,
503                                AMQP_FIELD_KIND_BYTES */
504     amqp_table_t table;     /**< amqp_table_t type AMQP_FIELD_KIND_TABLE */
505     amqp_array_t array;     /**< amqp_array_t type AMQP_FIELD_KIND_ARRAY */
506   } value;                  /**< a union of the value */
507 } amqp_field_value_t;
508 
509 /**
510  * An entry in a field-table
511  *
512  * \sa amqp_table_encode(), amqp_table_decode(), amqp_table_clone()
513  *
514  * \since v0.1
515  */
516 typedef struct amqp_table_entry_t_ {
517   amqp_bytes_t key; /**< the table entry key. Its a null-terminated UTF-8
518                      * string, with a maximum size of 128 bytes */
519   amqp_field_value_t value; /**< the table entry values */
520 } amqp_table_entry_t;
521 
522 /**
523  * Field value types
524  *
525  * \since v0.1
526  */
527 typedef enum {
528   AMQP_FIELD_KIND_BOOLEAN =
529       't', /**< boolean type. 0 = false, 1 = true @see amqp_boolean_t */
530   AMQP_FIELD_KIND_I8 = 'b',  /**< 8-bit signed integer, datatype: int8_t */
531   AMQP_FIELD_KIND_U8 = 'B',  /**< 8-bit unsigned integer, datatype: uint8_t */
532   AMQP_FIELD_KIND_I16 = 's', /**< 16-bit signed integer, datatype: int16_t */
533   AMQP_FIELD_KIND_U16 = 'u', /**< 16-bit unsigned integer, datatype: uint16_t */
534   AMQP_FIELD_KIND_I32 = 'I', /**< 32-bit signed integer, datatype: int32_t */
535   AMQP_FIELD_KIND_U32 = 'i', /**< 32-bit unsigned integer, datatype: uint32_t */
536   AMQP_FIELD_KIND_I64 = 'l', /**< 64-bit signed integer, datatype: int64_t */
537   AMQP_FIELD_KIND_U64 = 'L', /**< 64-bit unsigned integer, datatype: uint64_t */
538   AMQP_FIELD_KIND_F32 =
539       'f', /**< single-precision floating point value, datatype: float */
540   AMQP_FIELD_KIND_F64 =
541       'd', /**< double-precision floating point value, datatype: double */
542   AMQP_FIELD_KIND_DECIMAL =
543       'D', /**< amqp-decimal value, datatype: amqp_decimal_t */
544   AMQP_FIELD_KIND_UTF8 = 'S',      /**< UTF-8 null-terminated character string,
545                                       datatype: amqp_bytes_t */
546   AMQP_FIELD_KIND_ARRAY = 'A',     /**< field array (repeated values of another
547                                       datatype. datatype: amqp_array_t */
548   AMQP_FIELD_KIND_TIMESTAMP = 'T', /**< 64-bit timestamp. datatype uint64_t */
549   AMQP_FIELD_KIND_TABLE = 'F', /**< field table. encapsulates a table inside a
550                                   table entry. datatype: amqp_table_t */
551   AMQP_FIELD_KIND_VOID = 'V',  /**< empty entry */
552   AMQP_FIELD_KIND_BYTES =
553       'x' /**< unformatted byte string, datatype: amqp_bytes_t */
554 } amqp_field_value_kind_t;
555 
556 /**
557  * A list of allocation blocks
558  *
559  * \since v0.1
560  */
561 typedef struct amqp_pool_blocklist_t_ {
562   int num_blocks;   /**< Number of blocks in the block list */
563   void **blocklist; /**< Array of memory blocks */
564 } amqp_pool_blocklist_t;
565 
566 /**
567  * A memory pool
568  *
569  * \since v0.1
570  */
571 typedef struct amqp_pool_t_ {
572   size_t pagesize; /**< the size of the page in bytes. Allocations less than or
573                     * equal to this size are allocated in the pages block list.
574                     * Allocations greater than this are allocated in their own
575                     * own block in the large_blocks block list */
576 
577   amqp_pool_blocklist_t pages; /**< blocks that are the size of pagesize */
578   amqp_pool_blocklist_t large_blocks; /**< allocations larger than the pagesize
579                                        */
580 
581   int next_page;     /**< an index to the next unused page block */
582   char *alloc_block; /**< pointer to the current allocation block */
583   size_t alloc_used; /**< number of bytes in the current allocation block that
584                         has been used */
585 } amqp_pool_t;
586 
587 /**
588  * An amqp method
589  *
590  * \since v0.1
591  */
592 typedef struct amqp_method_t_ {
593   amqp_method_number_t id; /**< the method id number */
594   void *decoded;           /**< pointer to the decoded method,
595                             *    cast to the appropriate type to use */
596 } amqp_method_t;
597 
598 /**
599  * An AMQP frame
600  *
601  * \since v0.1
602  */
603 typedef struct amqp_frame_t_ {
604   uint8_t frame_type;     /**< frame type. The types:
605                            * - AMQP_FRAME_METHOD - use the method union member
606                            * - AMQP_FRAME_HEADER - use the properties union member
607                            * - AMQP_FRAME_BODY - use the body_fragment union member
608                            */
609   amqp_channel_t channel; /**< the channel the frame was received on */
610   union {
611     amqp_method_t method; /**< a method, use if frame_type == AMQP_FRAME_METHOD
612                            */
613     struct {
614       uint16_t class_id;        /**< the class for the properties */
615       uint64_t body_size;       /**< size of the body in bytes */
616       void *decoded;            /**< the decoded properties */
617       amqp_bytes_t raw;         /**< amqp-encoded properties structure */
618     } properties;               /**< message header, a.k.a., properties,
619                                       use if frame_type == AMQP_FRAME_HEADER */
620     amqp_bytes_t body_fragment; /**< a body fragment, use if frame_type ==
621                                    AMQP_FRAME_BODY */
622     struct {
623       uint8_t transport_high;         /**< @internal first byte of handshake */
624       uint8_t transport_low;          /**< @internal second byte of handshake */
625       uint8_t protocol_version_major; /**< @internal third byte of handshake */
626       uint8_t protocol_version_minor; /**< @internal fourth byte of handshake */
627     } protocol_header; /**< Used only when doing the initial handshake with the
628                           broker, don't use otherwise */
629   } payload;           /**< the payload of the frame */
630 } amqp_frame_t;
631 
632 /**
633  * Response type
634  *
635  * \since v0.1
636  */
637 typedef enum amqp_response_type_enum_ {
638   AMQP_RESPONSE_NONE = 0, /**< the library got an EOF from the socket */
639   AMQP_RESPONSE_NORMAL, /**< response normal, the RPC completed successfully */
640   AMQP_RESPONSE_LIBRARY_EXCEPTION, /**< library error, an error occurred in the
641                                       library, examine the library_error */
642   AMQP_RESPONSE_SERVER_EXCEPTION   /**< server exception, the broker returned an
643                                       error, check replay */
644 } amqp_response_type_enum;
645 
646 /**
647  * Reply from a RPC method on the broker
648  *
649  * \since v0.1
650  */
651 typedef struct amqp_rpc_reply_t_ {
652   amqp_response_type_enum reply_type; /**< the reply type:
653                                        * - AMQP_RESPONSE_NORMAL - the RPC
654                                        * completed successfully
655                                        * - AMQP_RESPONSE_SERVER_EXCEPTION - the
656                                        * broker returned
657                                        *     an exception, check the reply field
658                                        * - AMQP_RESPONSE_LIBRARY_EXCEPTION - the
659                                        * library
660                                        *    encountered an error, check the
661                                        * library_error field
662                                        */
663   amqp_method_t reply; /**< in case of AMQP_RESPONSE_SERVER_EXCEPTION this
664                         * field will be set to the method returned from the
665                         * broker */
666   int library_error;   /**< in case of AMQP_RESPONSE_LIBRARY_EXCEPTION this
667                         *    field will be set to an error code. An error
668                         *     string can be retrieved using amqp_error_string */
669 } amqp_rpc_reply_t;
670 
671 /**
672  * SASL method type
673  *
674  * \since v0.1
675  */
676 typedef enum amqp_sasl_method_enum_ {
677   AMQP_SASL_METHOD_UNDEFINED = -1, /**< Invalid SASL method */
678   AMQP_SASL_METHOD_PLAIN =
679       0, /**< the PLAIN SASL method for authentication to the broker */
680   AMQP_SASL_METHOD_EXTERNAL =
681       1 /**< the EXTERNAL SASL method for authentication to the broker */
682 } amqp_sasl_method_enum;
683 
684 /**
685  * connection state object
686  *
687  * \since v0.1
688  */
689 typedef struct amqp_connection_state_t_ *amqp_connection_state_t;
690 
691 /**
692  * Socket object
693  *
694  * \since v0.4.0
695  */
696 typedef struct amqp_socket_t_ amqp_socket_t;
697 
698 /**
699  * Status codes
700  *
701  * \since v0.4.0
702  */
703 /* NOTE: When updating this enum, update the strings in librabbitmq/amqp_api.c
704  */
705 typedef enum amqp_status_enum_ {
706   AMQP_STATUS_OK = 0x0,                             /**< Operation successful */
707   AMQP_STATUS_NO_MEMORY = -0x0001,                  /**< Memory allocation
708                                                          failed */
709   AMQP_STATUS_BAD_AMQP_DATA = -0x0002,              /**< Incorrect or corrupt
710                                                          data was received from
711                                                          the broker. This is a
712                                                          protocol error. */
713   AMQP_STATUS_UNKNOWN_CLASS = -0x0003,              /**< An unknown AMQP class
714                                                          was received. This is
715                                                          a protocol error. */
716   AMQP_STATUS_UNKNOWN_METHOD = -0x0004,             /**< An unknown AMQP method
717                                                          was received. This is
718                                                          a protocol error. */
719   AMQP_STATUS_HOSTNAME_RESOLUTION_FAILED = -0x0005, /**< Unable to resolve the
720                                                      * hostname */
721   AMQP_STATUS_INCOMPATIBLE_AMQP_VERSION = -0x0006,  /**< The broker advertised
722                                                          an incompaible AMQP
723                                                          version */
724   AMQP_STATUS_CONNECTION_CLOSED = -0x0007,          /**< The connection to the
725                                                          broker has been closed
726                                                          */
727   AMQP_STATUS_BAD_URL = -0x0008,                    /**< malformed AMQP URL */
728   AMQP_STATUS_SOCKET_ERROR = -0x0009,               /**< A socket error
729                                                          occurred */
730   AMQP_STATUS_INVALID_PARAMETER = -0x000A,          /**< An invalid parameter
731                                                          was passed into the
732                                                          function */
733   AMQP_STATUS_TABLE_TOO_BIG = -0x000B,              /**< The amqp_table_t object
734                                                          cannot be serialized
735                                                          because the output
736                                                          buffer is too small */
737   AMQP_STATUS_WRONG_METHOD = -0x000C,               /**< The wrong method was
738                                                          received */
739   AMQP_STATUS_TIMEOUT = -0x000D,                    /**< Operation timed out */
740   AMQP_STATUS_TIMER_FAILURE = -0x000E,              /**< The underlying system
741                                                          timer facility failed */
742   AMQP_STATUS_HEARTBEAT_TIMEOUT = -0x000F,          /**< Timed out waiting for
743                                                          heartbeat */
744   AMQP_STATUS_UNEXPECTED_STATE = -0x0010,           /**< Unexpected protocol
745                                                          state */
746   AMQP_STATUS_SOCKET_CLOSED = -0x0011,              /**< Underlying socket is
747                                                          closed */
748   AMQP_STATUS_SOCKET_INUSE = -0x0012,               /**< Underlying socket is
749                                                          already open */
750   AMQP_STATUS_BROKER_UNSUPPORTED_SASL_METHOD = -0x0013, /**< Broker does not
751                                                           support the requested
752                                                           SASL mechanism */
753   AMQP_STATUS_UNSUPPORTED = -0x0014, /**< Parameter is unsupported
754                                        in this version */
755   _AMQP_STATUS_NEXT_VALUE = -0x0015, /**< Internal value */
756 
757   AMQP_STATUS_TCP_ERROR = -0x0100,                /**< A generic TCP error
758                                                        occurred */
759   AMQP_STATUS_TCP_SOCKETLIB_INIT_ERROR = -0x0101, /**< An error occurred trying
760                                                        to initialize the
761                                                        socket library*/
762   _AMQP_STATUS_TCP_NEXT_VALUE = -0x0102,          /**< Internal value */
763 
764   AMQP_STATUS_SSL_ERROR = -0x0200,                  /**< A generic SSL error
765                                                          occurred. */
766   AMQP_STATUS_SSL_HOSTNAME_VERIFY_FAILED = -0x0201, /**< SSL validation of
767                                                          hostname against
768                                                          peer certificate
769                                                          failed */
770   AMQP_STATUS_SSL_PEER_VERIFY_FAILED = -0x0202,     /**< SSL validation of peer
771                                                          certificate failed. */
772   AMQP_STATUS_SSL_CONNECTION_FAILED = -0x0203, /**< SSL handshake failed. */
773   AMQP_STATUS_SSL_SET_ENGINE_FAILED = -0x0204, /**< SSL setting engine failed */
774   _AMQP_STATUS_SSL_NEXT_VALUE = -0x0205        /**< Internal value */
775 } amqp_status_enum;
776 
777 /**
778  * AMQP delivery modes.
779  * Use these values for the #amqp_basic_properties_t::delivery_mode field.
780  *
781  * \since v0.5
782  */
783 typedef enum {
784   AMQP_DELIVERY_NONPERSISTENT = 1, /**< Non-persistent message */
785   AMQP_DELIVERY_PERSISTENT = 2     /**< Persistent message */
786 } amqp_delivery_mode_enum;
787 
788 AMQP_END_DECLS
789 
790 #include <amqp_framing.h>
791 
792 AMQP_BEGIN_DECLS
793 
794 /**
795  * Empty bytes structure
796  *
797  * \since v0.2
798  */
799 AMQP_PUBLIC_VARIABLE const amqp_bytes_t amqp_empty_bytes;
800 
801 /**
802  * Empty table structure
803  *
804  * \since v0.2
805  */
806 AMQP_PUBLIC_VARIABLE const amqp_table_t amqp_empty_table;
807 
808 /**
809  * Empty table array structure
810  *
811  * \since v0.2
812  */
813 AMQP_PUBLIC_VARIABLE const amqp_array_t amqp_empty_array;
814 
815 /* Compatibility macros for the above, to avoid the need to update
816    code written against earlier versions of librabbitmq. */
817 
818 /**
819  * \def AMQP_EMPTY_BYTES
820  *
821  * Deprecated, use \ref amqp_empty_bytes instead
822  *
823  * \deprecated use \ref amqp_empty_bytes instead
824  *
825  * \since v0.1
826  */
827 #define AMQP_EMPTY_BYTES amqp_empty_bytes
828 
829 /**
830  * \def AMQP_EMPTY_TABLE
831  *
832  * Deprecated, use \ref amqp_empty_table instead
833  *
834  * \deprecated use \ref amqp_empty_table instead
835  *
836  * \since v0.1
837  */
838 #define AMQP_EMPTY_TABLE amqp_empty_table
839 
840 /**
841  * \def AMQP_EMPTY_ARRAY
842  *
843  * Deprecated, use \ref amqp_empty_array instead
844  *
845  * \deprecated use \ref amqp_empty_array instead
846  *
847  * \since v0.1
848  */
849 #define AMQP_EMPTY_ARRAY amqp_empty_array
850 
851 /**
852  * Initializes an amqp_pool_t memory allocation pool for use
853  *
854  * Readies an allocation pool for use. An amqp_pool_t
855  * must be initialized before use
856  *
857  * \param [in] pool the amqp_pool_t structure to initialize.
858  *              Calling this function on a pool a pool that has
859  *              already been initialized will result in undefined
860  *              behavior
861  * \param [in] pagesize the unit size that the pool will allocate
862  *              memory chunks in. Anything allocated against the pool
863  *              with a requested size will be carved out of a block
864  *              this size. Allocations larger than this will be
865  *              allocated individually
866  *
867  * \sa recycle_amqp_pool(), empty_amqp_pool(), amqp_pool_alloc(),
868  *     amqp_pool_alloc_bytes(), amqp_pool_t
869  *
870  * \since v0.1
871  */
872 AMQP_PUBLIC_FUNCTION
873 void AMQP_CALL init_amqp_pool(amqp_pool_t *pool, size_t pagesize);
874 
875 /**
876  * Recycles an amqp_pool_t memory allocation pool
877  *
878  * Recycles the space allocate by the pool
879  *
880  * This invalidates all allocations made against the pool before this call is
881  * made, any use of any allocations made before recycle_amqp_pool() is called
882  * will result in undefined behavior.
883  *
884  * Note: this may or may not release memory, to force memory to be released
885  * call empty_amqp_pool().
886  *
887  * \param [in] pool the amqp_pool_t to recycle
888  *
889  * \sa recycle_amqp_pool(), empty_amqp_pool(), amqp_pool_alloc(),
890  *      amqp_pool_alloc_bytes()
891  *
892  * \since v0.1
893  *
894  */
895 AMQP_PUBLIC_FUNCTION
896 void AMQP_CALL recycle_amqp_pool(amqp_pool_t *pool);
897 
898 /**
899  * Empties an amqp memory pool
900  *
901  * Releases all memory associated with an allocation pool
902  *
903  * \param [in] pool the amqp_pool_t to empty
904  *
905  * \since v0.1
906  */
907 AMQP_PUBLIC_FUNCTION
908 void AMQP_CALL empty_amqp_pool(amqp_pool_t *pool);
909 
910 /**
911  * Allocates a block of memory from an amqp_pool_t memory pool
912  *
913  * Memory will be aligned on a 8-byte boundary. If a 0-length allocation is
914  * requested, a NULL pointer will be returned.
915  *
916  * \param [in] pool the allocation pool to allocate the memory from
917  * \param [in] amount the size of the allocation in bytes.
918  * \return a pointer to the memory block, or NULL if the allocation cannot
919  *          be satisfied.
920  *
921  * \sa init_amqp_pool(), recycle_amqp_pool(), empty_amqp_pool(),
922  *     amqp_pool_alloc_bytes()
923  *
924  * \since v0.1
925  */
926 AMQP_PUBLIC_FUNCTION
927 void *AMQP_CALL amqp_pool_alloc(amqp_pool_t *pool, size_t amount);
928 
929 /**
930  * Allocates a block of memory from an amqp_pool_t to an amqp_bytes_t
931  *
932  * Memory will be aligned on a 8-byte boundary. If a 0-length allocation is
933  * requested, output.bytes = NULL.
934  *
935  * \param [in] pool the allocation pool to allocate the memory from
936  * \param [in] amount the size of the allocation in bytes
937  * \param [in] output the location to store the pointer. On success
938  *              output.bytes will be set to the beginning of the buffer
939  *              output.len will be set to amount
940  *              On error output.bytes will be set to NULL and output.len
941  *              set to 0
942  *
943  * \sa init_amqp_pool(), recycle_amqp_pool(), empty_amqp_pool(),
944  *     amqp_pool_alloc()
945  *
946  * \since v0.1
947  */
948 AMQP_PUBLIC_FUNCTION
949 void AMQP_CALL amqp_pool_alloc_bytes(amqp_pool_t *pool, size_t amount,
950                                      amqp_bytes_t *output);
951 
952 /**
953  * Wraps a c string in an amqp_bytes_t
954  *
955  * Takes a string, calculates its length and creates an
956  * amqp_bytes_t that points to it. The string is not duplicated.
957  *
958  * For a given input cstr, The amqp_bytes_t output.bytes is the
959  * same as cstr, output.len is the length of the string not including
960  * the \0 terminator
961  *
962  * This function uses strlen() internally so cstr must be properly
963  * terminated
964  *
965  * \param [in] cstr the c string to wrap
966  * \return an amqp_bytes_t that describes the string
967  *
968  * \since v0.1
969  */
970 AMQP_PUBLIC_FUNCTION
971 amqp_bytes_t AMQP_CALL amqp_cstring_bytes(char const *cstr);
972 
973 /**
974  * Duplicates an amqp_bytes_t buffer.
975  *
976  * The buffer is cloned and the contents copied.
977  *
978  * The memory associated with the output is allocated
979  * with amqp_bytes_malloc() and should be freed with
980  * amqp_bytes_free()
981  *
982  * \param [in] src
983  * \return a clone of the src
984  *
985  * \sa amqp_bytes_free(), amqp_bytes_malloc()
986  *
987  * \since v0.1
988  */
989 AMQP_PUBLIC_FUNCTION
990 amqp_bytes_t AMQP_CALL amqp_bytes_malloc_dup(amqp_bytes_t src);
991 
992 /**
993  * Allocates a amqp_bytes_t buffer
994  *
995  * Creates an amqp_bytes_t buffer of the specified amount, the buffer should be
996  * freed using amqp_bytes_free()
997  *
998  * \param [in] amount the size of the buffer in bytes
999  * \returns an amqp_bytes_t with amount bytes allocated.
1000  *           output.bytes will be set to NULL on error
1001  *
1002  * \sa amqp_bytes_free(), amqp_bytes_malloc_dup()
1003  *
1004  * \since v0.1
1005  */
1006 AMQP_PUBLIC_FUNCTION
1007 amqp_bytes_t AMQP_CALL amqp_bytes_malloc(size_t amount);
1008 
1009 /**
1010  * Frees an amqp_bytes_t buffer
1011  *
1012  * Frees a buffer allocated with amqp_bytes_malloc() or amqp_bytes_malloc_dup()
1013  *
1014  * Calling amqp_bytes_free on buffers not allocated with one
1015  * of those two functions will result in undefined behavior
1016  *
1017  * \param [in] bytes the buffer to free
1018  *
1019  * \sa amqp_bytes_malloc(), amqp_bytes_malloc_dup()
1020  *
1021  * \since v0.1
1022  */
1023 AMQP_PUBLIC_FUNCTION
1024 void AMQP_CALL amqp_bytes_free(amqp_bytes_t bytes);
1025 
1026 /**
1027  * Allocate and initialize a new amqp_connection_state_t object
1028  *
1029  * amqp_connection_state_t objects created with this function
1030  * should be freed with amqp_destroy_connection()
1031  *
1032  * \returns an opaque pointer on success, NULL or 0 on failure.
1033  *
1034  * \sa amqp_destroy_connection()
1035  *
1036  * \since v0.1
1037  */
1038 AMQP_PUBLIC_FUNCTION
1039 amqp_connection_state_t AMQP_CALL amqp_new_connection(void);
1040 
1041 /**
1042  * Get the underlying socket descriptor for the connection
1043  *
1044  * \warning Use the socket returned from this function carefully, incorrect use
1045  * of the socket outside of the library will lead to undefined behavior.
1046  * Additionally rabbitmq-c may use the socket differently version-to-version,
1047  * what may work in one version, may break in the next version. Be sure to
1048  * thoroughly test any applications that use the socket returned by this
1049  * function especially when using a newer version of rabbitmq-c
1050  *
1051  * \param [in] state the connection object
1052  * \returns the socket descriptor if one has been set, -1 otherwise
1053  *
1054  * \sa amqp_tcp_socket_new(), amqp_ssl_socket_new(), amqp_socket_open()
1055  *
1056  * \since v0.1
1057  */
1058 AMQP_PUBLIC_FUNCTION
1059 int AMQP_CALL amqp_get_sockfd(amqp_connection_state_t state);
1060 
1061 /**
1062  * Deprecated, use amqp_tcp_socket_new() or amqp_ssl_socket_new()
1063  *
1064  * \deprecated Use amqp_tcp_socket_new() or amqp_ssl_socket_new()
1065  *
1066  * Sets the socket descriptor associated with the connection. The socket
1067  * should be connected to a broker, and should not be read to or written from
1068  * before calling this function.  A socket descriptor can be created and opened
1069  * using amqp_open_socket()
1070  *
1071  * \param [in] state the connection object
1072  * \param [in] sockfd the socket
1073  *
1074  * \sa amqp_open_socket(), amqp_tcp_socket_new(), amqp_ssl_socket_new()
1075  *
1076  * \since v0.1
1077  */
1078 AMQP_DEPRECATED(AMQP_PUBLIC_FUNCTION void AMQP_CALL
1079                     amqp_set_sockfd(amqp_connection_state_t state, int sockfd));
1080 
1081 /**
1082  * Tune client side parameters
1083  *
1084  * \warning This function may call abort() if the connection is in a certain
1085  *  state. As such it should probably not be called code outside the library.
1086  *  connection parameters should be specified when calling amqp_login() or
1087  *  amqp_login_with_properties()
1088  *
1089  * This function changes channel_max, frame_max, and heartbeat parameters, on
1090  * the client side only. It does not try to renegotiate these parameters with
1091  * the broker. Using this function will lead to unexpected results.
1092  *
1093  * \param [in] state the connection object
1094  * \param [in] channel_max the maximum number of channels.
1095  *              The largest this can be is 65535
1096  * \param [in] frame_max the maximum size of an frame.
1097  *              The smallest this can be is 4096
1098  *              The largest this can be is 2147483647
1099  *              Unless you know what you're doing the recommended
1100  *              size is 131072 or 128KB
1101  * \param [in] heartbeat the number of seconds between heartbeats
1102  *
1103  * \return AMQP_STATUS_OK on success, an amqp_status_enum value otherwise.
1104  *  Possible error codes include:
1105  *  - AMQP_STATUS_NO_MEMORY memory allocation failed.
1106  *  - AMQP_STATUS_TIMER_FAILURE the underlying system timer indicated it
1107  *    failed.
1108  *
1109  * \sa amqp_login(), amqp_login_with_properties()
1110  *
1111  * \since v0.1
1112  */
1113 AMQP_PUBLIC_FUNCTION
1114 int AMQP_CALL amqp_tune_connection(amqp_connection_state_t state,
1115                                    int channel_max, int frame_max,
1116                                    int heartbeat);
1117 
1118 /**
1119  * Get the maximum number of channels the connection can handle
1120  *
1121  * The maximum number of channels is set when connection negotiation takes
1122  * place in amqp_login() or amqp_login_with_properties().
1123  *
1124  * \param [in] state the connection object
1125  * \return the maximum number of channels. 0 if there is no limit
1126  *
1127  * \since v0.1
1128  */
1129 AMQP_PUBLIC_FUNCTION
1130 int AMQP_CALL amqp_get_channel_max(amqp_connection_state_t state);
1131 
1132 /**
1133  * Get the maximum size of an frame the connection can handle
1134  *
1135  * The maximum size of an frame is set when connection negotiation takes
1136  * place in amqp_login() or amqp_login_with_properties().
1137  *
1138  * \param [in] state the connection object
1139  * \return the maximum size of an frame.
1140  *
1141  * \since v0.6
1142  */
1143 AMQP_PUBLIC_FUNCTION
1144 int AMQP_CALL amqp_get_frame_max(amqp_connection_state_t state);
1145 
1146 /**
1147  * Get the number of seconds between heartbeats of the connection
1148  *
1149  * The number of seconds between heartbeats is set when connection
1150  * negotiation takes place in amqp_login() or amqp_login_with_properties().
1151  *
1152  * \param [in] state the connection object
1153  * \return the number of seconds between heartbeats.
1154  *
1155  * \since v0.6
1156  */
1157 AMQP_PUBLIC_FUNCTION
1158 int AMQP_CALL amqp_get_heartbeat(amqp_connection_state_t state);
1159 
1160 /**
1161  * Destroys an amqp_connection_state_t object
1162  *
1163  * Destroys a amqp_connection_state_t object that was created with
1164  * amqp_new_connection(). If the connection with the broker is open, it will be
1165  * implicitly closed with a reply code of 200 (success). Any memory that
1166  * would be freed with amqp_maybe_release_buffers() or
1167  * amqp_maybe_release_buffers_on_channel() will be freed, and use of that
1168  * memory will caused undefined behavior.
1169  *
1170  * \param [in] state the connection object
1171  * \return AMQP_STATUS_OK on success. amqp_status_enum value failure
1172  *
1173  * \sa amqp_new_connection()
1174  *
1175  * \since v0.1
1176  */
1177 AMQP_PUBLIC_FUNCTION
1178 int AMQP_CALL amqp_destroy_connection(amqp_connection_state_t state);
1179 
1180 /**
1181  * Process incoming data
1182  *
1183  * \warning This is a low-level function intended for those who want to
1184  *  have greater control over input and output over the socket from the
1185  *  broker. Correctly using this function requires in-depth knowledge of AMQP
1186  *  and rabbitmq-c.
1187  *
1188  * For a given buffer of data received from the broker, decode the first
1189  * frame in the buffer. If more than one frame is contained in the input buffer
1190  * the return value will be less than the received_data size, the caller should
1191  * adjust received_data buffer descriptor to point to the beginning of the
1192  * buffer + the return value.
1193  *
1194  * \param [in] state the connection object
1195  * \param [in] received_data a buffer of data received from the broker. The
1196  *  function will return the number of bytes of the buffer it used. The
1197  *  function copies these bytes to an internal buffer: this part of the buffer
1198  *  may be reused after this function successfully completes.
1199  * \param [in,out] decoded_frame caller should pass in a pointer to an
1200  *  amqp_frame_t struct. If there is enough data in received_data for a
1201  *  complete frame, decoded_frame->frame_type will be set to something OTHER
1202  *  than 0. decoded_frame may contain members pointing to memory owned by
1203  *  the state object. This memory can be recycled with
1204  *  amqp_maybe_release_buffers() or amqp_maybe_release_buffers_on_channel().
1205  * \return number of bytes consumed from received_data or 0 if a 0-length
1206  *  buffer was passed. A negative return value indicates failure. Possible
1207  * errors:
1208  *  - AMQP_STATUS_NO_MEMORY failure in allocating memory. The library is likely
1209  *    in an indeterminate state making recovery unlikely. Client should note the
1210  *    error and terminate the application
1211  *  - AMQP_STATUS_BAD_AMQP_DATA bad AMQP data was received. The connection
1212  *    should be shutdown immediately
1213  *  - AMQP_STATUS_UNKNOWN_METHOD: an unknown method was received from the
1214  *    broker. This is likely a protocol error and the connection should be
1215  *    shutdown immediately
1216  *  - AMQP_STATUS_UNKNOWN_CLASS: a properties frame with an unknown class
1217  *    was received from the broker. This is likely a protocol error and the
1218  *    connection should be shutdown immediately
1219  *
1220  * \since v0.1
1221  */
1222 AMQP_PUBLIC_FUNCTION
1223 int AMQP_CALL amqp_handle_input(amqp_connection_state_t state,
1224                                 amqp_bytes_t received_data,
1225                                 amqp_frame_t *decoded_frame);
1226 
1227 /**
1228  * Check to see if connection memory can be released
1229  *
1230  * \deprecated This function is deprecated in favor of
1231  *  amqp_maybe_release_buffers() or amqp_maybe_release_buffers_on_channel()
1232  *
1233  * Checks the state of an amqp_connection_state_t object to see if
1234  * amqp_release_buffers() can be called successfully.
1235  *
1236  * \param [in] state the connection object
1237  * \returns TRUE if the buffers can be released FALSE otherwise
1238  *
1239  * \sa amqp_release_buffers() amqp_maybe_release_buffers()
1240  *  amqp_maybe_release_buffers_on_channel()
1241  *
1242  * \since v0.1
1243  */
1244 AMQP_PUBLIC_FUNCTION
1245 amqp_boolean_t AMQP_CALL amqp_release_buffers_ok(amqp_connection_state_t state);
1246 
1247 /**
1248  * Release amqp_connection_state_t owned memory
1249  *
1250  * \deprecated This function is deprecated in favor of
1251  *  amqp_maybe_release_buffers() or amqp_maybe_release_buffers_on_channel()
1252  *
1253  * \warning caller should ensure amqp_release_buffers_ok() returns true before
1254  *  calling this function. Failure to do so may result in abort() being called.
1255  *
1256  * Release memory owned by the amqp_connection_state_t for reuse by the
1257  * library. Use of any memory returned by the library before this function is
1258  * called will result in undefined behavior.
1259  *
1260  * \note internally rabbitmq-c tries to reuse memory when possible. As a result
1261  * its possible calling this function may not have a noticeable effect on
1262  * memory usage.
1263  *
1264  * \param [in] state the connection object
1265  *
1266  * \sa amqp_release_buffers_ok() amqp_maybe_release_buffers()
1267  *  amqp_maybe_release_buffers_on_channel()
1268  *
1269  * \since v0.1
1270  */
1271 AMQP_PUBLIC_FUNCTION
1272 void AMQP_CALL amqp_release_buffers(amqp_connection_state_t state);
1273 
1274 /**
1275  * Release amqp_connection_state_t owned memory
1276  *
1277  * Release memory owned by the amqp_connection_state_t object related to any
1278  * channel, allowing reuse by the library. Use of any memory returned by the
1279  * library before this function is called with result in undefined behavior.
1280  *
1281  * \note internally rabbitmq-c tries to reuse memory when possible. As a result
1282  * its possible calling this function may not have a noticeable effect on
1283  * memory usage.
1284  *
1285  * \param [in] state the connection object
1286  *
1287  * \sa amqp_maybe_release_buffers_on_channel()
1288  *
1289  * \since v0.1
1290  */
1291 AMQP_PUBLIC_FUNCTION
1292 void AMQP_CALL amqp_maybe_release_buffers(amqp_connection_state_t state);
1293 
1294 /**
1295  * Release amqp_connection_state_t owned memory related to a channel
1296  *
1297  * Release memory owned by the amqp_connection_state_t object related to the
1298  * specified channel, allowing reuse by the library. Use of any memory returned
1299  * the library for a specific channel will result in undefined behavior.
1300  *
1301  * \note internally rabbitmq-c tries to reuse memory when possible. As a result
1302  * its possible calling this function may not have a noticeable effect on
1303  * memory usage.
1304  *
1305  * \param [in] state the connection object
1306  * \param [in] channel the channel specifier for which memory should be
1307  *  released. Note that the library does not care about the state of the
1308  *  channel when calling this function
1309  *
1310  * \sa amqp_maybe_release_buffers()
1311  *
1312  * \since v0.4.0
1313  */
1314 AMQP_PUBLIC_FUNCTION
1315 void AMQP_CALL amqp_maybe_release_buffers_on_channel(
1316     amqp_connection_state_t state, amqp_channel_t channel);
1317 
1318 /**
1319  * Send a frame to the broker
1320  *
1321  * \param [in] state the connection object
1322  * \param [in] frame the frame to send to the broker
1323  * \return AMQP_STATUS_OK on success, an amqp_status_enum value on error.
1324  *  Possible error codes:
1325  *  - AMQP_STATUS_BAD_AMQP_DATA the serialized form of the method or
1326  *    properties was too large to fit in a single AMQP frame, or the
1327  *    method contains an invalid value. The frame was not sent.
1328  *  - AMQP_STATUS_TABLE_TOO_BIG the serialized form of an amqp_table_t is
1329  *    too large to fit in a single AMQP frame. Frame was not sent.
1330  *  - AMQP_STATUS_UNKNOWN_METHOD an invalid method type was passed in
1331  *  - AMQP_STATUS_UNKNOWN_CLASS an invalid properties type was passed in
1332  *  - AMQP_STATUS_TIMER_FAILURE system timer indicated failure. The frame
1333  *    was sent
1334  *  - AMQP_STATUS_SOCKET_ERROR
1335  *  - AMQP_STATUS_SSL_ERROR
1336  *
1337  * \since v0.1
1338  */
1339 AMQP_PUBLIC_FUNCTION
1340 int AMQP_CALL amqp_send_frame(amqp_connection_state_t state,
1341                               amqp_frame_t const *frame);
1342 
1343 /**
1344  * Compare two table entries
1345  *
1346  * Works just like strcmp(), comparing two the table keys, datatype, then values
1347  *
1348  * \param [in] entry1 the entry on the left
1349  * \param [in] entry2 the entry on the right
1350  * \return 0 if entries are equal, 0 < if left is greater, 0 > if right is
1351  * greater
1352  *
1353  * \since v0.1
1354  */
1355 AMQP_PUBLIC_FUNCTION
1356 int AMQP_CALL amqp_table_entry_cmp(void const *entry1, void const *entry2);
1357 
1358 /**
1359  * Open a socket to a remote host
1360  *
1361  * \deprecated This function is deprecated in favor of amqp_socket_open()
1362  *
1363  * Looks up the hostname, then attempts to open a socket to the host using
1364  * the specified portnumber. It also sets various options on the socket to
1365  * improve performance and correctness.
1366  *
1367  * \param [in] hostname this can be a hostname or IP address.
1368  *              Both IPv4 and IPv6 are acceptable
1369  * \param [in] portnumber the port to connect on. RabbitMQ brokers
1370  *              listen on port 5672, and 5671 for SSL
1371  * \return a positive value indicates success and is the sockfd. A negative
1372  *  value (see amqp_status_enum)is returned on failure. Possible error codes:
1373  *  - AMQP_STATUS_TCP_SOCKETLIB_INIT_ERROR Initialization of underlying socket
1374  *    library failed.
1375  *  - AMQP_STATUS_HOSTNAME_RESOLUTION_FAILED hostname lookup failed.
1376  *  - AMQP_STATUS_SOCKET_ERROR a socket error occurred. errno or
1377  *    WSAGetLastError() may return more useful information.
1378  *
1379  * \note IPv6 support was added in v0.3
1380  *
1381  * \sa amqp_socket_open() amqp_set_sockfd()
1382  *
1383  * \since v0.1
1384  */
1385 AMQP_PUBLIC_FUNCTION
1386 int AMQP_CALL amqp_open_socket(char const *hostname, int portnumber);
1387 
1388 /**
1389  * Send initial AMQP header to the broker
1390  *
1391  * \warning this is a low level function intended for those who want to
1392  * interact with the broker at a very low level. Use of this function without
1393  * understanding what it does will result in AMQP protocol errors.
1394  *
1395  * This function sends the AMQP protocol header to the broker.
1396  *
1397  * \param [in] state the connection object
1398  * \return AMQP_STATUS_OK on success, a negative value on failure. Possible
1399  *  error codes:
1400  * - AMQP_STATUS_CONNECTION_CLOSED the connection to the broker was closed.
1401  * - AMQP_STATUS_SOCKET_ERROR a socket error occurred. It is likely the
1402  *   underlying socket has been closed. errno or WSAGetLastError() may provide
1403  *   further information.
1404  * - AMQP_STATUS_SSL_ERROR a SSL error occurred. The connection to the broker
1405  *   was closed.
1406  *
1407  * \since v0.1
1408  */
1409 AMQP_PUBLIC_FUNCTION
1410 int AMQP_CALL amqp_send_header(amqp_connection_state_t state);
1411 
1412 /**
1413  * Checks to see if there are any incoming frames ready to be read
1414  *
1415  * Checks to see if there are any amqp_frame_t objects buffered by the
1416  * amqp_connection_state_t object. Having one or more frames buffered means
1417  * that amqp_simple_wait_frame() or amqp_simple_wait_frame_noblock() will
1418  * return a frame without potentially blocking on a read() call.
1419  *
1420  * \param [in] state the connection object
1421  * \return TRUE if there are frames enqueued, FALSE otherwise
1422  *
1423  * \sa amqp_simple_wait_frame() amqp_simple_wait_frame_noblock()
1424  *  amqp_data_in_buffer()
1425  *
1426  * \since v0.1
1427  */
1428 AMQP_PUBLIC_FUNCTION
1429 amqp_boolean_t AMQP_CALL amqp_frames_enqueued(amqp_connection_state_t state);
1430 
1431 /**
1432  * Read a single amqp_frame_t
1433  *
1434  * Waits for the next amqp_frame_t frame to be read from the broker.
1435  * This function has the potential to block for a long time in the case of
1436  * waiting for a basic.deliver method frame from the broker.
1437  *
1438  * The library may buffer frames. When an amqp_connection_state_t object
1439  * has frames buffered calling amqp_simple_wait_frame() will return an
1440  * amqp_frame_t without entering a blocking read(). You can test to see if
1441  * an amqp_connection_state_t object has frames buffered by calling the
1442  * amqp_frames_enqueued() function.
1443  *
1444  * The library has a socket read buffer. When there is data in an
1445  * amqp_connection_state_t read buffer, amqp_simple_wait_frame() may return an
1446  * amqp_frame_t without entering a blocking read(). You can test to see if an
1447  * amqp_connection_state_t object has data in its read buffer by calling the
1448  * amqp_data_in_buffer() function.
1449  *
1450  * \param [in] state the connection object
1451  * \param [out] decoded_frame the frame
1452  * \return AMQP_STATUS_OK on success, an amqp_status_enum value
1453  *  is returned otherwise. Possible errors include:
1454  *  - AMQP_STATUS_NO_MEMORY failure in allocating memory. The library is likely
1455  *    in an indeterminate state making recovery unlikely. Client should note the
1456  *    error and terminate the application
1457  *  - AMQP_STATUS_BAD_AMQP_DATA bad AMQP data was received. The connection
1458  *    should be shutdown immediately
1459  *  - AMQP_STATUS_UNKNOWN_METHOD: an unknown method was received from the
1460  *    broker. This is likely a protocol error and the connection should be
1461  *    shutdown immediately
1462  *  - AMQP_STATUS_UNKNOWN_CLASS: a properties frame with an unknown class
1463  *    was received from the broker. This is likely a protocol error and the
1464  *    connection should be shutdown immediately
1465  *  - AMQP_STATUS_HEARTBEAT_TIMEOUT timed out while waiting for heartbeat
1466  *    from the broker. The connection has been closed.
1467  *  - AMQP_STATUS_TIMER_FAILURE system timer indicated failure.
1468  *  - AMQP_STATUS_SOCKET_ERROR a socket error occurred. The connection has
1469  *    been closed
1470  *  - AMQP_STATUS_SSL_ERROR a SSL socket error occurred. The connection has
1471  *    been closed.
1472  *
1473  * \sa amqp_simple_wait_frame_noblock() amqp_frames_enqueued()
1474  *  amqp_data_in_buffer()
1475  *
1476  * \note as of v0.4.0 this function will no longer return heartbeat frames
1477  *  when enabled by specifying a non-zero heartbeat value in amqp_login().
1478  *  Heartbeating is handled internally by the library.
1479  *
1480  * \since v0.1
1481  */
1482 AMQP_PUBLIC_FUNCTION
1483 int AMQP_CALL amqp_simple_wait_frame(amqp_connection_state_t state,
1484                                      amqp_frame_t *decoded_frame);
1485 
1486 /**
1487  * Read a single amqp_frame_t with a timeout.
1488  *
1489  * Waits for the next amqp_frame_t frame to be read from the broker, up to
1490  * a timespan specified by tv. The function will return AMQP_STATUS_TIMEOUT
1491  * if the timeout is reached. The tv value is not modified by the function.
1492  *
1493  * If a 0 timeval is specified, the function behaves as if its non-blocking: it
1494  * will test to see if a frame can be read from the broker, and return
1495  * immediately.
1496  *
1497  * If NULL is passed in for tv, the function will behave like
1498  * amqp_simple_wait_frame() and block until a frame is received from the broker
1499  *
1500  * The library may buffer frames.  When an amqp_connection_state_t object
1501  * has frames buffered calling amqp_simple_wait_frame_noblock() will return an
1502  * amqp_frame_t without entering a blocking read(). You can test to see if an
1503  * amqp_connection_state_t object has frames buffered by calling the
1504  * amqp_frames_enqueued() function.
1505  *
1506  * The library has a socket read buffer. When there is data in an
1507  * amqp_connection_state_t read buffer, amqp_simple_wait_frame_noblock() may
1508  * return
1509  * an amqp_frame_t without entering a blocking read(). You can test to see if an
1510  * amqp_connection_state_t object has data in its read buffer by calling the
1511  * amqp_data_in_buffer() function.
1512  *
1513  * \note This function does not return heartbeat frames. When enabled,
1514  *  heartbeating is handled internally by the library.
1515  *
1516  * \param [in,out] state the connection object
1517  * \param [out] decoded_frame the frame
1518  * \param [in] tv the maximum time to wait for a frame to be read. Setting
1519  * tv->tv_sec = 0 and tv->tv_usec = 0 will do a non-blocking read. Specifying
1520  * NULL for tv will make the function block until a frame is read.
1521  * \return AMQP_STATUS_OK on success. An amqp_status_enum value is returned
1522  *  otherwise. Possible errors include:
1523  *  - AMQP_STATUS_TIMEOUT the timeout was reached while waiting for a frame
1524  *    from the broker.
1525  *  - AMQP_STATUS_INVALID_PARAMETER the tv parameter contains an invalid value.
1526  *  - AMQP_STATUS_NO_MEMORY failure in allocating memory. The library is likely
1527  *    in an indeterminate state making recovery unlikely. Client should note the
1528  *    error and terminate the application
1529  *  - AMQP_STATUS_BAD_AMQP_DATA bad AMQP data was received. The connection
1530  *    should be shutdown immediately
1531  *  - AMQP_STATUS_UNKNOWN_METHOD: an unknown method was received from the
1532  *    broker. This is likely a protocol error and the connection should be
1533  *    shutdown immediately
1534  *  - AMQP_STATUS_UNKNOWN_CLASS: a properties frame with an unknown class
1535  *    was received from the broker. This is likely a protocol error and the
1536  *    connection should be shutdown immediately
1537  *  - AMQP_STATUS_HEARTBEAT_TIMEOUT timed out while waiting for heartbeat
1538  *    from the broker. The connection has been closed.
1539  *  - AMQP_STATUS_TIMER_FAILURE system timer indicated failure.
1540  *  - AMQP_STATUS_SOCKET_ERROR a socket error occurred. The connection has
1541  *    been closed
1542  *  - AMQP_STATUS_SSL_ERROR a SSL socket error occurred. The connection has
1543  *    been closed.
1544  *
1545  * \sa amqp_simple_wait_frame() amqp_frames_enqueued() amqp_data_in_buffer()
1546  *
1547  * \since v0.4.0
1548  */
1549 AMQP_PUBLIC_FUNCTION
1550 int AMQP_CALL amqp_simple_wait_frame_noblock(amqp_connection_state_t state,
1551                                              amqp_frame_t *decoded_frame,
1552                                              const struct timeval *tv);
1553 
1554 /**
1555  * Waits for a specific method from the broker
1556  *
1557  * \warning You probably don't want to use this function. If this function
1558  *  doesn't receive exactly the frame requested it closes the whole connection.
1559  *
1560  * Waits for a single method on a channel from the broker.
1561  * If a frame is received that does not match expected_channel
1562  * or expected_method the program will abort
1563  *
1564  * \param [in] state the connection object
1565  * \param [in] expected_channel the channel that the method should be delivered
1566  *  on
1567  * \param [in] expected_method the method to wait for
1568  * \param [out] output the method
1569  * \returns AMQP_STATUS_OK on success. An amqp_status_enum value is returned
1570  *  otherwise. Possible errors include:
1571  *  - AMQP_STATUS_WRONG_METHOD a frame containing the wrong method, wrong frame
1572  *    type or wrong channel was received. The connection is closed.
1573  *  - AMQP_STATUS_NO_MEMORY failure in allocating memory. The library is likely
1574  *    in an indeterminate state making recovery unlikely. Client should note the
1575  *    error and terminate the application
1576  *  - AMQP_STATUS_BAD_AMQP_DATA bad AMQP data was received. The connection
1577  *    should be shutdown immediately
1578  *  - AMQP_STATUS_UNKNOWN_METHOD: an unknown method was received from the
1579  *    broker. This is likely a protocol error and the connection should be
1580  *    shutdown immediately
1581  *  - AMQP_STATUS_UNKNOWN_CLASS: a properties frame with an unknown class
1582  *    was received from the broker. This is likely a protocol error and the
1583  *    connection should be shutdown immediately
1584  *  - AMQP_STATUS_HEARTBEAT_TIMEOUT timed out while waiting for heartbeat
1585  *    from the broker. The connection has been closed.
1586  *  - AMQP_STATUS_TIMER_FAILURE system timer indicated failure.
1587  *  - AMQP_STATUS_SOCKET_ERROR a socket error occurred. The connection has
1588  *    been closed
1589  *  - AMQP_STATUS_SSL_ERROR a SSL socket error occurred. The connection has
1590  *    been closed.
1591  *
1592  * \since v0.1
1593  */
1594 
1595 AMQP_PUBLIC_FUNCTION
1596 int AMQP_CALL amqp_simple_wait_method(amqp_connection_state_t state,
1597                                       amqp_channel_t expected_channel,
1598                                       amqp_method_number_t expected_method,
1599                                       amqp_method_t *output);
1600 
1601 /**
1602  * Sends a method to the broker
1603  *
1604  * This is a thin wrapper around amqp_send_frame(), providing a way to send
1605  * a method to the broker on a specified channel.
1606  *
1607  * \param [in] state the connection object
1608  * \param [in] channel the channel object
1609  * \param [in] id the method number
1610  * \param [in] decoded the method object
1611  * \returns AMQP_STATUS_OK on success, an amqp_status_enum value otherwise.
1612  *  Possible errors include:
1613  *  - AMQP_STATUS_BAD_AMQP_DATA the serialized form of the method or
1614  *    properties was too large to fit in a single AMQP frame, or the
1615  *    method contains an invalid value. The frame was not sent.
1616  *  - AMQP_STATUS_TABLE_TOO_BIG the serialized form of an amqp_table_t is
1617  *    too large to fit in a single AMQP frame. Frame was not sent.
1618  *  - AMQP_STATUS_UNKNOWN_METHOD an invalid method type was passed in
1619  *  - AMQP_STATUS_UNKNOWN_CLASS an invalid properties type was passed in
1620  *  - AMQP_STATUS_TIMER_FAILURE system timer indicated failure. The frame
1621  *    was sent
1622  *  - AMQP_STATUS_SOCKET_ERROR
1623  *  - AMQP_STATUS_SSL_ERROR
1624  *
1625  * \since v0.1
1626  */
1627 AMQP_PUBLIC_FUNCTION
1628 int AMQP_CALL amqp_send_method(amqp_connection_state_t state,
1629                                amqp_channel_t channel, amqp_method_number_t id,
1630                                void *decoded);
1631 
1632 /**
1633  * Sends a method to the broker and waits for a method response
1634  *
1635  * \param [in] state the connection object
1636  * \param [in] channel the channel object
1637  * \param [in] request_id the method number of the request
1638  * \param [in] expected_reply_ids a 0 terminated array of expected response
1639  *             method numbers
1640  * \param [in] decoded_request_method the method to be sent to the broker
1641  * \return a amqp_rpc_reply_t:
1642  *  - r.reply_type == AMQP_RESPONSE_NORMAL. RPC completed successfully
1643  *  - r.reply_type == AMQP_RESPONSE_SERVER_EXCEPTION. The broker returned an
1644  *    exception:
1645  *    - If r.reply.id == AMQP_CHANNEL_CLOSE_METHOD a channel exception
1646  *      occurred, cast r.reply.decoded to amqp_channel_close_t* to see details
1647  *      of the exception. The client should amqp_send_method() a
1648  *      amqp_channel_close_ok_t. The channel must be re-opened before it
1649  *      can be used again. Any resources associated with the channel
1650  *      (auto-delete exchanges, auto-delete queues, consumers) are invalid
1651  *      and must be recreated before attempting to use them again.
1652  *    - If r.reply.id == AMQP_CONNECTION_CLOSE_METHOD a connection exception
1653  *      occurred, cast r.reply.decoded to amqp_connection_close_t* to see
1654  *      details of the exception. The client amqp_send_method() a
1655  *      amqp_connection_close_ok_t and disconnect from the broker.
1656  *  - r.reply_type == AMQP_RESPONSE_LIBRARY_EXCEPTION. An exception occurred
1657  *    within the library. Examine r.library_error and compare it against
1658  *    amqp_status_enum values to determine the error.
1659  *
1660  * \sa amqp_simple_rpc_decoded()
1661  *
1662  * \since v0.1
1663  */
1664 AMQP_PUBLIC_FUNCTION
1665 amqp_rpc_reply_t AMQP_CALL amqp_simple_rpc(
1666     amqp_connection_state_t state, amqp_channel_t channel,
1667     amqp_method_number_t request_id, amqp_method_number_t *expected_reply_ids,
1668     void *decoded_request_method);
1669 
1670 /**
1671  * Sends a method to the broker and waits for a method response
1672  *
1673  * \param [in] state the connection object
1674  * \param [in] channel the channel object
1675  * \param [in] request_id the method number of the request
1676  * \param [in] reply_id the method number expected in response
1677  * \param [in] decoded_request_method the request method
1678  * \return a pointer to the method returned from the broker, or NULL on error.
1679  *  On error amqp_get_rpc_reply() will return an amqp_rpc_reply_t with
1680  *  details on the error that occurred.
1681  *
1682  * \since v0.1
1683  */
1684 AMQP_PUBLIC_FUNCTION
1685 void *AMQP_CALL amqp_simple_rpc_decoded(amqp_connection_state_t state,
1686                                         amqp_channel_t channel,
1687                                         amqp_method_number_t request_id,
1688                                         amqp_method_number_t reply_id,
1689                                         void *decoded_request_method);
1690 
1691 /**
1692  * Get the last global amqp_rpc_reply
1693  *
1694  * The API methods corresponding to most synchronous AMQP methods
1695  * return a pointer to the decoded method result.  Upon error, they
1696  * return NULL, and we need some way of discovering what, if anything,
1697  * went wrong. amqp_get_rpc_reply() returns the most recent
1698  * amqp_rpc_reply_t instance corresponding to such an API operation
1699  * for the given connection.
1700  *
1701  * Only use it for operations that do not themselves return
1702  * amqp_rpc_reply_t; operations that do return amqp_rpc_reply_t
1703  * generally do NOT update this per-connection-global amqp_rpc_reply_t
1704  * instance.
1705  *
1706  * \param [in] state the connection object
1707  * \return the most recent amqp_rpc_reply_t:
1708  *  - r.reply_type == AMQP_RESPONSE_NORMAL. RPC completed successfully
1709  *  - r.reply_type == AMQP_RESPONSE_SERVER_EXCEPTION. The broker returned an
1710  *    exception:
1711  *    - If r.reply.id == AMQP_CHANNEL_CLOSE_METHOD a channel exception
1712  *      occurred, cast r.reply.decoded to amqp_channel_close_t* to see details
1713  *      of the exception. The client should amqp_send_method() a
1714  *      amqp_channel_close_ok_t. The channel must be re-opened before it
1715  *      can be used again. Any resources associated with the channel
1716  *      (auto-delete exchanges, auto-delete queues, consumers) are invalid
1717  *      and must be recreated before attempting to use them again.
1718  *    - If r.reply.id == AMQP_CONNECTION_CLOSE_METHOD a connection exception
1719  *      occurred, cast r.reply.decoded to amqp_connection_close_t* to see
1720  *      details of the exception. The client amqp_send_method() a
1721  *      amqp_connection_close_ok_t and disconnect from the broker.
1722  *  - r.reply_type == AMQP_RESPONSE_LIBRARY_EXCEPTION. An exception occurred
1723  *    within the library. Examine r.library_error and compare it against
1724  *    amqp_status_enum values to determine the error.
1725  *
1726  * \sa amqp_simple_rpc_decoded()
1727  *
1728  * \since v0.1
1729  */
1730 AMQP_PUBLIC_FUNCTION
1731 amqp_rpc_reply_t AMQP_CALL amqp_get_rpc_reply(amqp_connection_state_t state);
1732 
1733 /**
1734  * Login to the broker
1735  *
1736  * After using amqp_open_socket and amqp_set_sockfd, call
1737  * amqp_login to complete connecting to the broker
1738  *
1739  * \param [in] state the connection object
1740  * \param [in] vhost the virtual host to connect to on the broker. The default
1741  *              on most brokers is "/"
1742  * \param [in] channel_max the limit for number of channels for the connection.
1743  *              0 means no limit, and is a good default
1744  *              (AMQP_DEFAULT_MAX_CHANNELS)
1745  *              Note that the maximum number of channels the protocol supports
1746  *              is 65535 (2^16, with the 0-channel reserved). The server can
1747  *              set a lower channel_max and then the client will use the lowest
1748  *              of the two
1749  * \param [in] frame_max the maximum size of an AMQP frame on the wire to
1750  *              request of the broker for this connection. 4096 is the minimum
1751  *              size, 2^31-1 is the maximum, a good default is 131072 (128KB),
1752  *              or AMQP_DEFAULT_FRAME_SIZE
1753  * \param [in] heartbeat the number of seconds between heartbeat frames to
1754  *              request of the broker. A value of 0 disables heartbeats.
1755  *              Note rabbitmq-c only has partial support for heartbeats, as of
1756  *              v0.4.0 they are only serviced during amqp_basic_publish() and
1757  *              amqp_simple_wait_frame()/amqp_simple_wait_frame_noblock()
1758  * \param [in] sasl_method the SASL method to authenticate with the broker.
1759  *              followed by the authentication information. The following SASL
1760  *              methods are implemented:
1761  *              -  AMQP_SASL_METHOD_PLAIN, the AMQP_SASL_METHOD_PLAIN argument
1762  *                 should be followed by two arguments in this order:
1763  *                 const char* username, and const char* password.
1764  *              -  AMQP_SASL_METHOD_EXTERNAL, the AMQP_SASL_METHOD_EXTERNAL
1765  *                 argument should be followed one argument:
1766  *                 const char* identity.
1767  * \return amqp_rpc_reply_t indicating success or failure.
1768  *  - r.reply_type == AMQP_RESPONSE_NORMAL. Login completed successfully
1769  *  - r.reply_type == AMQP_RESPONSE_LIBRARY_EXCEPTION. In most cases errors
1770  *    from the broker when logging in will be represented by the broker closing
1771  *    the socket. In this case r.library_error will be set to
1772  *    AMQP_STATUS_CONNECTION_CLOSED. This error can represent a number of
1773  *    error conditions including: invalid vhost, authentication failure.
1774  *  - r.reply_type == AMQP_RESPONSE_SERVER_EXCEPTION. The broker returned an
1775  *    exception:
1776  *    - If r.reply.id == AMQP_CHANNEL_CLOSE_METHOD a channel exception
1777  *      occurred, cast r.reply.decoded to amqp_channel_close_t* to see details
1778  *      of the exception. The client should amqp_send_method() a
1779  *      amqp_channel_close_ok_t. The channel must be re-opened before it
1780  *      can be used again. Any resources associated with the channel
1781  *      (auto-delete exchanges, auto-delete queues, consumers) are invalid
1782  *      and must be recreated before attempting to use them again.
1783  *    - If r.reply.id == AMQP_CONNECTION_CLOSE_METHOD a connection exception
1784  *      occurred, cast r.reply.decoded to amqp_connection_close_t* to see
1785  *      details of the exception. The client amqp_send_method() a
1786  *      amqp_connection_close_ok_t and disconnect from the broker.
1787  *
1788  * \since v0.1
1789  */
1790 AMQP_PUBLIC_FUNCTION
1791 amqp_rpc_reply_t AMQP_CALL amqp_login(amqp_connection_state_t state,
1792                                       char const *vhost, int channel_max,
1793                                       int frame_max, int heartbeat,
1794                                       amqp_sasl_method_enum sasl_method, ...);
1795 
1796 /**
1797  * Login to the broker passing a properties table
1798  *
1799  * This function is similar to amqp_login() and differs in that it provides a
1800  * way to pass client properties to the broker. This is commonly used to
1801  * negotiate newer protocol features as they are supported by the broker.
1802  *
1803  * \param [in] state the connection object
1804  * \param [in] vhost the virtual host to connect to on the broker. The default
1805  *              on most brokers is "/"
1806  * \param [in] channel_max the limit for the number of channels for the
1807  *             connection.
1808  *             0 means no limit, and is a good default
1809  *             (AMQP_DEFAULT_MAX_CHANNELS)
1810  *             Note that the maximum number of channels the protocol supports
1811  *             is 65535 (2^16, with the 0-channel reserved). The server can
1812  *             set a lower channel_max and then the client will use the lowest
1813  *             of the two
1814  * \param [in] frame_max the maximum size of an AMQP frame ont he wire to
1815  *              request of the broker for this connection. 4096 is the minimum
1816  *              size, 2^31-1 is the maximum, a good default is 131072 (128KB),
1817  *              or AMQP_DEFAULT_FRAME_SIZE
1818  * \param [in] heartbeat the number of seconds between heartbeat frame to
1819  *             request of the broker. A value of 0 disables heartbeats.
1820  *             Note rabbitmq-c only has partial support for hearts, as of
1821  *             v0.4.0 heartbeats are only serviced during amqp_basic_publish(),
1822  *             and amqp_simple_wait_frame()/amqp_simple_wait_frame_noblock()
1823  * \param [in] properties a table of properties to send the broker.
1824  * \param [in] sasl_method the SASL method to authenticate with the broker
1825  *             followed by the authentication information. The following SASL
1826  *             methods are implemented:
1827  *             -  AMQP_SASL_METHOD_PLAIN, the AMQP_SASL_METHOD_PLAIN argument
1828  *                should be followed by two arguments in this order:
1829  *                const char* username, and const char* password.
1830  *             -  AMQP_SASL_METHOD_EXTERNAL, the AMQP_SASL_METHOD_EXTERNAL
1831  *                argument should be followed one argument:
1832  *                const char* identity.
1833  * \return amqp_rpc_reply_t indicating success or failure.
1834  *  - r.reply_type == AMQP_RESPONSE_NORMAL. Login completed successfully
1835  *  - r.reply_type == AMQP_RESPONSE_LIBRARY_EXCEPTION. In most cases errors
1836  *    from the broker when logging in will be represented by the broker closing
1837  *    the socket. In this case r.library_error will be set to
1838  *    AMQP_STATUS_CONNECTION_CLOSED. This error can represent a number of
1839  *    error conditions including: invalid vhost, authentication failure.
1840  *  - r.reply_type == AMQP_RESPONSE_SERVER_EXCEPTION. The broker returned an
1841  *    exception:
1842  *    - If r.reply.id == AMQP_CHANNEL_CLOSE_METHOD a channel exception
1843  *      occurred, cast r.reply.decoded to amqp_channel_close_t* to see details
1844  *      of the exception. The client should amqp_send_method() a
1845  *      amqp_channel_close_ok_t. The channel must be re-opened before it
1846  *      can be used again. Any resources associated with the channel
1847  *      (auto-delete exchanges, auto-delete queues, consumers) are invalid
1848  *      and must be recreated before attempting to use them again.
1849  *    - If r.reply.id == AMQP_CONNECTION_CLOSE_METHOD a connection exception
1850  *      occurred, cast r.reply.decoded to amqp_connection_close_t* to see
1851  *      details of the exception. The client amqp_send_method() a
1852  *      amqp_connection_close_ok_t and disconnect from the broker.
1853  *
1854  * \since v0.4.0
1855  */
1856 AMQP_PUBLIC_FUNCTION
1857 amqp_rpc_reply_t AMQP_CALL amqp_login_with_properties(
1858     amqp_connection_state_t state, char const *vhost, int channel_max,
1859     int frame_max, int heartbeat, const amqp_table_t *properties,
1860     amqp_sasl_method_enum sasl_method, ...);
1861 
1862 struct amqp_basic_properties_t_;
1863 
1864 /**
1865  * Publish a message to the broker
1866  *
1867  * Publish a message on an exchange with a routing key.
1868  *
1869  * Note that at the AMQ protocol level basic.publish is an async method:
1870  * this means error conditions that occur on the broker (such as publishing to
1871  * a non-existent exchange) will not be reflected in the return value of this
1872  * function.
1873  *
1874  * \param [in] state the connection object
1875  * \param [in] channel the channel identifier
1876  * \param [in] exchange the exchange on the broker to publish to
1877  * \param [in] routing_key the routing key to use when publishing the message
1878  * \param [in] mandatory indicate to the broker that the message MUST be routed
1879  *              to a queue. If the broker cannot do this it should respond with
1880  *              a basic.return method.
1881  * \param [in] immediate indicate to the broker that the message MUST be
1882  *             delivered to a consumer immediately. If the broker cannot do this
1883  *             it should respond with a basic.return method.
1884  * \param [in] properties the properties associated with the message
1885  * \param [in] body the message body
1886  * \return AMQP_STATUS_OK on success, amqp_status_enum value on failure. Note
1887  *         that basic.publish is an async method, the return value from this
1888  *         function only indicates that the message data was successfully
1889  *         transmitted to the broker. It does not indicate failures that occur
1890  *         on the broker, such as publishing to a non-existent exchange.
1891  *         Possible error values:
1892  *         - AMQP_STATUS_TIMER_FAILURE: system timer facility returned an error
1893  *           the message was not sent.
1894  *         - AMQP_STATUS_HEARTBEAT_TIMEOUT: connection timed out waiting for a
1895  *           heartbeat from the broker. The message was not sent.
1896  *         - AMQP_STATUS_NO_MEMORY: memory allocation failed. The message was
1897  *           not sent.
1898  *         - AMQP_STATUS_TABLE_TOO_BIG: a table in the properties was too large
1899  *           to fit in a single frame. Message was not sent.
1900  *         - AMQP_STATUS_CONNECTION_CLOSED: the connection was closed.
1901  *         - AMQP_STATUS_SSL_ERROR: a SSL error occurred.
1902  *         - AMQP_STATUS_TCP_ERROR: a TCP error occurred. errno or
1903  *           WSAGetLastError() may provide more information
1904  *
1905  * Note: this function does heartbeat processing as of v0.4.0
1906  *
1907  * \since v0.1
1908  */
1909 AMQP_PUBLIC_FUNCTION
1910 int AMQP_CALL amqp_basic_publish(
1911     amqp_connection_state_t state, amqp_channel_t channel,
1912     amqp_bytes_t exchange, amqp_bytes_t routing_key, amqp_boolean_t mandatory,
1913     amqp_boolean_t immediate, struct amqp_basic_properties_t_ const *properties,
1914     amqp_bytes_t body);
1915 
1916 /**
1917  * Closes an channel
1918  *
1919  * \param [in] state the connection object
1920  * \param [in] channel the channel identifier
1921  * \param [in] code the reason for closing the channel, AMQP_REPLY_SUCCESS is a
1922  *             good default
1923  * \return amqp_rpc_reply_t indicating success or failure
1924  *
1925  * \since v0.1
1926  */
1927 AMQP_PUBLIC_FUNCTION
1928 amqp_rpc_reply_t AMQP_CALL amqp_channel_close(amqp_connection_state_t state,
1929                                               amqp_channel_t channel, int code);
1930 
1931 /**
1932  * Closes the entire connection
1933  *
1934  * Implicitly closes all channels and informs the broker the connection
1935  * is being closed, after receiving acknowledgment from the broker it closes
1936  * the socket.
1937  *
1938  * \param [in] state the connection object
1939  * \param [in] code the reason code for closing the connection.
1940  *             AMQP_REPLY_SUCCESS is a good default.
1941  * \return amqp_rpc_reply_t indicating the result
1942  *
1943  * \since v0.1
1944  */
1945 AMQP_PUBLIC_FUNCTION
1946 amqp_rpc_reply_t AMQP_CALL amqp_connection_close(amqp_connection_state_t state,
1947                                                  int code);
1948 
1949 /**
1950  * Acknowledges a message
1951  *
1952  * Does a basic.ack on a received message
1953  *
1954  * \param [in] state the connection object
1955  * \param [in] channel the channel identifier
1956  * \param [in] delivery_tag the delivery tag of the message to be ack'd
1957  * \param [in] multiple if true, ack all messages up to this delivery tag, if
1958  *              false ack only this delivery tag
1959  * \return 0 on success,  0 > on failing to send the ack to the broker.
1960  *            this will not indicate failure if something goes wrong on the
1961  *            broker
1962  *
1963  * \since v0.1
1964  */
1965 AMQP_PUBLIC_FUNCTION
1966 int AMQP_CALL amqp_basic_ack(amqp_connection_state_t state,
1967                              amqp_channel_t channel, uint64_t delivery_tag,
1968                              amqp_boolean_t multiple);
1969 
1970 /**
1971  * Do a basic.get
1972  *
1973  * Synchonously polls the broker for a message in a queue, and
1974  * retrieves the message if a message is in the queue.
1975  *
1976  * \param [in] state the connection object
1977  * \param [in] channel the channel identifier to use
1978  * \param [in] queue the queue name to retrieve from
1979  * \param [in] no_ack if true the message is automatically ack'ed
1980  *              if false amqp_basic_ack should be called once the message
1981  *              retrieved has been processed
1982  * \return amqp_rpc_reply indicating success or failure
1983  *
1984  * \since v0.1
1985  */
1986 AMQP_PUBLIC_FUNCTION
1987 amqp_rpc_reply_t AMQP_CALL amqp_basic_get(amqp_connection_state_t state,
1988                                           amqp_channel_t channel,
1989                                           amqp_bytes_t queue,
1990                                           amqp_boolean_t no_ack);
1991 
1992 /**
1993  * Do a basic.reject
1994  *
1995  * Actively reject a message that has been delivered
1996  *
1997  * \param [in] state the connection object
1998  * \param [in] channel the channel identifier
1999  * \param [in] delivery_tag the delivery tag of the message to reject
2000  * \param [in] requeue indicate to the broker whether it should requeue the
2001  *              message or just discard it.
2002  * \return 0 on success, 0 > on failing to send the reject method to the broker.
2003  *          This will not indicate failure if something goes wrong on the
2004  * broker.
2005  *
2006  * \since v0.1
2007  */
2008 AMQP_PUBLIC_FUNCTION
2009 int AMQP_CALL amqp_basic_reject(amqp_connection_state_t state,
2010                                 amqp_channel_t channel, uint64_t delivery_tag,
2011                                 amqp_boolean_t requeue);
2012 
2013 /**
2014  * Do a basic.nack
2015  *
2016  * Actively reject a message, this has the same effect as amqp_basic_reject()
2017  * however, amqp_basic_nack() can negatively acknowledge multiple messages with
2018  * one call much like amqp_basic_ack() can acknowledge mutliple messages with
2019  * one call.
2020  *
2021  * \param [in] state the connection object
2022  * \param [in] channel the channel identifier
2023  * \param [in] delivery_tag the delivery tag of the message to reject
2024  * \param [in] multiple if set to 1 negatively acknowledge all unacknowledged
2025  *              messages on this channel.
2026  * \param [in] requeue indicate to the broker whether it should requeue the
2027  *              message or dead-letter it.
2028  * \return AMQP_STATUS_OK on success, an amqp_status_enum value otherwise.
2029  *
2030  * \since v0.5.0
2031  */
2032 AMQP_PUBLIC_FUNCTION
2033 int AMQP_CALL amqp_basic_nack(amqp_connection_state_t state,
2034                               amqp_channel_t channel, uint64_t delivery_tag,
2035                               amqp_boolean_t multiple, amqp_boolean_t requeue);
2036 /**
2037  * Check to see if there is data left in the receive buffer
2038  *
2039  * Can be used to see if there is data still in the buffer, if so
2040  * calling amqp_simple_wait_frame will not immediately enter a
2041  * blocking read.
2042  *
2043  * \param [in] state the connection object
2044  * \return true if there is data in the recieve buffer, false otherwise
2045  *
2046  * \since v0.1
2047  */
2048 AMQP_PUBLIC_FUNCTION
2049 amqp_boolean_t AMQP_CALL amqp_data_in_buffer(amqp_connection_state_t state);
2050 
2051 /**
2052  * Get the error string for the given error code.
2053  *
2054  * \deprecated This function has been deprecated in favor of
2055  *  \ref amqp_error_string2() which returns statically allocated
2056  *  string which do not need to be freed by the caller.
2057  *
2058  * The returned string resides on the heap; the caller is responsible
2059  * for freeing it.
2060  *
2061  * \param [in] err return error code
2062  * \return the error string
2063  *
2064  * \since v0.1
2065  */
2066 AMQP_DEPRECATED(
2067     AMQP_PUBLIC_FUNCTION char *AMQP_CALL amqp_error_string(int err));
2068 
2069 /**
2070  * Get the error string for the given error code.
2071  *
2072  * Get an error string associated with an error code. The string is statically
2073  * allocated and does not need to be freed
2074  *
2075  * \param [in] err the error code
2076  * \return the error string
2077  *
2078  * \since v0.4.0
2079  */
2080 AMQP_PUBLIC_FUNCTION
2081 const char *AMQP_CALL amqp_error_string2(int err);
2082 
2083 /**
2084  * Deserialize an amqp_table_t from AMQP wireformat
2085  *
2086  * This is an internal function and is not typically used by
2087  * client applications
2088  *
2089  * \param [in] encoded the buffer containing the serialized data
2090  * \param [in] pool memory pool used to allocate the table entries from
2091  * \param [in] output the amqp_table_t structure to fill in. Any existing
2092  *             entries will be erased
2093  * \param [in,out] offset The offset into the encoded buffer to start
2094  *                 reading the serialized table. It will be updated
2095  *                 by this function to end of the table
2096  * \return AMQP_STATUS_OK on success, an amqp_status_enum value on failure
2097  *  Possible error codes:
2098  *  - AMQP_STATUS_NO_MEMORY out of memory
2099  *  - AMQP_STATUS_BAD_AMQP_DATA invalid wireformat
2100  *
2101  * \since v0.1
2102  */
2103 AMQP_PUBLIC_FUNCTION
2104 int AMQP_CALL amqp_decode_table(amqp_bytes_t encoded, amqp_pool_t *pool,
2105                                 amqp_table_t *output, size_t *offset);
2106 
2107 /**
2108  * Serializes an amqp_table_t to the AMQP wireformat
2109  *
2110  * This is an internal function and is not typically used by
2111  * client applications
2112  *
2113  * \param [in] encoded the buffer where to serialize the table to
2114  * \param [in] input the amqp_table_t to serialize
2115  * \param [in,out] offset The offset into the encoded buffer to start
2116  *                 writing the serialized table. It will be updated
2117  *                 by this function to where writing left off
2118  * \return AMQP_STATUS_OK on success, an amqp_status_enum value on failure
2119  *  Possible error codes:
2120  *  - AMQP_STATUS_TABLE_TOO_BIG the serialized form is too large for the
2121  *    buffer
2122  *  - AMQP_STATUS_BAD_AMQP_DATA invalid table
2123  *
2124  * \since v0.1
2125  */
2126 AMQP_PUBLIC_FUNCTION
2127 int AMQP_CALL amqp_encode_table(amqp_bytes_t encoded, amqp_table_t *input,
2128                                 size_t *offset);
2129 
2130 /**
2131  * Create a deep-copy of an amqp_table_t object
2132  *
2133  * Creates a deep-copy of an amqp_table_t object, using the provided pool
2134  * object to allocate the necessary memory. This memory can be freed later by
2135  * call recycle_amqp_pool(), or empty_amqp_pool()
2136  *
2137  * \param [in] original the table to copy
2138  * \param [in,out] clone the table to copy to
2139  * \param [in] pool the initialized memory pool to do allocations for the table
2140  *             from
2141  * \return AMQP_STATUS_OK on success, amqp_status_enum value on failure.
2142  *  Possible error values:
2143  *  - AMQP_STATUS_NO_MEMORY - memory allocation failure.
2144  *  - AMQP_STATUS_INVALID_PARAMETER - invalid table (e.g., no key name)
2145  *
2146  * \since v0.4.0
2147  */
2148 AMQP_PUBLIC_FUNCTION
2149 int AMQP_CALL amqp_table_clone(const amqp_table_t *original,
2150                                amqp_table_t *clone, amqp_pool_t *pool);
2151 
2152 /**
2153  * A message object
2154  *
2155  * \since v0.4.0
2156  */
2157 typedef struct amqp_message_t_ {
2158   amqp_basic_properties_t properties; /**< message properties */
2159   amqp_bytes_t body;                  /**< message body */
2160   amqp_pool_t pool;                   /**< pool used to allocate properties */
2161 } amqp_message_t;
2162 
2163 /**
2164  * Reads the next message on a channel
2165  *
2166  * Reads a complete message (header + body) on a specified channel. This
2167  * function is intended to be used with amqp_basic_get() or when an
2168  * AMQP_BASIC_DELIVERY_METHOD method is received.
2169  *
2170  * \param [in,out] state the connection object
2171  * \param [in] channel the channel on which to read the message from
2172  * \param [in,out] message a pointer to a amqp_message_t object. Caller should
2173  *                 call amqp_message_destroy() when it is done using the
2174  *                 fields in the message object.  The caller is responsible for
2175  *                 allocating/destroying the amqp_message_t object itself.
2176  * \param [in] flags pass in 0. Currently unused.
2177  * \returns a amqp_rpc_reply_t object. ret.reply_type == AMQP_RESPONSE_NORMAL on
2178  * success.
2179  *
2180  * \since v0.4.0
2181  */
2182 AMQP_PUBLIC_FUNCTION
2183 amqp_rpc_reply_t AMQP_CALL amqp_read_message(amqp_connection_state_t state,
2184                                              amqp_channel_t channel,
2185                                              amqp_message_t *message,
2186                                              int flags);
2187 
2188 /**
2189  * Frees memory associated with a amqp_message_t allocated in amqp_read_message
2190  *
2191  * \param [in] message
2192  *
2193  * \since v0.4.0
2194  */
2195 AMQP_PUBLIC_FUNCTION
2196 void AMQP_CALL amqp_destroy_message(amqp_message_t *message);
2197 
2198 /**
2199  * Envelope object
2200  *
2201  * \since v0.4.0
2202  */
2203 typedef struct amqp_envelope_t_ {
2204   amqp_channel_t channel;     /**< channel message was delivered on */
2205   amqp_bytes_t consumer_tag;  /**< the consumer tag the message was delivered to
2206                                */
2207   uint64_t delivery_tag;      /**< the messages delivery tag */
2208   amqp_boolean_t redelivered; /**< flag indicating whether this message is being
2209                                  redelivered */
2210   amqp_bytes_t exchange;      /**< exchange this message was published to */
2211   amqp_bytes_t routing_key; /**< the routing key this message was published with
2212                              */
2213   amqp_message_t message;   /**< the message */
2214 } amqp_envelope_t;
2215 
2216 /**
2217  * Wait for and consume a message
2218  *
2219  * Waits for a basic.deliver method on any channel, upon receipt of
2220  * basic.deliver it reads that message, and returns. If any other method is
2221  * received before basic.deliver, this function will return an amqp_rpc_reply_t
2222  * with ret.reply_type == AMQP_RESPONSE_LIBRARY_EXCEPTION, and
2223  * ret.library_error == AMQP_STATUS_UNEXPECTED_STATE. The caller should then
2224  * call amqp_simple_wait_frame() to read this frame and take appropriate action.
2225  *
2226  * This function should be used after starting a consumer with the
2227  * amqp_basic_consume() function
2228  *
2229  * \param [in,out] state the connection object
2230  * \param [in,out] envelope a pointer to a amqp_envelope_t object. Caller
2231  *                 should call #amqp_destroy_envelope() when it is done using
2232  *                 the fields in the envelope object. The caller is responsible
2233  *                 for allocating/destroying the amqp_envelope_t object itself.
2234  * \param [in] timeout a timeout to wait for a message delivery. Passing in
2235  *             NULL will result in blocking behavior.
2236  * \param [in] flags pass in 0. Currently unused.
2237  * \returns a amqp_rpc_reply_t object.  ret.reply_type == AMQP_RESPONSE_NORMAL
2238  *          on success. If ret.reply_type == AMQP_RESPONSE_LIBRARY_EXCEPTION,
2239  *          and ret.library_error == AMQP_STATUS_UNEXPECTED_STATE, a frame other
2240  *          than AMQP_BASIC_DELIVER_METHOD was received, the caller should call
2241  *          amqp_simple_wait_frame() to read this frame and take appropriate
2242  *          action.
2243  *
2244  * \since v0.4.0
2245  */
2246 AMQP_PUBLIC_FUNCTION
2247 amqp_rpc_reply_t AMQP_CALL amqp_consume_message(amqp_connection_state_t state,
2248                                                 amqp_envelope_t *envelope,
2249                                                 const struct timeval *timeout,
2250                                                 int flags);
2251 
2252 /**
2253  * Frees memory associated with a amqp_envelope_t allocated in
2254  * amqp_consume_message()
2255  *
2256  * \param [in] envelope
2257  *
2258  * \since v0.4.0
2259  */
2260 AMQP_PUBLIC_FUNCTION
2261 void AMQP_CALL amqp_destroy_envelope(amqp_envelope_t *envelope);
2262 
2263 /**
2264  * Parameters used to connect to the RabbitMQ broker
2265  *
2266  * \since v0.2
2267  */
2268 struct amqp_connection_info {
2269   char *user; /**< the username to authenticate with the broker, default on most
2270                  broker is 'guest' */
2271   char *password; /**< the password to authenticate with the broker, default on
2272                      most brokers is 'guest' */
2273   char *host;     /**< the hostname of the broker */
2274   char *vhost; /**< the virtual host on the broker to connect to, a good default
2275                   is "/" */
2276   int port;    /**< the port that the broker is listening on, default on most
2277                   brokers is 5672 */
2278   amqp_boolean_t ssl;
2279 };
2280 
2281 /**
2282  * Initialze an amqp_connection_info to default values
2283  *
2284  * The default values are:
2285  * - user: "guest"
2286  * - password: "guest"
2287  * - host: "localhost"
2288  * - vhost: "/"
2289  * - port: 5672
2290  *
2291  * \param [out] parsed the connection info to set defaults on
2292  *
2293  * \since v0.2
2294  */
2295 AMQP_PUBLIC_FUNCTION
2296 void AMQP_CALL
2297     amqp_default_connection_info(struct amqp_connection_info *parsed);
2298 
2299 /**
2300  * Parse a connection URL
2301  *
2302  * An amqp connection url takes the form:
2303  *
2304  * amqp://[$USERNAME[:$PASSWORD]\@]$HOST[:$PORT]/[$VHOST]
2305  *
2306  * Examples:
2307  *  amqp://guest:guest\@localhost:5672//
2308  *  amqp://guest:guest\@localhost/myvhost
2309  *
2310  *  Any missing parts of the URL will be set to the defaults specified in
2311  *  amqp_default_connection_info. For amqps: URLs the default port will be set
2312  *  to 5671 instead of 5672 for non-SSL URLs.
2313  *
2314  * \note This function modifies url parameter.
2315  *
2316  * \param [in] url URI to parse, note that this parameter is modified by the
2317  *             function.
2318  * \param [out] parsed the connection info gleaned from the URI. The char*
2319  *              members will point to parts of the url input parameter.
2320  *              Memory management will depend on how the url is allocated.
2321  * \returns AMQP_STATUS_OK on success, AMQP_STATUS_BAD_URL on failure
2322  *
2323  * \since v0.2
2324  */
2325 AMQP_PUBLIC_FUNCTION
2326 int AMQP_CALL amqp_parse_url(char *url, struct amqp_connection_info *parsed);
2327 
2328 /* socket API */
2329 
2330 /**
2331  * Open a socket connection.
2332  *
2333  * This function opens a socket connection returned from amqp_tcp_socket_new()
2334  * or amqp_ssl_socket_new(). This function should be called after setting
2335  * socket options and prior to assigning the socket to an AMQP connection with
2336  * amqp_set_socket().
2337  *
2338  * \param [in,out] self A socket object.
2339  * \param [in] host Connect to this host.
2340  * \param [in] port Connect on this remote port.
2341  *
2342  * \return AMQP_STATUS_OK on success, an amqp_status_enum on failure
2343  *
2344  * \since v0.4.0
2345  */
2346 AMQP_PUBLIC_FUNCTION
2347 int AMQP_CALL amqp_socket_open(amqp_socket_t *self, const char *host, int port);
2348 
2349 /**
2350  * Open a socket connection.
2351  *
2352  * This function opens a socket connection returned from amqp_tcp_socket_new()
2353  * or amqp_ssl_socket_new(). This function should be called after setting
2354  * socket options and prior to assigning the socket to an AMQP connection with
2355  * amqp_set_socket().
2356  *
2357  * \param [in,out] self A socket object.
2358  * \param [in] host Connect to this host.
2359  * \param [in] port Connect on this remote port.
2360  * \param [in] timeout Max allowed time to spent on opening. If NULL - run in
2361  *             blocking mode
2362  *
2363  * \return AMQP_STATUS_OK on success, an amqp_status_enum on failure.
2364  *
2365  * \since v0.4.0
2366  */
2367 AMQP_PUBLIC_FUNCTION
2368 int AMQP_CALL amqp_socket_open_noblock(amqp_socket_t *self, const char *host,
2369                                        int port, const struct timeval *timeout);
2370 
2371 /**
2372  * Get the socket descriptor in use by a socket object.
2373  *
2374  * Retrieve the underlying socket descriptor. This function can be used to
2375  * perform low-level socket operations that aren't supported by the socket
2376  * interface. Use with caution!
2377  *
2378  * \param [in,out] self A socket object.
2379  *
2380  * \return The underlying socket descriptor, or -1 if there is no socket
2381  *  descriptor associated with
2382  *
2383  * \since v0.4.0
2384  */
2385 AMQP_PUBLIC_FUNCTION
2386 int AMQP_CALL amqp_socket_get_sockfd(amqp_socket_t *self);
2387 
2388 /**
2389  * Get the socket object associated with a amqp_connection_state_t
2390  *
2391  * \param [in] state the connection object to get the socket from
2392  * \return a pointer to the socket object, or NULL if one has not been assigned
2393  *
2394  * \since v0.4.0
2395  */
2396 AMQP_PUBLIC_FUNCTION
2397 amqp_socket_t *AMQP_CALL amqp_get_socket(amqp_connection_state_t state);
2398 
2399 /**
2400  * Get the broker properties table
2401  *
2402  * \param [in] state the connection object
2403  * \return a pointer to an amqp_table_t containing the properties advertised
2404  *  by the broker on connection. The connection object owns the table, it
2405  *  should not be modified.
2406  *
2407  * \since v0.5.0
2408  */
2409 AMQP_PUBLIC_FUNCTION
2410 amqp_table_t *AMQP_CALL
2411     amqp_get_server_properties(amqp_connection_state_t state);
2412 
2413 /**
2414  * Get the client properties table
2415  *
2416  * Get the properties that were passed to the broker on connection.
2417  *
2418  * \param [in] state the connection object
2419  * \return a pointer to an amqp_table_t containing the properties advertised
2420  *  by the client on connection. The connection object owns the table, it
2421  *  should not be modified.
2422  *
2423  * \since v0.7.0
2424  */
2425 AMQP_PUBLIC_FUNCTION
2426 amqp_table_t *AMQP_CALL
2427     amqp_get_client_properties(amqp_connection_state_t state);
2428 
2429 /**
2430  * Get the login handshake timeout.
2431  *
2432  * amqp_login and amqp_login_with_properties perform the login handshake with
2433  * the broker.  This function returns the timeout associated with completing
2434  * this operation from the client side. This value can be set by using the
2435  * amqp_set_handshake_timeout.
2436  *
2437  * Note that the RabbitMQ broker has configurable timeout for completing the
2438  * login handshake, the default is 10 seconds.  rabbitmq-c has a default of 12
2439  * seconds.
2440  *
2441  * \param [in] state the connection object
2442  * \return a struct timeval representing the current login timeout for the state
2443  *  object. A NULL value represents an infinite timeout. The memory returned is
2444  *  owned by the connection object.
2445  *
2446  * \since v0.9.0
2447  */
2448 AMQP_PUBLIC_FUNCTION
2449 struct timeval *AMQP_CALL
2450     amqp_get_handshake_timeout(amqp_connection_state_t state);
2451 
2452 /**
2453  * Set the login handshake timeout.
2454  *
2455  * amqp_login and amqp_login_with_properties perform the login handshake with
2456  * the broker. This function sets the timeout associated with completing this
2457  * operation from the client side.
2458  *
2459  * The timeout must be set before amqp_login or amqp_login_with_properties is
2460  * called to change from the default timeout.
2461  *
2462  * Note that the RabbitMQ broker has a configurable timeout for completing the
2463  * login handshake, the default is 10 seconds. rabbitmq-c has a default of 12
2464  * seconds.
2465  *
2466  * \param [in] state the connection object
2467  * \param [in] timeout a struct timeval* representing new login timeout for the
2468  *  state object. NULL represents an infinite timeout. The value of timeout is
2469  *  copied internally, the caller is responsible for ownership of the passed in
2470  *  pointer, it does not need to remain valid after this function is called.
2471  * \return AMQP_STATUS_OK on success.
2472  *
2473  * \since v0.9.0
2474  */
2475 AMQP_PUBLIC_FUNCTION
2476 int AMQP_CALL amqp_set_handshake_timeout(amqp_connection_state_t state,
2477                                          const struct timeval *timeout);
2478 
2479 /**
2480  * Get the RPC timeout
2481  *
2482  * Gets the timeout for any RPC-style AMQP command (e.g., amqp_queue_declare).
2483  * This timeout may be changed at any time by calling \amqp_set_rpc_timeout
2484  * function with a new timeout. The timeout applies individually to each RPC
2485  * that is made.
2486  *
2487  * The default value is NULL, or an infinite timeout.
2488  *
2489  * When an RPC times out, the function will return an error AMQP_STATUS_TIMEOUT,
2490  * and the connection will be closed.
2491  *
2492  *\warning RPC-timeouts are an advanced feature intended to be used to detect
2493  * dead connections quickly when the rabbitmq-c implementation of heartbeats
2494  * does not work. Do not use RPC timeouts unless you understand the implications
2495  * of doing so.
2496  *
2497  * \param [in] state the connection object
2498  * \return a struct timeval representing the current RPC timeout for the state
2499  * object. A NULL value represents an infinite timeout. The memory returned is
2500  * owned by the connection object.
2501  *
2502  * \since v0.9.0
2503  */
2504 AMQP_PUBLIC_FUNCTION
2505 struct timeval *AMQP_CALL amqp_get_rpc_timeout(amqp_connection_state_t state);
2506 
2507 /**
2508  * Set the RPC timeout
2509  *
2510  * Sets the timeout for any RPC-style AMQP command (e.g., amqp_queue_declare).
2511  * This timeout may be changed at any time by calling this function with a new
2512  * timeout. The timeout applies individually to each RPC that is made.
2513  *
2514  * The default value is NULL, or an infinite timeout.
2515  *
2516  * When an RPC times out, the function will return an error AMQP_STATUS_TIMEOUT,
2517  * and the connection will be closed.
2518  *
2519  *\warning RPC-timeouts are an advanced feature intended to be used to detect
2520  * dead connections quickly when the rabbitmq-c implementation of heartbeats
2521  * does not work. Do not use RPC timeouts unless you understand the implications
2522  * of doing so.
2523  *
2524  * \param [in] state the connection object
2525  * \param [in] timeout a struct timeval* representing new RPC timeout for the
2526  * state object. NULL represents an infinite timeout. The value of timeout is
2527  * copied internally, the caller is responsible for ownership of the passed
2528  * pointer, it does not need to remain valid after this function is called.
2529  * \return AMQP_STATUS_SUCCESS on success.
2530  *
2531  * \since v0.9.0
2532  */
2533 AMQP_PUBLIC_FUNCTION
2534 int AMQP_CALL amqp_set_rpc_timeout(amqp_connection_state_t state,
2535                                    const struct timeval *timeout);
2536 
2537 AMQP_END_DECLS
2538 
2539 #endif /* AMQP_H */
2540