You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by rh...@apache.org on 2012/06/19 19:50:16 UTC

svn commit: r1351786 - in /qpid/proton/trunk: examples/ examples/messenger/ proton-c/bindings/ proton-c/include/proton/ proton-c/src/ proton-c/src/codec/ proton-c/src/dispatcher/ proton-c/src/engine/ proton-c/src/message/

Author: rhs
Date: Tue Jun 19 17:50:15 2012
New Revision: 1351786

URL: http://svn.apache.org/viewvc?rev=1351786&view=rev
Log:
added error checking to messenger API; added messenger examples

Added:
    qpid/proton/trunk/examples/messenger/
    qpid/proton/trunk/examples/messenger/README.txt
    qpid/proton/trunk/examples/messenger/recv.py   (with props)
    qpid/proton/trunk/examples/messenger/send.py   (with props)
    qpid/proton/trunk/proton-c/include/proton/error.h
      - copied, changed from r1351530, qpid/proton/trunk/proton-c/include/proton/errors.h
Removed:
    qpid/proton/trunk/proton-c/include/proton/errors.h
Modified:
    qpid/proton/trunk/examples/README.txt
    qpid/proton/trunk/proton-c/bindings/cproton.i
    qpid/proton/trunk/proton-c/include/proton/driver.h
    qpid/proton/trunk/proton-c/include/proton/engine.h
    qpid/proton/trunk/proton-c/include/proton/message.h
    qpid/proton/trunk/proton-c/include/proton/messenger.h
    qpid/proton/trunk/proton-c/src/buffer.c
    qpid/proton/trunk/proton-c/src/codec/codec.c
    qpid/proton/trunk/proton-c/src/dispatcher/dispatcher.c
    qpid/proton/trunk/proton-c/src/driver.c
    qpid/proton/trunk/proton-c/src/engine/engine-internal.h
    qpid/proton/trunk/proton-c/src/engine/engine.c
    qpid/proton/trunk/proton-c/src/error.c
    qpid/proton/trunk/proton-c/src/message/message.c
    qpid/proton/trunk/proton-c/src/messenger.c
    qpid/proton/trunk/proton-c/src/parser.c
    qpid/proton/trunk/proton-c/src/proton.c
    qpid/proton/trunk/proton-c/src/scanner.c
    qpid/proton/trunk/proton-c/src/util.c
    qpid/proton/trunk/proton-c/src/util.h

Modified: qpid/proton/trunk/examples/README.txt
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/examples/README.txt?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/examples/README.txt (original)
+++ qpid/proton/trunk/examples/README.txt Tue Jun 19 17:50:15 2012
@@ -1,3 +1,5 @@
 This directory contains example applications that use the Proton library.
 
-mailbox/ - a toy mailbox client/server example
+  broker/    - a python message broker
+  mailbox/   - a toy mailbox client/server example
+  messenger/ - simple examples using the messenger API

Added: qpid/proton/trunk/examples/messenger/README.txt
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/examples/messenger/README.txt?rev=1351786&view=auto
==============================================================================
--- qpid/proton/trunk/examples/messenger/README.txt (added)
+++ qpid/proton/trunk/examples/messenger/README.txt Tue Jun 19 17:50:15 2012
@@ -0,0 +1,20 @@
+This directory contains example scripts using the messenger API.
+
+  send.py - a simple example of using the messenger API to send messages
+  recv.py - a simple example of using the messenger API to receive messages
+
+Note that depending on the address passed into these scripts, you can
+use them in either a peer to peer or a brokered scenario.
+
+For brokered usage:
+
+  recv.py //<broker>/<queue>
+
+  send.py -a //<broker>/<queue> msg_1 ... msg_n
+
+For peer to peer usage:
+
+  # execute on <host> to receive messages from all local network interfaces
+  recv.py //~0.0.0.0
+
+  send.py -a //<host msg_1 ... msg_n

