//
//
//   TLCWORTR.CPP
//
//   Copyright (c) 1997  Galacticomm, Inc.        All Rights Reserved
//
//   Worldlink Teleconference Transport
//   Implementation
//                                               - Phil Henning 7/7/97
//
/////////////////////////////////////////////////////////////////////////////

#include "gcomm.h"
#include "majorbbs.h"
#include "tlcwor.h"
#define __SPEAKONLY
#include "tlcwfda.h"
#include "tlcdcmd.h"

#define FILREV "$Revision: 31 $"

MARKSOURCE(tlcwortr);

TFUNCPTRS transWor={
     sizeof(TFUNCPTRS),
     TrWorConstruct,
     TrWorDestruct,
     NULL,
     NULL,
     TrWorSendAll,
     TrWorSendAllBut,
     TrWorRecvText,
     TrWorCmdResult,
     NULL,
     NULL,
     TRANS_NOBROADCAST|TRANS_IMPLCHAT
};

VOID* worbuf;

VOID
TrWorConstruct(VOID)
{
     worbuf=new CHAR[WORSNDBUFSIZ];
}

VOID
TrWorDestruct()
{
     delete [] worbuf;
}

VOID
TrWorSendAll(
const CHAR* pszUseridFrom,
const CHAR* pszUseridTo,
const CHAR* pMsg,
SHORT fType,
const CHAR* channel,
SHORT iMsgNum,
const CHAR* ptr1,
const CHAR* ptr2,
const CHAR* ptr3)
{
     UINT stlen=0;
     LPCHANINFO chanInfo;
     JINFSTR jinfo;

     if (channel != NULL) {
          chanInfo=tlcChannelGetInfo(channel);
          if (!worConnected() || chanInfo == NULL || !(chanInfo->m_type&CHAN_TYPE_WL_PUBLIC)) {
               if (chanInfo == NULL) {
                    shocst("TELECONFERENCE ERROR","Couldn't find channel %s",channel);
               }
               return;
          }
     }
     ASSERT(worsndbuf != NULL);
     ASSERT(pszUseridFrom != NULL);
     if (worWorldUser(pszUseridFrom)) {
          return;
     }
     if (fType == RECV_TYPE_USEREXIT) {
          LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
          if (pUser->m_iUsrnum >= 0 ) {
               memset(&jinfo,0,sizeof(JINFSTR));
               jinfo.unum=worUseridToNumber(pUser->m_pszName);
               chanInfo=tlcChannelGetInfo(pUser->m_pszChannel);
               if (chanInfo != NULL && (chanInfo->m_type&CHAN_TYPE_WL_PUBLIC)) {
                    jinfo.chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                    if (!(pUser->m_fFlags&USR_INVISB)) {
                         worSendFDA(WORAPID,WORCMD_USER_UNJOIN
                                   ,sizeof(JINFSTR),&jinfo,jinfoFDA);
                    }
               }
          }
          return;
     }
     else if (fType == RECV_TYPE_USERENTER) {
          LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
          if (pUser->m_iUsrnum >=0) {
               memset(&jinfo,0,sizeof(JINFSTR));
               jinfo.unum=worUseridToNumber(pUser->m_pszName);
               jinfo.tlcunum=tlcUserFindID(pszUseridFrom);
               chanInfo=tlcChannelGetInfo(pUser->m_pszChannel);
               if (chanInfo != NULL && (chanInfo->m_type&CHAN_TYPE_WL_PUBLIC)) {
                    jinfo.chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                    if (!(pUser->m_fFlags&USR_INVISB)) {
                         worSendFDA(WORAPID,WORCMD_USER_JOIN,sizeof(JINFSTR),&jinfo,jinfoFDA);
                         jinfo.chn=pUser->m_fFlags&USR_UNLIST;
                         worSendFDA(WORAPID,WORCMD_USER_UNLISTED,sizeof(JINFSTR),&jinfo,jinfoFDA);
                    }
               }
          }
          return;
     }
     else if (fType == RECV_TYPE_LISTCHG) {
          LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
          if (pUser->m_iUsrnum >=0) {
               memset(&jinfo,0,sizeof(JINFSTR));
               jinfo.unum=worUseridToNumber(pUser->m_pszName);
               jinfo.tlcunum=tlcUserFindID(pszUseridFrom);
               if (!(pUser->m_fFlags&USR_INVISB)) {
                     jinfo.chn=pUser->m_fFlags&USR_UNLIST;
                     worSendFDA(WORAPID,WORCMD_USER_UNLISTED,sizeof(JINFSTR),&jinfo,jinfoFDA);
               }
          }
          return;
     }
     else if (channel == NULL) {
          return;
     }
     else if (fType == RECV_TYPE_ACTION) {
          LPACTIONINF ainf=(LPACTIONINF)worsndbuf;
          LPACTION ap;

          if (actIsFile()) {
              return;
          }

          memset(ainf,0,sizeof(ACTIONINF));
          ap=actWordInfoGetCurrent(actListGetCurrent());
          if (ap != NULL) {
                const CHAR* pTo=actGetLastDirected();
                strcpy(ainf->name,ap->name);
                ainf->from=worUseridToNumber(pszUseridFrom);
                ainf->chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                if (ap->isyell) {
                     rstrin();
                     stlcpy(ainf->extra,margv[1],WORSNDBUFSIZ-sizeof(ACTIONINF));
                     stlen=strlen(ainf->extra);
                     parsin();
                     ainf->isyell=TRUE;
                }
                else {
                     if (!NULSTR(pTo)) {
                          if (sameas(pTo,SYSUID)) {
                               ainf->to=ACTTOALL;
                          }
                          else if (worWorldUser(pTo)) {
                               ainf->to=worAliasToNumber(pTo);
                          }
                          else {
                               ainf->to=worUseridToNumber(pTo);
                          }
                     }
                }
                if ((ainf->isyell && margc > 1) || ainf->to != 0) {
                     strcpy(ainf->fmt,ap->complx);
                     ainf->iscomplex=TRUE;
                }
                else {
                     strcpy(ainf->fmt,ap->simple);
                }
                if (sameas(actListGetCurrent(),primaryList)) {
                     strcpy(ainf->rate,primaryRating);
                }
                else if (sameas(actListGetCurrent(),secondaryList)) {
                     strcpy(ainf->rate,secondaryRating);
                }
                else {
                     strcpy(ainf->rate,worRatings[0]);
                }
                SHORT cmd=WORCMD_ACTION;
#ifdef DEBUG2
shocst("WORTRSENDALL FR","%s",pszUseridFrom);
shocst("WORTRSENDALL TO","%s",pTo);
#endif
                worSendFDA(WORAPID,cmd,fldoff(actioninf,extra)+stlen,
                            ainf,actioninfFDA);
          }
          return;
     }
     memset(worsndbuf, 0, sizeof(SPEAKINF));
     worsndbuf->chn=static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom)->num;
     worsndbuf->type=fType;
     worsndbuf->iMsgNum=iMsgNum;
     if (sameas(pszUseridFrom,SYSUID)) {
          worsndbuf->unumFrom=SYSUIDN;
     }
     else {
          worsndbuf->unumFrom=worUseridToNumber(pszUseridFrom);
     }
     if (ptr1 != NULL) {
          if (fType == RECV_TYPE_DIRECTED) {
               CHAR* num;
               if (worWorldUser(ptr1)) {
                    num=ul2as(worAliasToNumber(ptr1));
               }
               else {
                    num=ul2as(worUseridToNumber(ptr1));
               }
               stzcpy(worsndbuf->ptr1,num,TLCUIDSIZ);
          }
          else {
               stlcpy(worsndbuf->ptr1,ptr1,TLCUIDSIZ);
          }
     }
     if (ptr2 != NULL) {
          stlcpy(worsndbuf->ptr2,ptr2,TLCUIDSIZ);
     }
     if (ptr3 != NULL) {
          stlcpy(worsndbuf->ptr3,ptr3,TLCUIDSIZ);
     }
     if (pMsg != NULL) {
          stlcpy(worsndbuf->msg,pMsg,WORSNDBUFSIZ-sizeof(SPEAKINF));
     }
     stlen=strlen(worsndbuf->msg);
     if (pszUseridTo != NULL) {
          if (worWorldUser(pszUseridTo)) {
               worsndbuf->unumTo=worAliasToNumber(pszUseridTo);
          }
          else {
               worsndbuf->unumTo=worUseridToNumber(pszUseridTo);
          }
     }
     else {

           worSendFDA(WORAPID,WORCMD_PUBLIC_SEND,fldoff(speakinf,msg)+stlen,worsndbuf,speakinfFDA);
     }
}


