Создала приложение вида
fast/
ebin/
src/
fast.app.src
fast_app.erl
fast_server.erl
fast_sup.erl
fast.conf
fast_app.erl
-module(fast_app).
-behaviour(application).
%% Application callbacks
-export([start/2, stop/1]).
%% ===================================================================
%% Application callbacks
%% ===================================================================
start(_StartType, _startArgs) ->
case file:path_consult("fast.conf", ["."]) of
{ok, Env, _} ->
application:set_env(fast, config, Env);
_ ->
ok
end,
fast_sup:start_link().
stop(_State) ->
ok.
fast_server.erl
-module(fast_server).
-behaviour(gen_server).
-compile(export_all).
-record(state, {
buffer
}).
start_link(Socket) ->
gen_server:start_link(?MODULE, Socket, []).
init(Socket) ->
{ok, Env} = application:get_env(fast, config),
{source, Source} = lists:keyfind(source,1,Env),
{port, Port} = lists:keyfind(port,1,Env),
{group, Group} = lists:keyfind(group,1,Env),
{ok,SourceAddress} = inet:parse_address(Source),
{ok,GroupAddress} = inet:parse_address(Group),
GroupIp = ip_to_binary(GroupAddress),
LocalIp = ip_to_binary({0,0,0,0}),
SourceIp = ip_to_binary(SourceAddress),
Bin = << GroupIp/binary,LocalIp/binary,SourceIp/binary >>,
{ok, Socket} = gen_udp:open(erlang:list_to_integer(Port),
[
inet,
binary,
{active, true},
{reuseaddr, true},
{multicast_ttl, 30},
{raw, 0, 39, Bin}
]),
Pid = gen_server:cast(self(), Socket),
ok = gen_udp:controlling_process(Socket, Pid).
ip_to_binary(Ip) ->
list_to_binary(tuple_to_list(Ip)).
handle_cast(Socket, #state{} = Server) ->
case Socket of
{udp, _Socket, _Ip, _Port, Bin} ->
io:format("Bin ~p:~n", [Bin]),
handle_cast(Socket, #state{buffer = Bin});
Msg ->
{noreply, Server}
end.
fast_sup.erl
-module(fast_sup).
-behaviour(supervisor).
%% API
-export([start_link/0]).
%% Supervisor callbacks
-export([init/1]).
%% Helper macro for declaring children of supervisor
%%-define(CHILD(I, Type), {I, {I, start_link, []}, permanent, 5000, Type, [I]}).
%% ===================================================================
%% API functions
%% ===================================================================
start_link() ->
supervisor:start_link({local, ?MODULE}, ?MODULE, []).
%% ===================================================================
%% Supervisor callbacks
%% ===================================================================
init([fast_server]) ->
MaxRestart = 5,
MaxTime = 100,
{ok, { {one_for_one, MaxRestart, MaxTime},
[{undefined,
{fast_server, start_link, []},
temporary,
5000,
worker,
[]}]} }.
в итоге после компиляции и запуска
s5@s5:~/fast$ rebar compile
==> fast (compile)
Compiled src/fast_sup.erl
s5@s5:~/fast$ erl -pa ./ebin
Erlang/OTP 17 [erts-6.1] [source] [64-bit] [smp:8:8] [async-threads:10] [kernel-poll:false]
Eshell V6.1 (abort with ^G)
1> application:start(fast).
{error,{{function_clause,[{fast_sup,init,
[[]],
[{file,"src/fast_sup.erl"},{line,25}]},
{supervisor,init,1,[{file,"supervisor.erl"},{line,243}]},
{gen_server,init_it,6,[{file,"gen_server.erl"},{line,306}]},
{proc_lib,init_p_do_apply,3,
[{file,"proc_lib.erl"},{line,239}]}]},
{fast_app,start,[normal,[]]}}}
=INFO REPORT==== 25-Aug-2014::14:41:39 ===
application: fast
exited: {{function_clause,
[{fast_sup,init,[[]],[{file,"src/fast_sup.erl"},{line,25}]},
{supervisor,init,1,[{file,"supervisor.erl"},{line,243}]},
{gen_server,init_it,6,[{file,"gen_server.erl"},{line,306}]},
{proc_lib,init_p_do_apply,3,
[{file,"proc_lib.erl"},{line,239}]}]},
{fast_app,start,[normal,[]]}}
type: temporary
2>
и чего ему не хватает? Хоть появились вопросы, на которые надо искать ответы.
PS.
После небольших доработок
fast_server.erl
-module(fast_server).
-behaviour(gen_server).
-compile(export_all).
-record(state, {
socket,
buffer
}).
start_link(Socket) ->
gen_server:start_link(?MODULE, Socket, []).
init([]) ->
{ok, Env} = application:get_env(fast, config),
{source, Source} = lists:keyfind(source,1,Env),
{port, Port} = lists:keyfind(port,1,Env),
{group, Group} = lists:keyfind(group,1,Env),
{ok,SourceAddress} = inet:parse_address(Source),
{ok,GroupAddress} = inet:parse_address(Group),
GroupIp = ip_to_binary(GroupAddress),
LocalIp = ip_to_binary({0,0,0,0}),
SourceIp = ip_to_binary(SourceAddress),
Bin = << GroupIp/binary,LocalIp/binary,SourceIp/binary >>,
{ok, Socket} = gen_udp:open(erlang:list_to_integer(Port),
[
inet,
binary,
{active, true},
{reuseaddr, true},
{multicast_ttl, 30},
{raw, 0, 39, Bin}
]),
Pid = gen_server:cast(self(), Socket),
ok = gen_udp:controlling_process(Socket, Pid),
{ok, #state{socket = Socket}}.
ip_to_binary(Ip) ->
list_to_binary(tuple_to_list(Ip)).
handle_cast(Socket, #state{} = Server) ->
case Socket of
{udp, _Socket, _Ip, _Port, Bin} ->
io:format("Bin ~p:~n", [Bin]),
handle_cast(Socket, #state{buffer = Bin});
_Msg ->
{noreply, Server}
end.
и в fast_sup.erl
-module(fast_sup).
-behaviour(supervisor).
%% API
-export([start_link/0]).
%% Supervisor callbacks
-export([init/1]).
%% Helper macro for declaring children of supervisor
%%-define(CHILD(I, Type), {I, {I, start_link, []}, permanent, 5000, Type, [I]}).
%% ===================================================================
%% API functions
%% ===================================================================
start_link() ->
supervisor:start_link({local, ?MODULE}, ?MODULE, []).
%% ===================================================================
%% Supervisor callbacks
%% ===================================================================
init([]) ->
{ok, { {simple_one_for_one, 5, 100},
[{undefined,
{fast_server, start_link, []},
temporary,
5000,
worker,
[fast_server]}]} }.
-module(fast_sup).
-behaviour(supervisor).
%% API
-export([start_link/0]).
%% Supervisor callbacks
-export([init/1]).
%% Helper macro for declaring children of supervisor
%%-define(CHILD(I, Type), {I, {I, start_link, []}, permanent, 5000, Type, [I]}).
%% ===================================================================
%% API functions
%% ===================================================================
start_link() ->
supervisor:start_link({local, ?MODULE}, ?MODULE, []).
%% ===================================================================
%% Supervisor callbacks
%% ===================================================================
init([]) ->
{ok, { {simple_one_for_one, 5, 100},
[{undefined,
{fast_server, start_link, []},
temporary,
5000,
worker,
[fast_server]}]} }.
результат стал менее интересен
s5@s5:~/fast$ rebar compile
==> fast (compile)
s5@s5:~/fast$ erl -pa ./ebin
Erlang/OTP 17 [erts-6.1] [source] [64-bit] [smp:8:8] [async-threads:10] [kernel-poll:false]
Eshell V6.1 (abort with ^G)
1> application:start(fast).
ok
куда двигать дальше - непонятно.