Added: qpid/proton/trunk/examples/messenger/recv.py
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/examples/messenger/recv.py?rev=1351786&view=auto
==============================================================================
--- qpid/proton/trunk/examples/messenger/recv.py (added)
+++ qpid/proton/trunk/examples/messenger/recv.py Tue Jun 19 17:50:15 2012
@@ -0,0 +1,51 @@
+#!/usr/bin/python
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements.  See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership.  The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License.  You may obtain a copy of the License at
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied.  See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+import sys, optparse
+from xproton import *
+
+parser = optparse.OptionParser(usage="usage: %prog [options] addr_1 ... addr_n",
+                               description="simple message receiver")
+
+opts, args = parser.parse_args()
+
+if not args:
+  args = ["//~0.0.0.0"]
+
+m = pn_messenger()
+pn_messenger_start(m)
+
+for a in args:
+  if pn_messenger_subscribe(m, a):
+    print pn_messenger_error(m)
+    break
+
+msg = pn_message()
+while True:
+  if pn_messenger_recv(m, 10):
+    print pn_messenger_error(m)
+    break
+  while pn_messenger_incoming(m):
+    if pn_messenger_get(m, msg):
+      print pn_messenger_error(m)
+    else:
+      print "%s: %s" % (pn_message_get_address(msg), pn_message_get_subject(msg))
+
+pn_messenger_stop(m)
+pn_messenger_free(m)

Propchange: qpid/proton/trunk/examples/messenger/recv.py
------------------------------------------------------------------------------
    svn:executable = *

Added: qpid/proton/trunk/examples/messenger/send.py
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/examples/messenger/send.py?rev=1351786&view=auto
==============================================================================
--- qpid/proton/trunk/examples/messenger/send.py (added)
+++ qpid/proton/trunk/examples/messenger/send.py Tue Jun 19 17:50:15 2012
@@ -0,0 +1,49 @@
+#!/usr/bin/python
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements.  See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership.  The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License.  You may obtain a copy of the License at
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied.  See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+import sys, optparse
+from xproton import *
+
+parser = optparse.OptionParser(usage="usage: %prog [options] msg_1 ... msg_n",
+                               description="simple message sender")
+parser.add_option("-a", "--address", default="//0.0.0.0",
+                  help="address: //<domain>[/<name>] (default %default)")
+
+opts, args = parser.parse_args()
+if not args:
+  args = ["Hello World!"]
+
+mng = pn_messenger()
+pn_messenger_start(mng)
+
+msg = pn_message()
+for m in args:
+  pn_message_set_address(msg, opts.address)
+  pn_message_set_subject(msg, m)
+  if pn_messenger_put(mng, msg):
+    print pn_messenger_error(mng)
+    break
+
+if pn_messenger_send(mng):
+  print pn_messenger_error(mng)
+else:
+  print "sent:", ", ".join(args)
+
+pn_messenger_stop(mng)
+pn_messenger_free(mng)

Propchange: qpid/proton/trunk/examples/messenger/send.py
------------------------------------------------------------------------------
    svn:executable = *

Modified: qpid/proton/trunk/proton-c/bindings/cproton.i
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/bindings/cproton.i?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/bindings/cproton.i (original)
+++ qpid/proton/trunk/proton-c/bindings/cproton.i Tue Jun 19 17:50:15 2012
@@ -1,6 +1,8 @@
 /* Parse these interface header files to generate APIs for script languages */
 %include "proton/types.h"
-%include "proton/errors.h"
+%ignore pn_error_format;
+%ignore pn_error_vformat;
+%include "proton/error.h"
 %include "proton/engine.h"
 %include "proton/message.h"
 %include "proton/sasl.h"

Modified: qpid/proton/trunk/proton-c/include/proton/driver.h
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/include/proton/driver.h?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/include/proton/driver.h (original)
+++ qpid/proton/trunk/proton-c/include/proton/driver.h Tue Jun 19 17:50:15 2012
@@ -22,7 +22,7 @@
  *
  */
 
-#include <proton/errors.h>
+#include <proton/error.h>
 #include <proton/engine.h>
 #include <proton/sasl.h>
 

Modified: qpid/proton/trunk/proton-c/include/proton/engine.h
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/include/proton/engine.h?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/include/proton/engine.h (original)
+++ qpid/proton/trunk/proton-c/include/proton/engine.h Tue Jun 19 17:50:15 2012
@@ -25,7 +25,7 @@
 #include <stdbool.h>
 #include <stddef.h>
 #include <sys/types.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 
 /** @file
  * API for the proton Engine.
@@ -33,7 +33,6 @@
  * @todo
  */
 
-typedef struct pn_error_t pn_error_t;
 typedef struct pn_transport_t pn_transport_t;
 typedef struct pn_connection_t pn_connection_t; /**< Connection */
 typedef struct pn_session_t pn_session_t;       /**< Session */