VOID
TrWorSendAllBut(
const CHAR* pszUseridFrom,
const CHAR* pszUseridTo,
const CHAR* pMsg,
SHORT fType,
const CHAR* channel,
SHORT iMsgNum,
const CHAR* ptr1,
const CHAR* ptr2,
const CHAR* ptr3,
const CHAR* not1,
const CHAR* not2)
{
     UINT stlen=0;
     LPCHANINFO chanInfo;
     JINFSTR jinfo;

     if (channel != NULL) {
          chanInfo=tlcChannelGetInfo(channel);
          if (!worConnected() || chanInfo == NULL || !(chanInfo->m_type&CHAN_TYPE_WL_PUBLIC)) {
               if (chanInfo == NULL) {
                    shocst("TELECONFERENCE ERROR","Couldn't find channel %s",channel);
               }
               return;
          }
     }
     ASSERT(worsndbuf != NULL);
     ASSERT(pszUseridFrom != NULL);
     if (worWorldUser(pszUseridFrom)) {
          return;
     }
     if (fType == RECV_TYPE_USEREXIT) {
          LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
          if (pUser->m_iUsrnum >= 0) {
               memset(&jinfo,0,sizeof(JINFSTR));
               jinfo.unum=worUseridToNumber(pUser->m_pszName);
               chanInfo=tlcChannelGetInfo(pUser->m_pszChannel);
               if (chanInfo != NULL) {
                    jinfo.chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                    if (!(pUser->m_fFlags&USR_INVISB)) {
                         worSendFDA(WORAPID,WORCMD_USER_UNJOIN
                                   ,sizeof(JINFSTR),&jinfo,jinfoFDA);
                    }
               }
          }
     }
     else if (fType == RECV_TYPE_USERENTER) {
          LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
          if (pUser->m_iUsrnum >=0) {
               memset(&jinfo,0,sizeof(JINFSTR));
               jinfo.unum=worUseridToNumber(pUser->m_pszName);
               jinfo.tlcunum=tlcUserFindID(pszUseridFrom);
               chanInfo=tlcChannelGetInfo(pUser->m_pszChannel);
               if (chanInfo != NULL) {
                    jinfo.chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                    if (!(pUser->m_fFlags&USR_INVISB)) {
                         worSendFDA(WORAPID,WORCMD_USER_JOIN,sizeof(JINFSTR),&jinfo,jinfoFDA);
                         jinfo.chn=pUser->m_fFlags&USR_UNLIST;
                         worSendFDA(WORAPID,WORCMD_USER_UNLISTED,sizeof(JINFSTR),&jinfo,jinfoFDA);
                    }
               }
          }
     }
     else if (fType == RECV_TYPE_LISTCHG) {
          LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
          if (pUser->m_iUsrnum >=0) {
               memset(&jinfo,0,sizeof(JINFSTR));
               jinfo.unum=worUseridToNumber(pUser->m_pszName);
               jinfo.tlcunum=tlcUserFindID(pszUseridFrom);
               if (!(pUser->m_fFlags&USR_INVISB)) {
                     jinfo.chn=pUser->m_fFlags&USR_UNLIST;
                     worSendFDA(WORAPID,WORCMD_USER_UNLISTED,sizeof(JINFSTR),&jinfo,jinfoFDA);
               }
          }
     }
     else if (channel == NULL) {
          return;
     }
     else if (fType == RECV_TYPE_ACTION) {
          LPACTIONINF ainf=(LPACTIONINF)worsndbuf;
          LPACTION ap;

          if (actIsFile()) {
              return;
          }

          memset(ainf,0,sizeof(ACTIONINF));
          ap=actWordInfoGetCurrent(actListGetCurrent());
          if (ap != NULL) {
                const CHAR* pTo=actGetLastDirected();
                strcpy(ainf->name,ap->name);
                ainf->from=worUseridToNumber(pszUseridFrom);
                ainf->chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                if (ap->isyell) {
                     rstrin();
                     stlcpy(ainf->extra,margv[1],WORSNDBUFSIZ-sizeof(ACTIONINF));
                     stlen=strlen(ainf->extra);
                     parsin();
                     ainf->isyell=TRUE;
                }
                else {
                     if (!NULSTR(pTo)) {
                          if (sameas(pTo,SYSUID)) {
                               ainf->to=ACTTOALL;
                          }
                          else if (worWorldUser(pTo)) {
                               ainf->to=worAliasToNumber(pTo);
                          }
                          else {
                               ainf->to=worUseridToNumber(pTo);
                          }
                     }
                }
                if ((ainf->isyell && margc > 1) || ainf->to != 0) {
                     strcpy(ainf->fmt,ap->complx);
                     ainf->iscomplex=TRUE;
                }
                else {
                     strcpy(ainf->fmt,ap->simple);
                }

                if (sameas(actListGetCurrent(),primaryList)) {
                     strcpy(ainf->rate,primaryRating);
                }
                else if (sameas(actListGetCurrent(),secondaryList)) {
                     strcpy(ainf->rate,secondaryRating);
                }
                else {
                     strcpy(ainf->rate,worRatings[0]);
                }
                SHORT cmd=WORCMD_ACTION;
#ifdef DEBUG2
shocst("WORTRSENDALLBUT FR","%s",pszUseridFrom);
shocst("WORTRSENDALLBUT TO","%s",pTo);
#endif
                worSendFDA(WORAPID,cmd,fldoff(actioninf,extra)+stlen,
                            ainf,actioninfFDA);
          }
          return;
     }
     memset(worsndbuf, 0, sizeof(SPEAKINF));
     worsndbuf->chn=static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom)->num;
     worsndbuf->type=fType;
     worsndbuf->iMsgNum=iMsgNum;
     if (sameas(pszUseridFrom,SYSUID)) {
          worsndbuf->unumFrom=SYSUIDN;
     }
     else {
          worsndbuf->unumFrom=worUseridToNumber(pszUseridFrom);
     }
     if (ptr1 != NULL) {
          if (fType == RECV_TYPE_DIRECTED) {
               CHAR* num;
               if (worWorldUser(ptr1)) {
                    num=ul2as(worAliasToNumber(ptr1));
               }
               else {
                    num=ul2as(worUseridToNumber(ptr1));
               }
               stzcpy(worsndbuf->ptr1,num,TLCUIDSIZ);
          }
          else {
               stlcpy(worsndbuf->ptr1,ptr1,TLCUIDSIZ);
          }
     }
     if (ptr2 != NULL) {
          stlcpy(worsndbuf->ptr2,ptr2,TLCUIDSIZ);
     }
     if (ptr3 != NULL) {
          stlcpy(worsndbuf->ptr3,ptr3,TLCUIDSIZ);
     }
     if (pMsg != NULL) {
          stlcpy(worsndbuf->msg,pMsg,WORSNDBUFSIZ-sizeof(SPEAKINF));
     }
     stlen=strlen(worsndbuf->msg);
     if (pszUseridTo != NULL) {
          if (worWorldUser(pszUseridTo)) {
               worsndbuf->unumTo=worAliasToNumber(pszUseridTo);
          }
          else {
               worsndbuf->unumTo=worUseridToNumber(pszUseridTo);
          }
     }
     else {
           worSendFDA(WORAPID,WORCMD_PUBLIC_SEND,fldoff(speakinf,msg)+stlen,worsndbuf,speakinfFDA);
     }

     (VOID)not1;
     (VOID)not2;
}


