2.3. Bug Fixes


950501 - python clients throw "[Errno 1] _ssl.c:1217: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry"

In circumstances when the python client code tried to re-write queued data to a previously blocked socket, it was discovered that the python client code was changing the pointer used prior to the socket blocking. The underlying OpenSSL library detected that the pointer had changed since the last call to write, and threw an exception. The python client is now modified to keep the original pointer constant when new data is added. When the socket becomes writable again, the address of the pointer passed to the socket is identical to the address passed prior to the socket blocking, as required by OpenSSL.
908224 - reconnect_timeout ignored in qpid.messaging.Connection()

It was discovered that the reconnect_timeout argument was ignored when creating a connection. Passing a reconnect_timeout when creating a connection did not raise an exception after the specified number of seconds. The fix passes the reconnect_timeout to the open() method, which allows an attempt to create a connection to timeout correctly.
719589 - Python example "server" fails

It was discovered that the server example application referenced a non-existent ReceiveError, which caused the server example to crash upon start-up. The fix corrects the ReceiveError to ReceiverError, which allows the server example to operate as expected.
772028 - malfunctioning unsettled() receiver method

It was discovered that the python messaging method receiver.unsettled() referenced a non-existent "acked" variable. Calling receiver.unsettled() raised an exception. The fix now uses session.acked instead of receiver.acked, which ensures the correct number of unsettled messages are returned.


1023322 - qpid c++ client Address string compatibility regression in parsing (long) int value postfixed by 'L'

It was discovered that numeric queue configuration options specified as strings were not checked when parsed, to ensure there were no trailing non-digit characters after the number. Values such as 40000L were previously accepted as was 40000xyz, with the trailing characters simply being ignored. This may have given the incorrect impression in some cases that values such as 40000L were recognized as being a long integer. The parsing logic when converting from string to numeric option now ensures there are no illegal trailing characters. Values such as 40000L are now rejected as invalid.
1012852 - [AMQP 1.0] Message size resolution differs for AMQP 0.10 and 1.0

It was discovered that qpid-cpp was only reporting broker statistics or enforcing queue depth limits based on the size of the AMPQ 0-10 message body, instead of additionally including the header size. This caused statistics to incorrectly reflect the size of headers in the message. For example, a message with no body but many headers would not contribute to the aggregate size in bytes of a queue onto which it was enqueued. Because AMQP 1.0 messages included headers and other meta-data with the message, this issue had the potential to introduce unnecessary confusion. The size of AMQP 0-10 messages is now fixed to take the sum of the content and headers segments into account when calculating the logical size of the message. Statistics and queue limits reported or controlled in bytes now more accurately reflect the logical size of the message, and there is less difference between the 1.0 and 0-10 encodings in terms of their overall size. It is expected that queue limits will be reached earlier due to the correct logical size now being reported and enforced.
913448 - invoking Receiver::fetch() in a loop for slow producer causes only first <prefetch> messages received

It was discovered that if a fetch timed-out, information about the current credit window quota was cleared from the broker. This prevented the credit window reported by the client to be moved forward by the broker, and prevent a receiver from receiving messages even though there were messages available on the queue. The broker is now notified which messages have been received whenever a fetch times out. The credit window is now always moved forward correctly, and messages continue to be received when available.
919017 - XML exchange does not update statistics when no binding key matches routing key

It was discovered that doRoute(msg, b) was not called when the routing key of a message did not match the binding key of an XML exchange. This caused the QMF statistics msgIn, msgDrop, byteIn and byteDrop to incorrectly update. The fix calls doRoute(…) even if the routing key and binding key do not match. The QMF statistics now update as expected.
865689 - "Recovery found" logs of wrong severity

An issue with journal recovery messages reported at the WARN level caused customers to assume that action on their part was required to fix the issue when this was not the case. The fix lowers the priority of the recovery messages to INFO level, which sets the appropriate log level for this normal provisioning setting.
955578 - Multi-threaded fetching messages from different queues causes fetch delay

It was discovered that if there was more than one thread concurrently processing the session queue, a message of interest to one thread may be processed by another thread preventing the correct thread from seeing it. The fix ensures only one thread at a time can process the incoming queue. Concurrent fetch() calls now work as expected without needing to timeout to see a message as it arrives.
912519 - broker ignores if_empty and if_unused flags when deleting queues

It was discovered that the C++ broker ignored the if_empty and if_unused flags when a queue was deleted. If the queue was in use or non-empty, and a call was made to delete the queue only if it was unused or empty, the queue would incorrectly be deleted anyway. The fix inspects the if_empty and if_unused flags, and will not delete the queue if it is in use or non-empty when appropriate. Queues are no longer incorrectly deleted when the if_empty or if_unused flags are used.
740152 - Invalid handling of qpid.max_size

