home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 2 BBS / 02-BBS.zip / lora299s.zip / DETECT.CPP < prev    next >
C/C++ Source or Header  |  1998-05-12  |  73KB  |  2,360 lines

  1.  
  2. // LoraBBS Version 2.99 Free Edition
  3. // Copyright (C) 1987-98 Marco Maccaferri
  4. //
  5. // This program is free software; you can redistribute it and/or modify
  6. // it under the terms of the GNU General Public License as published by
  7. // the Free Software Foundation; either version 2 of the License, or
  8. // (at your option) any later version.
  9. //
  10. // This program is distributed in the hope that it will be useful,
  11. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13. // GNU General Public License for more details.
  14. //
  15. // You should have received a copy of the GNU General Public License
  16. // along with this program; if not, write to the Free Software
  17. // Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  18.  
  19. #include "_ldefs.h"
  20. #include "ftrans.h"
  21. #include "lora.h"
  22.  
  23. #define YOOHOO             0xF1
  24. #define TSYNC              0xAE
  25.  
  26. #define isOPUS             0x05
  27. #define isLORA             0x4E
  28. #define isMAX_PRODUCT      0xE2
  29.  
  30. #define EMSI_NONE          0
  31. #define EMSI_ACK           1
  32. #define EMSI_NAK           2
  33. #define EMSI_ICI           3
  34. #define EMSI_INQ           4
  35. #define EMSI_REQ           5
  36. #define EMSI_DAT           6
  37.  
  38. typedef struct {
  39.    USHORT Signal;
  40.    USHORT Version;
  41.    USHORT Product;
  42.    USHORT ProductMaj;
  43.    USHORT ProductMin;
  44.    CHAR   Name[60];
  45.    CHAR   Sysop[20];
  46.    USHORT Zone;
  47.    USHORT Net;
  48.    USHORT Node;
  49.    USHORT Point;
  50.    CHAR   Password[8];
  51.    UCHAR  Reserved1[4];
  52.    USHORT PktFiles;           // Used only by LoraBBS >= 2.20
  53.    USHORT DataFiles;          // Used only by LoraBBS >= 2.20
  54.    USHORT Capabilities;
  55.    ULONG  Tranx;              // Used only by LoraBBS >= 2.10
  56.    ULONG  PktBytes;           // Used only by LoraBBS >= 2.20
  57.    ULONG  DataBytes;          // Used only by LoraBBS >= 2.20
  58. } HELLO;
  59.  
  60. #define Y_DIETIFNA         0x0001
  61. #define FTB_USER           0x0002
  62. #define ZED_ZIPPER         0x0004
  63. #define ZED_ZAPPER         0x0008
  64. #define DOES_IANUS         0x0010
  65. #define DO_DOMAIN          0x4000
  66. #define WZ_FREQ            0x8000
  67.  
  68. char *ProductNames[] = {
  69.    "Fido",
  70.    "Rover",
  71.    "SEAdog",
  72.    "",
  73.    "Slick/150",
  74.    "Opus",
  75.    "Dutchie",
  76.    "",
  77.    "Tabby",
  78.    "Hoster",
  79.    "Wolf/68k",
  80.    "QMM",
  81.    "FrontDoor",
  82.    "",
  83.    "",
  84.    "",
  85.    "",
  86.    "MailMan",
  87.    "OOPS",
  88.    "GS-Point",
  89.    "BGMail",
  90.    "CrossBow",
  91.    "",
  92.    "",
  93.    "",
  94.    "BinkScan",
  95.    "D'Bridge",
  96.    "BinkleyTerm",
  97.    "Yankee",
  98.    "FGet/FSend",
  99.    "Daisy,Apple ][",
  100.    "Polar Bear",
  101.    "The-Box",
  102.    "STARgate/2",
  103.    "TMail",
  104.    "TCOMMail",
  105.    "Bananna",
  106.    "RBBSMail",
  107.    "Apple-Netmail",
  108.    "Chameleon",
  109.    "Majik Board",
  110.    "QMail",
  111.    "Point And Click",
  112.    "Aurora Three Bundler",
  113.    "FourDog",
  114.    "MSG-PACK",
  115.    "AMAX",
  116.    "Domain Communication System",
  117.    "LesRobot",
  118.    "Rose",
  119.    "Paragon",
  120.    "BinkleyTerm",
  121.    "StarNet",
  122.    "ZzyZx",
  123.    "QEcho",
  124.    "BOOM",
  125.    "PBBS",
  126.    "TrapDoor",
  127.    "Welmat",
  128.    "NetGate",
  129.    "Odie",
  130.    "Quick Gimme",
  131.    "dbLink",
  132.    "TosScan",
  133.    "Beagle",
  134.    "Igor",
  135.    "TIMS",
  136.    "Isis",
  137.    "AirMail",
  138.    "XRS",
  139.    "Juliet Mail System",
  140.    "Jabberwocky",
  141.    "XST",
  142.    "MailStorm",
  143.    "BIX-Mail",
  144.    "IMAIL",
  145.    "FTNGate",
  146.    "RealMail",
  147.    "LoraBBS",
  148.    "TDCS",
  149.    "InterMail",
  150.    "RFD",
  151.    "Yuppie!",
  152.    "EMMA",
  153.    "QBoxMail",
  154.    "Number 4",
  155.    "Number 5",
  156.    "GSBBS",
  157.    "Merlin",
  158.    "TPCS",
  159.    "Raid",
  160.    "Outpost",
  161.    "Nizze",
  162.    "Armadillo",
  163.    "rfmail",
  164.    "Msgtoss",
  165.    "InfoTex",
  166.    "GEcho",
  167.    "CDEhost",
  168.    "Pktize",
  169.    "PC-RAIN",
  170.    "Truffle",
  171.    "Foozle",
  172.    "White Pointer",
  173.    "GateWorks",
  174.    "Portal of Power",
  175.    "MacWoof",
  176.    "Mosaic",
  177.    "TPBEcho",
  178.    "HandyMail",
  179.    "EchoSmith",
  180.    "FileHost",
  181.    "SFScan",
  182.    "Benjamin",
  183.    "RiBBS",
  184.    "MP",
  185.    "Ping",
  186.    "Door2Europe",
  187.    "SWIFT",
  188.    "WMAIL",
  189.    "RATS",
  190.    "Harry the Dirty Dog",
  191.    "Maximus-CBCS",
  192.    "SwifEcho",
  193.    "GCChost",
  194.    "RPX-Mail",
  195.    "Tosser",
  196.    "TCL",
  197.    "MsgTrack",
  198.    "FMail",
  199.    "Scantoss",
  200.    "Point Manager",
  201.    "Dropped",
  202.    "Simplex",
  203.    "UMTP",
  204.    "Indaba",
  205.    "Echomail Engine",
  206.    "DragonMail",
  207.    "Prox",
  208.    "Tick",
  209.    "RA-Echo",
  210.    "TrapToss",
  211.    "Babel",
  212.    "UMS",
  213.    "RWMail",
  214.    "WildMail",
  215.    "AlMAIL",
  216.    "XCS",
  217.    "Fone-Link",
  218.    "Dogfight",
  219.    "Ascan",
  220.    "FastMail",
  221.    "DoorMan",
  222.    "PhaedoZap",
  223.    "SCREAM",
  224.    "MoonMail",
  225.    "Backdoor",
  226.    "MailLink",
  227.    "Mail Manager",
  228.    "Black Star",
  229.    "Bermuda",
  230.    "PT",
  231.    "UltiMail",
  232.    "GMD",
  233.    "FreeMail",
  234.    "Meliora",
  235.    "Foodo",
  236.    "MSBBS",
  237.    "Boston BBS",
  238.    "XenoMail",
  239.    "XenoLink",
  240.    "ObjectMatrix",
  241.    "Milquetoast",
  242.    "PipBase",
  243.    "EzyMail",
  244.    "FastEcho",
  245.    "IOS",
  246.    "Communique",
  247.    "PointMail",
  248.    "Harvey's Robot",
  249.    "2daPoint",
  250.    "CommLink",
  251.    "fronttoss",
  252.    "SysopPoint",
  253.    "PTMAIL",
  254.    "AECHO",
  255.    "DLGMail",
  256.    "GatePrep",
  257.    "Spoint",
  258.    "TurboMail",
  259.    "FXMAIL",
  260.    "NextBBS",
  261.    "EchoToss",
  262.    "SilverBox",
  263.    "MBMail",
  264.    "SkyFreq",
  265.    "ProMailer",
  266.    "Mega Mail",
  267.    "YaBom",
  268.    "TachEcho",
  269.    "XAP",
  270.    "EZMAIL",
  271.    "Arc-Binkley",
  272.    "Roser",
  273.    "UU2",
  274.    "NMS",
  275.    "BBCSCAN",
  276.    "XBBS",
  277.    "LoTek Vzrul",
  278.    "Private Point Project",
  279.    "NoSnail",
  280.    "SmlNet",
  281.    "STIR",
  282.    "RiscBBS",
  283.    "Hercules",
  284.    "AMPRGATE",
  285.    "BinkEMSI",
  286.    "EditMsg",
  287.    "Roof",
  288.    "QwkPkt",
  289.    "MARISCAN",
  290.    "NewsFlash",
  291.    "Paradise",
  292.    "DogMatic-ACB",
  293.    "T-Mail",
  294.    "JetMail",
  295.    "MainDoor"
  296. };
  297.  
  298. TDetect::TDetect (void)
  299. {
  300.    Ansi = Avatar = Rip = FALSE;
  301.    Remote = REMOTE_NONE;
  302.    EMSI = YooHoo = IEMSI = FALSE;
  303.    Com = NULL;
  304.    Cfg = NULL;
  305.    Progress = NULL;
  306.    MailerStatus = NULL;
  307.    Status = NULL;
  308.    LastPktName = 0L;
  309.    Speed = 57600L;
  310.  
  311.    ReceiveEMSI = ReceiveIEMSI;
  312.    SendEMSI = SendIEMSI;
  313.    Address.Clear ();
  314. }
  315.  
  316. TDetect::~TDetect (void)
  317. {
  318. }
  319.  
  320. USHORT TDetect::AbortSession (VOID)
  321. {
  322.    USHORT RetVal = FALSE;
  323.  
  324.    if (Com != NULL) {
  325.       if (Com->Carrier () == FALSE)
  326.          RetVal = TRUE;
  327.    }
  328.  
  329.    return (RetVal);
  330. }
  331.  
  332. USHORT TDetect::CheckEMSIPacket (VOID)
  333. {
  334.    USHORT key, RetVal = EMSI_NONE;
  335.    CHAR pkt[4];
  336.  
  337.    do {
  338.       key = TimedRead ();
  339.       if (key != 'E' && key != '*')
  340.          return (RetVal);
  341.    } while (key != 'E');
  342.  
  343.    if (TimedRead () != 'M')
  344.       return (RetVal);
  345.    if (TimedRead () != 'S')
  346.       return (RetVal);
  347.    if (TimedRead () != 'I')
  348.       return (RetVal);
  349.    if (TimedRead () != '_')
  350.       return (RetVal);
  351.  
  352.    if ((pkt[0] = (CHAR)TimedRead ()) == -1)
  353.       return (RetVal);
  354.    if ((pkt[1] = (CHAR)TimedRead ()) == -1)
  355.       return (RetVal);
  356.    if ((pkt[2] = (CHAR)TimedRead ()) == -1)
  357.       return (RetVal);
  358.    pkt[3] = '\0';
  359.  
  360.    if (!stricmp (pkt, "ICI"))
  361.       RetVal = EMSI_ICI;
  362.    else if (!stricmp (pkt, "INQ")) {
  363.       if (TimedRead () != 'C')
  364.          return (RetVal);
  365.       if (TimedRead () != '8')
  366.          return (RetVal);
  367.       if (TimedRead () != '1')
  368.          return (RetVal);
  369.       if (TimedRead () != '6')
  370.          return (RetVal);
  371. //      TimedRead ();
  372.       RetVal = EMSI_INQ;
  373.    }
  374.    else if (!stricmp (pkt, "DAT"))
  375.       RetVal = EMSI_DAT;
  376.    else if (!stricmp (pkt, "REQ")) {
  377.       if (TimedRead () != 'A')
  378.          return (RetVal);
  379.       if (TimedRead () != '7')
  380.          return (RetVal);
  381.       if (TimedRead () != '7')
  382.          return (RetVal);
  383.       if (TimedRead () != 'E')
  384.          return (RetVal);
  385. //      TimedRead ();
  386.       RetVal = EMSI_REQ;
  387.    }
  388.    else if (!stricmp (pkt, "NAK")) {
  389.       if (TimedRead () != 'E')
  390.          return (RetVal);
  391.       if (TimedRead () != 'E')
  392.          return (RetVal);
  393.       if (TimedRead () != 'C')
  394.          return (RetVal);
  395.       if (TimedRead () != '3')
  396.          return (RetVal);
  397. //      TimedRead ();
  398.       RetVal = EMSI_NAK;
  399.    }
  400.    else if (!stricmp (pkt, "ACK")) {
  401.       if (TimedRead () == -1)
  402.          return (RetVal);
  403.       if (TimedRead () == -1)
  404.          return (RetVal);
  405.       if (TimedRead () == -1)
  406.          return (RetVal);
  407.       if (TimedRead () == -1)
  408.          return (RetVal);
  409. //      TimedRead ();
  410.       RetVal = EMSI_ACK;
  411.    }
  412.    else if (!stricmp (pkt, "HBT")) {
  413.       if (TimedRead () == -1)
  414.          return (RetVal);
  415.       if (TimedRead () == -1)
  416.          return (RetVal);
  417.       if (TimedRead () == -1)
  418.          return (RetVal);
  419.       if (TimedRead () == -1)
  420.          return (RetVal);
  421. //      TimedRead ();
  422.       RetVal = EMSI_NONE;
  423.    }
  424.  
  425.    return (RetVal);
  426. }
  427.  
  428. VOID TDetect::IEMSIReceiver (VOID)
  429. {
  430.    if (Status != NULL)
  431.       Status->SetLine (0, "Receiving IEMSI packet");
  432.  
  433.    if (ReceiveIEMSIPacket () == TRUE) {
  434.       if (Status != NULL)
  435.          Status->SetLine (0, "Sending IEMSI packet");
  436.       SendIEMSIPacket ();
  437.       ParseIEMSIPacket ();
  438.    }
  439. }
  440.  
  441. USHORT TDetect::RemoteMailer (VOID)
  442. {
  443.    USHORT key, prev, i, IsEMSI, IsYOOHOO;
  444.    ULONG tout;
  445.  
  446.    StartCall = time (NULL);
  447.  
  448.    if (Cfg != NULL)
  449.       strcpy (Inbound, Cfg->NormalInbound);
  450.    if (Com != NULL)
  451.       Com->ClearInbound ();
  452.    tout = TimerSet (400);
  453.    prev = 0;
  454.    Remote = REMOTE_NONE;
  455.    IsYOOHOO = IsEMSI = FALSE;
  456.  
  457.    if (Status != NULL)
  458.       Status->Clear ();
  459.  
  460.    for (i = 0; i < 5 && Remote == REMOTE_NONE && AbortSession () == FALSE; i++) {
  461.       Com->SendBytes ((UCHAR *)" \r \r", 4);
  462.       while (!TimeUp (tout) && AbortSession () == FALSE) {
  463.          if (Com->BytesReady () == TRUE) {
  464.             key = Com->ReadByte ();
  465.             switch (key) {
  466.                case '*':
  467.                   if (prev == '*') {
  468.                      switch (CheckEMSIPacket ()) {
  469.                         case EMSI_REQ:
  470.                            if (IsYOOHOO == FALSE && Cfg->EMSI == TRUE) {
  471.                               Com->SendBytes ((UCHAR *)"**EMSI_INQC816\r", 15);
  472.                               Remote = REMOTE_MAILER;
  473.                               EMSISender ();
  474.                               IsEMSI = TRUE;
  475.                            }
  476.                            break;
  477.                      }
  478.                   }
  479.                   break;
  480.  
  481.                case ENQ:
  482.                   if (IsEMSI == FALSE && Cfg->WaZoo == TRUE) {
  483.                      Remote = REMOTE_MAILER;
  484.                      WaZOOSender ();
  485.                      IsYOOHOO = TRUE;
  486.                   }
  487.                   break;
  488.             }
  489.             prev = key;
  490.          }
  491.  
  492. #if defined(__OS2__)
  493.          DosSleep (1L);
  494. #elif defined(__NT__)
  495.          Sleep (1L);
  496. #endif
  497.       }
  498.  
  499.       if (Remote == REMOTE_NONE && AbortSession () == FALSE && Com != NULL) {
  500.          if (Cfg->EMSI == TRUE)
  501.             Com->BufferBytes ((UCHAR *)"\r**EMSI_INQC816\r**EMSI_INQC816\r", 31);
  502.          if (Cfg->WaZoo == TRUE)
  503.             Com->BufferByte (YOOHOO);
  504.          Com->BufferByte (TSYNC);
  505.          Com->UnbufferBytes ();
  506.  
  507.          tout = TimerSet (400);
  508.       }
  509.    }
  510.  
  511.    if (Remote == REMOTE_NONE && Log != NULL)
  512.       Log->Write ("*Sensor doesn't report intelligent life");
  513.  
  514.    return (Remote);
  515. }
  516.  
  517. USHORT TDetect::ReceiveEMSIPacket (VOID)
  518. {
  519.    FILE *fp;
  520.    SHORT key;
  521.    USHORT RetVal = FALSE, i, len, Crc, OtherCrc;
  522.  
  523.    if (Status != NULL)
  524.       Status->SetLine (0, "Receiving EMSI Packet");
  525.  
  526.    Crc = StringCrc16 ("EMSI_DAT", 0);
  527.  
  528.    if ((fp = fopen ("lastemsi.dat", "wb")) != NULL)
  529.       fprintf (fp, "**EMSI_DAT");
  530.  
  531.    len = 0;
  532.    for (i = 0; i < 4; i++) {
  533.       if ((key = TimedRead ()) == -1)
  534.          return (FALSE);
  535.       if (fp != NULL)
  536.          fputc (key, fp);
  537.       Crc = Crc16 ((UCHAR)key, Crc);
  538.       len <<= 4;
  539.       key = (USHORT)(toupper (key) - 48);
  540.       if (key > 9)
  541.          key = (SHORT)(key - 7);
  542.       len |= key;
  543.    }
  544.  
  545.    for (i = 0; i < len; i++) {
  546.       if ((key = TimedRead ()) == -1)
  547.          return (FALSE);
  548.       if (fp != NULL)
  549.          fputc (key, fp);
  550.       ReceiveEMSI[i] = (CHAR)key;
  551.       Crc = Crc16 ((UCHAR)key, Crc);
  552.    }
  553.    ReceiveEMSI[i] = '\0';
  554.  
  555.    OtherCrc = 0;
  556.    for (i = 0; i < 4; i++) {
  557.       if ((key = TimedRead ()) == -1)
  558.          return (FALSE);
  559.       if (fp != NULL)
  560.          fputc (key, fp);
  561.       OtherCrc <<= 4;
  562.       key = (USHORT)(toupper (key) - 48);
  563.       if (key > 9)
  564.          key = (SHORT)(key - 7);
  565.       OtherCrc |= key;
  566.    }
  567.  
  568.    TimedRead ();
  569.  
  570.    if (fp != NULL)
  571.       fclose (fp);
  572.  
  573.    if (Crc != OtherCrc) {
  574.       Log->Write (":  CRC Error (%08lX / %08lX)", Crc, OtherCrc);
  575.       Com->SendBytes ((UCHAR *)"**EMSI_NAKEEC3\r", 15);
  576.    }
  577.    else {
  578.       Com->SendBytes ((UCHAR *)"**EMSI_ACKA490\r**EMSI_ACKA490\r", 30);
  579.       RetVal = TRUE;
  580.    }
  581.  
  582.    return (RetVal);
  583. }
  584.  
  585. USHORT TDetect::ReceiveIEMSIPacket (VOID)
  586. {
  587.    SHORT key;
  588.    USHORT RetVal = TRUE, i, len;
  589.    ULONG Crc, OtherCrc;
  590.  
  591.    Crc = StringCrc32 ("EMSI_ICI", 0xFFFFFFFFL);
  592.  
  593.    len = 0;
  594.    for (i = 0; i < 4; i++) {
  595.       if ((key = TimedRead ()) == -1)
  596.          return (FALSE);
  597.       Crc = Crc32 ((UCHAR)key, Crc);
  598.       len <<= 4;
  599.       key = (USHORT)(toupper (key) - 48);
  600.       if (key > 9)
  601.          key = (SHORT)(key - 7);
  602.       len |= key;
  603.    }
  604.  
  605.    for (i = 0; i < len; i++) {
  606.       if ((key = TimedRead ()) == -1)
  607.          return (FALSE);
  608.       ReceiveIEMSI[i] = (CHAR)key;
  609.       Crc = Crc32 ((UCHAR)key, Crc);
  610.    }
  611.    ReceiveIEMSI[i] = '\0';
  612.  
  613.    OtherCrc = 0;
  614.    for (i = 0; i < 8; i++) {
  615.       if ((key = TimedRead ()) == -1)
  616.          return (FALSE);
  617.       OtherCrc <<= 4;
  618.       key = (USHORT)(toupper (key) - 48);
  619.       if (key > 9)
  620.          key = (SHORT)(key - 7);
  621.       OtherCrc |= key;
  622.    }
  623.  
  624.    TimedRead ();
  625.  
  626.    if (Crc != OtherCrc) {
  627.       Com->SendBytes ((UCHAR *)"**EMSI_NAKEEC3\r", 15);
  628.       RetVal = FALSE;
  629.    }
  630.  
  631.    return (RetVal);
  632. }
  633.  
  634. VOID TDetect::SendEMSIPacket (VOID)
  635. {
  636.    CHAR Temp[64], FoundPw = FALSE;
  637.    USHORT Crc, OutPktFiles, OutDataFiles;
  638.    ULONG OutPktBytes, OutDataBytes;
  639.    class TNodes *Nodes;
  640.    class TOutbound *Outbound;
  641.  
  642.    if (Status != NULL)
  643.       Status->SetLine (0, "Sending EMSI Packet");
  644.  
  645.    OutPktFiles = OutDataFiles = 0L;
  646.    OutPktBytes = OutDataBytes = 0L;
  647.  
  648.    strcpy (SendEMSI, "{EMSI}{");
  649.    if (Cfg->MailAddress.First () == TRUE) {
  650.       strcat (SendEMSI, Cfg->MailAddress.String);
  651.       while (Cfg->MailAddress.Next () == TRUE) {
  652.          strcat (SendEMSI, " ");
  653.          strcat (SendEMSI, Cfg->MailAddress.String);
  654.       }
  655.    }
  656.    strcat (SendEMSI, "}{");
  657.  
  658.    if ((Nodes = new TNodes (Cfg->NodelistPath)) != NULL) {
  659.       if (Address.First () == TRUE)
  660.          do {
  661.             if (Nodes->Read (Address) == TRUE) {
  662.                if (Nodes->SessionPwd[0] != '\0') {
  663.                   strcat (SendEMSI, Nodes->SessionPwd);
  664.                   FoundPw = TRUE;
  665.                }
  666.             }
  667.          } while (FoundPw == FALSE && Address.Next () == TRUE);
  668.       delete Nodes;
  669.    }
  670.  
  671.    if (Cfg->Janus == TRUE)
  672.       strcat (SendEMSI, "}{8N1,PUA}{JAN,ZAP,ZMO,ARC,XMA");
  673.    else
  674.       strcat (SendEMSI, "}{8N1,PUA}{ZAP,ZMO,ARC,XMA");
  675.    if (Events->AllowRequests == FALSE)
  676.       strcat (SendEMSI, ",NRQ");
  677.    strcat (SendEMSI, "}");
  678.  
  679. #if defined(__OS2__)
  680.    sprintf (Temp, "{%02X}{%s/OS2}{%s}{}{IDENT}{", PRODUCT_ID, NAME, VERSION);
  681. #elif defined(__NT__)
  682.    sprintf (Temp, "{%02X}{%s/NT}{%s}{}{IDENT}{", PRODUCT_ID, NAME, VERSION);
  683. #elif defined(__LINUX__)
  684.    sprintf (Temp, "{%02X}{%s/Linux}{%s}{}{IDENT}{", PRODUCT_ID, NAME, VERSION);
  685. #else
  686.    sprintf (Temp, "{%02X}{%s/DOS}{%s}{}{IDENT}{", PRODUCT_ID, NAME, VERSION);
  687. #endif
  688.    strcat (SendEMSI, Temp);
  689.    sprintf (Temp, "[%s][%s]", Cfg->SystemName, Cfg->Location);
  690.    strcat (SendEMSI, Temp);
  691.    sprintf (Temp, "[%s][%s]", Cfg->SysopName, Cfg->Phone);
  692.    strcat (SendEMSI, Temp);
  693.    sprintf (Temp, "[9600][%s]}", Cfg->NodelistFlags);
  694.    strcat (SendEMSI, Temp);
  695.  
  696.    sprintf (Temp, "{TRX#}{[%08lX]}", time (NULL));
  697.    strcat (SendEMSI, Temp);
  698.  
  699.    if ((Outbound = new TOutbound (Cfg->Outbound)) != NULL) {
  700.       if (Cfg->MailAddress.First () == TRUE)
  701.          Outbound->DefaultZone = Cfg->MailAddress.Zone;
  702.  
  703.       if (Address.First () == TRUE) {
  704.          do {
  705.             Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  706.          } while (Address.Next () == TRUE);
  707.       }
  708.  
  709.       if (Outbound->First () == TRUE)
  710.          do {
  711.             if (Outbound->ArcMail == TRUE || Outbound->MailPKT == TRUE) {
  712.                OutPktFiles++;
  713.                OutPktBytes += Outbound->Size;
  714.             }
  715.             else if (Outbound->Poll == FALSE) {
  716.                OutDataFiles++;
  717.                OutDataBytes += Outbound->Size;
  718.             }
  719.          } while (Outbound->Next () == TRUE);
  720.  
  721.       delete Outbound;
  722.    }
  723.  
  724.    sprintf (Temp, "{MTX#}{[%u][%lu][%u][%lu]}", OutPktFiles, OutPktBytes, OutDataFiles, OutDataBytes);
  725.    strcat (SendEMSI, Temp);
  726.  
  727.    Com->BufferBytes ((UCHAR *)"**", 2);
  728.  
  729.    sprintf (Temp, "EMSI_DAT%04X", strlen (SendEMSI));
  730.    Com->BufferBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  731.    Crc = StringCrc16 (Temp, 0);
  732.  
  733.    Com->BufferBytes ((UCHAR *)SendEMSI, (USHORT)strlen (SendEMSI));
  734.    Crc = StringCrc16 (SendEMSI, Crc);
  735.    Com->UnbufferBytes ();
  736.  
  737.    Com->ClearInbound ();
  738.    while (Com->BytesReady () == TRUE)
  739.       Com->ReadByte ();
  740.  
  741.    sprintf (Temp, "%04X\r", Crc);
  742.    Com->SendBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  743. }
  744.  
  745. VOID TDetect::SendIEMSIPacket (VOID)
  746. {
  747.    CHAR Temp[64];
  748.    ULONG Crc;
  749.  
  750.    tzset ();
  751.  
  752. #if defined(__OS2__)
  753.    sprintf (SendIEMSI, "{%s/OS2,%s,Unregistered}{", NAME, VERSION);
  754. #elif defined(__NT__)
  755.    sprintf (SendIEMSI, "{%s/NT,%s,Unregistered}{", NAME, VERSION);
  756. #elif defined(__LINUX__)
  757.    sprintf (SendIEMSI, "{%s/Linux,%s,Unregistered}{", NAME, VERSION);
  758. #else
  759.    sprintf (SendIEMSI, "{%s/DOS,%s,Unregistered}{", NAME, VERSION);
  760. #endif
  761.    strcat (SendIEMSI, Cfg->SystemName);
  762.    strcat (SendIEMSI, "}{");
  763.    strcat (SendIEMSI, Cfg->Location);
  764.    strcat (SendIEMSI, "}{");
  765.    strcat (SendIEMSI, Cfg->SysopName);
  766.    sprintf (Temp, "}{%08lX}{}{}{}{}", time (NULL));
  767.    strcat (SendIEMSI, Temp);
  768.  
  769.    Com->BufferBytes ((UCHAR *)"**", 2);
  770.  
  771.    sprintf (Temp, "EMSI_ISI%04X", strlen (SendIEMSI));
  772.    Com->BufferBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  773.    Crc = StringCrc32 (Temp, 0xFFFFFFFFL);
  774.  
  775.    Com->BufferBytes ((UCHAR *)SendIEMSI, (USHORT)strlen (SendIEMSI));
  776.    Com->UnbufferBytes ();
  777.    Crc = StringCrc32 (SendIEMSI, Crc);
  778.    Com->ClearInbound ();
  779.  
  780.    sprintf (Temp, "%08lX\r", Crc);
  781.    Com->SendBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  782. }
  783.  
  784. USHORT TDetect::EMSIReceiver (VOID)
  785. {
  786.    USHORT RetVal = FALSE;
  787.    SHORT key, prev;
  788.    ULONG tout, tout1;
  789.  
  790.    if (ReceiveEMSIPacket () == TRUE) {
  791.       Remote = REMOTE_MAILER;
  792.       ParseEMSIPacket ();
  793.  
  794.       SendEMSIPacket ();
  795.  
  796.       prev = 0;
  797.       tout = TimerSet (6000);
  798.       tout1 = TimerSet (1000);
  799.  
  800.       while (!TimeUp (tout) && AbortSession () == FALSE) {
  801.          if (Com->BytesReady () == TRUE) {
  802.             key = Com->ReadByte ();
  803.             switch (key) {
  804.                case '*':
  805.                   if (prev == '*') {
  806.                      switch (CheckEMSIPacket ()) {
  807.                         case EMSI_ACK:
  808.                            RetVal = TRUE;
  809.                            tout = TimerSet (100);
  810.                            tout1 = TimerSet (1000);
  811.                            break;
  812.  
  813.                         case EMSI_NAK:
  814.                            SendEMSIPacket ();
  815.                            tout1 = TimerSet (1000);
  816.                            break;
  817.                      }
  818.                   }
  819.                   break;
  820.             }
  821.             prev = key;
  822.          }
  823.          if (TimeUp (tout1)) {
  824.             SendEMSIPacket ();
  825.             tout1 = TimerSet (1000);
  826.          }
  827.       }
  828.    }
  829.  
  830.    if (RetVal == TRUE)
  831.       Receiver ();
  832.  
  833.    return (RetVal);
  834. }
  835.  
  836. USHORT TDetect::EMSISender (VOID)
  837. {
  838.    USHORT RetVal = FALSE, MaybeError;
  839.    SHORT key, prev;
  840.    ULONG tout, acktout;
  841.  
  842.    SendEMSIPacket ();
  843.  
  844.    prev = 0;
  845.    tout = TimerSet (3000);
  846.    acktout = TimerSet (500);
  847.    MaybeError = FALSE;
  848.  
  849.    while (!TimeUp (tout) && AbortSession () == FALSE) {
  850.       if (Com->BytesReady () == TRUE) {
  851.          key = Com->ReadByte ();
  852.          switch (key) {
  853.             case '*':
  854.                if (prev == '*') {
  855.                   switch (CheckEMSIPacket ()) {
  856.                      case EMSI_DAT:
  857.                         RetVal = TRUE;
  858.                         tout = TimerSet (100);
  859.                         if (ReceiveEMSIPacket () == TRUE) {
  860.                            Remote = REMOTE_MAILER;
  861.                            ParseEMSIPacket ();
  862.                         }
  863.                         break;
  864.  
  865.                      case EMSI_REQ:
  866.                         if (MaybeError == TRUE) {
  867.                            Com->SendBytes ((UCHAR *)"**EMSI_INQC816\r", 15);
  868.                            SendEMSIPacket ();
  869.                            acktout = TimerSet (500);
  870.                         }
  871.                         break;
  872.  
  873.                      case EMSI_NAK:
  874.                         SendEMSIPacket ();
  875.                         acktout = TimerSet (500);
  876.                         break;
  877.                      default:
  878.                         break;
  879.                   }
  880.                }
  881.                break;
  882.          }
  883.          prev = key;
  884.       }
  885.       if (TimeUp (acktout)) {
  886.          acktout = TimerSet (500);
  887.          Com->SendBytes ((UCHAR *)"**EMSI_NAKEEC3\r", 15);
  888.          MaybeError = TRUE;
  889.       }
  890.    }
  891.  
  892.    if (RetVal == TRUE)
  893.       Sender ();
  894.  
  895.    return (RetVal);
  896. }
  897.  
  898. VOID TDetect::Terminal (VOID)
  899. {
  900.    USHORT key, prev, pos, i, gotAnswer, IsEMSI, ripos;
  901.    USHORT canexit, MailOnly;
  902.    CHAR Temp[128], RipTemp[32];
  903.    ULONG tout;
  904.    PSZ Announce = "\rAuto-Sensing Terminal...\r";
  905.  
  906.    StartCall = time (NULL);
  907.    canexit = FALSE;
  908.    ripos = 0;
  909.  
  910.    if (Cfg != NULL)
  911.       strcpy (Inbound, Cfg->NormalInbound);
  912.    if (Com != NULL)
  913.       Com->ClearInbound ();
  914.    gotAnswer = FALSE;
  915.    tout = TimerSet (400);
  916.    prev = 0;
  917.    IsEMSI = FALSE;
  918.  
  919.    if (Cfg->Ansi == NO) {
  920.       Ansi = FALSE;
  921.       gotAnswer = TRUE;
  922.    }
  923.    else if (Cfg->Ansi == YES) {
  924.       Ansi = TRUE;
  925.       gotAnswer = TRUE;
  926.    }
  927.    if (Cfg->UseAvatar == NO) {
  928.       Avatar = FALSE;
  929.       gotAnswer = TRUE;
  930.    }
  931.    else if (Cfg->UseAvatar == YES) {
  932.       Avatar = TRUE;
  933.       gotAnswer = TRUE;
  934.    }
  935.  
  936.    MailOnly = Events->MailOnly;
  937.    Remote = (MailOnly == TRUE) ? REMOTE_NONE : REMOTE_USER;
  938.  
  939.    for (i = 0; i < 5 && (gotAnswer == FALSE || i == 0) && AbortSession () == FALSE; i++) {
  940.       while (!TimeUp (tout) && AbortSession () == FALSE) {
  941.          if (Com->BytesReady () == TRUE) {
  942.             key = Com->ReadByte ();
  943.             switch (ripos) {
  944.                case 0:
  945.                   if (key == 'R')
  946.                      RipTemp[ripos++] = (CHAR)key;
  947.                   else
  948.                      ripos = 0;
  949.                   break;
  950.                case 1:
  951.                   if (key == 'I')
  952.                      RipTemp[ripos++] = (CHAR)key;
  953.                   else
  954.                      ripos = 0;
  955.                   break;
  956.                case 2:
  957.                   if (key == 'P')
  958.                      RipTemp[ripos++] = (CHAR)key;
  959.                   else
  960.                      ripos = 0;
  961.                   break;
  962.                case 3:
  963.                   if (key == 'S')
  964.                      RipTemp[ripos++] = (CHAR)key;
  965.                   else
  966.                      ripos = 0;
  967.                   break;
  968.                case 4:
  969.                   if (key == 'C')
  970.                      RipTemp[ripos++] = (CHAR)key;
  971.                   else
  972.                      ripos = 0;
  973.                   break;
  974.                case 5:
  975.                   if (key == 'R')
  976.                      RipTemp[ripos++] = (CHAR)key;
  977.                   else
  978.                      ripos = 0;
  979.                   break;
  980.                case 6:
  981.                   if (key == 'I')
  982.                      RipTemp[ripos++] = (CHAR)key;
  983.                   else
  984.                      ripos = 0;
  985.                   break;
  986.                case 7:
  987.                   if (key == 'P')
  988.                      RipTemp[ripos++] = (CHAR)key;
  989.                   else
  990.                      ripos = 0;
  991.                   break;
  992.                default:
  993.                   if (ripos > 7 && ripos < 14) {
  994.                      if (isdigit (key))
  995.                         RipTemp[ripos++] = (CHAR)key;
  996.                      else
  997.                         ripos = 0;
  998.                      if (ripos == 13) {
  999.                         if (RipTemp[12] == '0' && RipTemp[13] == '0')
  1000.                            ;
  1001. //                           Max = TRUE;
  1002.                         else
  1003.                            Rip = TRUE;
  1004.                         Ansi = TRUE;
  1005.                         Remote = REMOTE_USER;
  1006.                         gotAnswer = TRUE;
  1007.                      }
  1008.                   }
  1009.                   break;
  1010.             }
  1011.  
  1012.             switch (key) {
  1013.                case '~': {
  1014.                   CHAR Temp[64];
  1015.  
  1016.                   if (MailOnly == FALSE && Cfg->EnablePPP == TRUE && Cfg->PPPCmd[0]) {
  1017.                      if (Log != NULL)
  1018.                         Log->Write ("+Detected PPP connection");
  1019.  
  1020.                      sprintf (Temp, Cfg->PPPCmd, Task);
  1021.                      if (Log != NULL)
  1022.                         Log->Write (":Running %s", Temp);
  1023.  
  1024.                      RunExternal (Temp, Cfg->PPPTimeLimit);
  1025.  
  1026.                      tout = TimerSet (0L);
  1027.                      Remote = REMOTE_PPP;
  1028.                      gotAnswer = TRUE;
  1029.                   }
  1030.                   break;
  1031.                }
  1032.                case '*':
  1033.                   if (prev == '*') {
  1034.                      switch (CheckEMSIPacket ()) {
  1035.                         case EMSI_ICI:
  1036.                            if (MailOnly == FALSE && Cfg->IEMSI == YES) {
  1037.                               IEMSIReceiver ();
  1038.                               tout = TimerSet (200);
  1039.                               Remote = REMOTE_USER;
  1040.                               gotAnswer = TRUE;
  1041.                            }
  1042.                            break;
  1043.                         case EMSI_INQ:
  1044.                            if (Com != NULL)
  1045.                               Com->SendBytes ((UCHAR *)"**EMSI_REQA77E\r", 15);
  1046.                            IsEMSI = TRUE;
  1047.                            break;
  1048.                         case EMSI_DAT:
  1049.                            if (Cfg->EMSI == TRUE) {
  1050.                               EMSIReceiver ();
  1051.                               gotAnswer = TRUE;
  1052.                            }
  1053.                            break;
  1054.                      }
  1055.                   }
  1056.                   break;
  1057.  
  1058. /*
  1059.                case 'I':
  1060.                   if (prev == 'R')
  1061.                      mayberip = TRUE;
  1062.                   break;
  1063.                case 'P':
  1064.                   if (mayberip == TRUE) {
  1065.                      Rip = TRUE;
  1066.                      Ansi = TRUE;
  1067.                      Remote = REMOTE_USER;
  1068.                      gotAnswer = TRUE;
  1069.                   }
  1070.                   break;
  1071. */
  1072.  
  1073.                case 0x1B:
  1074.                   if (prev == 0x1B) {
  1075.                      if (canexit == TRUE) {
  1076.                         if (MailOnly == FALSE) {
  1077.                            if (Com != NULL)
  1078.                               Com->SendBytes ((UCHAR *)"\r\n\r\n", 4);
  1079.                            Remote = REMOTE_USER;
  1080.                            return;
  1081.                         }
  1082.                         else {
  1083.                            if (Cfg->MailOnly[0] != '\0')
  1084.                               sprintf (Temp, "%s\r", Cfg->MailOnly);
  1085.                            else
  1086.                               sprintf (Temp, "%s\r", "Processing mail only. Please call later.");
  1087.                            Com->SendBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  1088.                            key = 0;
  1089.                         }
  1090.                      }
  1091.                   }
  1092.                   if (canexit == FALSE)
  1093.                      key = 0;
  1094.                   break;
  1095.  
  1096.                case '[':
  1097.                   if (prev == 0x1B && Cfg->Ansi == AUTO) {
  1098.                      Ansi = TRUE;
  1099.                      pos = 0;
  1100.                      Remote = REMOTE_USER;
  1101.                      gotAnswer = TRUE;
  1102.                   }
  1103.                   break;
  1104.  
  1105.                case ';':
  1106.                   if (pos == 12) {
  1107.                      Avatar = TRUE;
  1108.                      gotAnswer = TRUE;
  1109.                   }
  1110.                   break;
  1111.  
  1112.                case YOOHOO:
  1113.                   if (IsEMSI == FALSE && Cfg->WaZoo == TRUE) {
  1114.                      WaZOOReceiver ();
  1115.                      Remote = REMOTE_MAILER;
  1116.                      gotAnswer = TRUE;
  1117.                   }
  1118.                   break;
  1119.  
  1120.                default:
  1121. //                  mayberip = FALSE;
  1122.                   if (isdigit (key)) {
  1123.                      pos = (USHORT)(pos * 10);
  1124.                      pos += (USHORT)(key - '0');
  1125.                   }
  1126.                   break;
  1127.             }
  1128.             prev = key;
  1129.          }
  1130.  
  1131.          if (gotAnswer == TRUE && MailOnly == TRUE) {
  1132.             if (Cfg->MailOnly[0] != '\0')
  1133.                sprintf (Temp, "%s\r", Cfg->MailOnly);
  1134.             else
  1135.                sprintf (Temp, "%s\r", "Processing mail only. Please call later.");
  1136.             Com->SendBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  1137.             gotAnswer = FALSE;
  1138.          }
  1139.  
  1140. #if defined(__OS2__)
  1141.          DosSleep (1L);
  1142. #elif defined(__NT__)
  1143.          Sleep (1L);
  1144. #endif
  1145.       }
  1146.  
  1147.       if (gotAnswer == FALSE && AbortSession () == FALSE && Com != NULL) {
  1148.          Com->BufferBytes ((UCHAR *)" \r", 2);
  1149.  
  1150.          if (Cfg->EMSI == TRUE)
  1151.             Com->BufferBytes ((UCHAR *)"\r**EMSI_REQA77E\r", 16);
  1152.          if (Cfg->IEMSI == TRUE && MailOnly == FALSE)
  1153.             Com->BufferBytes ((UCHAR *)"\r**EMSI_IRQ8E08\r", 16);
  1154.          if (MailOnly == FALSE)
  1155.             Com->BufferBytes ((UCHAR *)"\x1B[!", 3);
  1156.          if (Cfg->Ansi == AUTO && MailOnly == FALSE) {
  1157.             Com->BufferBytes ((UCHAR *)"\r\x19\x20\x0B", 4);
  1158.             Com->BufferBytes ((UCHAR *)"\x1B[6n", 4);
  1159.          }
  1160.  
  1161.          Com->BufferBytes ((UCHAR *)Announce, (USHORT)strlen (Announce));
  1162.          if (MailOnly == TRUE) {
  1163.             if (Cfg->MailOnly[0] != '\0')
  1164.                sprintf (Temp, "%s\r", Cfg->MailOnly);
  1165.             else
  1166.                sprintf (Temp, "%s\r", "Processing mail only. Please call later.");
  1167.             Com->BufferBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  1168.          }
  1169.          else if (Cfg->EnterBBS[0] != '\0') {
  1170.             sprintf (Temp, "%s\r", Cfg->EnterBBS);
  1171.             Com->BufferBytes ((UCHAR *)Temp, (USHORT)strlen (Temp));
  1172.          }
  1173.          Com->UnbufferBytes ();
  1174.  
  1175.          tout = TimerSet (400);
  1176.          canexit = TRUE;
  1177.       }
  1178.    }
  1179.  
  1180.    if (AbortSession () == FALSE && Com != NULL) {
  1181.       if (MailOnly == FALSE)
  1182.          Com->SendBytes ((UCHAR *)"\r\n\r\n", 4);
  1183.    }
  1184. }
  1185.  
  1186. SHORT TDetect::TimedRead (VOID)
  1187. {
  1188.    SHORT RetVal = -1;
  1189.    ULONG tout;
  1190.  
  1191.    if (Com->BytesReady () == FALSE) {
  1192.       tout = TimerSet (100);
  1193.       do {
  1194.          if (Com->BytesReady () == TRUE) {
  1195.             RetVal = (SHORT)Com->ReadByte ();
  1196.             break;
  1197.          }
  1198. #if defined(__OS2__)
  1199.          DosSleep (1L);
  1200. #elif defined(__NT__)
  1201.          Sleep (1L);
  1202. #endif
  1203.       } while (!TimeUp (tout) && AbortSession () == FALSE && RetVal == -1);
  1204.    }
  1205.    else
  1206.       RetVal = (SHORT)Com->ReadByte ();
  1207.  
  1208.  
  1209.    return (RetVal);
  1210. }
  1211.  
  1212. #define IEMSI_NAME         0
  1213. #define IEMSI_ALIAS        1
  1214. #define IEMSI_LOCATION     2
  1215. #define IEMSI_DATAPHONE    3
  1216. #define IEMSI_VOICEPHONE   4
  1217. #define IEMSI_PASSWORD     5
  1218. #define IEMSI_BIRTHDATE    6
  1219. #define IEMSI_CRTDEF       7
  1220. #define IEMSI_PROTOCOLS    8
  1221. #define IEMSI_CAPS         9
  1222. #define IEMSI_REQUESTS     10
  1223. #define IEMSI_SOFTWARE     11
  1224. #define IEMSI_XLAT         12
  1225.  
  1226. #define MAX_IEMSITOKEN     14
  1227.  
  1228. #define EMSI_FINGERPRINT   0
  1229. #define EMSI_ADDRESS       1
  1230. #define EMSI_PASSWORD      2
  1231. #define EMSI_LINKCODES     3
  1232. #define EMSI_COMPATIBILITY 4
  1233. #define EMSI_MAILERCODE    5
  1234. #define EMSI_MAILERNAME    6
  1235. #define EMSI_MAILERVERSION 7
  1236. #define EMSI_MAILERSERIAL  8
  1237. #define EMSI_SYSTEMNAME    20
  1238. #define EMSI_LOCATION      21
  1239. #define EMSI_SYSOPNAME     22
  1240. #define EMSI_PHONE         23
  1241. #define EMSI_SPEED         24
  1242. #define EMSI_FLAGS         25
  1243. #define EMSI_TRANX         26
  1244. #define EMSI_MAILFILES     27
  1245. #define EMSI_MAILBYTES     28
  1246. #define EMSI_DATAFILES     29
  1247. #define EMSI_DATABYTES     30
  1248.  
  1249. #define MAX_EMSITOKEN      40
  1250.  
  1251. VOID TDetect::ParseEMSIPacket (VOID)
  1252. {
  1253.    USHORT i, t, idents, firstEntry;
  1254.    UCHAR Byte, *Read, *Write, c, FoundKnown, FoundProt;
  1255.    CHAR *Tokens[MAX_EMSITOKEN], Temp[64], *p, List[128];
  1256.    class TNodes *Nodes;
  1257.    class TOutbound *Outbound;
  1258.  
  1259.    for (i = 0; i < MAX_EMSITOKEN; i++)
  1260.       Tokens[i] = NULL;
  1261.  
  1262.    Read = Write = (UCHAR *)ReceiveEMSI;
  1263.    i = EMSI_FINGERPRINT;
  1264.    Capabilities = 0;
  1265.  
  1266.    while (*Read) {
  1267.       if (*Read == '\\') {
  1268.          Read++;
  1269.          if (*Read != '\\') {
  1270.             Byte = (UCHAR)(*Read - 48);
  1271.             if (Byte > 9)
  1272.                Byte = (UCHAR)(Byte - 7);
  1273.             Byte <<= 4;
  1274.             Read++;
  1275.             c = (UCHAR)(*Read - 48);
  1276.             if (c > 9)
  1277.                c = (UCHAR)(c - 7);
  1278.             Byte |= c;
  1279.             *Write++ = Byte;
  1280.          }
  1281.          else
  1282.             *Write++ = *Read;
  1283.       }
  1284.       else {
  1285.          *Write = *Read;
  1286.          if (*Write == '{') {
  1287.             if (i < MAX_EMSITOKEN)
  1288.                Tokens[i++] = (CHAR *)(Write + 1);
  1289.          }
  1290.          else if (*Write == '}')
  1291.             *Write = '\0';
  1292.          Write++;
  1293.       }
  1294.  
  1295.       Read++;
  1296.    }
  1297.  
  1298.    Tokens[i] = NULL;
  1299.  
  1300.    if (strstr (Tokens[EMSI_COMPATIBILITY], "DZA") != NULL || strstr (Tokens[EMSI_COMPATIBILITY], "ZMO") != NULL)
  1301.       Capabilities |= ZED_ZIPPER;
  1302.    if (strstr (Tokens[EMSI_COMPATIBILITY], "ZAP") != NULL)
  1303.       Capabilities |= ZED_ZAPPER;
  1304.    if (strstr (Tokens[EMSI_COMPATIBILITY], "JAN") != NULL)
  1305.       Capabilities |= DOES_IANUS;
  1306.  
  1307.    if ((p = strtok (Tokens[EMSI_ADDRESS], " ,")) != NULL)
  1308.       do {
  1309.          Address.Add (p);
  1310.       } while ((p = strtok (NULL, " ,")) != NULL);
  1311.  
  1312.    idents = i;
  1313.    for (t = 0; t < idents; t++) {
  1314.       if (!stricmp (Tokens[t], "IDENT") || !stricmp (Tokens[t], "TRX#") || !stricmp (Tokens[t], "MTX#")) {
  1315.          if ((Read = (UCHAR *)Tokens[t + 1]) != NULL) {
  1316.             i = MAX_EMSITOKEN;
  1317.             strcpy (Temp, Tokens[t]);
  1318.             if (!stricmp (Tokens[t], "IDENT"))
  1319.                i = EMSI_SYSTEMNAME;
  1320.             else if (!stricmp (Tokens[t], "TRX#"))
  1321.                i = EMSI_TRANX;
  1322.             else if (!stricmp (Tokens[t], "MTX#"))
  1323.                i = EMSI_MAILFILES;
  1324.  
  1325.             while (*Read) {
  1326.                if (*Read == '[') {
  1327.                   if (i < MAX_EMSITOKEN)
  1328.                      Tokens[i++] = (CHAR *)(Read + 1);
  1329.                }
  1330.                else if (*Read == ']')
  1331.                   *Read = '\0';
  1332.                Read++;
  1333.             }
  1334.  
  1335.             if (!stricmp (Temp, "IDENT")) {
  1336.                if (strlen (Tokens[EMSI_SYSTEMNAME]) > sizeof (RemoteSystem) - 1)
  1337.                   Tokens[EMSI_SYSTEMNAME][sizeof (RemoteSystem) - 1] = '\0';
  1338.                strcpy (RemoteSystem, Tokens[EMSI_SYSTEMNAME]);
  1339.                if (strlen (Tokens[EMSI_SYSOPNAME]) > sizeof (RemoteSysop) - 1)
  1340.                   Tokens[EMSI_SYSOPNAME][sizeof (RemoteSysop) - 1] = '\0';
  1341.                strcpy (RemoteSysop, Tokens[EMSI_SYSOPNAME]);
  1342.                if (strlen (Tokens[EMSI_LOCATION]) > sizeof (RemoteLocation) - 1)
  1343.                   Tokens[EMSI_LOCATION][sizeof (RemoteLocation) - 1] = '\0';
  1344.                strcpy (RemoteLocation, Tokens[EMSI_LOCATION]);
  1345.                if (Tokens[EMSI_MAILERSERIAL][0] != '\0')
  1346.                   sprintf (RemoteProgram, "%s %s/%s", Tokens[EMSI_MAILERNAME], Tokens[EMSI_MAILERVERSION], Tokens[EMSI_MAILERSERIAL]);
  1347.                else
  1348.                   sprintf (RemoteProgram, "%s %s", Tokens[EMSI_MAILERNAME], Tokens[EMSI_MAILERVERSION]);
  1349.             }
  1350.             else if (!stricmp (Temp, "MTX#")) {
  1351.                if (MailerStatus != NULL) {
  1352.                   MailerStatus->InPktFiles = (USHORT)atoi (Tokens[EMSI_MAILFILES]);
  1353.                   MailerStatus->InPktBytes = (ULONG)atol (Tokens[EMSI_MAILBYTES]);
  1354.                   MailerStatus->InDataFiles = (USHORT)atoi (Tokens[EMSI_DATAFILES]);
  1355.                   MailerStatus->InDataBytes = (ULONG)atol (Tokens[EMSI_DATABYTES]);
  1356.                }
  1357.             }
  1358.          }
  1359.       }
  1360.    }
  1361.  
  1362.    if (MailerStatus != NULL) {
  1363.       if ((Outbound = new TOutbound (Cfg->Outbound)) != NULL) {
  1364.          if (Cfg->MailAddress.First () == TRUE)
  1365.             Outbound->DefaultZone = Cfg->MailAddress.Zone;
  1366.       }
  1367.  
  1368.       if (Address.First () == TRUE) {
  1369.          if (Outbound != NULL)
  1370.             Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  1371.          strcpy (MailerStatus->Address, Address.String);
  1372.          if (Address.Next () == TRUE) {
  1373.             MailerStatus->Akas[0] = '\0';
  1374.             do {
  1375.                if (Outbound != NULL)
  1376.                   Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  1377.                sprintf (Temp, "%s ", Address.String);
  1378.                if ((strlen (MailerStatus->Akas) + strlen (Temp) + 1) <= sizeof (MailerStatus->Akas))
  1379.                   strcat (MailerStatus->Akas, Temp);
  1380.             } while (Address.Next () == TRUE);
  1381.          }
  1382.       }
  1383.  
  1384.       if (Outbound != NULL) {
  1385.          if (Outbound->First () == TRUE)
  1386.             do {
  1387.                if (Outbound->ArcMail == TRUE || Outbound->MailPKT == TRUE) {
  1388.                   MailerStatus->OutPktFiles++;
  1389.                   MailerStatus->OutPktBytes += Outbound->Size;
  1390.                }
  1391.                else if (Outbound->Poll == FALSE) {
  1392.                   MailerStatus->OutDataFiles++;
  1393.                   MailerStatus->OutDataBytes += Outbound->Size;
  1394.                }
  1395.             } while (Outbound->Next () == TRUE);
  1396.          delete Outbound;
  1397.       }
  1398.  
  1399.       if (strlen (RemoteSystem) > sizeof (MailerStatus->SystemName) - 1)
  1400.          RemoteSystem[sizeof (MailerStatus->SystemName) - 1] = '\0';
  1401.       strcpy (MailerStatus->SystemName, RemoteSystem);
  1402.       if (strlen (RemoteSysop) > sizeof (MailerStatus->SysopName) - 1)
  1403.          RemoteSysop[sizeof (MailerStatus->SysopName) - 1] = '\0';
  1404.       strcpy (MailerStatus->SysopName, RemoteSysop);
  1405.       if (strlen (RemoteLocation) > sizeof (MailerStatus->Location) - 1)
  1406.          RemoteLocation[sizeof (MailerStatus->Location) - 1] = '\0';
  1407.       strcpy (MailerStatus->Location, RemoteLocation);
  1408.       strcpy (MailerStatus->Program, RemoteProgram);
  1409.       MailerStatus->Speed = Speed;
  1410.       MailerStatus->Update ();
  1411.    }
  1412.  
  1413.    if (Address.First () == TRUE) {
  1414.       Log->Write ("*%s (%s)", RemoteSystem, Address.String);
  1415.       if (Address.Next () == TRUE) {
  1416.          List[0] = '\0';
  1417.          firstEntry = TRUE;
  1418.          do {
  1419.             sprintf (Temp, "%s ", Address.String);
  1420.             if ((strlen (List) + strlen (Temp)) > 64) {
  1421.                if (firstEntry == TRUE)
  1422.                   Log->Write ("*Aka(s): %s", List);
  1423.                else
  1424.                   Log->Write ("*        %s", List);
  1425.                List[0] = '\0';
  1426.                firstEntry = FALSE;
  1427.             }
  1428.             else
  1429.                strcat (List, Temp);
  1430.          } while (Address.Next () == TRUE);
  1431.  
  1432.          if (List[0] != '\0') {
  1433.             if (firstEntry == TRUE)
  1434.                Log->Write ("*Aka(s): %s", List);
  1435.             else
  1436.                Log->Write ("*        %s", List);
  1437.          }
  1438.       }
  1439.    }
  1440.    else
  1441.       Log->Write ("*%s", RemoteSystem);
  1442.  
  1443.    Log->Write ("*Remote Uses %s", RemoteProgram);
  1444.    Log->Write (":SysOp: %s", RemoteSysop);
  1445.  
  1446.    if (Tokens[EMSI_TRANX] != NULL)
  1447.       Log->Write (":Tranx: %08lX / %s", time (NULL), Tokens[EMSI_TRANX]);
  1448.    else
  1449.       Log->Write (":No transaction number presented");
  1450.  
  1451.    if ((Nodes = new TNodes (Cfg->NodelistPath)) != NULL) {
  1452.       strupr (Tokens[EMSI_PASSWORD]);
  1453.       FoundKnown = FoundProt = FALSE;
  1454.       if (Address.First () == TRUE)
  1455.          do {
  1456. /*
  1457.             if (Nodes->Read (Address) == FALSE) {
  1458.                Nodes->New ();
  1459.                strcpy (Nodes->Address, Address.String);
  1460.                strcpy (Nodes->SystemName, Tokens[EMSI_SYSTEMNAME]);
  1461.                strcpy (Nodes->SysopName, Tokens[EMSI_SYSOPNAME]);
  1462.                strcpy (Nodes->Location, Tokens[EMSI_LOCATION]);
  1463.                strcpy (Nodes->Flags, Tokens[EMSI_FLAGS]);
  1464.                strcpy (Nodes->Phone, Tokens[EMSI_PHONE]);
  1465.                Nodes->Speed = atol (Tokens[EMSI_SPEED]);
  1466.                strcpy (Nodes->SessionPwd, Tokens[EMSI_PASSWORD]);
  1467.                Nodes->Add ();
  1468.             }
  1469.             else {
  1470. */
  1471.             if (Nodes->Read (Address) == TRUE) {
  1472.                if (FoundKnown == FALSE) {
  1473.                   strcpy (Inbound, Cfg->KnownInbound);
  1474.                   FoundKnown = TRUE;
  1475.                }
  1476.                if (FoundProt == FALSE) {
  1477.                   strupr (Nodes->SessionPwd);
  1478.                   if (Nodes->SessionPwd[0] != '\0' && !strcmp (Tokens[EMSI_PASSWORD], Nodes->SessionPwd)) {
  1479.                      strcpy (Inbound, Cfg->ProtectedInbound);
  1480.                      FoundProt = TRUE;
  1481.                   }
  1482.                }
  1483.             }
  1484.          } while (Address.Next () == TRUE);
  1485.       delete Nodes;
  1486.  
  1487.       if (FoundProt == TRUE)
  1488.          Log->Write ("*Password-protected session");
  1489.    }
  1490.  
  1491.    Temp[0] = '\0';
  1492.    if (Capabilities & WZ_FREQ)
  1493.       strcat (Temp, "FReqs ");
  1494.    if (Capabilities & ZED_ZIPPER)
  1495.       strcat (Temp, "ZedZIP ");
  1496.    if (Capabilities & ZED_ZAPPER)
  1497.       strcat (Temp, "ZedZAP ");
  1498.    if (Capabilities & DOES_IANUS)
  1499.       strcat (Temp, "Janus ");
  1500.    Log->Write (":Offer: %s", Temp);
  1501. }
  1502.  
  1503. #define IEMSI_NAME         0
  1504. #define IEMSI_ALIAS        1
  1505. #define IEMSI_LOCATION     2
  1506. #define IEMSI_DATAPHONE    3
  1507. #define IEMSI_VOICEPHONE   4
  1508. #define IEMSI_PASSWORD     5
  1509. #define IEMSI_BIRTHDATE    6
  1510. #define IEMSI_CRTDEF       7
  1511. #define IEMSI_PROTOCOLS    8
  1512. #define IEMSI_CAPS         9
  1513. #define IEMSI_REQUESTS     10
  1514. #define IEMSI_SOFTWARE     11
  1515. #define IEMSI_XLAT         12
  1516.  
  1517. #define MAX_IEMSITOKEN     14
  1518.  
  1519. VOID TDetect::ParseIEMSIPacket (VOID)
  1520. {
  1521.    USHORT i;
  1522.    UCHAR Byte, *Read, *Write, c;
  1523.    CHAR *Tokens[MAX_IEMSITOKEN];
  1524.  
  1525.    IEMSI = TRUE;
  1526.    Read = Write = (UCHAR *)ReceiveIEMSI;
  1527.    i = 0;
  1528.  
  1529.    while (*Read != '\0') {
  1530.       if (*Read == '\\') {
  1531.          Read++;
  1532.          if (*Read != '\\') {
  1533.             Byte = (UCHAR)(*Read - 48);
  1534.             if (Byte > 9)
  1535.                Byte = (UCHAR)(Byte - 7);
  1536.             Byte <<= 4;
  1537.             Read++;
  1538.             c = (UCHAR)(*Read - 48);
  1539.             if (c > 9)
  1540.                c = (UCHAR)(c - 7);
  1541.             Byte |= c;
  1542.             *Write++ = Byte;
  1543.          }
  1544.          else
  1545.             *Write++ = *Read;
  1546.       }
  1547.       else {
  1548.          *Write = *Read;
  1549.          if (*Write == '{') {
  1550.             if (i < MAX_IEMSITOKEN)
  1551.                Tokens[i++] = (CHAR *)(Write + 1);
  1552.          }
  1553.          else if (*Write == '}')
  1554.             *Write = '\0';
  1555.          Write++;
  1556.       }
  1557.  
  1558.       Read++;
  1559.    }
  1560.  
  1561.    Tokens[i] = NULL;
  1562.  
  1563.    strupr (Tokens[IEMSI_CRTDEF]);
  1564.    if (strstr (Tokens[IEMSI_CRTDEF], "AVT0") != NULL) {
  1565.       Ansi = TRUE;
  1566.       Avatar = TRUE;
  1567.    }
  1568.    if (strstr (Tokens[IEMSI_CRTDEF], "ANSI") != NULL)
  1569.       Ansi = TRUE;
  1570.    if (strstr (Tokens[IEMSI_CRTDEF], "VT52") != NULL)
  1571.       Ansi = TRUE;
  1572.    if (strstr (Tokens[IEMSI_CRTDEF], "VT100") != NULL)
  1573.       Ansi = TRUE;
  1574.  
  1575.    strupr (Tokens[IEMSI_CAPS]);
  1576.    if (strstr (Tokens[IEMSI_CAPS], "ASCII8") != NULL)
  1577.       IBMChars = TRUE;
  1578.  
  1579.    strupr (Tokens[IEMSI_REQUESTS]);
  1580.    if (strstr (Tokens[IEMSI_REQUESTS], "MORE") != NULL)
  1581.       MorePrompt = TRUE;
  1582.    if (strstr (Tokens[IEMSI_REQUESTS], "HOT") != NULL)
  1583.       HotKeys = TRUE;
  1584.    if (strstr (Tokens[IEMSI_REQUESTS], "CLR") != NULL)
  1585.       ScreenClear = TRUE;
  1586.    if (strstr (Tokens[IEMSI_REQUESTS], "FSED") != NULL)
  1587.       FullEd = TRUE;
  1588.    if (strstr (Tokens[IEMSI_REQUESTS], "MAIL") != NULL)
  1589.       MailCheck = TRUE;
  1590.    if (strstr (Tokens[IEMSI_REQUESTS], "FILE") != NULL)
  1591.       FileCheck = TRUE;
  1592.  
  1593.    strcpy (Name, Tokens[IEMSI_NAME]);
  1594.    strcpy (RealName, Tokens[IEMSI_ALIAS]);
  1595.    strcpy (City, Tokens[IEMSI_LOCATION]);
  1596.    strcpy (Password, Tokens[IEMSI_PASSWORD]);
  1597. }
  1598.  
  1599. USHORT TDetect::ReceiveHello (VOID)
  1600. {
  1601.    USHORT RetVal = FALSE, Crc, IsPacket, FoundKnown, FoundProt;
  1602.    USHORT Received, RemoteCrc, CrcCount;
  1603.    UCHAR c, *p;
  1604.    CHAR Temp[40];
  1605.    LONG Timer, Retry;
  1606.    HELLO Hello;
  1607.    class TNodes *Nodes;
  1608.    class TOutbound *Outbound;
  1609.  
  1610.    p = (UCHAR *)&Hello;
  1611.    IsPacket = FALSE;
  1612.    CrcCount = Received = 0;
  1613.    RemoteCrc = 0xFFFFU;
  1614.    Crc = 0;
  1615.  
  1616.    Timer = TimerSet (4000);
  1617.  
  1618.    do {
  1619.       Com->SendByte (ENQ);
  1620.       Retry = TimerSet (800);
  1621.       do {
  1622.          if (Com->BytesReady () == TRUE) {
  1623.             c = (UCHAR)Com->ReadByte ();
  1624.             if (IsPacket == FALSE && c == 0x1F) {
  1625.                p = (UCHAR *)&Hello;
  1626.                IsPacket = TRUE;
  1627.                CrcCount = Received = 0;
  1628.                RemoteCrc = 0xFFFFU;
  1629.                Crc = 0;
  1630.                Retry = TimerSet (800);
  1631.             }
  1632.             else {
  1633.                if (Received < 128) {
  1634.                   *p++ = c;
  1635.                   Received++;
  1636.                   Crc = Crc16 (c, Crc);
  1637.                }
  1638.                else if (CrcCount < 2) {
  1639.                   RemoteCrc <<= 8;
  1640.                   RemoteCrc |= c;
  1641.                   CrcCount++;
  1642.                }
  1643.             }
  1644.          }
  1645.       } while (!TimeUp (Retry) && CrcCount < 2 && Com->Carrier () == TRUE);
  1646.    } while (AbortSession () == FALSE && !TimeUp (Timer) && Crc != RemoteCrc);
  1647.  
  1648.    if (AbortSession () == FALSE && Crc == RemoteCrc) {
  1649.       Address.Add (Hello.Zone, Hello.Net, Hello.Node, Hello.Point);
  1650.       Address.First ();
  1651.  
  1652.       if (MailerStatus != NULL) {
  1653.          if ((Outbound = new TOutbound (Cfg->Outbound)) != NULL) {
  1654.             if (Cfg->MailAddress.First () == TRUE)
  1655.                Outbound->DefaultZone = Cfg->MailAddress.Zone;
  1656.  
  1657.             Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  1658.             if (Outbound->First () == TRUE)
  1659.                do {
  1660.                   if (Outbound->ArcMail == TRUE || Outbound->MailPKT == TRUE) {
  1661.                      MailerStatus->OutPktFiles++;
  1662.                      MailerStatus->OutPktBytes += Outbound->Size;
  1663.                   }
  1664.                   else if (Outbound->Poll == FALSE) {
  1665.                      MailerStatus->OutDataFiles++;
  1666.                      MailerStatus->OutDataBytes += Outbound->Size;
  1667.                   }
  1668.                } while (Outbound->Next () == TRUE);
  1669.             delete Outbound;
  1670.          }
  1671.          strcpy (MailerStatus->Address, Address.String);
  1672.          MailerStatus->Akas[0] = '\0';
  1673.          strcpy (MailerStatus->SystemName, Hello.Name);
  1674.          strcpy (MailerStatus->SysopName, Hello.Sysop);
  1675.          if (Hello.Product == isOPUS)
  1676.             sprintf (MailerStatus->Program, "Opus Version %d.%02d", Hello.ProductMaj, (Hello.ProductMin == 48) ? 0 : Hello.ProductMin);
  1677.          else if (Hello.Product <= isMAX_PRODUCT)
  1678.             sprintf (MailerStatus->Program, "%s Version %d.%02d", ProductNames[Hello.Product], Hello.ProductMaj, Hello.ProductMin);
  1679.          else
  1680.             sprintf (MailerStatus->Program, "Program '%02x' Version %d.%02d", Hello.Product, Hello.ProductMaj, Hello.ProductMin);
  1681.          MailerStatus->Speed = Speed;
  1682.  
  1683.          if (Hello.Product == isLORA) {
  1684.             MailerStatus->InPktFiles = Hello.PktFiles;
  1685.             MailerStatus->InDataFiles = Hello.DataFiles;
  1686.             MailerStatus->InPktBytes = Hello.PktBytes;
  1687.             MailerStatus->InDataBytes = Hello.DataBytes;
  1688.          }
  1689.  
  1690.          MailerStatus->Update ();
  1691.       }
  1692.  
  1693.       Log->Write ("*%s (%s)", Hello.Name, Address.String);
  1694.       if (Hello.Product == isOPUS)
  1695.          Log->Write ("*Remote Uses Opus Version %d.%02d", Hello.ProductMaj, (Hello.ProductMin == 48) ? 0 : Hello.ProductMin);
  1696.       else if (Hello.Product <= isMAX_PRODUCT)
  1697.          Log->Write ("*Remote Uses %s Version %d.%02d", ProductNames[Hello.Product], Hello.ProductMaj, Hello.ProductMin);
  1698.       else
  1699.          Log->Write ("*Remote Uses Program '%02x' Version %d.%02d", Hello.Product, Hello.ProductMaj, Hello.ProductMin);
  1700.       Log->Write (":SysOp: %s", strcpy (RemoteSysop, Hello.Sysop));
  1701.  
  1702.       if ((Nodes = new TNodes (Cfg->NodelistPath)) != NULL) {
  1703.          FoundKnown = FoundProt = FALSE;
  1704.          if (Address.First () == TRUE)
  1705.             do {
  1706. /*
  1707.                if (Nodes->Read (Address) == FALSE) {
  1708.                   Nodes->New ();
  1709.                   strcpy (Nodes->Address, Address.String);
  1710.                   strcpy (Nodes->SystemName, Hello.Name);
  1711.                   strcpy (Nodes->SysopName, Hello.Sysop);
  1712.                   strcpy (Nodes->SessionPwd, Hello.Password);
  1713.                   Nodes->Add ();
  1714.                }
  1715.                else {
  1716. */
  1717.                if (Nodes->Read (Address) == TRUE) {
  1718.                   if (FoundKnown == FALSE) {
  1719.                      strcpy (Inbound, Cfg->KnownInbound);
  1720.                      FoundKnown = TRUE;
  1721.                   }
  1722.                   if (FoundProt == FALSE) {
  1723.                      if (Nodes->SessionPwd[0] != '\0' && !stricmp (Hello.Password, Nodes->SessionPwd)) {
  1724.                         strcpy (Inbound, Cfg->ProtectedInbound);
  1725.                         FoundProt = TRUE;
  1726.                      }
  1727.                   }
  1728.                }
  1729.             } while (Address.Next () == TRUE);
  1730.          delete Nodes;
  1731.       }
  1732.  
  1733.       Temp[0] = '\0';
  1734.       Capabilities = (USHORT)(Hello.Capabilities|Y_DIETIFNA);
  1735.       if (Capabilities & WZ_FREQ)
  1736.          strcat (Temp, "FReqs ");
  1737.       if (Capabilities & ZED_ZIPPER)
  1738.          strcat (Temp, "ZedZIP ");
  1739.       if (Capabilities & ZED_ZAPPER)
  1740.          strcat (Temp, "ZedZAP ");
  1741.       if (Capabilities & DOES_IANUS)
  1742.          strcat (Temp, "Janus ");
  1743.       Log->Write (":Offer: %s", Temp);
  1744.  
  1745.       if (Hello.Product == isLORA) {
  1746.          if (Hello.Tranx) {
  1747.             if (Log != NULL)
  1748.                Log->Write (":Tranx: %08lX / %08lX", time (NULL), Hello.Tranx);
  1749.          }
  1750.          else {
  1751.             if (Log != NULL)
  1752.                Log->Write (":No transaction number presented");
  1753.          }
  1754.       }
  1755.       else {
  1756.          if (Log != NULL)
  1757.             Log->Write (":No transaction number presented");
  1758.       }
  1759.  
  1760.       Com->SendByte (ACK);
  1761.       Com->SendByte (YOOHOO);
  1762.  
  1763.       RetVal = TRUE;
  1764.    }
  1765.  
  1766.    return (RetVal);
  1767. }
  1768.  
  1769. VOID TDetect::Receiver (VOID)
  1770. {
  1771.    FILE *fp;
  1772.    USHORT FileReceived, FileSent, RetVal, RequestFiles;
  1773.    CHAR FinalPhase = FALSE, *p, Stop, Temp[128], Name[32], *rname;
  1774.    ULONG ReceivedSize, SentSize, Length, RequestSize;
  1775.    struct stat statbuf;
  1776.    class TTransfer *Transfer;
  1777. #if !defined(__LINUX__)
  1778.    class TJanus *Janus;
  1779. #endif
  1780.    class TOutbound *Outbound;
  1781. #if !defined(__POINT__)
  1782.    class TFileBase *File;
  1783.    class TOkFile *OkFile;
  1784. #endif
  1785.    class TCollection Request;
  1786.    class PACKET *Packet;
  1787.  
  1788.    if ((Outbound = new TOutbound (Cfg->Outbound)) != NULL) {
  1789.       if (Cfg->MailAddress.First () == TRUE)
  1790.          Outbound->DefaultZone = Cfg->MailAddress.Zone;
  1791.  
  1792.       FileSent = FileReceived = 0;
  1793.       SentSize = ReceivedSize = 0L;
  1794.  
  1795.       if (Cfg->Janus == TRUE && (Capabilities & DOES_IANUS)) {
  1796.          Log->Write (":Session method: %s", "Janus");
  1797.  
  1798. #if !defined(__LINUX__)
  1799.          if ((Janus = new TJanus ()) != NULL) {
  1800.             Janus->Com = Com;
  1801.             Janus->Log = Log;
  1802.             Janus->Speed = Speed;
  1803.             Janus->AllowRequests = Events->AllowRequests;
  1804.             strcpy (Janus->RxPath, Inbound);
  1805.  
  1806.             if (AbortSession () == FALSE) {
  1807.                Stop = FALSE;
  1808.                if (Address.First () == TRUE)
  1809.                   do {
  1810.                      Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  1811.                   } while (Address.Next () == TRUE);
  1812.  
  1813.                Janus->Outbound = Outbound;
  1814.                Janus->Transfer ();
  1815.             }
  1816.  
  1817.             delete Janus;
  1818.          }
  1819. #endif
  1820.       }
  1821.       else if (Capabilities & (ZED_ZIPPER|ZED_ZAPPER)) {
  1822.          Log->Write (":Session method: %s", "ZedZap");
  1823.  
  1824.          if ((Transfer = new TTransfer ()) != NULL) {
  1825.             Transfer->Com = Com;
  1826.             Transfer->Log = Log;
  1827.             Transfer->Progress = Progress;
  1828.             Transfer->Speed = Speed;
  1829.             Transfer->Telnet = Cfg->ZModemTelnet;
  1830. // ----------------------------------------------------------------------
  1831. // The first phase of a ZedZap/ZedZip transfer in answering mode is
  1832. // the receipt of the files sent by the remote.
  1833. // ----------------------------------------------------------------------
  1834.             Request.Clear ();
  1835.             if ((rname = Transfer->ReceiveZModem (Inbound)) != NULL)
  1836.                do {
  1837.                   FileReceived++;
  1838.                   if (stat (rname, &statbuf) == 0)
  1839.                      ReceivedSize += statbuf.st_size;
  1840. #if !defined(__LINUX__)
  1841.                   strlwr (rname);
  1842. #endif
  1843.                   if (strstr (rname, ".req") != NULL) {
  1844.                      if (Events->AllowRequests == FALSE)
  1845.                         unlink (rname);
  1846.                      if ((fp = fopen (rname, "rt")) != NULL) {
  1847.                         while (fgets (Temp, sizeof (Temp) - 1, fp) != NULL) {
  1848.                            if ((p = strchr (Temp, '\r')) != NULL)
  1849.                               *p = '\0';
  1850.                            if ((p = strchr (Temp, '\n')) != NULL)
  1851.                               *p = '\0';
  1852.                            Request.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1853.                         }
  1854.                         fclose (fp);
  1855.                         unlink (rname);
  1856.                      }
  1857.                   }
  1858.                } while ((rname = Transfer->ReceiveZModem (Inbound)) != NULL && AbortSession () == FALSE);
  1859.  
  1860.             if (AbortSession () == FALSE) {
  1861. // ----------------------------------------------------------------------
  1862. // Second phase, now it is our turn to send our files to the remote
  1863. // system.
  1864. // ----------------------------------------------------------------------
  1865.                Stop = FALSE;
  1866.                if (Address.First () == TRUE) {
  1867.                   do {
  1868.                      Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  1869.                      if (Outbound->First () == TRUE) {
  1870.                         do {
  1871.                            if (Outbound->Poll == FALSE) {
  1872.                               if (Outbound->MailPKT == TRUE) {
  1873.                                  while (time (NULL) == LastPktName)
  1874.                                     ;
  1875.                                  sprintf (Name, "%08lx.pkt", time (NULL));
  1876.                               }
  1877.                               else
  1878.                                  strcpy (Name, Outbound->Name);
  1879.                               if (Capabilities & ZED_ZAPPER)
  1880.                                  RetVal = Transfer->SendZModem8K (Outbound->Complete, Name);
  1881.                               else
  1882.                                  RetVal = Transfer->SendZModem (Outbound->Complete, Name);
  1883.  
  1884.                               if (RetVal == FALSE)
  1885.                                  Stop = TRUE;
  1886.                               else {
  1887.                                  FileSent++;
  1888.                                  SentSize += Outbound->Size;
  1889.                                  if (Outbound->Request == TRUE)
  1890.                                     FinalPhase = TRUE;
  1891.                                  Outbound->Remove ();
  1892.                               }
  1893.                            }
  1894.                            else
  1895.                               Outbound->Remove ();
  1896.                         } while (Stop == FALSE && Outbound->First () == TRUE);
  1897.                         Outbound->Update ();
  1898.                      }
  1899.                      else
  1900.                         Log->Write ("+Nothing to send to %s", Address.String);
  1901.                   } while (Stop == FALSE && Address.Next () == TRUE && AbortSession () == FALSE);
  1902.                }
  1903.  
  1904. #if !defined(__POINT__)
  1905.                if ((File = new TFileBase (Cfg->SystemPath, "")) != NULL) {
  1906.                   if ((rname = (CHAR *)Request.First ()) != NULL) {
  1907.                      Log->Write ("+Processing file requests");
  1908.                      RequestFiles = 0;
  1909.                      RequestSize = 0L;
  1910.  
  1911.                      // Crea il pkt contenente il messaggio riassuntivo del file-request
  1912.                      if ((Packet = new PACKET) != NULL) {
  1913.                         if (Address.First () == TRUE)
  1914.                            strcpy (Packet->ToAddress, Address.String);
  1915.                         if (Cfg->MailAddress.First () == TRUE)
  1916.                            strcpy (Packet->FromAddress, Cfg->MailAddress.String);
  1917.                         sprintf (Name, "%08lx.pkt", time (NULL));
  1918.  
  1919.                         Packet->New ();
  1920.                         if (Packet->Open (Name) == TRUE) {
  1921.                            sprintf (Packet->From, "%s", NAME);
  1922.                            strcpy (Packet->To, "Sysop");
  1923.                            strcpy (Packet->Subject, "Report on file-request");
  1924.  
  1925.                            sprintf (Temp, "The following is the result of a file-request to %s ...", Packet->FromAddress);
  1926.                            Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1927.                            Packet->Text.Add ("", 1);
  1928.                            p = "Filename        Bytes   Description";
  1929.                            Packet->Text.Add (p, (USHORT)(strlen (p) + 1));
  1930.                            p = "--------      -------   -----------";
  1931.                            Packet->Text.Add (p, (USHORT)(strlen (p) + 1));
  1932.                         }
  1933.                      }
  1934.  
  1935.                      do {
  1936.                         RetVal = TRUE;
  1937.                         if (File->First (rname) == TRUE) {
  1938.                            do {
  1939.                               if (stat (File->Complete, &statbuf) == 0) {
  1940.                                  if (Capabilities & ZED_ZAPPER)
  1941.                                     RetVal = Transfer->SendZModem8K (File->Complete, File->Name);
  1942.                                  else
  1943.                                     RetVal = Transfer->SendZModem (File->Complete, File->Name);
  1944.                                  if (RetVal == TRUE) {
  1945.                                     File->DlTimes++;
  1946.                                     File->ReplaceHeader ();
  1947.                                     RequestFiles++;
  1948.                                     RequestSize += File->Size;
  1949.  
  1950.                                     // Aggiunge la descrizione al messaggio riassuntivo
  1951.                                     if (Packet != NULL) {
  1952.                                        if ((p = (CHAR *)File->Description->First ()) == NULL)
  1953.                                           p = "";
  1954.                                        sprintf (Temp, "%-12s %8lu   %s", File->Name, File->Size, p);
  1955.                                        Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1956.                                        while ((p = (CHAR *)File->Description->Next ()) != NULL)
  1957.                                           Packet->Text.Add (p, (USHORT)(strlen (p) + 1));
  1958.                                     }
  1959.                                  }
  1960.                               }
  1961.                               else if (Packet != NULL) {
  1962.                                  sprintf (Temp, "%-12s            %s", File->Name, "* Removed from filebase *");
  1963.                                  Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1964.                               }
  1965.                            } while (RetVal == TRUE && File->Next (rname) == TRUE);
  1966.                         }
  1967.                         else if (Packet != NULL) {
  1968.                            // Il file non e' stato trovato nel database dei files, adesso
  1969.                            // verifica se fa parte dei magic names.
  1970.                            if ((OkFile = new TOkFile (Cfg->SystemPath)) != NULL) {
  1971.                               if (OkFile->Read (rname) == TRUE) {
  1972.                                  if (stat (OkFile->Path, &statbuf) == 0) {
  1973.                                     if (Capabilities & ZED_ZAPPER)
  1974.                                        RetVal = Transfer->SendZModem8K (OkFile->Path);
  1975.                                     else
  1976.                                        RetVal = Transfer->SendZModem (OkFile->Path);
  1977.                                     if (RetVal == TRUE) {
  1978.                                        if (Packet != NULL) {
  1979.                                           sprintf (Temp, "%-12s %8lu   %s", OkFile->Name, statbuf.st_size, "");
  1980.                                           Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1981.                                        }
  1982.                                     }
  1983.                                  }
  1984.                               }
  1985.                               else {
  1986.                                  sprintf (Temp, "%-12s            %s", rname, "* Not found *");
  1987.                                  Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1988.                               }
  1989.                               delete OkFile;
  1990.                            }
  1991.                         }
  1992.                      } while ((rname = (CHAR *)Request.Next ()) != NULL && RetVal == TRUE && AbortSession () == FALSE);
  1993.  
  1994.                      if (Packet != NULL) {
  1995.                         p = "              -------";
  1996.                         Packet->Text.Add (p, (USHORT)(strlen (p) + 1));
  1997.                         sprintf (Temp, "Total        %8lu", RequestSize);
  1998.                         Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  1999.  
  2000.                         // In fondo al messaggio viene appeso il nome del sysop,
  2001.                         // l'indirizzo primario e il nome del BBS.
  2002.                         Packet->Text.Add ("", 1);
  2003.                         sprintf (Temp, "%s, %s", Cfg->SysopName, Cfg->MailAddress.String);
  2004.                         Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  2005.                         sprintf (Temp, "%s", Cfg->SystemName);
  2006.                         Packet->Text.Add (Temp, (USHORT)(strlen (Temp) + 1));
  2007.  
  2008.                         Packet->Add (Packet->Text);
  2009.                         delete Packet;
  2010.  
  2011.                         if (AbortSession () == FALSE && RetVal == TRUE) {
  2012.                            if (Capabilities & ZED_ZAPPER)
  2013.                               RetVal = Transfer->SendZModem8K (Name, Name);
  2014.                            else
  2015.                               RetVal = Transfer->SendZModem (Name, Name);
  2016.                         }
  2017.                         unlink (Name);
  2018.                      }
  2019.                   }
  2020.                   delete File;
  2021.  
  2022.                   Transfer->SendZModem (NULL);
  2023.                }
  2024. #endif
  2025.                Request.Clear ();
  2026.             }
  2027.  
  2028.             if (FinalPhase == TRUE) {
  2029.                if ((p = Transfer->ReceiveZModem (Inbound)) != NULL)
  2030.                   do {
  2031.                      FileReceived++;
  2032.                      if (stat (p, &statbuf) == 0)
  2033.                         ReceivedSize += statbuf.st_size;
  2034.                   } while ((p = Transfer->ReceiveZModem (Inbound)) != NULL && AbortSession () == FALSE);
  2035.             }
  2036.             delete Transfer;
  2037.          }
  2038.       }
  2039.  
  2040.       delete Outbound;
  2041.       Length = time (NULL) - StartCall;
  2042.  
  2043.       if (FileReceived > 0)
  2044.          Remote = REMOTE_MAILRECEIVED;
  2045.  
  2046.       Log->Write ("*End of WaZOO/EMSI Session");
  2047.       Log->Write (" Received: %u/%lu Sent: %u/%lu Total: %u/%lu", FileReceived, ReceivedSize, FileSent, SentSize, FileReceived + FileSent, ReceivedSize + SentSize);
  2048.       Address.First ();
  2049.       if (Length < 60)
  2050.          Log->Write ("*Seconds: %lu  System: %s", Length, Address.String);
  2051.       else
  2052.          Log->Write ("*Minutes: %lu:%02lu  System: %s", Length / 60L, Length % 60L, Address.String);
  2053.    }
  2054. }
  2055.  
  2056. VOID TDetect::Sender (VOID)
  2057. {
  2058.    USHORT FileReceived, FileSent, RetVal;
  2059.    CHAR *p, Stop, Name[32];
  2060.    ULONG ReceivedSize, SentSize, Length;
  2061.    struct stat statbuf;
  2062.    class TTransfer *Transfer;
  2063.    class TJanus *Janus;
  2064.    class TOutbound *Outbound;
  2065.  
  2066.    if ((Outbound = new TOutbound (Cfg->Outbound)) != NULL) {
  2067.       if (Cfg->MailAddress.First () == TRUE)
  2068.          Outbound->DefaultZone = Cfg->MailAddress.Zone;
  2069.  
  2070.       FileSent = FileReceived = 0;
  2071.       SentSize = ReceivedSize = 0L;
  2072.  
  2073.       if (Cfg->Janus == TRUE && (Capabilities & DOES_IANUS)) {
  2074.          Log->Write (":Session method: %s", "Janus");
  2075.  
  2076.          if ((Janus = new TJanus ()) != NULL) {
  2077.             Janus->Com = Com;
  2078.             Janus->Log = Log;
  2079.             Janus->Speed = Speed;
  2080.             Janus->MakeRequests = Events->MakeRequests;
  2081.             strcpy (Janus->RxPath, Inbound);
  2082.  
  2083.             if (AbortSession () == FALSE) {
  2084.                Stop = FALSE;
  2085.                if (Address.First () == TRUE)
  2086.                   do {
  2087.                      Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  2088.                      Outbound->ClearAttempt (Address.String);
  2089.                   } while (Address.Next () == TRUE);
  2090.  
  2091.                Janus->Outbound = Outbound;
  2092.                Janus->Transfer ();
  2093.             }
  2094.  
  2095.             delete Janus;
  2096.          }
  2097.       }
  2098.       else if (Capabilities & (ZED_ZIPPER|ZED_ZAPPER)) {
  2099.          Log->Write (":Session method: %s", "ZedZap");
  2100.  
  2101.          if ((Transfer = new TTransfer ()) != NULL) {
  2102.             Transfer->Com = Com;
  2103.             Transfer->Log = Log;
  2104.             Transfer->Progress = Progress;
  2105.             Transfer->Speed = Speed;
  2106.             Transfer->Telnet = Cfg->ZModemTelnet;
  2107.  
  2108.             if (AbortSession () == FALSE) {
  2109.                Stop = FALSE;
  2110.                if (Address.First () == TRUE) {
  2111.                   do {
  2112.                      Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  2113.                      Outbound->ClearAttempt (Address.String);
  2114.                      if (Outbound->First () == TRUE) {
  2115.                         do {
  2116.                            if (Outbound->Poll == FALSE && (Outbound->Request == FALSE || Events->MakeRequests == TRUE)) {
  2117.                               if (Outbound->MailPKT == TRUE) {
  2118.                                  while (time (NULL) == LastPktName)
  2119.                                     ;
  2120.                                  sprintf (Name, "%08lx.pkt", time (NULL));
  2121.                               }
  2122.                               else
  2123.                                  strcpy (Name, Outbound->Name);
  2124.                               if (Capabilities & ZED_ZAPPER)
  2125.                                  RetVal = Transfer->SendZModem8K (Outbound->Complete, Name);
  2126.                               else
  2127.                                  RetVal = Transfer->SendZModem (Outbound->Complete, Name);
  2128.  
  2129.                               if (RetVal == FALSE)
  2130.                                  Stop = TRUE;
  2131.                               else {
  2132.                                  FileSent++;
  2133.                                  SentSize += Outbound->Size;
  2134.                                  Outbound->Remove ();
  2135.                               }
  2136.                            }
  2137.                            else if (Outbound->Poll == TRUE)
  2138.                               Outbound->Remove ();
  2139.                         } while (Stop == FALSE && Outbound->First () == TRUE);
  2140.                         Outbound->Update ();
  2141.                      }
  2142.                      else
  2143.                         Log->Write ("+Nothing to send to %s", Address.String);
  2144.                   } while (Stop == FALSE && Address.Next () == TRUE);
  2145.                }
  2146.                Transfer->SendZModem (NULL);
  2147.             }
  2148.  
  2149.             if ((p = Transfer->ReceiveZModem (Inbound)) != NULL)
  2150.                do {
  2151.                   FileReceived++;
  2152.                   if (stat (p, &statbuf) == 0)
  2153.                      ReceivedSize += statbuf.st_size;
  2154.                } while ((p = Transfer->ReceiveZModem (Inbound)) != NULL);
  2155.  
  2156.             if (AbortSession () == FALSE)
  2157.                Transfer->SendZModem (NULL);
  2158.  
  2159.             delete Transfer;
  2160.          }
  2161.       }
  2162.  
  2163.       delete Outbound;
  2164.       Length = time (NULL) - StartCall;
  2165.  
  2166.       if (FileReceived > 0)
  2167.          Remote = REMOTE_MAILRECEIVED;
  2168.  
  2169.       Log->Write ("*End of WaZOO/EMSI Session");
  2170.       Log->Write (" Received: %u/%lu Sent: %u/%lu Total: %u/%lu", FileReceived, ReceivedSize, FileSent, SentSize, FileReceived + FileSent, ReceivedSize + SentSize);
  2171.       Address.First ();
  2172.       if (Length < 60)
  2173.          Log->Write ("*Seconds: %lu  System: %s", Length, Address.String);
  2174.       else
  2175.          Log->Write ("*Minutes: %lu:%02lu  System: %s", Length / 60L, Length % 60L, Address.String);
  2176.    }
  2177. }
  2178.  
  2179. USHORT TDetect::SendHello (VOID)
  2180. {
  2181.    USHORT i, RetVal = FALSE, Crc, FoundPw, OutPktFiles, OutDataFiles;
  2182.    UCHAR *p, Resp = 0;
  2183.    ULONG Timer, Retry, OutPktBytes, OutDataBytes;
  2184.    HELLO Hello;
  2185.    class TNodes *Nodes;
  2186.    class TOutbound *Outbound;
  2187.    class TEvents *Events;
  2188.  
  2189.    OutPktFiles = OutDataFiles = 0;
  2190.    OutPktBytes = OutDataBytes = 0L;
  2191.  
  2192.    memset (&Hello, 0, sizeof (Hello));
  2193.    Hello.Signal = 'o';
  2194.    Hello.Version =  1;
  2195.    Hello.Product = PRODUCT_ID;
  2196.    Hello.ProductMaj = VER_MAJOR;
  2197.    Hello.ProductMin = VER_MINOR;
  2198.    strcpy (Hello.Name, Cfg->SystemName);
  2199.    strcpy (Hello.Sysop, Cfg->SysopName);
  2200.  
  2201.    FoundPw = FALSE;
  2202.    if ((Nodes = new TNodes (Cfg->NodelistPath)) != NULL) {
  2203.       if (Address.First () == TRUE)
  2204.          do {
  2205.             if (Nodes->Read (Address) == TRUE) {
  2206.                if (Nodes->SessionPwd[0] != '\0') {
  2207.                   strcpy (Hello.Password, Nodes->SessionPwd);
  2208.                   FoundPw = TRUE;
  2209.                }
  2210.             }
  2211.          } while (FoundPw == FALSE && Address.Next () == TRUE);
  2212.       delete Nodes;
  2213.    }
  2214.  
  2215.    if (Cfg->MailAddress.First () == TRUE) {
  2216.       Hello.Zone = Cfg->MailAddress.Zone;
  2217.       Hello.Net = Cfg->MailAddress.Net;
  2218.       Hello.Node = Cfg->MailAddress.Node;
  2219.       Hello.Point = Cfg->MailAddress.Point;
  2220.    }
  2221.    Hello.Capabilities |= Y_DIETIFNA;
  2222.    Hello.Capabilities |= ZED_ZAPPER|ZED_ZIPPER;
  2223.    if (Cfg->Janus == TRUE)
  2224.       Hello.Capabilities |= DOES_IANUS;
  2225.  
  2226. #if !defined(__POINT__)
  2227.    if ((Events = new TEvents (Cfg->SchedulerFile)) != NULL) {
  2228.       Events->Load ();
  2229.       Events->SetCurrent ();
  2230.       if (Events->AllowRequests == TRUE)
  2231.          Hello.Capabilities |= WZ_FREQ;
  2232.       delete Events;
  2233.    }
  2234. #endif
  2235.  
  2236.    Hello.Tranx = time (NULL);
  2237.  
  2238.    if ((Outbound = new TOutbound (Cfg->Outbound)) != NULL) {
  2239.       if (Cfg->MailAddress.First () == TRUE)
  2240.          Outbound->DefaultZone = Cfg->MailAddress.Zone;
  2241.  
  2242.       if (Address.First () == TRUE) {
  2243.          do {
  2244.             Outbound->Add (Address.Zone, Address.Net, Address.Node, Address.Point, Address.Domain);
  2245.          } while (Address.Next () == TRUE);
  2246.       }
  2247.  
  2248.       if (Outbound->First () == TRUE)
  2249.          do {
  2250.             if (Outbound->ArcMail == TRUE || Outbound->MailPKT == TRUE) {
  2251.                OutPktFiles++;
  2252.                OutPktBytes += Outbound->Size;
  2253.             }
  2254.             else if (Outbound->Poll == FALSE) {
  2255.                OutDataFiles++;
  2256.                OutDataBytes += Outbound->Size;
  2257.             }
  2258.          } while (Outbound->Next () == TRUE);
  2259.  
  2260.       delete Outbound;
  2261.    }
  2262.  
  2263.    Timer = TimerSet (4000);
  2264.  
  2265.    do {
  2266.       if (Com->Carrier () == TRUE) {
  2267.          Com->BufferByte (0x1F);
  2268.          Com->BufferBytes ((UCHAR *)&Hello, sizeof (Hello));
  2269.          p = (UCHAR *)&Hello;
  2270.          for (i = 0, Crc = 0; i < sizeof (Hello); i++)
  2271.             Crc = Crc16 (*p++, Crc);
  2272.          Com->UnbufferBytes ();
  2273.          Com->SendByte ((UCHAR)(Crc >> 8));
  2274.          Com->SendByte ((UCHAR)(Crc & 0xFF));
  2275.  
  2276.          Resp = 0;
  2277.          Retry = TimerSet (800);
  2278.          do {
  2279.             if (Com->BytesReady () == TRUE)
  2280.                Resp = Com->ReadByte ();
  2281.          } while (Com->Carrier () == TRUE && Resp != ACK && Resp != ENQ && Resp != '?' && !TimeUp (Retry));
  2282.       }
  2283.    } while (Com->Carrier () == TRUE && Resp != ACK && !TimeUp (Timer));
  2284.  
  2285.    if (Resp == ACK)
  2286.       RetVal = TRUE;
  2287.  
  2288.    return (RetVal);
  2289. }
  2290.  
  2291. USHORT TDetect::WaZOOReceiver (VOID)
  2292. {
  2293.    USHORT RetVal = FALSE;
  2294.    ULONG Timer;
  2295.  
  2296.    if (Status != NULL)
  2297.       Status->SetLine (0, "YooHoo");
  2298.  
  2299.    if (ReceiveHello () == TRUE) {
  2300.       if (Status != NULL)
  2301.          Status->SetLine (0, "YooHoo/2U2");
  2302.       Remote = REMOTE_MAILER;
  2303.       Timer = TimerSet (500);
  2304.       do {
  2305.          if (Com->BytesReady () == TRUE) {
  2306.             if (Com->ReadByte () == ENQ)
  2307.                RetVal = SendHello ();
  2308.          }
  2309.       } while (RetVal == FALSE && AbortSession () == FALSE && !TimeUp (Timer));
  2310.    }
  2311.  
  2312.    if (RetVal == TRUE)
  2313.       Receiver ();
  2314.  
  2315.    return (RetVal);
  2316. }
  2317.  
  2318. USHORT TDetect::WaZOOSender (VOID)
  2319. {
  2320.    USHORT RetVal = FALSE;
  2321.  
  2322.    if (Status != NULL)
  2323.       Status->SetLine (0, "YooHoo");
  2324.  
  2325.    if (SendHello () == TRUE) {
  2326.       if (Status != NULL)
  2327.          Status->SetLine (0, "YooHoo/2U2");
  2328.       if (ReceiveHello () == TRUE) {
  2329.          Remote = REMOTE_MAILER;
  2330.          RetVal = TRUE;
  2331.       }
  2332.    }
  2333.  
  2334.    if (RetVal == TRUE)
  2335.       Sender ();
  2336.  
  2337.    return (RetVal);
  2338. }
  2339.  
  2340. // ----------------------------------------------------------------------
  2341.  
  2342. TMailerStatus::TMailerStatus (void)
  2343. {
  2344.    SystemName[0] = SysopName[0] = Location[0] = '\0';
  2345.    Address[0] = Akas[0] = Program[0] = '\0';
  2346.    InPktFiles = InDataFiles = 0xFFFFU;
  2347.    OutPktFiles = OutDataFiles = 0;
  2348.    InPktBytes = InDataBytes = OutPktBytes = OutDataBytes = 0L;
  2349.    Speed = 57600L;
  2350. }
  2351.  
  2352. TMailerStatus::~TMailerStatus (void)
  2353. {
  2354. }
  2355.  
  2356. VOID TMailerStatus::Update (VOID)
  2357. {
  2358. }
  2359.  
  2360.