VOID
TrWorRecvText(
const CHAR* pszUseridFrom,
const CHAR* pszUseridTo,
const CHAR* pMsg,
SHORT fType,
SHORT iMsgNum,
const CHAR* ptr1,
const CHAR* ptr2,
const CHAR* ptr3)
{
     UINT stlen=0;

     if (!worConnected()) {
          return;
     }
     if (pszUseridTo == NULL) {
          return;
     }
     if (worWorldUser(pszUseridFrom)) {
          return;
     }
     if (fType == RECV_TYPE_ACTION) {
          LPACTIONINF ainf=(LPACTIONINF)worsndbuf;
          LPACTION ap;

          if (actIsFile()) {
              return;
          }

          memset(ainf,0,sizeof(ACTIONINF));
          ap=actWordInfoGetCurrent(actListGetCurrent());
          if (ap != NULL) {
                LPUSRSTRUCT pUser=tlcUserGetInfo(pszUseridFrom);
                LPCHANINFO chanInfo=tlcChannelGetInfo(pUser->m_pszChannel);
                const CHAR* pTo=actGetLastDirected();
                strcpy(ainf->name,ap->name);
                ainf->from=worUseridToNumber(pszUseridFrom);
                ainf->chn=(static_cast<LPWORCHANCUSTOM>(chanInfo->m_pCustom))->num;
                if (ap->isyell) {
                     rstrin();
                     stlcpy(ainf->extra,margv[1],WORSNDBUFSIZ-sizeof(ACTIONINF));
                     stlen=strlen(ainf->extra);
                     parsin();
                     ainf->isyell=TRUE;
                }
                else {
                     if (pTo != NULL && !sameas(pTo,"")) {
                          if (worWorldUser(pTo)) {
                               ainf->to=worAliasToNumber(pTo);
                          }
                          else {
                               ainf->to=worUseridToNumber(pTo);
                          }
                     }
                }
                if (ainf->isyell || pTo != NULL) {
                     strcpy(ainf->fmt,ap->complx);
                     ainf->iscomplex=TRUE;
                }
                else {
                     strcpy(ainf->fmt,ap->simple);
                }
                if (sameas(actListGetCurrent(),primaryList)) {
                     strcpy(ainf->rate,primaryRating);
                }
                else if (sameas(actListGetCurrent(),secondaryList)) {
                     strcpy(ainf->rate,secondaryRating);
                }
                else {
                     strcpy(ainf->rate,worRatings[0]);
                }
                SHORT cmd;
                if (actIsSecret()) {
                    cmd=WORCMD_PRIVATE_ACTION;
                }
                else {
                    cmd=WORCMD_ACTION_REQUEST;
                }
#ifdef DEBUG2
shocst("WORTRSENDALLBUT FR","%s",pszUseridFrom);
shocst("WORTRSENDALLBUT TO","%s",pTo);
#endif
                worSendFDA(WORAPID,cmd,fldoff(actioninf,extra)+stlen,
                            ainf,actioninfFDA);
          }
          return;
     }
     else if (fType == RECV_TYPE_RETCHATUSER) {
          return;
     }
     memset(worsndbuf,0,sizeof(SPEAKINF));
     if (worWorldUser(pszUseridTo)) {
          worsndbuf->unumTo=worAliasToNumber(pszUseridTo);
     }
     else {
          worsndbuf->unumTo=worUseridToNumber(pszUseridTo);
     }
     worsndbuf->chn=-1;
     worsndbuf->type=fType;
     worsndbuf->iMsgNum=iMsgNum;

     if (sameas(pszUseridFrom,SYSUID)) {
          worsndbuf->unumFrom=SYSUIDN;
     }
     worsndbuf->unumFrom=worUseridToNumber(pszUseridFrom);
     if (ptr1 != NULL) {
          if (fType == RECV_TYPE_DIRECTED) {
               CHAR* num;
               if (worWorldUser(pszUseridTo)) {
                    num=ul2as(worAliasToNumber(ptr1));
               }
               else {
                    num=ul2as(worUseridToNumber(ptr1));
               }
               stlcpy(worsndbuf->ptr1,num,TLCUIDSIZ);
          }
          else {
               stlcpy(worsndbuf->ptr1,ptr1,TLCUIDSIZ);
          }
     }
     if (ptr2 != NULL) {
          stlcpy(worsndbuf->ptr2,ptr2,TLCUIDSIZ);
     }
     if (ptr3 != NULL) {
          stlcpy(worsndbuf->ptr3,ptr3,TLCUIDSIZ);
     }
     if (pMsg != NULL) {
          stlcpy(worsndbuf->msg,pMsg,WORSNDBUFSIZ-sizeof(SPEAKINF));
     }
     stlen=strlen(worsndbuf->msg);
     worSendFDA(WORAPID,WORCMD_PRIVATE_SEND,fldoff(speakinf,msg)+stlen,
                     worsndbuf,speakinfFDA);

}