Copied: qpid/proton/trunk/proton-c/include/proton/error.h (from r1351530, qpid/proton/trunk/proton-c/include/proton/errors.h)
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/include/proton/error.h?p2=qpid/proton/trunk/proton-c/include/proton/error.h&p1=qpid/proton/trunk/proton-c/include/proton/errors.h&r1=1351530&r2=1351786&rev=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/include/proton/errors.h (original)
+++ qpid/proton/trunk/proton-c/include/proton/error.h Tue Jun 19 17:50:15 2012
@@ -1,5 +1,5 @@
-#ifndef _PROTON_ERRORS_H
-#define _PROTON_ERRORS_H 1
+#ifndef _PROTON_ERROR_H
+#define _PROTON_ERROR_H 1
 
 /*
  *
@@ -22,6 +22,10 @@
  *
  */
 
+#include <stdarg.h>
+
+typedef struct pn_error_t pn_error_t;
+
 #define PN_EOS (-1)
 #define PN_ERR (-2)
 #define PN_OVERFLOW (-3)
@@ -29,6 +33,15 @@
 #define PN_STATE_ERR (-5)
 #define PN_ARG_ERR (-6)
 
-const char *pn_error(int err);
+const char *pn_code(int code);
+
+pn_error_t *pn_error();
+void pn_error_free(pn_error_t *error);
+void pn_error_clear(pn_error_t *error);
+int pn_error_set(pn_error_t *error, int code, const char *text);
+int pn_error_vformat(pn_error_t *error, int code, const char *fmt, va_list ap);
+int pn_error_format(pn_error_t *error, int code, const char *fmt, ...);
+int pn_error_code(pn_error_t *error);
+const char *pn_error_text(pn_error_t *error);
 
-#endif /* errors.h */
+#endif /* error.h */

Modified: qpid/proton/trunk/proton-c/include/proton/message.h
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/include/proton/message.h?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/include/proton/message.h (original)
+++ qpid/proton/trunk/proton-c/include/proton/message.h Tue Jun 19 17:50:15 2012
@@ -39,6 +39,8 @@ pn_message_t * pn_message();
 void           pn_message_free(pn_message_t *msg);
 
 void           pn_message_clear(pn_message_t *msg);
+int            pn_message_errno(pn_message_t *msg);
+const char *   pn_message_error(pn_message_t *msg);
 
 // standard message headers and properties
 bool           pn_message_is_durable            (pn_message_t *msg);

Modified: qpid/proton/trunk/proton-c/include/proton/messenger.h
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/include/proton/messenger.h?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/include/proton/messenger.h (original)
+++ qpid/proton/trunk/proton-c/include/proton/messenger.h Tue Jun 19 17:50:15 2012
@@ -29,6 +29,9 @@ typedef int pn_source_t;
 typedef int pn_target_t;
 
 pn_messenger_t *pn_messenger();
+void pn_messenger_free(pn_messenger_t *messenger);
+
+const char *pn_messenger_error(pn_messenger_t *messenger);
 
 int pn_messenger_start(pn_messenger_t *messenger);
 int pn_messenger_stop(pn_messenger_t *messenger);

Modified: qpid/proton/trunk/proton-c/src/buffer.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/buffer.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/buffer.c (original)
+++ qpid/proton/trunk/proton-c/src/buffer.c Tue Jun 19 17:50:15 2012
@@ -20,7 +20,7 @@
  */
 
 #include <proton/buffer.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 #include <stdbool.h>
 #include <stdlib.h>
 #include <string.h>

Modified: qpid/proton/trunk/proton-c/src/codec/codec.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/codec/codec.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/codec/codec.c (original)
+++ qpid/proton/trunk/proton-c/src/codec/codec.c Tue Jun 19 17:50:15 2012
@@ -22,7 +22,7 @@
 #define _GNU_SOURCE
 
 #include <proton/codec.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 #include <proton/buffer.h>
 #include <proton/util.h>
 #include <stdio.h>

