⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 megaco_test_generic_transport.erl

📁 OTP是开放电信平台的简称
💻 ERL
字号:
%% ``The contents of this file are subject to the Erlang Public License,%% Version 1.1, (the "License"); you may not use this file except in%% compliance with the License. You should have received a copy of the%% Erlang Public License along with this software. If not, it can be%% retrieved via the world wide web at http://www.erlang.org/.%%%% Software distributed under the License is distributed on an "AS IS"%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See%% the License for the specific language governing rights and limitations%% under the License.%%%% The Initial Developer of the Original Code is Ericsson Utvecklings AB.%% Portions created by Ericsson are Copyright 2007, Ericsson Utvecklings%% AB. All Rights Reserved.''%%%%     $Id$%%%%----------------------------------------------------------------------%% Purpose: Generic megaco transport simulator module%%-----------------------------------------------------------------------module(megaco_test_generic_transport).-behaviour(gen_server).-behaviour(megaco_transport).-export([	 start_transport/0, 	 connect/2, 	 start/1,	 stop/0,	 incomming_message/2	]).%% gen_server callbacks-export([	 init/1, 	 handle_call/3, 	 handle_cast/2, 	 handle_info/2, 	 terminate/2,	 code_change/3	]).%% megaco_transport callbacks-export([	 send_message/2,	 resend_message/2	]).-record(state, {parent, 		controller, 		receive_handle}).-include_lib("megaco/include/megaco.hrl").%% -include("megaco_test_lib.hrl").-define(SERVER, ?MODULE).%%-------------------------------------------------------------------%% API%%-------------------------------------------------------------------start(RH) ->    {ok, Pid} = start_transport(),    {ok, SendHandle, _} = connect(Pid, [{receive_handle, RH}]),    {ok, SendHandle}.start_transport() ->    %% GS_ARGS = [{debug,[trace]}],     GS_ARGS = [],     {ok, Pid} = gen_server:start_link({local, ?SERVER}, ?MODULE, [self()], GS_ARGS),    unlink(Pid),    {ok, Pid}.connect(Sup, Opts) ->    call({connect, Sup, Opts}).stop() ->    call(stop).%%----------------------------------------------------------------------%% Megaco transport callback%%----------------------------------------------------------------------send_message(SendHandle, Bin) ->    call({transport, {send_message, SendHandle, Bin}}).resend_message(SendHandle, Bin) ->    call({transport, {resend_message, SendHandle, Bin}}).incomming_message(Pid, Msg) ->    cast(Pid, {incomming_message, Msg}).%%%-------------------------------------------------------------------%%% Callback functions from gen_server%%%-------------------------------------------------------------------%%--------------------------------------------------------------------%% Func: init/1%% Returns: {ok, State}          |%%          {ok, State, Timeout} |%%          ignore               |%%          {stop, Reason}%%--------------------------------------------------------------------init([Parent]) ->    {ok, #state{parent = Parent}}.%%--------------------------------------------------------------------%% Func: handle_call/3%% Returns: {reply, Reply, State}          |%%          {reply, Reply, State, Timeout} |%%          {noreply, State}               |%%          {noreply, State, Timeout}      |%%          {stop, Reason, Reply, State}   | (terminate/2 is called)%%          {stop, Reason, State}            (terminate/2 is called)%%--------------------------------------------------------------------handle_call({connect, _Sup, Opts}, _From, State) ->    d("handle_call(connect) -> entry with"      "~n   Opts: ~p", [Opts]),    {value, {_, ReceiveHandle}} = lists:keysearch(receive_handle, 1, Opts),    {value, {_, Controller}}    = lists:keysearch(port, 1, Opts),    SendHandle = self(),     ControlPid = self(),    Reply  = {ok, SendHandle, ControlPid},    {reply, Reply, State#state{controller     = Controller,			       receive_handle = ReceiveHandle}};handle_call(stop, _From, State) ->    d("handle_call(stop) -> entry"),    Reply  = ok,    Reason = normal,     {stop, Reason, Reply, State};handle_call({transport, Event}, _From, 	    #state{controller = Pid, receive_handle = RH} = State) ->    d("handle_call(transport) -> entry with"      "~n   Event: ~p", [Event]),    Reply = handle_transport(Pid, RH, Event),    {reply, Reply, State};handle_call(Req, From, State) ->    d("handle_call -> entry with"      "~n   Req: ~p", [Req]),    Reply  = {error, {unknown_request, Req}},     Reason = {received_unexpected_request, Req, From},    {stop, Reason, Reply, State}.%%--------------------------------------------------------------------%% Func: handle_cast/2%% Returns: {noreply, State}          |%%          {noreply, State, Timeout} |%%          {stop, Reason, State}            (terminate/2 is called)%%--------------------------------------------------------------------handle_cast({incomming_message, Msg}, 	    #state{receive_handle = RH} = State) ->    d("handle_cast(incomming_message) -> entry with"      "~n   Msg: ~p", [Msg]),    handle_incomming_message(Msg, RH),    {noreply, State};handle_cast(Msg, State) ->    d("handle_cast -> entry with"      "~n   Msg: ~p", [Msg]),    Reason = {received_unexpected_message, Msg},    {stop, Reason, State}.%%--------------------------------------------------------------------%% Func: handle_info/2%% Returns: {noreply, State}          |%%          {noreply, State, Timeout} |%%          {stop, Reason, State}            (terminate/2 is called)%%--------------------------------------------------------------------handle_info(Info, State) ->    d("handle_info -> entry with"      "~n   Info: ~p", [Info]),    Reason = {received_unexpected_info, Info},    {stop, Reason, State}.%%--------------------------------------------------------------------%% Func: terminate/2%% Purpose: Shutdown the server%% Returns: any (ignored by gen_server)%%--------------------------------------------------------------------terminate(_Reason, _State) ->    ok.%%----------------------------------------------------------------------%% Func: code_change/3%% Purpose: Convert process state when code is changed%% Returns: {ok, NewState}%%----------------------------------------------------------------------code_change(_Vsn, State, _Extra) ->    {ok, State}.%%%-------------------------------------------------------------------%%% Internal functions%%%-------------------------------------------------------------------handle_transport(Pid, 		 #megaco_receive_handle{encoding_mod    = EM,					encoding_config = EC},		 {Event, SendHandle, Bin}) ->    Info = 	case (catch EM:decode_message(EC, Bin)) of	    {ok, MegMsg} ->		MegMsg;	    Error ->		d("handle_transport -> decode failed"		  "~n   Error: ~p", [Error]),		{bad_message, Error, Bin}	end,    Pid ! {transport_event, {Event, SendHandle, Info}, self()},    receive	{transport_reply, Reply, Pid} ->	    d("handle_transport -> received reply"	      "~n   Reply: ~p", [Reply]),	    Reply    after 10000 ->	    receive		Any ->		    d("handle_transport -> received crap after timeout"		      "~n   Any: ~p", [Any]),		    exit({timeout, Any})	    after 0 ->		    d("handle_transport -> timeout"),		    exit(timeout)	    end    end.%% This function is used to simulate incomming messageshandle_incomming_message(Msg, #megaco_receive_handle{encoding_mod    = EM,						     encoding_config = EC} = RH) ->    Self = self(),    case EM:encode_message(EC, Msg) of	{ok, Bin} ->	    spawn(fun() -> megaco:process_received_message(RH, Self, Self, Bin) end),	    ok;	Error ->	    d("handle_incomming_message -> encode failed"	      "~n   Error: ~p", [Error]),	    exit(Error)    end.			  %%-------------------------------------------------------------------call(Req) ->    call(Req, infinity).call(Req, Timeout) ->    case (catch gen_server:call(?SERVER, Req, Timeout)) of        {'EXIT', _} ->            {error, not_started};        Res ->            Res    end.%% cast(Msg) ->%%     cast(whereis(?SERVER), Msg).cast(Pid, Msg) ->    d("cast -> entry with"      "~n   Pid: ~p"      "~n   Msg: ~p", [Pid, Msg]),    case (catch gen_server:cast(Pid, Msg)) of        {'EXIT', Reason} ->	    d("cast -> failed casting"	      "~n   Reason: ~p", [Reason]),            {error, not_started};        Res ->            Res    end.    %%-------------------------------------------------------------------d(F) ->    d(F, []).d(F, A) ->    print(now(), F, A).print(Ts, F, A) ->    io:format("*** [~s] GENERIC TRANSPORT [~p] ***"	      "~n   " ++ F ++ "~n", 	      [format_timestamp(Ts), self() | A]).format_timestamp({_N1, _N2, N3} = Now) ->    {Date, Time}   = calendar:now_to_datetime(Now),    {YYYY,MM,DD}   = Date,    {Hour,Min,Sec} = Time,    FormatDate =         io_lib:format("~.4w:~.2.0w:~.2.0w ~.2.0w:~.2.0w:~.2.0w 4~w",                      [YYYY,MM,DD,Hour,Min,Sec,round(N3/1000)]),      lists:flatten(FormatDate).

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -