diff options
author | Michael Bridgen <mikeb@lshift.net> | 2009-11-11 16:06:42 +0000 |
---|---|---|
committer | Michael Bridgen <mikeb@lshift.net> | 2009-11-11 16:06:42 +0000 |
commit | 3281811ad1d2a066241ed670fbfe6ea76738058d (patch) | |
tree | dffc990f456c863a896643efc04dcb7374250a51 | |
parent | 8392aa492f3ff4d503c7b635568a9defeefe51be (diff) | |
download | rabbitmq-server-bug21929.tar.gz |
Support field-arrays in the parser. This involves a similar factoringbug21929
of field-value to the generator (since field-value is used both for
field-table and field-array).
Also fixed a dumb mistake in the array bit of rabbit_binary_generator.
-rw-r--r-- | src/rabbit_binary_generator.erl | 2 | ||||
-rw-r--r-- | src/rabbit_binary_parser.erl | 65 | ||||
-rw-r--r-- | src/rabbit_tests.erl | 14 |
3 files changed, 49 insertions, 32 deletions
diff --git a/src/rabbit_binary_generator.erl b/src/rabbit_binary_generator.erl index 3e0e99a0..01ac4f02 100644 --- a/src/rabbit_binary_generator.erl +++ b/src/rabbit_binary_generator.erl @@ -183,7 +183,7 @@ table_to_binary(Table) when is_list(Table) -> array_to_binary(Array) when is_list(Array) -> BinArray = generate_array(Array), - [<<(size(Array)):32>>, BinArray]. + [<<(size(BinArray)):32>>, BinArray]. generate_table(Table) when is_list(Table) -> list_to_binary(lists:map(fun table_field_to_binary/1, Table)). diff --git a/src/rabbit_binary_parser.erl b/src/rabbit_binary_parser.erl index 4ef382aa..506e87ec 100644 --- a/src/rabbit_binary_parser.erl +++ b/src/rabbit_binary_parser.erl @@ -56,45 +56,57 @@ parse_table(<<>>) -> []; +parse_table(<<NLen:8/unsigned, NameString:NLen/binary, ValueAndRest/binary>>) -> + {Type, Value, Rest} = parse_field_value(ValueAndRest), + [{NameString, Type, Value} | parse_table(Rest)]. -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "S", VLen:32/unsigned, ValueString:VLen/binary, Rest/binary>>) -> - [{NameString, longstr, ValueString} | parse_table(Rest)]; +parse_array(<<>>) -> + []; +parse_array(<<ValueAndRest/binary>>) -> + {Type, Value, Rest} = parse_field_value(ValueAndRest), + [{Type, Value} | parse_array(Rest)]. + +parse_field_value(<<"S", VLen:32/unsigned, ValueString:VLen/binary, Rest/binary>>) -> + {longstr, ValueString, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "I", Value:32/signed, Rest/binary>>) -> - [{NameString, signedint, Value} | parse_table(Rest)]; +parse_field_value(<<"I", Value:32/signed, Rest/binary>>) -> + {signedint, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "D", Before:8/unsigned, After:32/unsigned, Rest/binary>>) -> - [{NameString, decimal, {Before, After}} | parse_table(Rest)]; +parse_field_value(<<"D", Before:8/unsigned, After:32/unsigned, Rest/binary>>) -> + {decimal, {Before, After}, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "T", Value:64/unsigned, Rest/binary>>) -> - [{NameString, timestamp, Value} | parse_table(Rest)]; +parse_field_value(<<"T", Value:64/unsigned, Rest/binary>>) -> + {timestamp, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "F", VLen:32/unsigned, Table:VLen/binary, Rest/binary>>) -> - [{NameString, table, parse_table(Table)} | parse_table(Rest)]; +parse_field_value(<<"F", VLen:32/unsigned, Table:VLen/binary, Rest/binary>>) -> + {table, parse_table(Table), Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "b", Value:8/unsigned, Rest/binary>>) -> - [{NameString, byte, Value} | parse_table(Rest)]; +parse_field_value(<<"A", VLen:32/unsigned, Array:VLen/binary, Rest/binary>>) -> + {array, parse_array(Array), Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "d", Value:64/float, Rest/binary>>) -> - [{NameString, double, Value} | parse_table(Rest)]; +parse_field_value(<<"b", Value:8/unsigned, Rest/binary>>) -> + {byte, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "f", Value:32/float, Rest/binary>>) -> - [{NameString, float, Value} | parse_table(Rest)]; +parse_field_value(<<"d", Value:64/float, Rest/binary>>) -> + {double, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "l", Value:64/signed, Rest/binary>>) -> - [{NameString, long, Value} | parse_table(Rest)]; +parse_field_value(<<"f", Value:32/float, Rest/binary>>) -> + {float, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "s", Value:16/signed, Rest/binary>>) -> - [{NameString, short, Value} | parse_table(Rest)]; +parse_field_value(<<"l", Value:64/signed, Rest/binary>>) -> + {long, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "t", Value:8/unsigned, Rest/binary>>) -> - [{NameString, bool, (Value /= 0)} | parse_table(Rest)]; +parse_field_value(<<"s", Value:16/signed, Rest/binary>>) -> + {short, Value, Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "x", VLen:32/unsigned, ValueString:VLen/binary, Rest/binary>>) -> - [{NameString, binary, ValueString} | parse_table(Rest)]; +parse_field_value(<<"t", Value:8/unsigned, Rest/binary>>) -> + {bool, (Value /= 0), Rest}; -parse_table(<<NLen:8/unsigned, NameString:NLen/binary, "V", Rest/binary>>) -> - [{NameString, void, undefined} | parse_table(Rest)]. +parse_field_value(<<"x", VLen:32/unsigned, ValueString:VLen/binary, Rest/binary>>) -> + {binary, ValueString, Rest}; + +parse_field_value(<<"V", Rest/binary>>) -> + {void, undefined, Rest}. parse_properties([], _PropBin) -> @@ -147,7 +159,6 @@ parse_property(bit, 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_tests.erl b/src/rabbit_tests.erl index baa59a19..ba048184 100644 --- a/src/rabbit_tests.erl +++ b/src/rabbit_tests.erl @@ -254,7 +254,7 @@ test_content_properties() -> end. test_field_values() -> - %% NB this does not test inexact numbers (double and float) yet, + %% FIXME this does not test inexact numbers (double and float) yet, %% because they won't pass the equality assertions test_content_prop_roundtrip( [{table, [{<<"longstr">>, longstr, <<"Here is a long string">>}, @@ -268,13 +268,16 @@ test_field_values() -> {<<"short">>, short, 655}, {<<"bool">>, bool, true}, {<<"binary">>, binary, <<"a binary string">>}, - {<<"void">>, void, undefined} + {<<"void">>, void, undefined}, + {<<"array">>, array, [{signedint, 54321}, + {longstr, <<"A long string">>}]} + ]}], << % property-flags 16#8000:16, % table length in bytes - 194:32, + 228:32, 7,"longstr", "S", 21:32, "Here is a long string", % = 34 9,"signedint", "I", 12345:32/signed, % + 15 = 49 @@ -288,7 +291,10 @@ test_field_values() -> 5,"short", "s", 655:16, % + 9 = 154 4,"bool", "t", 1, % + 7 = 161 6,"binary", "x", 15:32, "a binary string", % + 27 = 188 - 4,"void", "V" % + 6 = 194 + 4,"void", "V", % + 6 = 194 + 5,"array", "A", 23:32, % + 11 = 205 + "I", 54321:32, % + 5 = 210 + "S", 13:32, "A long string" % + 18 = 228 >>), passed. |