Modified: qpid/proton/trunk/proton-c/src/dispatcher/dispatcher.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/dispatcher/dispatcher.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/dispatcher/dispatcher.c (original)
+++ qpid/proton/trunk/proton-c/src/dispatcher/dispatcher.c Tue Jun 19 17:50:15 2012
@@ -105,7 +105,7 @@ ssize_t pn_dispatcher_input(pn_dispatche
       size_t dsize = frame.size;
       int e = pn_data_decode(disp->args, frame.payload, &dsize);
       if (e) {
-        fprintf(stderr, "Error decoding frame: %s\n", pn_error(e));
+        fprintf(stderr, "Error decoding frame: %s\n", pn_code(e));
         pn_fprint_data(stderr, frame.payload, frame.size);
         fprintf(stderr, "\n");
         return e;
@@ -175,7 +175,7 @@ int pn_post_frame(pn_dispatcher_t *disp,
   int err = pn_data_vfill(disp->output_args, fmt, ap);
   va_end(ap);
   if (err) {
-    fprintf(stderr, "error posting frame: %s, %s\n", fmt, pn_error(err));
+    fprintf(stderr, "error posting frame: %s, %s\n", fmt, pn_code(err));
     return PN_ERR;
   }
 
@@ -193,7 +193,7 @@ int pn_post_frame(pn_dispatcher_t *disp,
         size *= 2;
         continue;
       } else {
-        fprintf(stderr, "error posting frame: %s", pn_error(err));
+        fprintf(stderr, "error posting frame: %s", pn_code(err));
         return PN_ERR;
       }
     } else if (size - wr < disp->output_size) {

Modified: qpid/proton/trunk/proton-c/src/driver.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/driver.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/driver.c (original)
+++ qpid/proton/trunk/proton-c/src/driver.c Tue Jun 19 17:50:15 2012
@@ -460,7 +460,7 @@ static void pn_connector_process_input(p
       if (n == PN_EOS) {
         pn_connector_consume(ctor, ctor->input_size);
       } else {
-        printf("error in process_input: %s\n", pn_error(n));
+        printf("error in process_input: %s\n", pn_code(n));
       }
       ctor->input_done = true;
       break;
@@ -559,7 +559,7 @@ static void pn_connector_process_output(
       break;
     } else {
       if (n != PN_EOS) {
-        fprintf(stderr, "error in process_output: %s\n", pn_error(n));
+        fprintf(stderr, "error in process_output: %s\n", pn_code(n));
       }
       ctor->output_done = true;
       break;

Modified: qpid/proton/trunk/proton-c/src/engine/engine-internal.h
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/engine/engine-internal.h?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/engine/engine-internal.h (original)
+++ qpid/proton/trunk/proton-c/src/engine/engine-internal.h Tue Jun 19 17:50:15 2012
@@ -27,13 +27,6 @@
 #include "../dispatcher/dispatcher.h"
 #include "../util.h"
 
-#define DESCRIPTION (1024)
-
-struct pn_error_t {
-  const char *condition;
-  char description[DESCRIPTION];
-};
-
 typedef enum pn_endpoint_type_t {CONNECTION, SESSION, SENDER, RECEIVER, TRANSPORT} pn_endpoint_type_t;
 
 typedef struct pn_endpoint_t pn_endpoint_t;
@@ -41,7 +34,7 @@ typedef struct pn_endpoint_t pn_endpoint
 struct pn_endpoint_t {
   pn_endpoint_type_t type;
   pn_state_t state;
-  pn_error_t error;
+  pn_error_t *error;
   pn_endpoint_t *endpoint_next;
   pn_endpoint_t *endpoint_prev;
   pn_endpoint_t *transport_next;
@@ -105,6 +98,7 @@ struct pn_transport_t {
   size_t session_capacity;
   pn_session_state_t **channels;
   size_t channel_capacity;
+  const char *condition;
   char scratch[SCRATCH];
 };
 

Modified: qpid/proton/trunk/proton-c/src/engine/engine.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/engine/engine.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/engine/engine.c (original)
+++ qpid/proton/trunk/proton-c/src/engine/engine.c Tue Jun 19 17:50:15 2012
@@ -361,7 +361,7 @@ void pn_endpoint_init(pn_endpoint_t *end
 {
   endpoint->type = type;
   endpoint->state = PN_LOCAL_UNINIT | PN_REMOTE_UNINIT;
-  endpoint->error = (pn_error_t) {.condition = NULL};
+  endpoint->error = pn_error();
   endpoint->endpoint_next = NULL;
   endpoint->endpoint_prev = NULL;
   endpoint->transport_next = NULL;
@@ -404,7 +404,7 @@ pn_state_t pn_connection_state(pn_connec
 
 pn_error_t *pn_connection_error(pn_connection_t *connection)
 {
-  return connection ? &connection->endpoint.error : NULL;
+  return connection ? connection->endpoint.error : NULL;
 }
 
 const char *pn_connection_container(pn_connection_t *connection)
@@ -642,7 +642,7 @@ pn_state_t pn_session_state(pn_session_t
 
 pn_error_t *pn_session_error(pn_session_t *session)
 {
-  return &session->endpoint.error;
+  return session->endpoint.error;
 }
 
 int pn_do_open(pn_dispatcher_t *disp);
@@ -682,6 +682,8 @@ void pn_transport_init(pn_transport_t *t
 
   transport->channels = NULL;
   transport->channel_capacity = 0;
+
+  transport->condition = NULL;
 }
 
 pn_session_state_t *pn_session_get_state(pn_transport_t *transport, pn_session_t *ssn)
@@ -732,7 +734,7 @@ pn_transport_t *pn_transport(pn_connecti
 
 pn_error_t *pn_transport_error(pn_transport_t *transport)
 {
-  return &transport->endpoint.error;
+  return transport->endpoint.error;
 }
 
 void pn_link_init(pn_link_t *link, int type, pn_session_t *session, const char *name)
@@ -839,7 +841,7 @@ pn_state_t pn_link_state(pn_link_t *link
 
 pn_error_t *pn_link_error(pn_link_t *link)
 {
-  return &link->endpoint.error;
+  return link->endpoint.error;
 }
 
 const char *pn_link_name(pn_link_t *link)
@@ -1032,24 +1034,26 @@ void pn_settle(pn_delivery_t *delivery)
 
 int pn_post_close(pn_transport_t *transport)
 {
-  const char *condition = transport->endpoint.error.condition;
+  const char *condition = transport->condition;
   return pn_post_frame(transport->disp, 0, "DL[?DL[s]]", CLOSE, (bool) condition, ERROR, condition);
 }
 
 int pn_do_error(pn_transport_t *transport, const char *condition, const char *fmt, ...)
 {
   va_list ap;
-  transport->endpoint.error.condition = condition;
+  transport->condition = condition;
   va_start(ap, fmt);
+  char buf[1024];
   // XXX: result
-  vsnprintf(transport->endpoint.error.description, DESCRIPTION, fmt, ap);
+  vsnprintf(buf, 1024, fmt, ap);
   va_end(ap);
+  pn_error_set(transport->endpoint.error, PN_ERR, buf);
   if (!transport->close_sent) {
     pn_post_close(transport);
     transport->close_sent = true;
   }
   transport->disp->halt = true;
-  fprintf(stderr, "ERROR %s %s\n", condition, transport->endpoint.error.description);
+  fprintf(stderr, "ERROR %s %s\n", condition, pn_error_text(transport->endpoint.error));
   return PN_ERR;
 }
 

Modified: qpid/proton/trunk/proton-c/src/error.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/error.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/error.c (original)
+++ qpid/proton/trunk/proton-c/src/error.c Tue Jun 19 17:50:15 2012
@@ -19,11 +19,83 @@
  *
  */
 
-#include <proton/errors.h>
+#include <proton/error.h>
+#include <stdlib.h>
+#include "util.h"
 
-const char *pn_error(int err)
+struct pn_error_t {
+  int code;
+  char *text;
+  pn_error_t *root;
+};
+
+pn_error_t *pn_error()
+{
+  pn_error_t *error = malloc(sizeof(pn_error_t));
+  error->code = 0;
+  error->text = NULL;
+  error->root = NULL;
+  return error;
+}
+
+void pn_error_free(pn_error_t *error)
+{
+  if (error) {
+    free(error->text);
+    free(error);
+  }
+}
+
+void pn_error_clear(pn_error_t *error)
+{
+  if (error) {
+    error->code = 0;
+    free(error->text);
+    error->text = NULL;
+    error->root = NULL;
+  }
+}
+
+int pn_error_set(pn_error_t *error, int code, const char *text)
+{
+  pn_error_clear(error);
+  error->code = code;
+  error->text = pn_strdup(text);
+  return code;
+}
+
+int pn_error_vformat(pn_error_t *error, int code, const char *fmt, va_list ap)
+{
+  char text[1024];
+  int n = vsnprintf(text, 1024, fmt, ap);
+  if (n >= 1024) {
+    text[1023] = '\0';
+  }
+  return pn_error_set(error, code, text);
+}
+
+int pn_error_format(pn_error_t *error, int code, const char *fmt, ...)
+{
+  va_list ap;
+  va_start(ap, fmt);
+  int rcode = pn_error_vformat(error, code, fmt, ap);
+  va_end(ap);
+  return rcode;
+}
+
+int pn_error_code(pn_error_t *error)
+{
+  return error ? error->code : PN_ARG_ERR;
+}
+
+const char *pn_error_text(pn_error_t *error)
+{
+  return error ? error->text : NULL;
+}
+
+const char *pn_code(int code)
 {
-  switch (err)
+  switch (code)
   {
   case 0: return "<ok>";
   case PN_EOS: return "PN_EOS";

Modified: qpid/proton/trunk/proton-c/src/message/message.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/message/message.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/message/message.c (original)
+++ qpid/proton/trunk/proton-c/src/message/message.c Tue Jun 19 17:50:15 2012
@@ -22,7 +22,7 @@
 #include <proton/message.h>
 #include <proton/buffer.h>
 #include <proton/codec.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 #include <proton/parser.h>
 #include <stdlib.h>
 #include <string.h>
@@ -149,6 +149,15 @@ void pn_message_clear(pn_message_t *msg)
   if (msg->data) pn_data_clear(msg->data);
 }
 
+int pn_message_errno(pn_message_t *msg)
+{
+  if (msg && msg->parser) {
+    return pn_parser_errno(msg->parser);
+  } else {
+    return 0;
+  }
+}
+
 const char *pn_message_error(pn_message_t *msg)
 {
   if (msg && msg->parser) {

Modified: qpid/proton/trunk/proton-c/src/messenger.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/messenger.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/messenger.c (original)
+++ qpid/proton/trunk/proton-c/src/messenger.c Tue Jun 19 17:50:15 2012
@@ -30,8 +30,10 @@ struct pn_messenger_t {
   pn_driver_t *driver;
   pn_connector_t *connectors[1024];
   size_t size;
+  size_t listeners;
   int credit;
   uint64_t next_tag;
+  pn_error_t *error;
 };
 
 pn_messenger_t *pn_messenger()
@@ -41,13 +43,32 @@ pn_messenger_t *pn_messenger()
   if (m) {
     m->driver = pn_driver();
     m->size = 0;
+    m->listeners = 0;
     m->credit = 0;
     m->next_tag = 0;
+    m->error = pn_error();
   }
 
   return m;
 }
 
+void pn_messenger_free(pn_messenger_t *messenger)
+{
+  if (messenger) {
+    pn_driver_destroy(messenger->driver);
+    pn_error_free(messenger->error);
+  }
+}
+
+const char *pn_messenger_error(pn_messenger_t *messenger)
+{
+  if (messenger) {
+    return pn_error_text(messenger->error);
+  } else {
+    return NULL;
+  }
+}
+
 void pn_messenger_flow(pn_messenger_t *messenger)
 {
   while (messenger->credit > 0) {
@@ -258,6 +279,7 @@ pn_connection_t *pn_messenger_domain(pn_
   }
 
   pn_connector_t *connector = pn_connector(messenger->driver, domain, "5672", NULL);
+  if (!connector) return NULL;
   messenger->connectors[messenger->size++] = connector;
   pn_sasl_t *sasl = pn_connector_sasl(connector);
   pn_sasl_mechanisms(sasl, "ANONYMOUS");
@@ -284,6 +306,7 @@ pn_link_t *pn_messenger_link(pn_messenge
   parse_address(address ? buf : NULL, &domain, &name);
 
   pn_connection_t *connection = pn_messenger_domain(messenger, domain);
+  if (!connection) return NULL;
 
   pn_link_t *link = pn_link_head(connection, PN_LOCAL_ACTIVE);
   while (link) {
@@ -329,23 +352,42 @@ pn_listener_t *pn_messenger_isource(pn_m
   parse_address(buf, &domain, &name);
 
   pn_listener_t *listener = pn_listener(messenger->driver, domain + 1, "5672", pn_strdup(domain + 1));
+  if (listener) {
+    messenger->listeners++;
+  }
   return listener;
 }
 
 int pn_messenger_subscribe(pn_messenger_t *messenger, const char *source)
 {
   if (strlen(source) >= 3 && source[0] == '/' && source[1] == '/' && source[2] == '~') {
-    pn_messenger_isource(messenger, source);
-    return 0;
+    pn_listener_t *lnr = pn_messenger_isource(messenger, source);
+    if (lnr) {
+      return 0;
+    } else {
+      return pn_error_format(messenger->error, PN_ERR,
+                             "unable to subscribe to source: %s", source);
+    }
   } else {
-    pn_messenger_source(messenger, source);
-    return 0;
+    pn_link_t *src = pn_messenger_source(messenger, source);
+    if (src) {
+      return 0;
+    } else {
+      return pn_error_format(messenger->error, PN_ERR,
+                             "unable to subscribe to source: %s", source);
+    }
   }
 }
 
 int pn_messenger_put(pn_messenger_t *messenger, pn_message_t *msg)
 {
-  pn_link_t *sender = pn_messenger_target(messenger, pn_message_get_address(msg));
+  if (!messenger) return PN_ARG_ERR;
+  if (!msg) return pn_error_set(messenger->error, PN_ARG_ERR, "null message");
+  const char *address = pn_message_get_address(msg);
+  pn_link_t *sender = pn_messenger_target(messenger, address);
+  if (!sender)
+    return pn_error_format(messenger->error, PN_ERR,
+                           "unable to send to address: %s", address);
   // XXX: proper tag
   char tag[8];
   void *ptr = &tag;
@@ -430,6 +472,9 @@ int pn_messenger_send(pn_messenger_t *me
 
 int pn_messenger_recv(pn_messenger_t *messenger, int n)
 {
+  if (!messenger) return PN_ARG_ERR;
+  if (!messenger->listeners && !messenger->size)
+    return pn_error_format(messenger->error, PN_STATE_ERR, "no valid sources");
   messenger->credit += n;
   pn_messenger_flow(messenger);
   return pn_messenger_sync(messenger, pn_messenger_rcvd);
@@ -451,8 +496,11 @@ int pn_messenger_get(pn_messenger_t *mes
         pn_settle(d);
         if (n < 0) return n;
         int err = pn_message_decode(msg, PN_AMQP, buf, n);
-        if (err) return err;
-        return 0;
+        if (err)
+          return pn_error_format(messenger->error, err, "error decoding message: %s",
+                                 pn_message_error(msg));
+        else
+          return 0;
       }
       d = pn_work_next(d);
     }

Modified: qpid/proton/trunk/proton-c/src/parser.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/parser.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/parser.c (original)
+++ qpid/proton/trunk/proton-c/src/parser.c Tue Jun 19 17:50:15 2012
@@ -21,7 +21,7 @@
 
 #include <proton/parser.h>
 #include <proton/scanner.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 #include <stdlib.h>
 #include <string.h>
 #include <ctype.h>

Modified: qpid/proton/trunk/proton-c/src/proton.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/proton.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/proton.c (original)
+++ qpid/proton/trunk/proton-c/src/proton.c Tue Jun 19 17:50:15 2012
@@ -62,13 +62,13 @@ int buffer(int argc, char **argv)
   pn_data_t *data = pn_data(16);
   int err = pn_data_fill(data, "Ds[iSi]", "desc", 1, "two", 3);
   if (err) {
-    printf("%s\n", pn_error(err));
+    printf("%s\n", pn_code(err));
   }
   pn_data_print(data); printf("\n");
   pn_bytes_t str;
   err = pn_data_scan(data, "D.[.S.]", &str);
   if (err) {
-    printf("%s\n", pn_error(err));
+    printf("%s\n", pn_code(err));
   } else {
     printf("%.*s\n", (int) str.size, str.start);
   }
@@ -96,7 +96,7 @@ int value(int argc, char **argv)
                           "pi", 3.14159265359, "e", 2.7,
                           (uint64_t) 42, PN_SYMBOL, "one", "two", "three");
   if (err) {
-    printf("err = %s\n", pn_error(err));
+    printf("err = %s\n", pn_code(err));
   } else {
     pn_print_atoms(&atoms);
     printf("\n");
@@ -122,7 +122,7 @@ int value(int argc, char **argv)
   err = pn_scan_atoms(&atoms, "DDsL[i[i]?i]{sfsf}@DLT[.s.]", &blam, &n, &one, &two, &threeq, &three,
                       &key1, &val1, &key2, &val2, &al, &type, &sym);
   if (err) {
-    printf("err = %s\n", pn_error(err));
+    printf("err = %s\n", pn_code(err));
   } else {
     printf("scan=%.*s %" PRIu64 " %i %i %i %.*s %f %.*s %f %" PRIu64 " %i %.*s\n", (int) blam.size,
 	   blam.start, n, one, two, three, (int) key1.size, key1.start, val1, (int) key2.size,
@@ -154,18 +154,18 @@ int value(int argc, char **argv)
 
   err = pn_parser_parse(parser, str, &parserd);
   if (err) {
-    printf("parse err=%s, %s\n", pn_error(err), pn_parser_error(parser));
+    printf("parse err=%s, %s\n", pn_code(err), pn_parser_error(parser));
   } else {
     printf("--\n");
     for (int i = 0; i < parserd.size; i++) {
       printf("%s: ", pn_type_str(parserd.start[i].type));
       err = pn_print_atom(parserd.start[i]);
-      if (err) printf("err=%s", pn_error(err));
+      if (err) printf("err=%s", pn_code(err));
       printf("\n");
     }
     printf("--\n");
     err = pn_print_atoms(&parserd);
-    if (err) printf("print err=%s", pn_error(err));
+    if (err) printf("print err=%s", pn_code(err));
     printf("\n");
   }
 

Modified: qpid/proton/trunk/proton-c/src/scanner.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/scanner.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/scanner.c (original)
+++ qpid/proton/trunk/proton-c/src/scanner.c Tue Jun 19 17:50:15 2012
@@ -20,7 +20,7 @@
  */
 
 #include <proton/scanner.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 #include <stdbool.h>
 #include <stdlib.h>
 #include <stdio.h>
@@ -36,8 +36,7 @@ struct pn_scanner_t {
   char *atoms;
   size_t size;
   size_t capacity;
-  int errno;
-  char error[ERROR_SIZE];
+  pn_error_t *error;
 };
 
 const char *pn_token_type(pn_token_type_t type)
@@ -75,8 +74,7 @@ pn_scanner_t *pn_scanner()
   pn_scanner_t *scanner = malloc(sizeof(pn_scanner_t));
   if (scanner) {
     scanner->input = NULL;
-    scanner->errno = 0;
-    scanner->error[0] = '\0';
+    scanner->error = pn_error();
   }
   return scanner;
 }
@@ -121,44 +119,40 @@ int pn_scanner_err(pn_scanner_t *scanner
 
 int pn_scanner_verr(pn_scanner_t *scanner, int code, const char *fmt, va_list ap)
 {
-  scanner->errno = code;
+  char error[ERROR_SIZE];
 
   int line, col;
   pn_scanner_line_info(scanner, &line, &col);
   int size = scanner->token.size;
-  int ln = snprintf(scanner->error, ERROR_SIZE,
+  int ln = snprintf(error, ERROR_SIZE,
                     "input line %i column %i %s:'%.*s': ", line, col,
                     pn_token_type(scanner->token.type),
                     size, scanner->token.start);
   if (ln >= ERROR_SIZE) {
     return pn_scanner_err(scanner, code, "error info truncated");
   } else if (ln < 0) {
-    scanner->error[0] = '\0';
+    error[0] = '\0';
   }
 
-  int n = snprintf(scanner->error + ln, ERROR_SIZE - ln, fmt, ap);
+  int n = snprintf(error + ln, ERROR_SIZE - ln, fmt, ap);
 
   if (n >= ERROR_SIZE - ln) {
     return pn_scanner_err(scanner, code, "error info truncated");
   } else if (n < 0) {
-    scanner->error[0] = '\0';
+    error[0] = '\0';
   }
 
-  return code;
+  return pn_error_set(scanner->error, code, error);
 }
 
 int pn_scanner_errno(pn_scanner_t *scanner)
 {
-  return scanner->errno;
+  return pn_error_code(scanner->error);
 }
 
 const char *pn_scanner_error(pn_scanner_t *scanner)
 {
-  if (scanner->errno) {
-    return scanner->error;
-  } else {
-    return NULL;
-  }
+  return pn_error_text(scanner->error);
 }
 
 void pn_scanner_emit(pn_scanner_t *scanner, pn_token_type_t type, const char *start, size_t size)

Modified: qpid/proton/trunk/proton-c/src/util.c
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/util.c?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/util.c (original)
+++ qpid/proton/trunk/proton-c/src/util.c Tue Jun 19 17:50:15 2012
@@ -28,7 +28,7 @@
 #include <stdint.h>
 #include <ctype.h>
 #include <string.h>
-#include <proton/errors.h>
+#include <proton/error.h>
 
 ssize_t pn_quote_data(char *dst, size_t capacity, const char *src, size_t size)
 {

Modified: qpid/proton/trunk/proton-c/src/util.h
URL: http://svn.apache.org/viewvc/qpid/proton/trunk/proton-c/src/util.h?rev=1351786&r1=1351785&r2=1351786&view=diff
==============================================================================
--- qpid/proton/trunk/proton-c/src/util.h (original)
+++ qpid/proton/trunk/proton-c/src/util.h Tue Jun 19 17:50:15 2012
@@ -22,10 +22,12 @@
  *
  */
 
+#include <errno.h>
+#include <stdbool.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
-#include <errno.h>
+#include <sys/types.h>
 
 ssize_t pn_quote_data(char *dst, size_t capacity, const char *src, size_t size);
 void pn_fprint_data(FILE *stream, const char *bytes, size_t size);



---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org