Logo Search packages:      
Sourcecode: bayonne version File versions  Download package

driver.cpp

// Copyright (C) 2000-2002 Open Source Telecom Corporation.
// 
// Author: Jeremy J. McNamara 
// 
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
// 
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
// 
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software 
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.

//#include <ptlib.h>

#include "driver.h"

//#include "lpc10codec.h"
//#include "mscodecs.h"

#ifdef      CCXX_NAMESPACES
using namespace std;
namespace ost {
#endif

OH323Audio::OH323Audio()
      : URLAudio()
{
}

OH323Audio::~OH323Audio()
{
}

BOOL OH323Audio::Read(void * buf, PINDEX len)
{
      return true;
}

BOOL OH323Audio::Write(const void * buf, PINDEX len)
{
      return true;
}

BOOL OH323Audio::Close()
{
      return true;
}

BOOL OH323Audio::IsOpen()
{
      return isOpen();
}

OH323Connection::OH323Connection(OH323EndPoint & ep, unsigned ref)
      : H323Connection(ep, ref)
{
}

OH323Connection::~OH323Connection()
{
}

BOOL OH323Connection::OnStartLogicalChannel(H323Channel & channel)
{
      if(!H323Connection::OnStartLogicalChannel(channel))
            return false;

      slog(Slog::levelInfo) << "Started a logical channel: caps - " << channel.GetCapability() << endl;

      return true;
}

void OH323Connection::OnUserInputString(const PString & value)
{
      slog(Slog::levelInfo) << "User input: " << value << endl;
}

OH323EndPoint::OH323EndPoint()
{
}
          
        
OH323EndPoint::~OH323EndPoint()
{
}

BOOL OH323EndPoint::Initialise()
{
      //PString UserName = "Bayonne";
      //SetLocalUserName(UserName);

      SetCapability(0, 0, new H323_G711Capability(H323_G711Capability::muLaw, H323_G711Capability::At64k));
      SetCapability(0, 0, new H323_G711Capability(H323_G711Capability::ALaw, H323_G711Capability::At64k));
      SetCapability(0, 0, new H323_GSM0610Capability);
      SetCapability(0, 0, new MicrosoftGSMAudioCapability);


      H323ListenerTCP * listener;
      
      PIPSocket::Address interfaceAddress(INADDR_ANY);
      WORD listenPort = oh323ivr.getSignalPort();

      listener = new H323ListenerTCP(*this, interfaceAddress, listenPort);

      if (!StartListener(listener)) {
            slog(Slog::levelError) <<  "Could not open H.323 listener port on " << listener->GetListenerPort() << endl;
            delete listener;
            return false;
      }

      slog(Slog::levelInfo) << "Waiting for incoming calls for \"" << GetLocalUserName() << '"' << endl;
      return true;

}

H323Connection * OH323EndPoint::CreateConnection(unsigned callRef)
{
      return new OH323Connection(*this, callRef);
}

BOOL OH323EndPoint::OnIncomingCall(H323Connection & connection,
                                        const H323SignalPDU &,
                                        H323SignalPDU &)
{
      slog(Slog::levelInfo) << "Incomming H.323 call from " << connection.GetRemotePartyName() << endl;

      //if(callToken.IsEmpty())
      //    return true;

      return true;
};

H323Connection::AnswerCallResponse OH323EndPoint::OnAnswerCall(H323Connection & connection,
            const PString & callerName,
            const H323SignalPDU &,
            H323SignalPDU &)
{
      callToken = connection.GetCallToken();
      slog(Slog::levelDebug) << callToken << endl;

      slog(Slog::levelInfo) << "Answer call response fired" << endl;
      if(true)
            return H323Connection::AnswerCallNow;

      return H323Connection::AnswerCallPending;
}

void OH323EndPoint::OnConnectionEstablished(H323Connection & connection, const PString & token)
{
      callToken = token;

      slog(Slog::levelInfo) << "In call with " << connection.GetRemotePartyName() << endl;
}

void OH323EndPoint::OnConnectionCleared(H323Connection & connection, const PString & token)
{
      if(callToken == token)
            callToken = NULL;

      switch(connection.GetCallEndReason())
      {
      case H323Connection::EndedByRemoteUser:
            slog(Slog::levelInfo) << " has cleared the call" << endl;
            break;
      case H323Connection::EndedByCallerAbort:
            slog(Slog::levelInfo) << " has stopped calling" << endl;
            break;
      case H323Connection::EndedByNoAnswer:
            slog(Slog::levelInfo) << " didn't answer" << endl;
            break;
      case H323Connection::EndedByRefusal:
            slog(Slog::levelInfo) << " refused the call" << endl;
            break;
      case H323Connection::EndedByTransportFail:
            slog(Slog::levelInfo) << " ended by transport failure" << endl;
            break;
      case H323Connection::EndedByCapabilityExchange:
            slog(Slog::levelInfo) << " ended due to codec negotiation" << endl;
            break;
      case H323Connection::EndedByNoAccept:
            slog(Slog::levelInfo) << " did not accept our call" << endl;
            break;
      case H323Connection::EndedByAnswerDenied:
            slog(Slog::levelInfo) << " refused our call" << endl;
            break;
      case H323Connection::EndedByNoUser:
            slog(Slog::levelInfo) << " couldn't be found by the GK" << endl;
            break;
      case H323Connection::EndedByNoBandwidth:
            slog(Slog::levelInfo) << " aborted due to lack of bandwidth" << endl;
            break;
      case H323Connection::EndedByUnreachable:
            slog(Slog::levelInfo) << " was unreachable" << endl;
            break;
      case H323Connection::EndedByHostOffline:
            slog(Slog::levelInfo) << " is offline" << endl;
            break;
      case H323Connection::EndedByNoEndPoint:
            slog(Slog::levelInfo) << " doesn't have an EP to connect to" << endl;
            break;
      case H323Connection::EndedByConnectFail:
            slog(Slog::levelInfo) << " connection failed" << endl;
            break;
      default:
            slog(Slog::levelInfo) << " call completed with unhandled reason" << endl;
            break;
      }

      slog(Slog::levelInfo) << "duration: " << (PTime() - connection.GetConnectionStartTime()) << endl;
}

BOOL OH323EndPoint::OpenAudioChannel(H323Connection & connection,
            BOOL isEncoding,
            unsigned bufferSize,
            H323AudioCodec & codec)
{
      OH323Audio * soundChannel = new OH323Audio;
      slog(Slog::levelInfo) << "new instance of oh323audio for" << (isEncoding ? "record" : "play") << endl;
      return codec.AttachChannel(soundChannel);
}

OH323Config::OH323Config() :
Keydata("/bayonne/h323")
{
      static Keydata::Define defkeys[] = {
      {"first", "3128"},
      {"count", "32"},
      {"inc", "4"},
      {"interface", "*"},
      {"port", "1720"},
      {NULL, NULL}};

      if(isFHS())
            load("/drivers/h323");

      load(defkeys);
}

InetAddress OH323Config::getBindAddress(void)
{
      const char *cp = getLast("bind");
      if(!cp)
            cp = getLast("address");
      if(!cp)
            cp = getLast("interface");

      return InetAddress(cp);
}

OH323Driver::OH323Driver() :
Driver()
{
      port_count = oh323ivr.getRTPCount();

      ports = NULL;
      groups = NULL;
      
      endpoint = new OH323EndPoint;

      ports = new OH323Trunk *[port_count];
      groups = new TrunkGroup *[port_count];

      if(ports)
            memset(ports, 0, sizeof(OH323Trunk *) * port_count);

      if(groups)
            memset(groups, 0, sizeof(TrunkGroup *) * port_count);

      slog(Slog::levelInfo) << "H323 trunk driver loaded; capacity=" << port_count << endl;
}

OH323Driver::~OH323Driver()
{
      stop();
      if(ports)
            delete[] ports;

      if(groups)
            delete[] groups;
}

int OH323Driver::start(void)
{
      int count = oh323ivr.getRTPCount();

      if(active)
      {
            slog(Slog::levelError) << "oh323 driver already started" << endl;
            return 0;
      }

      slog(Slog::levelInfo) << "oh323 driver starting..." << endl;

      // Do we want this here or in the OH323Driver constructor?
      if (!endpoint->Initialise())
            return 0;
      
      active = true;
      return count;
}

void OH323Driver::stop(void)
{
      if(!active)
            return;

      if(ports)
            memset(ports, 0, sizeof(OH323Trunk *) * port_count);

      active = false;
      slog(Slog::levelInfo) << "oh323 driver stopping..." << endl;
}


Trunk *OH323Driver::getTrunkPort(int id)
{
      if(id < 0 || id >= port_count)
            return NULL;

      if(!ports)
            return NULL;

      return (Trunk *)ports[id];
}

OH323Driver oh323ivr;

#ifdef      CCXX_NAMESPACES
};
#endif

Generated by  Doxygen 1.6.0   Back to index