aboutsummaryrefslogtreecommitdiffstats
path: root/lib/mnesia/src/mnesia_loader.erl
diff options
context:
space:
mode:
authorIgor Ribeiro Sucupira <[email protected]>2010-01-10 03:37:34 -0200
committerBjörn Gustavsson <[email protected]>2010-02-02 12:18:23 +0100
commit3757d8fb1dfd1ff9b80aed2376070b5c4888aaba (patch)
treeb45c518db1277d723c6d7b69bb00fd960c93a970 /lib/mnesia/src/mnesia_loader.erl
parent36c0041ea56d915ba9a2259cc918fca76b8c08f9 (diff)
downloadotp-3757d8fb1dfd1ff9b80aed2376070b5c4888aaba.tar.gz
otp-3757d8fb1dfd1ff9b80aed2376070b5c4888aaba.tar.bz2
otp-3757d8fb1dfd1ff9b80aed2376070b5c4888aaba.zip
Add option to compress data when copying tables between Mnesia nodes
Optionally using data compression for copying Mnesia tables allows the system to be tuned to eliminate network bottlenecks from deployments where enough CPU is available to use zlib. With this patch, running erl -mnesia send_compressed <level> will enable compression for sending tables between nodes. The compression level can be any integer in [0, 9], with 0 (the default) meaning no compression (exactly the previous behaviour) and 9 being the highest compression level. To set any non-zero compression level at the sender, both nodes must have the updated Mnesia modules (the receiver will work according to the sender's configuration).
Diffstat (limited to 'lib/mnesia/src/mnesia_loader.erl')
-rw-r--r--lib/mnesia/src/mnesia_loader.erl35
1 files changed, 33 insertions, 2 deletions
diff --git a/lib/mnesia/src/mnesia_loader.erl b/lib/mnesia/src/mnesia_loader.erl
index 77c317abc5..5657f6e299 100644
--- a/lib/mnesia/src/mnesia_loader.erl
+++ b/lib/mnesia/src/mnesia_loader.erl
@@ -438,6 +438,9 @@ make_table_fun(Pid, TabRec) ->
get_data(Pid, TabRec) ->
receive
+ {Pid, {more_z, CompressedRecs}} when is_binary(CompressedRecs) ->
+ Pid ! {TabRec, more},
+ {zlib_uncompress(CompressedRecs), make_table_fun(Pid,TabRec)};
{Pid, {more, Recs}} ->
Pid ! {TabRec, more},
{Recs, make_table_fun(Pid,TabRec)};
@@ -769,6 +772,27 @@ dets_bchunk(Tab, Chunk) -> %% Arrg
Else -> Else
end.
+zlib_compress(Data, Level) ->
+ BinData = term_to_binary(Data),
+ Z = zlib:open(),
+ zlib:deflateInit(Z, Level),
+ Bs = zlib:deflate(Z, BinData, finish),
+ zlib:deflateEnd(Z),
+ zlib:close(Z),
+ list_to_binary(Bs).
+
+zlib_uncompress(Data) when is_binary(Data) ->
+ binary_to_term(zlib:uncompress(Data)).
+
+compression_level() ->
+ NoCompression = 0,
+ case ?catch_val(send_compressed) of
+ {'EXIT', _} ->
+ mnesia_lib:set(send_compressed, NoCompression),
+ NoCompression;
+ Val -> Val
+ end.
+
send_packet(N, Pid, _Chunk, '$end_of_table', OldNode) ->
case OldNode of
true -> ignore; %% Old nodes can't handle the new no_more
@@ -779,8 +803,15 @@ send_packet(N, Pid, Chunk, {[], Cont}, OldNode) ->
send_packet(N, Pid, Chunk, Chunk(Cont), OldNode);
send_packet(N, Pid, Chunk, {Recs, Cont}, OldNode) when N < ?MAX_NOPACKETS ->
case OldNode of
- true -> Pid ! {self(), {more, [Recs]}}; %% Old need's wrapping list
- false -> Pid ! {self(), {more, Recs}}
+ true ->
+ Pid ! {self(), {more, [Recs]}}; %% Old need's wrapping list
+ false ->
+ case compression_level() of
+ 0 ->
+ Pid ! {self(), {more, Recs}};
+ Level ->
+ Pid ! {self(), {more_z, zlib_compress(Recs, Level)}}
+ end
end,
send_packet(N+1, Pid, Chunk, Chunk(Cont), OldNode);
send_packet(_N, _Pid, _Chunk, DataState, _OldNode) ->