/* iksemel (XML parser for Jabber) ** Copyright (C) 2000-2007 Gurer Ozen ** This code is free software; you can redistribute it and/or ** modify it under the terms of GNU Lesser General Public License. */ #ifndef IKSEMEL_H #define IKSEMEL_H 1 #ifdef __cplusplus #include /* size_t for C++ */ extern "C" { #else #include /* size_t for C */ #endif /***** object stack *****/ struct ikstack_struct; typedef struct ikstack_struct ikstack; ikstack *iks_stack_new (size_t meta_chunk, size_t data_chunk); void *iks_stack_alloc (ikstack *s, size_t size); char *iks_stack_strdup (ikstack *s, const char *src, size_t len); char *iks_stack_strcat (ikstack *s, char *old, size_t old_len, const char *src, size_t src_len); void iks_stack_stat (ikstack *s, size_t *allocated, size_t *used); void iks_stack_delete (ikstack **sp); /***** utilities *****/ void *iks_malloc (size_t size); void iks_real_free (void *ptr); void iks_set_mem_funcs (void *(*malloc_func)(size_t size), void (*free_func)(void *ptr)); char *iks_strdup (const char *src); char *iks_strcat (char *dest, const char *src); int iks_strcmp (const char *a, const char *b); int iks_strcasecmp (const char *a, const char *b); int iks_strncmp (const char *a, const char *b, size_t n); int iks_strncasecmp (const char *a, const char *b, size_t n); size_t iks_strlen (const char *src); char *iks_escape (ikstack *s, char *src, size_t len); char *iks_unescape (ikstack *s, char *src, size_t len); #define iks_free(p) if (p) {iks_real_free(p) ; p = NULL;} /***** dom tree *****/ enum ikstype { IKS_NONE = 0, IKS_TAG, IKS_ATTRIBUTE, IKS_CDATA }; struct iks_struct; typedef struct iks_struct iks; iks *iks_new (const char *name); iks *iks_new_within (const char *name, ikstack *s); iks *iks_insert (iks *x, const char *name); iks *iks_insert_cdata (iks *x, const char *data, size_t len); iks *iks_insert_attrib (iks *x, const char *name, const char *value); iks *iks_insert_node (iks *x, iks *y); iks *iks_append (iks *x, const char *name); iks *iks_prepend (iks *x, const char *name); iks *iks_append_cdata (iks *x, const char *data, size_t len); iks *iks_prepend_cdata (iks *x, const char *data, size_t len); void iks_hide (iks *x); void iks_delete (iks *x); iks *iks_next (iks *x); iks *iks_next_tag (iks *x); iks *iks_prev (iks *x); iks *iks_prev_tag (iks *x); iks *iks_parent (iks *x); iks *iks_root (iks *x); iks *iks_child (iks *x); iks *iks_first_tag (iks *x); iks *iks_attrib (iks *x); iks *iks_find (iks *x, const char *name); char *iks_find_cdata (iks *x, const char *name); char *iks_find_attrib (iks *x, const char *name); iks *iks_find_with_attrib (iks *x, const char *tagname, const char *attrname, const char *value); ikstack *iks_stack (iks *x); enum ikstype iks_type (iks *x); char *iks_name (iks *x); char *iks_cdata (iks *x); size_t iks_cdata_size (iks *x); int iks_has_children (iks *x); int iks_has_attribs (iks *x); char *iks_string (ikstack *s, iks *x); iks *iks_copy (iks *x); iks *iks_copy_within (iks *x, ikstack *s); /***** sax parser *****/ enum ikserror { IKS_OK = 0, IKS_NOMEM, IKS_BADXML, IKS_HOOK }; enum ikstagtype { IKS_OPEN, IKS_CLOSE, IKS_SINGLE }; typedef int (iksTagHook)(void *user_data, char *name, char **atts, int type); typedef int (iksCDataHook)(void *user_data, char *data, size_t len); typedef void (iksDeleteHook)(void *user_data); struct iksparser_struct; typedef struct iksparser_struct iksparser; iksparser *iks_sax_new (void *user_data, iksTagHook *tagHook, iksCDataHook *cdataHook); iksparser *iks_sax_extend (ikstack *s, void *user_data, iksTagHook *tagHook, iksCDataHook *cdataHook, iksDeleteHook *deleteHook); ikstack *iks_parser_stack (iksparser *prs); void *iks_user_data (iksparser *prs); unsigned long iks_nr_bytes (iksparser *prs); unsigned long iks_nr_lines (iksparser *prs); int iks_parse (iksparser *prs, const char *data, size_t len, int finish); void iks_parser_reset (iksparser *prs); void iks_parser_delete (iksparser *prs); /***** dom parser *****/ enum iksfileerror { IKS_FILE_NOFILE = 4, IKS_FILE_NOACCESS, IKS_FILE_RWERR }; iksparser *iks_dom_new (iks **iksptr); void iks_set_size_hint (iksparser *prs, size_t approx_size); iks *iks_tree (const char *xml_str, size_t len, int *err); int iks_load (const char *fname, iks **xptr); int iks_save (const char *fname, iks *x); /***** transport layer *****/ enum iksasyncevents { IKS_ASYNC_RESOLVED, IKS_ASYNC_CONNECTED, IKS_ASYNC_WRITE, IKS_ASYNC_WRITTEN, IKS_ASYNC_READ, IKS_ASYNC_CLOSED, IKS_ASYNC_ERROR }; typedef struct iksasyncevent_struct { int event; int data0; int data1; } iksasyncevent; typedef void (iksTClose)(void *socket); typedef int (iksTConnect)(iksparser *prs, void **socketptr, const char *server, int port); typedef int (iksTSend)(void *socket, const char *data, size_t len); typedef int (iksTRecv)(void *socket, char *buffer, size_t buf_len, int timeout); typedef int (iksAsyncNotify)(void *user_data, iksasyncevent *event); typedef int (iksTConnectAsync)(iksparser *prs, void **socketptr, const char *server, const char *server_name, int port, void *notify_data, iksAsyncNotify *notify_func); #define IKS_TRANSPORT_V1 0 typedef const struct ikstransport_struct { int abi_version; /* basic api, connect can be NULL if only async api is provided */ iksTConnect *connect; iksTSend *send; iksTRecv *recv; iksTClose *close; /* optional async api */ iksTConnectAsync *connect_async; } ikstransport; extern ikstransport iks_default_transport; /***** stream parser *****/ enum iksneterror { IKS_NET_NODNS = 4, IKS_NET_NOSOCK, IKS_NET_NOCONN, IKS_NET_RWERR, IKS_NET_NOTSUPP, IKS_NET_TLSFAIL, IKS_NET_DROPPED, IKS_NET_UNKNOWN }; enum iksnodetype { IKS_NODE_START, IKS_NODE_NORMAL, IKS_NODE_ERROR, IKS_NODE_STOP }; enum ikssasltype { IKS_SASL_PLAIN, IKS_SASL_DIGEST_MD5 }; #define IKS_JABBER_PORT 5222 typedef int (iksStreamHook)(void *user_data, int type, iks *node); typedef void (iksLogHook)(void *user_data, const char *data, size_t size, int is_incoming); iksparser *iks_stream_new (char *name_space, void *user_data, iksStreamHook *streamHook); void *iks_stream_user_data (iksparser *prs); void iks_set_log_hook (iksparser *prs, iksLogHook *logHook); int iks_connect_tcp (iksparser *prs, const char *server, int port); int iks_connect_fd (iksparser *prs, int fd); int iks_connect_via (iksparser *prs, const char *server, int port, const char *server_name); int iks_connect_with (iksparser *prs, const char *server, int port, const char *server_name, ikstransport *trans); int iks_connect_async (iksparser *prs, const char *server, int port, void *notify_data, iksAsyncNotify *notify_func); int iks_connect_async_with (iksparser *prs, const char *server, int port, const char *server_name, ikstransport *trans, void *notify_data, iksAsyncNotify *notify_func); int iks_fd (iksparser *prs); int iks_recv (iksparser *prs, int timeout); int iks_send_header (iksparser *prs, const char *to); int iks_send (iksparser *prs, iks *x); int iks_send_raw (iksparser *prs, const char *xmlstr); void iks_disconnect (iksparser *prs); int iks_has_tls (void); int iks_is_secure (iksparser *prs); int iks_start_tls (iksparser *prs); int iks_proceed_tls (iksparser *prs, const char *cert_file, const char *key_file); int iks_start_sasl (iksparser *prs, enum ikssasltype type, char *username, char *pass); /***** jabber *****/ #define IKS_NS_CLIENT "jabber:client" #define IKS_NS_SERVER "jabber:server" #define IKS_NS_AUTH "jabber:iq:auth" #define IKS_NS_AUTH_0K "jabber:iq:auth:0k" #define IKS_NS_REGISTER "jabber:iq:register" #define IKS_NS_ROSTER "jabber:iq:roster" #define IKS_NS_XROSTER "jabber:x:roster" #define IKS_NS_OFFLINE "jabber:x:offline" #define IKS_NS_AGENT "jabber:iq:agent" #define IKS_NS_AGENTS "jabber:iq:agents" #define IKS_NS_BROWSE "jabber:iq:browse" #define IKS_NS_CONFERENCE "jabber:iq:conference" #define IKS_NS_DELAY "jabber:x:delay" #define IKS_NS_VERSION "jabber:iq:version" #define IKS_NS_TIME "jabber:iq:time" #define IKS_NS_VCARD "vcard-temp" #define IKS_NS_PRIVATE "jabber:iq:private" #define IKS_NS_SEARCH "jabber:iq:search" #define IKS_NS_OOB "jabber:iq:oob" #define IKS_NS_XOOB "jabber:x:oob" #define IKS_NS_ADMIN "jabber:iq:admin" #define IKS_NS_FILTER "jabber:iq:filter" #define IKS_NS_GATEWAY "jabber:iq:gateway" #define IKS_NS_LAST "jabber:iq:last" #define IKS_NS_SIGNED "jabber:x:signed" #define IKS_NS_ENCRYPTED "jabber:x:encrypted" #define IKS_NS_ENVELOPE "jabber:x:envelope" #define IKS_NS_EVENT "jabber:x:event" #define IKS_NS_EXPIRE "jabber:x:expire" #define IKS_NS_XHTML "http://www.w3.org/1999/xhtml" #define IKS_NS_XMPP_SASL "urn:ietf:params:xml:ns:xmpp-sasl" #define IKS_NS_XMPP_BIND "urn:ietf:params:xml:ns:xmpp-bind" #define IKS_NS_XMPP_SESSION "urn:ietf:params:xml:ns:xmpp-session" #define IKS_ID_USER 1 #define IKS_ID_SERVER 2 #define IKS_ID_RESOURCE 4 #define IKS_ID_PARTIAL IKS_ID_USER | IKS_ID_SERVER #define IKS_ID_FULL IKS_ID_USER | IKS_ID_SERVER | IKS_ID_RESOURCE #define IKS_STREAM_STARTTLS 1 #define IKS_STREAM_SESSION 2 #define IKS_STREAM_BIND 4 #define IKS_STREAM_SASL_PLAIN 8 #define IKS_STREAM_SASL_MD5 16 typedef struct iksid_struct { char *user; char *server; char *resource; char *partial; char *full; } iksid; iksid *iks_id_new (ikstack *s, const char *jid); int iks_id_cmp (iksid *a, iksid *b, int parts); enum ikspaktype { IKS_PAK_NONE = 0, IKS_PAK_MESSAGE, IKS_PAK_PRESENCE, IKS_PAK_IQ, IKS_PAK_S10N }; enum iksubtype { IKS_TYPE_NONE = 0, IKS_TYPE_ERROR, IKS_TYPE_CHAT, IKS_TYPE_GROUPCHAT, IKS_TYPE_HEADLINE, IKS_TYPE_GET, IKS_TYPE_SET, IKS_TYPE_RESULT, IKS_TYPE_SUBSCRIBE, IKS_TYPE_SUBSCRIBED, IKS_TYPE_UNSUBSCRIBE, IKS_TYPE_UNSUBSCRIBED, IKS_TYPE_PROBE, IKS_TYPE_AVAILABLE, IKS_TYPE_UNAVAILABLE }; enum ikshowtype { IKS_SHOW_UNAVAILABLE = 0, IKS_SHOW_AVAILABLE, IKS_SHOW_CHAT, IKS_SHOW_AWAY, IKS_SHOW_XA, IKS_SHOW_DND }; typedef struct ikspak_struct { iks *x; iksid *from; iks *query; char *ns; char *id; enum ikspaktype type; enum iksubtype subtype; enum ikshowtype show; } ikspak; ikspak *iks_packet (iks *x); iks *iks_make_auth (iksid *id, const char *pass, const char *sid); iks *iks_make_msg (enum iksubtype type, const char *to, const char *body); iks *iks_make_s10n (enum iksubtype type, const char *to, const char *msg); iks *iks_make_pres (enum ikshowtype show, const char *status); iks *iks_make_iq (enum iksubtype type, const char *xmlns); iks *iks_make_resource_bind(iksid *id); iks *iks_make_session(void); int iks_stream_features(iks *x); /***** jabber packet filter *****/ #define IKS_RULE_DONE 0 #define IKS_RULE_ID 1 #define IKS_RULE_TYPE 2 #define IKS_RULE_SUBTYPE 4 #define IKS_RULE_FROM 8 #define IKS_RULE_FROM_PARTIAL 16 #define IKS_RULE_NS 32 enum iksfilterret { IKS_FILTER_PASS, IKS_FILTER_EAT }; typedef int (iksFilterHook)(void *user_data, ikspak *pak); struct iksfilter_struct; typedef struct iksfilter_struct iksfilter; struct iksrule_struct; typedef struct iksrule_struct iksrule; iksfilter *iks_filter_new (void); iksrule *iks_filter_add_rule (iksfilter *f, iksFilterHook *filterHook, void *user_data, ...); void iks_filter_remove_rule (iksfilter *f, iksrule *rule); void iks_filter_remove_hook (iksfilter *f, iksFilterHook *filterHook); void iks_filter_packet (iksfilter *f, ikspak *pak); void iks_filter_delete (iksfilter *f); /***** sha1 *****/ struct iksha_struct; typedef struct iksha_struct iksha; iksha *iks_sha_new (void); void iks_sha_reset (iksha *sha); void iks_sha_hash (iksha *sha, const unsigned char *data, size_t len, int finish); void iks_sha_print (iksha *sha, char *hash); void iks_sha_delete (iksha *sha); void iks_sha (const char *data, char *hash); /***** md5 *****/ struct ikmd5_struct; typedef struct iksmd5_struct iksmd5; iksmd5 *iks_md5_new(void); void iks_md5_reset(iksmd5 *md5); void iks_md5_hash(iksmd5 *md5, const unsigned char *data, size_t slen, int finish); void iks_md5_delete(iksmd5 *md5); void iks_md5_print(iksmd5 *md5, char *buf); void iks_md5_digest(iksmd5 *md5, unsigned char *digest); void iks_md5(const char *data, char *buf); /***** base64 *****/ char *iks_base64_decode(const char *buf); char *iks_base64_encode(const char *buf, int len); #ifdef __cplusplus } #endif #endif /* IKSEMEL_H */