It was discovered that the broker retrieved the maximum queue size option as a uint32, even though it should be a uint64. The maximum value expressible for the aggregate queue size in bytes was needlessly limited, which prevented large queue sizes from being configured. The broker now correctly retrieves the size as a uint64. Any value expressible as a uint64 is now valid as the maximum queue size (in bytes).


784270 - AMQDestination equals() validation is broken for addresses

It was discovered that the AMQDestination equals method did not take into account the differences between the ADDR and BURL syntax. The legacy fields were not populated until the address was validated resulting in a null pointer exception if equals was called beforehand. The fix now handles equals and hashcode separately for ADDR and BURL, which allow the equals and hashcode methods to behave as expected.
828442 - When sending a message, Java client gets unauthorized-access error due to using "ILADDRESS=<emailaddr>" as the user-id

The Java client code was excepting the Certificate Name (CN) to be the first entry in the name string. If the CN was not the first entry, the extracted value was not the correct user-id, which could have resulted in issues when message authentication was used. The fix now ensures the parsing logic finds the CN string first before extracting the user-id, which results in the correct user-id not being extracted from the name string.
845999 - second invocation of createConsumer fails for queue in JNDI properties file

If the address had a delete directive, the queue or exchange would be deleted when the consumer or producer closed (as specified in the delete directive). Because the destination was marked as resolved, no validation (or creation) of the queue or exchange was performed when it was used again. A not-found-exception occurred if the same destination was reused to create another producer or consumer after the queue or exchange was deleted. The fix now resets the address resolution flag when the queue or exchange is deleted. If the same exchange is re-used, it will go through address resolution again. If there is a directive to create the queue or exchange, it will be created. An error is thrown otherwise.
890532 - NullPointerException raised in AMQDestination.equals method

It was discovered that the AMQDestination.equals method did not take into account the differences between the ADDR and BURL syntax. The legacy fields were not populated until the address was validated, which resulted in a null pointer exception if equals was called beforehand.The fix now handles equals and hashcode separately for ADDR and BURL, which now allow the equals and and hashcode methods to behave as expected.
896570 - retries parameter ignored for the very first broker

It was discovered that when the current broker details were not set, the _serverRetries parameter was set to zero. This caused the Java client failover to not attempt to retry after the very first connection loss to the broker it was already connected to. The fix sets the current broker details in the constructor, which ensures the retry parameter is honored on the first broker when set.
728509 - Specifying username/password in JMS clients should not be mandatory

It was discovered that the URLParser threw an exception if the username and password was missing from a connection URL. Due to this behavior, it was mandatory to specify a username and password, even if the SASL mechanism chosen did not require it. The URL parser no longer throws an exception if the username or password is missing. Instead it checks if the chosen SASL mechanism (selected during connection negotiation) requires it and then throws an exception at that point.
755651 - getJMSReplyTo does not return null for null ReplyTo property

It was discovered that the replyTo structure in getJMSReplyTo was checked for null values, however it’s attributes were not checked. The replyTo struct could be set with null for the exchange and routing key, which resulted in a Destination being created with the exchange and routing key set to null on the receivers side. The fix checks for a null exchange and routing key, and returns null. This allows getJMSReplyTo to return null as designed.
705015 - Message.setJMSMessageID() not compatible with ActiveMQ MessageID

It was discovered that the message implementation did not allow a non-UUID string to be set as the message ID. When a Qpid JMS message was sent through a third-party message provider, setting the message-id resulted in an exception if the message-id was not a valid UUID. The fix now allows any string prefixed with an "ID:", to be set as the message ID. When sending the message through the Qpid JMS producer, it is set as a UUID (as per the JMS spec and AMQP spec).


715284 - Examples C++ "hello_world" and "hello_xml" are not able to be compilled from solution file

It was discovered that the hello_world and hello_xml projects were not produced by default from the distribution kit. Users requiring these projects needed to add the projects manually to the CMakeLists.txt file before running cmake. The fix adds the files to CMakeLists.txt, which results in hello_world and hello_xml being produced by default.


872111 - qpid-config traceback in case of ACL denial

It was discovered that if an operation was performed that caused an ACL denied exception, and that connection was closed, the entire backtrace of the ACL exception was displayed instead of only the ACL denied error message. The fix now detects when an ACL exception is raised during connection close, and does not display the backtrace. Instead, only the ACL error text is displayed when the connection is closed.
895515 - '--ssl-key' option missing in several management tools

It was discovered that some of the QPID command-line tools did not provide a way for the user to supply a private key when a certificate was used to identify the user of the command to the broker. This caused the command to fail because it was not able to use the certificate without the key. The fix ensures all QPID command line tools that allow user identification through a self-identifying certificate now allow the private key to be supplied via the --ssl-key option. This option takes a path to a file that contains the certificate’s private key in PEM format. The command line tool now presents the certificate to the broker for authorization, and the command is executed successfully. This feature is documented in the "Enable SSL in Python Clients" section of the Messaging Installation and Configuration Guide and the "Connection Options Reference" of the Messaging Programming Reference Guide.