GBOOL
TrWorCmdResult(
LPUSRSTRUCT user,
SHORT operation,
GBOOL success,
SHORT reason)
{
     WORCHAT wchat;

     wchat.error=0;
     switch (operation) {
     case CMD_CHAT:
          switch (reason) {
          case CMD_CHAT_ACCEPTED:
               wchat.unumTo=worAliasToNumber(user->m_pszName);
               wchat.unumFrom=worUseridToNumber(tlcUserGetChatUser(user->m_pszName));
               worSendFDA(WORAPID,WORCMD_CHAT_ACCEPT,sizeof(WORCHAT),&wchat,worchatFDA);
               break;
          case CMD_CHAT_HANGUP:
          case CMD_CHAT_STOPCHATTING:
               wchat.unumTo=worAliasToNumber(user->m_pszName);
               wchat.unumFrom=worUseridToNumber(tlcUserGetChatUser(user->m_pszName));
               wchat.error=reason;
               worSendFDA(WORAPID,WORCMD_CHAT_DONE,sizeof(WORCHAT),&wchat,worchatFDA);
               break;
          case CMD_CHAT_NOTIFY:
               wchat.unumTo=worAliasToNumber(user->m_pszName);
               wchat.unumFrom=worUseridToNumber((CHAR*)tlcwrk);
               worSendFDA(WORAPID,WORCMD_CHAT_NOTIFY,sizeof(WORCHAT),&wchat,worchatFDA);
               break;
          default:
               return(TRUE);
          }
          break;
     default:
          return(TRUE);
     }
     (VOID)success;
     return(FALSE);
}
