summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlexandru Scvortov <alexandru@rabbitmq.com>2011-10-18 16:39:05 +0100
committerAlexandru Scvortov <alexandru@rabbitmq.com>2011-10-18 16:39:05 +0100
commit835ffbdafa7c86aca68eb0193171963f00232b85 (patch)
treef6c1e765d8a87169b3402fbfdd0834859cabaf75
parent80be238cda258b231c37b0adadff85ed72c9da9c (diff)
downloadrabbitmq-server-835ffbdafa7c86aca68eb0193171963f00232b85.tar.gz
small routing optimisation and re-add parse_properties
Parse_properties is now only used to test encode_properties.
-rw-r--r--src/rabbit_binary_parser.erl55
-rw-r--r--src/rabbit_router.erl4
2 files changed, 58 insertions, 1 deletions
diff --git a/src/rabbit_binary_parser.erl b/src/rabbit_binary_parser.erl
index f3ca4e98..88026bab 100644
--- a/src/rabbit_binary_parser.erl
+++ b/src/rabbit_binary_parser.erl
@@ -18,7 +18,7 @@
-include("rabbit.hrl").
--export([parse_table/1]).
+-export([parse_table/1, parse_properties/2]).
-export([ensure_content_decoded/1, clear_decoded_content/1]).
%%----------------------------------------------------------------------------
@@ -26,6 +26,8 @@
-ifdef(use_specs).
-spec(parse_table/1 :: (binary()) -> rabbit_framing:amqp_table()).
+-spec(parse_properties/2 ::
+ ([rabbit_framing:amqp_property_type()], binary()) -> [any()]).
-spec(ensure_content_decoded/1 ::
(rabbit_types:content()) -> rabbit_types:decoded_content()).
-spec(clear_decoded_content/1 ::
@@ -92,6 +94,57 @@ parse_field_value(<<"x", VLen:32/unsigned, ValueString:VLen/binary, Rest/binary>
parse_field_value(<<"V", Rest/binary>>) ->
{void, undefined, Rest}.
+
+parse_properties([], _PropBin) ->
+ [];
+parse_properties(TypeList, PropBin) ->
+ FlagCount = length(TypeList),
+ %% round up to the nearest multiple of 15 bits, since the 16th bit
+ %% in each short is a "continuation" bit.
+ FlagsLengthBytes = trunc((FlagCount + 14) / 15) * 2,
+ <<Flags:FlagsLengthBytes/binary, Properties/binary>> = PropBin,
+ <<FirstShort:16, Remainder/binary>> = Flags,
+ parse_properties(0, TypeList, [], FirstShort, Remainder, Properties).
+
+parse_properties(_Bit, [], Acc, _FirstShort,
+ _Remainder, <<>>) ->
+ lists:reverse(Acc);
+parse_properties(_Bit, [], _Acc, _FirstShort,
+ _Remainder, _LeftoverBin) ->
+ exit(content_properties_binary_overflow);
+parse_properties(15, TypeList, Acc, _OldFirstShort,
+ <<NewFirstShort:16,Remainder/binary>>, Properties) ->
+ parse_properties(0, TypeList, Acc, NewFirstShort, Remainder, Properties);
+parse_properties(Bit, [Type | TypeListRest], Acc, FirstShort,
+ Remainder, Properties) ->
+ {Value, Rest} =
+ if (FirstShort band (1 bsl (15 - Bit))) /= 0 ->
+ parse_property(Type, Properties);
+ Type == bit -> {false , Properties};
+ true -> {undefined, Properties}
+ end,
+ parse_properties(Bit + 1, TypeListRest, [Value | Acc], FirstShort,
+ Remainder, Rest).
+
+parse_property(shortstr, <<Len:8/unsigned, String:Len/binary, Rest/binary>>) ->
+ {String, Rest};
+parse_property(longstr, <<Len:32/unsigned, String:Len/binary, Rest/binary>>) ->
+ {String, Rest};
+parse_property(octet, <<Int:8/unsigned, Rest/binary>>) ->
+ {Int, Rest};
+parse_property(shortint, <<Int:16/unsigned, Rest/binary>>) ->
+ {Int, Rest};
+parse_property(longint, <<Int:32/unsigned, Rest/binary>>) ->
+ {Int, Rest};
+parse_property(longlongint, <<Int:64/unsigned, Rest/binary>>) ->
+ {Int, Rest};
+parse_property(timestamp, <<Int:64/unsigned, Rest/binary>>) ->
+ {Int, Rest};
+parse_property(bit, Rest) ->
+ {true, Rest};
+parse_property(table, <<Len:32/unsigned, Table:Len/binary, Rest/binary>>) ->
+ {parse_table(Table), Rest}.
+
ensure_content_decoded(Content = #content{properties = Props})
when Props =/= none ->
Content;
diff --git a/src/rabbit_router.erl b/src/rabbit_router.erl
index e9c4479a..fad18695 100644
--- a/src/rabbit_router.erl
+++ b/src/rabbit_router.erl
@@ -44,6 +44,10 @@
%%----------------------------------------------------------------------------
+deliver([], #delivery{mandatory = false,
+ immediate = false}) ->
+ %% /dev/null optimisation
+ {routed, []};
deliver(QNames, Delivery = #delivery{mandatory = false,
immediate = false}) ->
%% optimisation: when Mandatory = false and Immediate = false,